2 /* From NetBSD: grammar.y,v 1.2 1995/03/06 11:38:27 mycroft Exp */
5 * Copyright (c) 1988, 1989, 1990, 1991, 1992, 1993, 1994
6 * The Regents of the University of California. All rights reserved.
8 * Redistribution and use in source and binary forms, with or without
9 * modification, are permitted provided that: (1) source code distributions
10 * retain the above copyright notice and this paragraph in its entirety, (2)
11 * distributions including binary code include the above copyright notice and
12 * this paragraph in its entirety in the documentation or other materials
13 * provided with the distribution, and (3) all advertising materials mentioning
14 * features or use of this software display the following acknowledgement:
15 * ``This product includes software developed by the University of California,
16 * Lawrence Berkeley Laboratory and its contributors.'' Neither the name of
17 * the University nor the names of its contributors may be used to endorse
18 * or promote products derived from this software without specific prior
20 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
21 * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
22 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
27 "@(#) Header: grammar.y,v 1.39 94/06/14 20:09:25 leres Exp (LBL)";
31 #include <sys/types.h>
33 #include <sys/socket.h>
35 #include <net/ppp_defs.h>
36 #include "bpf_compile.h"
39 #define QSET(q, p, d, a) (q).proto = (p),\
45 static struct qual qerr = { Q_UNDEF, Q_UNDEF, Q_UNDEF, Q_UNDEF };
79 %type <blk> expr id nid pid term rterm qid
81 %type <i> pqual dqual aqual
83 %type <i> byteop pname pnum relop irelop
84 %type <blk> and or paren not null prog
88 %token NET PORT LESS GREATER PROTO BYTE
89 %token IP TCP UDP ICMP
90 %token TK_BROADCAST TK_MULTICAST
91 %token NUM INBOUND OUTBOUND
117 null: /* null */ { $$.q = qerr; }
120 | expr and term { gen_and($1.b, $3.b); $$ = $3; }
121 | expr and id { gen_and($1.b, $3.b); $$ = $3; }
122 | expr or term { gen_or($1.b, $3.b); $$ = $3; }
123 | expr or id { gen_or($1.b, $3.b); $$ = $3; }
125 and: AND { $$ = $<blk>0; }
127 or: OR { $$ = $<blk>0; }
130 | pnum { $$.b = gen_ncode((unsigned long)$1,
132 | paren pid ')' { $$ = $2; }
134 nid: ID { $$.b = gen_scode($1, $$.q = $<blk>0.q); }
135 | HID { $$.b = gen_ncode(__pcap_atoin((char *)$1),
137 | not id { gen_not($2.b); $$ = $2; }
139 not: '!' { $$ = $<blk>0; }
141 paren: '(' { $$ = $<blk>0; }
144 | qid and id { gen_and($1.b, $3.b); $$ = $3; }
145 | qid or id { gen_or($1.b, $3.b); $$ = $3; }
147 qid: pnum { $$.b = gen_ncode((unsigned long)$1,
152 | not term { gen_not($2.b); $$ = $2; }
154 head: pqual dqual aqual { QSET($$.q, $1, $2, $3); }
155 | pqual dqual { QSET($$.q, $1, $2, Q_DEFAULT); }
156 | pqual aqual { QSET($$.q, $1, Q_DEFAULT, $2); }
157 | pqual PROTO { QSET($$.q, $1, Q_DEFAULT, Q_PROTO); }
159 rterm: head id { $$ = $2; }
160 | paren expr ')' { $$.b = $2.b; $$.q = $1.q; }
161 | pname { $$.b = gen_proto_abbrev($1); $$.q = qerr; }
162 | arth relop arth { $$.b = gen_relation($2, $1, $3, 0);
164 | arth irelop arth { $$.b = gen_relation($2, $1, $3, 1);
166 | other { $$.b = $1; $$.q = qerr; }
168 /* protocol level qualifiers */
170 | { $$ = Q_DEFAULT; }
172 /* 'direction' qualifiers */
173 dqual: SRC { $$ = Q_SRC; }
174 | DST { $$ = Q_DST; }
175 | SRC OR DST { $$ = Q_OR; }
176 | DST OR SRC { $$ = Q_OR; }
177 | SRC AND DST { $$ = Q_AND; }
178 | DST AND SRC { $$ = Q_AND; }
180 /* address type qualifiers */
181 aqual: HOST { $$ = Q_HOST; }
182 | NET { $$ = Q_NET; }
183 | PORT { $$ = Q_PORT; }
185 pname: LINK { $$ = Q_LINK; }
187 | TCP { $$ = Q_TCP; }
188 | UDP { $$ = Q_UDP; }
189 | ICMP { $$ = Q_ICMP; }
191 other: pqual TK_BROADCAST { $$ = gen_broadcast($1); }
192 | pqual TK_MULTICAST { $$ = gen_multicast($1); }
193 | LESS NUM { $$ = gen_less($2); }
194 | GREATER NUM { $$ = gen_greater($2); }
195 | BYTE NUM byteop NUM { $$ = gen_byteop($3, $2, $4); }
196 | INBOUND { $$ = gen_inbound(0); }
197 | OUTBOUND { $$ = gen_inbound(1); }
199 relop: '>' { $$ = BPF_JGT; }
200 | GEQ { $$ = BPF_JGE; }
201 | '=' { $$ = BPF_JEQ; }
203 irelop: LEQ { $$ = BPF_JGT; }
204 | '<' { $$ = BPF_JGE; }
205 | NEQ { $$ = BPF_JEQ; }
207 arth: pnum { $$ = gen_loadi($1); }
210 narth: pname '[' arth ']' { $$ = gen_load($1, $3, 1); }
211 | pname '[' arth ':' NUM ']' { $$ = gen_load($1, $3, $5); }
212 | arth '+' arth { $$ = gen_arth(BPF_ADD, $1, $3); }
213 | arth '-' arth { $$ = gen_arth(BPF_SUB, $1, $3); }
214 | arth '*' arth { $$ = gen_arth(BPF_MUL, $1, $3); }
215 | arth '/' arth { $$ = gen_arth(BPF_DIV, $1, $3); }
216 | arth '&' arth { $$ = gen_arth(BPF_AND, $1, $3); }
217 | arth '|' arth { $$ = gen_arth(BPF_OR, $1, $3); }
218 | arth LSH arth { $$ = gen_arth(BPF_LSH, $1, $3); }
219 | arth RSH arth { $$ = gen_arth(BPF_RSH, $1, $3); }
220 | '-' arth %prec UMINUS { $$ = gen_neg($2); }
221 | paren narth ')' { $$ = $2; }
222 | LEN { $$ = gen_loadlen(); }
224 byteop: '&' { $$ = '&'; }
231 | paren pnum ')' { $$ = $2; }