1 
2 # line 7 "../ipmon_y.y"
3 #include "ipf.h"
4 #include <syslog.h>
5 #undef	OPT_NAT
6 #undef	OPT_VERBOSE
7 #include "ipmon_l.h"
8 #include "ipmon.h"
9 
10 #define	YYDEBUG	1
11 
12 extern	void	ipmon_yyerror __P((char *));
13 extern	int	ipmon_yyparse __P((void));
14 extern	int	ipmon_yylex __P((void));
15 extern	int	ipmon_yydebug;
16 extern	FILE	*ipmon_yyin;
17 extern	int	ipmon_yylineNum;
18 
19 typedef	struct	opt	{
20 	struct	opt	*o_next;
21 	int		o_line;
22 	int		o_type;
23 	int		o_num;
24 	char		*o_str;
25 	struct in_addr	o_ip;
26 } opt_t;
27 
28 static	void	build_action __P((struct opt *));
29 static	opt_t	*new_opt __P((int));
30 static	void	free_action __P((ipmon_action_t *));
31 
32 static	ipmon_action_t	*alist = NULL;
33 
34 # line 39 "../ipmon_y.y"
35 typedef union
36 #ifdef __cplusplus
37 	YYSTYPE
38 #endif
39 	{
40 	char	*str;
41 	u_32_t	num;
42 	struct in_addr	addr;
43 	struct opt	*opt;
44 	union	i6addr	ip6;
45 } YYSTYPE;
46 # define YY_NUMBER 257
47 # define YY_HEX 258
48 # define YY_STR 259
49 # define YY_IPV6 260
50 # define YY_COMMENT 261
51 # define YY_CMP_EQ 262
52 # define YY_CMP_NE 263
53 # define YY_CMP_LE 264
54 # define YY_CMP_GE 265
55 # define YY_CMP_LT 266
56 # define YY_CMP_GT 267
57 # define YY_RANGE_OUT 268
58 # define YY_RANGE_IN 269
59 # define IPM_MATCH 270
60 # define IPM_BODY 271
61 # define IPM_COMMENT 272
62 # define IPM_DIRECTION 273
63 # define IPM_DSTIP 274
64 # define IPM_DSTPORT 275
65 # define IPM_EVERY 276
66 # define IPM_EXECUTE 277
67 # define IPM_GROUP 278
68 # define IPM_INTERFACE 279
69 # define IPM_IN 280
70 # define IPM_NO 281
71 # define IPM_OUT 282
72 # define IPM_PACKET 283
73 # define IPM_PACKETS 284
74 # define IPM_POOL 285
75 # define IPM_PROTOCOL 286
76 # define IPM_RESULT 287
77 # define IPM_RULE 288
78 # define IPM_SECOND 289
79 # define IPM_SECONDS 290
80 # define IPM_SRCIP 291
81 # define IPM_SRCPORT 292
82 # define IPM_LOGTAG 293
83 # define IPM_WITH 294
84 # define IPM_DO 295
85 # define IPM_SAVE 296
86 # define IPM_SYSLOG 297
87 # define IPM_NOTHING 298
88 # define IPM_RAW 299
89 # define IPM_TYPE 300
90 # define IPM_NAT 301
91 # define IPM_STATE 302
92 # define IPM_NATTAG 303
93 # define IPM_IPF 304
94 
95 #include <inttypes.h>
96 
97 #ifdef __STDC__
98 #include <stdlib.h>
99 #include <string.h>
100 #define	YYCONST	const
101 #else
102 #include <malloc.h>
103 #include <memory.h>
104 #define	YYCONST
105 #endif
106 
107 #include <values.h>
108 
109 #if defined(__cplusplus) || defined(__STDC__)
110 
111 #if defined(__cplusplus) && defined(__EXTERN_C__)
112 extern "C" {
113 #endif
114 #ifndef ipmon_yyerror
115 #if defined(__cplusplus)
116 	void ipmon_yyerror(YYCONST char *);
117 #endif
118 #endif
119 #ifndef ipmon_yylex
120 	int ipmon_yylex(void);
121 #endif
122 	int ipmon_yyparse(void);
123 #if defined(__cplusplus) && defined(__EXTERN_C__)
124 }
125 #endif
126 
127 #endif
128 
129 #define ipmon_yyclearin ipmon_yychar = -1
130 #define ipmon_yyerrok ipmon_yyerrflag = 0
131 extern int ipmon_yychar;
132 extern int ipmon_yyerrflag;
133 YYSTYPE ipmon_yylval;
134 YYSTYPE ipmon_yyval;
135 typedef int ipmon_yytabelem;
136 #ifndef YYMAXDEPTH
137 #define YYMAXDEPTH 150
138 #endif
139 #if YYMAXDEPTH > 0
140 int ipmon_yy_ipmon_yys[YYMAXDEPTH], *ipmon_yys = ipmon_yy_ipmon_yys;
141 YYSTYPE ipmon_yy_ipmon_yyv[YYMAXDEPTH], *ipmon_yyv = ipmon_yy_ipmon_yyv;
142 #else	/* user does initial allocation */
143 int *ipmon_yys;
144 YYSTYPE *ipmon_yyv;
145 #endif
146 static int ipmon_yymaxdepth = YYMAXDEPTH;
147 # define YYERRCODE 256
148 
149 # line 245 "../ipmon_y.y"
150 
151 static	struct	wordtab	ipmon_yywords[] = {
152 	{ "body",	IPM_BODY },
153 	{ "direction",	IPM_DIRECTION },
154 	{ "do",		IPM_DO },
155 	{ "dstip",	IPM_DSTIP },
156 	{ "dstport",	IPM_DSTPORT },
157 	{ "every",	IPM_EVERY },
158 	{ "execute",	IPM_EXECUTE },
159 	{ "group",	IPM_GROUP },
160 	{ "in",		IPM_IN },
161 	{ "interface",	IPM_INTERFACE },
162 	{ "ipf",	IPM_IPF },
163 	{ "logtag",	IPM_LOGTAG },
164 	{ "match",	IPM_MATCH },
165 	{ "nat",	IPM_NAT },
166 	{ "nattag",	IPM_NATTAG },
167 	{ "no",		IPM_NO },
168 	{ "nothing",	IPM_NOTHING },
169 	{ "out",	IPM_OUT },
170 	{ "packet",	IPM_PACKET },
171 	{ "packets",	IPM_PACKETS },
172 	{ "protocol",	IPM_PROTOCOL },
173 	{ "result",	IPM_RESULT },
174 	{ "rule",	IPM_RULE },
175 	{ "save",	IPM_SAVE },
176 	{ "raw",	IPM_RAW },
177 	{ "second",	IPM_SECOND },
178 	{ "seconds",	IPM_SECONDS },
179 	{ "srcip",	IPM_SRCIP },
180 	{ "srcport",	IPM_SRCPORT },
181 	{ "state",	IPM_STATE },
182 	{ "syslog",	IPM_SYSLOG },
183 	{ "with",	IPM_WITH },
184 	{ NULL,		0 }
185 };
186 
187 static int macflags[17][2] = {
188 	{ IPM_DIRECTION,	IPMAC_DIRECTION	},
189 	{ IPM_DSTIP,		IPMAC_DSTIP	},
190 	{ IPM_DSTPORT,		IPMAC_DSTPORT	},
191 	{ IPM_GROUP,		IPMAC_GROUP	},
192 	{ IPM_INTERFACE,	IPMAC_INTERFACE	},
193 	{ IPM_LOGTAG,		IPMAC_LOGTAG 	},
194 	{ IPM_NATTAG,		IPMAC_NATTAG 	},
195 	{ IPM_PACKET,		IPMAC_EVERY	},
196 	{ IPM_PROTOCOL,		IPMAC_PROTOCOL	},
197 	{ IPM_RESULT,		IPMAC_RESULT	},
198 	{ IPM_RULE,		IPMAC_RULE	},
199 	{ IPM_SECOND,		IPMAC_EVERY	},
200 	{ IPM_SRCIP,		IPMAC_SRCIP	},
201 	{ IPM_SRCPORT,		IPMAC_SRCPORT	},
202 	{ IPM_TYPE,		IPMAC_TYPE 	},
203 	{ IPM_WITH,		IPMAC_WITH 	},
204 	{ 0, 0 }
205 };
206 
207 static opt_t *new_opt(type)
208 int type;
209 {
210 	opt_t *o;
211 
212 	o = (opt_t *)malloc(sizeof(*o));
213 	if (o == NULL)
214 		ipmon_yyerror("sorry, out of memory");
215 	o->o_type = type;
216 	o->o_line = ipmon_yylineNum;
217 	o->o_num = 0;
218 	o->o_str = (char *)0;
219 	o->o_next = NULL;
220 	return o;
221 }
222 
223 static void build_action(olist)
224 opt_t *olist;
225 {
226 	ipmon_action_t *a;
227 	opt_t *o;
228 	char c;
229 	int i;
230 
231 	a = (ipmon_action_t *)calloc(1, sizeof(*a));
232 	if (a == NULL)
233 		return;
234 	while ((o = olist) != NULL) {
235 		/*
236 		 * Check to see if the same comparator is being used more than
237 		 * once per matching statement.
238 		 */
239 		for (i = 0; macflags[i][0]; i++)
240 			if (macflags[i][0] == o->o_type)
241 				break;
242 		if (macflags[i][1] & a->ac_mflag) {
243 			fprintf(stderr, "%s redfined on line %d\n",
244 				ipmon_yykeytostr(o->o_type), ipmon_yylineNum);
245 			if (o->o_str != NULL)
246 				free(o->o_str);
247 			olist = o->o_next;
248 			free(o);
249 			continue;
250 		}
251 
252 		a->ac_mflag |= macflags[i][1];
253 
254 		switch (o->o_type)
255 		{
256 		case IPM_DIRECTION :
257 			a->ac_direction = o->o_num;
258 			break;
259 		case IPM_DSTIP :
260 			a->ac_dip = o->o_ip.s_addr;
261 			a->ac_dmsk = htonl(0xffffffff << (32 - o->o_num));
262 			break;
263 		case IPM_DSTPORT :
264 			a->ac_dport = htons(o->o_num);
265 			break;
266 		case IPM_EXECUTE :
267 			a->ac_exec = o->o_str;
268 			c = *o->o_str;
269 			if (c== '"'|| c == '\'') {
270 				if (o->o_str[strlen(o->o_str) - 1] == c) {
271 					a->ac_run = strdup(o->o_str + 1);
272 					a->ac_run[strlen(a->ac_run) - 1] ='\0';
273 				} else
274 					a->ac_run = o->o_str;
275 			} else
276 				a->ac_run = o->o_str;
277 			o->o_str = NULL;
278 			break;
279 		case IPM_INTERFACE :
280 			a->ac_iface = o->o_str;
281 			o->o_str = NULL;
282 			break;
283 		case IPM_GROUP :
284 			if (o->o_str != NULL)
285 				strncpy(a->ac_group, o->o_str, FR_GROUPLEN);
286 			else
287 				sprintf(a->ac_group, "%d", o->o_num);
288 			break;
289 		case IPM_LOGTAG :
290 			a->ac_logtag = o->o_num;
291 			break;
292 		case IPM_NATTAG :
293 			strncpy(a->ac_nattag, o->o_str, sizeof(a->ac_nattag));
294 			break;
295 		case IPM_PACKET :
296 			a->ac_packet = o->o_num;
297 			break;
298 		case IPM_PROTOCOL :
299 			a->ac_proto = o->o_num;
300 			break;
301 		case IPM_RULE :
302 			a->ac_rule = o->o_num;
303 			break;
304 		case IPM_RESULT :
305 			if (!strcasecmp(o->o_str, "pass"))
306 				a->ac_result = IPMR_PASS;
307 			else if (!strcasecmp(o->o_str, "block"))
308 				a->ac_result = IPMR_BLOCK;
309 			else if (!strcasecmp(o->o_str, "nomatch"))
310 				a->ac_result = IPMR_NOMATCH;
311 			else if (!strcasecmp(o->o_str, "log"))
312 				a->ac_result = IPMR_LOG;
313 			break;
314 		case IPM_SECOND :
315 			a->ac_second = o->o_num;
316 			break;
317 		case IPM_SRCIP :
318 			a->ac_sip = o->o_ip.s_addr;
319 			a->ac_smsk = htonl(0xffffffff << (32 - o->o_num));
320 			break;
321 		case IPM_SRCPORT :
322 			a->ac_sport = htons(o->o_num);
323 			break;
324 		case IPM_SAVE :
325 			if (a->ac_savefile != NULL) {
326 				fprintf(stderr, "%s redfined on line %d\n",
327 					ipmon_yykeytostr(o->o_type), ipmon_yylineNum);
328 				break;
329 			}
330 			a->ac_savefile = strdup(o->o_str);
331 			a->ac_savefp = fopen(o->o_str, "a");
332 			a->ac_dflag |= o->o_num & IPMDO_SAVERAW;
333 			break;
334 		case IPM_SYSLOG :
335 			if (a->ac_syslog != 0) {
336 				fprintf(stderr, "%s redfined on line %d\n",
337 					ipmon_yykeytostr(o->o_type), ipmon_yylineNum);
338 				break;
339 			}
340 			a->ac_syslog = 1;
341 			break;
342 		case IPM_TYPE :
343 			a->ac_type = o->o_num;
344 			break;
345 		case IPM_WITH :
346 			break;
347 		default :
348 			break;
349 		}
350 
351 		olist = o->o_next;
352 		if (o->o_str != NULL)
353 			free(o->o_str);
354 		free(o);
355 	}
356 	a->ac_next = alist;
357 	alist = a;
358 }
359 
360 
361 int check_action(buf, log, opts, lvl)
362 char *buf, *log;
363 int opts, lvl;
364 {
365 	ipmon_action_t *a;
366 	struct timeval tv;
367 	ipflog_t *ipf;
368 	tcphdr_t *tcp;
369 	iplog_t *ipl;
370 	int matched;
371 	u_long t1;
372 	ip_t *ip;
373 
374 	matched = 0;
375 	ipl = (iplog_t *)buf;
376 	ipf = (ipflog_t *)(ipl +1);
377 	ip = (ip_t *)(ipf + 1);
378 	tcp = (tcphdr_t *)((char *)ip + (IP_HL(ip) << 2));
379 
380 	for (a = alist; a != NULL; a = a->ac_next) {
381 		if ((a->ac_mflag & IPMAC_DIRECTION) != 0) {
382 			if (a->ac_direction == IPM_IN) {
383 				if ((ipf->fl_flags & FR_INQUE) == 0)
384 					continue;
385 			} else if (a->ac_direction == IPM_OUT) {
386 				if ((ipf->fl_flags & FR_OUTQUE) == 0)
387 					continue;
388 			}
389 		}
390 
391 		if ((a->ac_type != 0) && (a->ac_type != ipl->ipl_magic))
392 			continue;
393 
394 		if ((a->ac_mflag & IPMAC_EVERY) != 0) {
395 			gettimeofday(&tv, NULL);
396 			t1 = tv.tv_sec - a->ac_lastsec;
397 			if (tv.tv_usec <= a->ac_lastusec)
398 				t1--;
399 			if (a->ac_second != 0) {
400 				if (t1 < a->ac_second)
401 					continue;
402 				a->ac_lastsec = tv.tv_sec;
403 				a->ac_lastusec = tv.tv_usec;
404 			}
405 
406 			if (a->ac_packet != 0) {
407 				if (a->ac_pktcnt == 0)
408 					a->ac_pktcnt++;
409 				else if (a->ac_pktcnt == a->ac_packet) {
410 					a->ac_pktcnt = 0;
411 					continue;
412 				} else {
413 					a->ac_pktcnt++;
414 					continue;
415 				}
416 			}
417 		}
418 
419 		if ((a->ac_mflag & IPMAC_DSTIP) != 0) {
420 			if ((ip->ip_dst.s_addr & a->ac_dmsk) != a->ac_dip)
421 				continue;
422 		}
423 
424 		if ((a->ac_mflag & IPMAC_DSTPORT) != 0) {
425 			if (ip->ip_p != IPPROTO_UDP && ip->ip_p != IPPROTO_TCP)
426 				continue;
427 			if (tcp->th_dport != a->ac_dport)
428 				continue;
429 		}
430 
431 		if ((a->ac_mflag & IPMAC_GROUP) != 0) {
432 			if (strncmp(a->ac_group, ipf->fl_group,
433 				    FR_GROUPLEN) != 0)
434 				continue;
435 		}
436 
437 		if ((a->ac_mflag & IPMAC_INTERFACE) != 0) {
438 			if (strcmp(a->ac_iface, ipf->fl_ifname))
439 				continue;
440 		}
441 
442 		if ((a->ac_mflag & IPMAC_PROTOCOL) != 0) {
443 			if (a->ac_proto != ip->ip_p)
444 				continue;
445 		}
446 
447 		if ((a->ac_mflag & IPMAC_RESULT) != 0) {
448 			if ((ipf->fl_flags & FF_LOGNOMATCH) != 0) {
449 				if (a->ac_result != IPMR_NOMATCH)
450 					continue;
451 			} else if (FR_ISPASS(ipf->fl_flags)) {
452 				if (a->ac_result != IPMR_PASS)
453 					continue;
454 			} else if (FR_ISBLOCK(ipf->fl_flags)) {
455 				if (a->ac_result != IPMR_BLOCK)
456 					continue;
457 			} else {	/* Log only */
458 				if (a->ac_result != IPMR_LOG)
459 					continue;
460 			}
461 		}
462 
463 		if ((a->ac_mflag & IPMAC_RULE) != 0) {
464 			if (a->ac_rule != ipf->fl_rule)
465 				continue;
466 		}
467 
468 		if ((a->ac_mflag & IPMAC_SRCIP) != 0) {
469 			if ((ip->ip_src.s_addr & a->ac_smsk) != a->ac_sip)
470 				continue;
471 		}
472 
473 		if ((a->ac_mflag & IPMAC_SRCPORT) != 0) {
474 			if (ip->ip_p != IPPROTO_UDP && ip->ip_p != IPPROTO_TCP)
475 				continue;
476 			if (tcp->th_sport != a->ac_sport)
477 				continue;
478 		}
479 
480 		if ((a->ac_mflag & IPMAC_LOGTAG) != 0) {
481 			if (a->ac_logtag != ipf->fl_logtag)
482 				continue;
483 		}
484 
485 		if ((a->ac_mflag & IPMAC_NATTAG) != 0) {
486 			if (strncmp(a->ac_nattag, ipf->fl_nattag.ipt_tag,
487 				    IPFTAG_LEN) != 0)
488 				continue;
489 		}
490 
491 		matched = 1;
492 
493 		/*
494 		 * It matched so now execute the command
495 		 */
496 		if (a->ac_syslog != 0) {
497 			syslog(lvl, "%s", log);
498 		}
499 
500 		if (a->ac_savefp != NULL) {
501 			if (a->ac_dflag & IPMDO_SAVERAW)
502 				fwrite(ipl, 1, ipl->ipl_dsize, a->ac_savefp);
503 			else
504 				fputs(log, a->ac_savefp);
505 		}
506 
507 		if (a->ac_exec != NULL) {
508 			switch (fork())
509 			{
510 			case 0 :
511 			{
512 				FILE *pi;
513 
514 				pi = popen(a->ac_run, "w");
515 				if (pi != NULL) {
516 					fprintf(pi, "%s\n", log);
517 					if ((opts & OPT_HEXHDR) != 0) {
518 						dumphex(pi, 0, buf,
519 							sizeof(*ipl) +
520 							sizeof(*ipf));
521 					}
522 					if ((opts & OPT_HEXBODY) != 0) {
523 						dumphex(pi, 0, (char *)ip,
524 							ipf->fl_hlen +
525 							ipf->fl_plen);
526 					}
527 					pclose(pi);
528 				}
529 				exit(1);
530 			}
531 			case -1 :
532 				break;
533 			default :
534 				break;
535 			}
536 		}
537 	}
538 
539 	return matched;
540 }
541 
542 
543 static void free_action(a)
544 ipmon_action_t *a;
545 {
546 	if (a->ac_savefile != NULL) {
547 		free(a->ac_savefile);
548 		a->ac_savefile = NULL;
549 	}
550 	if (a->ac_savefp != NULL) {
551 		fclose(a->ac_savefp);
552 		a->ac_savefp = NULL;
553 	}
554 	if (a->ac_exec != NULL) {
555 		free(a->ac_exec);
556 		if (a->ac_run == a->ac_exec)
557 			a->ac_run = NULL;
558 		a->ac_exec = NULL;
559 	}
560 	if (a->ac_run != NULL) {
561 		free(a->ac_run);
562 		a->ac_run = NULL;
563 	}
564 	if (a->ac_iface != NULL) {
565 		free(a->ac_iface);
566 		a->ac_iface = NULL;
567 	}
568 	a->ac_next = NULL;
569 	free(a);
570 }
571 
572 
573 int load_config(file)
574 char *file;
575 {
576 	ipmon_action_t *a;
577 	FILE *fp;
578 	char *s;
579 
580 	s = getenv("YYDEBUG");
581 	if (s != NULL)
582 		ipmon_yydebug = atoi(s);
583 	else
584 		ipmon_yydebug = 0;
585 
586 	while ((a = alist) != NULL) {
587 		alist = a->ac_next;
588 		free_action(a);
589 	}
590 
591 	ipmon_yylineNum = 1;
592 
593 	(void) ipmon_yysettab(ipmon_yywords);
594 
595 	fp = fopen(file, "r");
596 	if (!fp) {
597 		perror("load_config:fopen:");
598 		return -1;
599 	}
600 	ipmon_yyin = fp;
601 	while (!feof(fp))
602 		ipmon_yyparse();
603 	fclose(fp);
604 	return 0;
605 }
606 static YYCONST ipmon_yytabelem ipmon_yyexca[] ={
607 -1, 1,
608 	0, -1,
609 	-2, 0,
610 	};
611 # define YYNPROD 66
612 # define YYLAST 178
613 static YYCONST ipmon_yytabelem ipmon_yyact[]={
614 
615     29,    30,    31,    32,   111,    33,    34,    87,    88,    63,
616     86,    50,    99,    35,    36,    37,    72,   115,    38,    39,
617     40,    65,    71,    66,    81,   108,    82,    42,    84,    78,
618     41,   100,   101,   102,     7,    75,     6,    51,    76,    73,
619     77,    74,    69,    49,    70,     4,    43,     5,   120,   117,
620    105,   104,   103,    83,    68,    79,   106,    44,    89,    10,
621    109,    93,    61,    60,    59,    58,    57,    56,    55,    54,
622     53,    52,    48,    47,    46,    12,   113,    62,    67,    92,
623     90,   119,   112,    91,    13,   116,   107,    45,     3,     2,
624      9,     8,    11,     1,    85,   110,    98,    97,    96,    94,
625     28,    27,    14,    26,    25,    24,    23,    22,    21,    20,
626     19,    95,    18,    17,    16,    15,     0,     0,     0,     0,
627      0,     0,     0,     0,     0,     0,     0,     0,     0,     0,
628     64,     0,     0,     0,     0,     0,    80,     0,     0,     0,
629      0,     0,     0,     0,     0,     0,     0,     0,     0,     0,
630      0,     0,     0,     0,     0,     0,     0,     0,     0,     0,
631      0,     0,     0,     0,     0,     0,     0,     0,     0,   114,
632      0,     0,     0,     0,     0,     0,     0,   118 };
633 static YYCONST ipmon_yytabelem ipmon_yypact[]={
634 
635   -225,  -225,-10000000,-10000000,   -64,-10000000,-10000000,    14,-10000000,-10000000,
636   -273,  -213,-10000000,   -68,    43,-10000000,-10000000,-10000000,-10000000,-10000000,
637 -10000000,-10000000,-10000000,-10000000,-10000000,-10000000,-10000000,-10000000,-10000000,    13,
638     12,    11,  -246,    10,     9,     8,     7,     6,     5,     4,
639      3,     2,     1,    18,  -286,  -273,  -259,  -203,  -215,-10000000,
640   -268,-10000000,  -218,  -224,  -219,  -230,  -202,  -203,  -233,  -204,
641   -231,  -294,-10000000,   -65,-10000000,-10000000,-10000000,    33,    37,-10000000,
642 -10000000,-10000000,-10000000,-10000000,-10000000,-10000000,-10000000,-10000000,-10000000,-10000000,
643     32,-10000000,-10000000,-10000000,-10000000,-10000000,-10000000,-10000000,-10000000,  -265,
644   -205,  -206,  -207,   -69,    42,-10000000,-10000000,-10000000,-10000000,  -234,
645   -295,-10000000,-10000000,-10000000,    36,-10000000,    17,  -265,-10000000,  -242,
646     41,-10000000,  -208,-10000000,-10000000,-10000000,  -295,    35,-10000000,  -209,
647 -10000000 };
648 static YYCONST ipmon_yytabelem ipmon_yypgo[]={
649 
650      0,    78,   115,   114,   113,   112,   111,   110,   109,   108,
651    107,   106,   105,   104,   103,    84,   102,   101,   100,    99,
652     61,    98,    97,    96,    60,    95,    94,    93,    89,    88,
653     92 };
654 static YYCONST ipmon_yytabelem ipmon_yyr1[]={
655 
656      0,    27,    27,    27,    27,    28,    28,    28,    29,    30,
657     15,    15,    16,    16,    16,    16,    16,    16,    16,    16,
658     16,    16,    16,    16,    16,    16,    20,    20,    19,    19,
659     19,    19,     2,     2,     3,     4,     4,     5,     5,     5,
660      5,     7,     7,     8,    14,    17,     9,     9,    10,    11,
661     12,    13,    13,    18,    26,    26,    26,     6,    21,    24,
662     24,    24,    25,    22,    23,     1 };
663 static YYCONST ipmon_yytabelem ipmon_yyr2[]={
664 
665      0,     2,     2,     4,     4,    19,     2,     2,     9,     3,
666      3,     7,     3,     3,     3,     3,     3,     3,     3,     3,
667      3,     3,     3,     3,     3,     3,     3,     7,     3,     3,
668      3,     3,     7,     7,    11,     7,     7,     5,     7,     5,
669      7,     7,     7,     7,     7,     7,     7,     7,     7,     7,
670     11,     7,     7,     7,     3,     3,     3,     5,     7,     1,
671      3,     7,     3,     3,     3,    15 };
672 static YYCONST ipmon_yytabelem ipmon_yychk[]={
673 
674 -10000000,   -27,   -28,   -29,   270,   272,   261,   259,   -28,   -29,
675    123,   -30,    61,   -15,   -16,    -2,    -3,    -4,    -5,    -7,
676     -8,    -9,   -10,   -11,   -12,   -13,   -14,   -17,   -18,   273,
677    274,   275,   276,   278,   279,   286,   287,   288,   291,   292,
678    293,   303,   300,   259,   125,    44,    61,    61,    61,   289,
679    257,   283,    61,    61,    61,    61,    61,    61,    61,    61,
680     61,    61,    59,   295,   -15,   280,   282,    -1,   257,   257,
681    259,   290,   284,   257,   259,   259,   257,   259,   259,   257,
682     -1,   257,   259,   257,   259,   -26,   304,   301,   302,   123,
683     47,    46,    47,   -20,   -19,    -6,   -21,   -22,   -23,   277,
684    296,   297,   298,   257,   257,   257,   125,    44,   259,   -24,
685    -25,   299,    46,    59,   -20,   259,    44,   257,   -24,    46,
686    257 };
687 static YYCONST ipmon_yytabelem ipmon_yydef[]={
688 
689      0,    -2,     1,     2,     0,     6,     7,     0,     3,     4,
690      0,     0,     9,     0,    10,    12,    13,    14,    15,    16,
691     17,    18,    19,    20,    21,    22,    23,    24,    25,     0,
692      0,     0,     0,     0,     0,     0,     0,     0,     0,     0,
693      0,     0,     0,     0,     0,     0,     0,     0,     0,    37,
694      0,    39,     0,     0,     0,     0,     0,     0,     0,     0,
695      0,     0,     8,     0,    11,    32,    33,     0,     0,    35,
696     36,    38,    40,    41,    42,    43,    46,    47,    48,    49,
697      0,    51,    52,    44,    45,    53,    54,    55,    56,     0,
698      0,     0,     0,     0,    26,    28,    29,    30,    31,     0,
699     59,    63,    64,    34,     0,    50,     0,     0,    57,     0,
700     60,    62,     0,     5,    27,    58,    59,     0,    61,     0,
701     65 };
702 typedef struct
703 #ifdef __cplusplus
704 	ipmon_yytoktype
705 #endif
706 {
707 #ifdef __cplusplus
708 const
709 #endif
710 char *t_name; int t_val; } ipmon_yytoktype;
711 #ifndef YYDEBUG
712 #	define YYDEBUG	0	/* don't allow debugging */
713 #endif
714 
715 #if YYDEBUG
716 
717 ipmon_yytoktype ipmon_yytoks[] =
718 {
719 	"YY_NUMBER",	257,
720 	"YY_HEX",	258,
721 	"YY_STR",	259,
722 	"YY_IPV6",	260,
723 	"YY_COMMENT",	261,
724 	"YY_CMP_EQ",	262,
725 	"YY_CMP_NE",	263,
726 	"YY_CMP_LE",	264,
727 	"YY_CMP_GE",	265,
728 	"YY_CMP_LT",	266,
729 	"YY_CMP_GT",	267,
730 	"YY_RANGE_OUT",	268,
731 	"YY_RANGE_IN",	269,
732 	"IPM_MATCH",	270,
733 	"IPM_BODY",	271,
734 	"IPM_COMMENT",	272,
735 	"IPM_DIRECTION",	273,
736 	"IPM_DSTIP",	274,
737 	"IPM_DSTPORT",	275,
738 	"IPM_EVERY",	276,
739 	"IPM_EXECUTE",	277,
740 	"IPM_GROUP",	278,
741 	"IPM_INTERFACE",	279,
742 	"IPM_IN",	280,
743 	"IPM_NO",	281,
744 	"IPM_OUT",	282,
745 	"IPM_PACKET",	283,
746 	"IPM_PACKETS",	284,
747 	"IPM_POOL",	285,
748 	"IPM_PROTOCOL",	286,
749 	"IPM_RESULT",	287,
750 	"IPM_RULE",	288,
751 	"IPM_SECOND",	289,
752 	"IPM_SECONDS",	290,
753 	"IPM_SRCIP",	291,
754 	"IPM_SRCPORT",	292,
755 	"IPM_LOGTAG",	293,
756 	"IPM_WITH",	294,
757 	"IPM_DO",	295,
758 	"IPM_SAVE",	296,
759 	"IPM_SYSLOG",	297,
760 	"IPM_NOTHING",	298,
761 	"IPM_RAW",	299,
762 	"IPM_TYPE",	300,
763 	"IPM_NAT",	301,
764 	"IPM_STATE",	302,
765 	"IPM_NATTAG",	303,
766 	"IPM_IPF",	304,
767 	"-unknown-",	-1	/* ends search */
768 };
769 
770 #ifdef __cplusplus
771 const
772 #endif
773 char * ipmon_yyreds[] =
774 {
775 	"-no such reduction-",
776 	"file : line",
777 	"file : assign",
778 	"file : file line",
779 	"file : file assign",
780 	"line : IPM_MATCH '{' matching '}' IPM_DO '{' doing '}' ';'",
781 	"line : IPM_COMMENT",
782 	"line : YY_COMMENT",
783 	"assign : YY_STR assigning YY_STR ';'",
784 	"assigning : '='",
785 	"matching : matchopt",
786 	"matching : matchopt ',' matching",
787 	"matchopt : direction",
788 	"matchopt : dstip",
789 	"matchopt : dstport",
790 	"matchopt : every",
791 	"matchopt : group",
792 	"matchopt : interface",
793 	"matchopt : protocol",
794 	"matchopt : result",
795 	"matchopt : rule",
796 	"matchopt : srcip",
797 	"matchopt : srcport",
798 	"matchopt : logtag",
799 	"matchopt : nattag",
800 	"matchopt : type",
801 	"doing : doopt",
802 	"doing : doopt ',' doing",
803 	"doopt : execute",
804 	"doopt : save",
805 	"doopt : syslog",
806 	"doopt : nothing",
807 	"direction : IPM_DIRECTION '=' IPM_IN",
808 	"direction : IPM_DIRECTION '=' IPM_OUT",
809 	"dstip : IPM_DSTIP '=' ipv4 '/' YY_NUMBER",
810 	"dstport : IPM_DSTPORT '=' YY_NUMBER",
811 	"dstport : IPM_DSTPORT '=' YY_STR",
812 	"every : IPM_EVERY IPM_SECOND",
813 	"every : IPM_EVERY YY_NUMBER IPM_SECONDS",
814 	"every : IPM_EVERY IPM_PACKET",
815 	"every : IPM_EVERY YY_NUMBER IPM_PACKETS",
816 	"group : IPM_GROUP '=' YY_NUMBER",
817 	"group : IPM_GROUP '=' YY_STR",
818 	"interface : IPM_INTERFACE '=' YY_STR",
819 	"logtag : IPM_LOGTAG '=' YY_NUMBER",
820 	"nattag : IPM_NATTAG '=' YY_STR",
821 	"protocol : IPM_PROTOCOL '=' YY_NUMBER",
822 	"protocol : IPM_PROTOCOL '=' YY_STR",
823 	"result : IPM_RESULT '=' YY_STR",
824 	"rule : IPM_RULE '=' YY_NUMBER",
825 	"srcip : IPM_SRCIP '=' ipv4 '/' YY_NUMBER",
826 	"srcport : IPM_SRCPORT '=' YY_NUMBER",
827 	"srcport : IPM_SRCPORT '=' YY_STR",
828 	"type : IPM_TYPE '=' typeopt",
829 	"typeopt : IPM_IPF",
830 	"typeopt : IPM_NAT",
831 	"typeopt : IPM_STATE",
832 	"execute : IPM_EXECUTE YY_STR",
833 	"save : IPM_SAVE saveopts YY_STR",
834 	"saveopts : /* empty */",
835 	"saveopts : saveopt",
836 	"saveopts : saveopt ',' saveopts",
837 	"saveopt : IPM_RAW",
838 	"syslog : IPM_SYSLOG",
839 	"nothing : IPM_NOTHING",
840 	"ipv4 : YY_NUMBER '.' YY_NUMBER '.' YY_NUMBER '.' YY_NUMBER",
841 };
842 #endif /* YYDEBUG */
843 # line	1 "/usr/share/lib/ccs/yaccpar"
844 /*
845  * CDDL HEADER START
846  *
847  * The contents of this file are subject to the terms of the
848  * Common Development and Distribution License, Version 1.0 only
849  * (the "License").  You may not use this file except in compliance
850  * with the License.
851  *
852  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
853  * or http://www.opensolaris.org/os/licensing.
854  * See the License for the specific language governing permissions
855  * and limitations under the License.
856  *
857  * When distributing Covered Code, include this CDDL HEADER in each
858  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
859  * If applicable, add the following below this CDDL HEADER, with the
860  * fields enclosed by brackets "[]" replaced with your own identifying
861  * information: Portions Copyright [ipmon_yyipmon_yy] [name of copyright owner]
862  *
863  * CDDL HEADER END
864  */
865 /*
866  * Copyright 1993 Sun Microsystems, Inc.  All rights reserved.
867  * Use is subject to license terms.
868  */
869 
870 /* Copyright (c) 1988 AT&T */
871 /* All Rights Reserved */
872 
873 #pragma ident	"%Z%%M%	%I%	%E% SMI"
874 
875 /*
876 ** Skeleton parser driver for yacc output
877 */
878 
879 /*
880 ** yacc user known macros and defines
881 */
882 #define YYERROR		goto ipmon_yyerrlab
883 #define YYACCEPT	return(0)
884 #define YYABORT		return(1)
885 #define YYBACKUP( newtoken, newvalue )\
886 {\
887 	if ( ipmon_yychar >= 0 || ( ipmon_yyr2[ ipmon_yytmp ] >> 1 ) != 1 )\
888 	{\
889 		ipmon_yyerror( "syntax error - cannot backup" );\
890 		goto ipmon_yyerrlab;\
891 	}\
892 	ipmon_yychar = newtoken;\
893 	ipmon_yystate = *ipmon_yyps;\
894 	ipmon_yylval = newvalue;\
895 	goto ipmon_yynewstate;\
896 }
897 #define YYRECOVERING()	(!!ipmon_yyerrflag)
898 #define YYNEW(type)	malloc(sizeof(type) * ipmon_yynewmax)
899 #define YYCOPY(to, from, type) \
900 	(type *) memcpy(to, (char *) from, ipmon_yymaxdepth * sizeof (type))
901 #define YYENLARGE( from, type) \
902 	(type *) realloc((char *) from, ipmon_yynewmax * sizeof(type))
903 #ifndef YYDEBUG
904 #	define YYDEBUG	1	/* make debugging available */
905 #endif
906 
907 /*
908 ** user known globals
909 */
910 int ipmon_yydebug;			/* set to 1 to get debugging */
911 
912 /*
913 ** driver internal defines
914 */
915 #define YYFLAG		(-10000000)
916 
917 /*
918 ** global variables used by the parser
919 */
920 YYSTYPE *ipmon_yypv;			/* top of value stack */
921 int *ipmon_yyps;			/* top of state stack */
922 
923 int ipmon_yystate;			/* current state */
924 int ipmon_yytmp;			/* extra var (lasts between blocks) */
925 
926 int ipmon_yynerrs;			/* number of errors */
927 int ipmon_yyerrflag;			/* error recovery flag */
928 int ipmon_yychar;			/* current input token number */
929 
930 
931 
932 #ifdef YYNMBCHARS
933 #define YYLEX()		ipmon_yycvtok(ipmon_yylex())
934 /*
935 ** ipmon_yycvtok - return a token if i is a wchar_t value that exceeds 255.
936 **	If i<255, i itself is the token.  If i>255 but the neither
937 **	of the 30th or 31st bit is on, i is already a token.
938 */
939 #if defined(__STDC__) || defined(__cplusplus)
940 int ipmon_yycvtok(int i)
941 #else
942 int ipmon_yycvtok(i) int i;
943 #endif
944 {
945 	int first = 0;
946 	int last = YYNMBCHARS - 1;
947 	int mid;
948 	wchar_t j;
949 
950 	if(i&0x60000000){/*Must convert to a token. */
951 		if( ipmon_yymbchars[last].character < i ){
952 			return i;/*Giving up*/
953 		}
954 		while ((last>=first)&&(first>=0)) {/*Binary search loop*/
955 			mid = (first+last)/2;
956 			j = ipmon_yymbchars[mid].character;
957 			if( j==i ){/*Found*/
958 				return ipmon_yymbchars[mid].tvalue;
959 			}else if( j<i ){
960 				first = mid + 1;
961 			}else{
962 				last = mid -1;
963 			}
964 		}
965 		/*No entry in the table.*/
966 		return i;/* Giving up.*/
967 	}else{/* i is already a token. */
968 		return i;
969 	}
970 }
971 #else/*!YYNMBCHARS*/
972 #define YYLEX()		ipmon_yylex()
973 #endif/*!YYNMBCHARS*/
974 
975 /*
976 ** ipmon_yyparse - return 0 if worked, 1 if syntax error not recovered from
977 */
978 #if defined(__STDC__) || defined(__cplusplus)
979 int ipmon_yyparse(void)
980 #else
981 int ipmon_yyparse()
982 #endif
983 {
984 	register YYSTYPE *ipmon_yypvt = 0;	/* top of value stack for $vars */
985 
986 #if defined(__cplusplus) || defined(lint)
987 /*
988 	hacks to please C++ and lint - goto's inside
989 	switch should never be executed
990 */
991 	static int __yaccpar_lint_hack__ = 0;
992 	switch (__yaccpar_lint_hack__)
993 	{
994 		case 1: goto ipmon_yyerrlab;
995 		case 2: goto ipmon_yynewstate;
996 	}
997 #endif
998 
999 	/*
1000 	** Initialize externals - ipmon_yyparse may be called more than once
1001 	*/
1002 	ipmon_yypv = &ipmon_yyv[-1];
1003 	ipmon_yyps = &ipmon_yys[-1];
1004 	ipmon_yystate = 0;
1005 	ipmon_yytmp = 0;
1006 	ipmon_yynerrs = 0;
1007 	ipmon_yyerrflag = 0;
1008 	ipmon_yychar = -1;
1009 
1010 #if YYMAXDEPTH <= 0
1011 	if (ipmon_yymaxdepth <= 0)
1012 	{
1013 		if ((ipmon_yymaxdepth = YYEXPAND(0)) <= 0)
1014 		{
1015 			ipmon_yyerror("yacc initialization error");
1016 			YYABORT;
1017 		}
1018 	}
1019 #endif
1020 
1021 	{
1022 		register YYSTYPE *ipmon_yy_pv;	/* top of value stack */
1023 		register int *ipmon_yy_ps;		/* top of state stack */
1024 		register int ipmon_yy_state;		/* current state */
1025 		register int  ipmon_yy_n;		/* internal state number info */
1026 	goto ipmon_yystack;	/* moved from 6 lines above to here to please C++ */
1027 
1028 		/*
1029 		** get globals into registers.
1030 		** branch to here only if YYBACKUP was called.
1031 		*/
1032 	ipmon_yynewstate:
1033 		ipmon_yy_pv = ipmon_yypv;
1034 		ipmon_yy_ps = ipmon_yyps;
1035 		ipmon_yy_state = ipmon_yystate;
1036 		goto ipmon_yy_newstate;
1037 
1038 		/*
1039 		** get globals into registers.
1040 		** either we just started, or we just finished a reduction
1041 		*/
1042 	ipmon_yystack:
1043 		ipmon_yy_pv = ipmon_yypv;
1044 		ipmon_yy_ps = ipmon_yyps;
1045 		ipmon_yy_state = ipmon_yystate;
1046 
1047 		/*
1048 		** top of for (;;) loop while no reductions done
1049 		*/
1050 	ipmon_yy_stack:
1051 		/*
1052 		** put a state and value onto the stacks
1053 		*/
1054 #if YYDEBUG
1055 		/*
1056 		** if debugging, look up token value in list of value vs.
1057 		** name pairs.  0 and negative (-1) are special values.
1058 		** Note: linear search is used since time is not a real
1059 		** consideration while debugging.
1060 		*/
1061 		if ( ipmon_yydebug )
1062 		{
1063 			register int ipmon_yy_i;
1064 
1065 			printf( "State %d, token ", ipmon_yy_state );
1066 			if ( ipmon_yychar == 0 )
1067 				printf( "end-of-file\n" );
1068 			else if ( ipmon_yychar < 0 )
1069 				printf( "-none-\n" );
1070 			else
1071 			{
1072 				for ( ipmon_yy_i = 0; ipmon_yytoks[ipmon_yy_i].t_val >= 0;
1073 					ipmon_yy_i++ )
1074 				{
1075 					if ( ipmon_yytoks[ipmon_yy_i].t_val == ipmon_yychar )
1076 						break;
1077 				}
1078 				printf( "%s\n", ipmon_yytoks[ipmon_yy_i].t_name );
1079 			}
1080 		}
1081 #endif /* YYDEBUG */
1082 		if ( ++ipmon_yy_ps >= &ipmon_yys[ ipmon_yymaxdepth ] )	/* room on stack? */
1083 		{
1084 			/*
1085 			** reallocate and recover.  Note that pointers
1086 			** have to be reset, or bad things will happen
1087 			*/
1088 			long ipmon_yyps_index = (ipmon_yy_ps - ipmon_yys);
1089 			long ipmon_yypv_index = (ipmon_yy_pv - ipmon_yyv);
1090 			long ipmon_yypvt_index = (ipmon_yypvt - ipmon_yyv);
1091 			int ipmon_yynewmax;
1092 #ifdef YYEXPAND
1093 			ipmon_yynewmax = YYEXPAND(ipmon_yymaxdepth);
1094 #else
1095 			ipmon_yynewmax = 2 * ipmon_yymaxdepth;	/* double table size */
1096 			if (ipmon_yymaxdepth == YYMAXDEPTH)	/* first time growth */
1097 			{
1098 				char *newipmon_yys = (char *)YYNEW(int);
1099 				char *newipmon_yyv = (char *)YYNEW(YYSTYPE);
1100 				if (newipmon_yys != 0 && newipmon_yyv != 0)
1101 				{
1102 					ipmon_yys = YYCOPY(newipmon_yys, ipmon_yys, int);
1103 					ipmon_yyv = YYCOPY(newipmon_yyv, ipmon_yyv, YYSTYPE);
1104 				}
1105 				else
1106 					ipmon_yynewmax = 0;	/* failed */
1107 			}
1108 			else				/* not first time */
1109 			{
1110 				ipmon_yys = YYENLARGE(ipmon_yys, int);
1111 				ipmon_yyv = YYENLARGE(ipmon_yyv, YYSTYPE);
1112 				if (ipmon_yys == 0 || ipmon_yyv == 0)
1113 					ipmon_yynewmax = 0;	/* failed */
1114 			}
1115 #endif
1116 			if (ipmon_yynewmax <= ipmon_yymaxdepth)	/* tables not expanded */
1117 			{
1118 				ipmon_yyerror( "yacc stack overflow" );
1119 				YYABORT;
1120 			}
1121 			ipmon_yymaxdepth = ipmon_yynewmax;
1122 
1123 			ipmon_yy_ps = ipmon_yys + ipmon_yyps_index;
1124 			ipmon_yy_pv = ipmon_yyv + ipmon_yypv_index;
1125 			ipmon_yypvt = ipmon_yyv + ipmon_yypvt_index;
1126 		}
1127 		*ipmon_yy_ps = ipmon_yy_state;
1128 		*++ipmon_yy_pv = ipmon_yyval;
1129 
1130 		/*
1131 		** we have a new state - find out what to do
1132 		*/
1133 	ipmon_yy_newstate:
1134 		if ( ( ipmon_yy_n = ipmon_yypact[ ipmon_yy_state ] ) <= YYFLAG )
1135 			goto ipmon_yydefault;		/* simple state */
1136 #if YYDEBUG
1137 		/*
1138 		** if debugging, need to mark whether new token grabbed
1139 		*/
1140 		ipmon_yytmp = ipmon_yychar < 0;
1141 #endif
1142 		if ( ( ipmon_yychar < 0 ) && ( ( ipmon_yychar = YYLEX() ) < 0 ) )
1143 			ipmon_yychar = 0;		/* reached EOF */
1144 #if YYDEBUG
1145 		if ( ipmon_yydebug && ipmon_yytmp )
1146 		{
1147 			register int ipmon_yy_i;
1148 
1149 			printf( "Received token " );
1150 			if ( ipmon_yychar == 0 )
1151 				printf( "end-of-file\n" );
1152 			else if ( ipmon_yychar < 0 )
1153 				printf( "-none-\n" );
1154 			else
1155 			{
1156 				for ( ipmon_yy_i = 0; ipmon_yytoks[ipmon_yy_i].t_val >= 0;
1157 					ipmon_yy_i++ )
1158 				{
1159 					if ( ipmon_yytoks[ipmon_yy_i].t_val == ipmon_yychar )
1160 						break;
1161 				}
1162 				printf( "%s\n", ipmon_yytoks[ipmon_yy_i].t_name );
1163 			}
1164 		}
1165 #endif /* YYDEBUG */
1166 		if ( ( ( ipmon_yy_n += ipmon_yychar ) < 0 ) || ( ipmon_yy_n >= YYLAST ) )
1167 			goto ipmon_yydefault;
1168 		if ( ipmon_yychk[ ipmon_yy_n = ipmon_yyact[ ipmon_yy_n ] ] == ipmon_yychar )	/*valid shift*/
1169 		{
1170 			ipmon_yychar = -1;
1171 			ipmon_yyval = ipmon_yylval;
1172 			ipmon_yy_state = ipmon_yy_n;
1173 			if ( ipmon_yyerrflag > 0 )
1174 				ipmon_yyerrflag--;
1175 			goto ipmon_yy_stack;
1176 		}
1177 
1178 	ipmon_yydefault:
1179 		if ( ( ipmon_yy_n = ipmon_yydef[ ipmon_yy_state ] ) == -2 )
1180 		{
1181 #if YYDEBUG
1182 			ipmon_yytmp = ipmon_yychar < 0;
1183 #endif
1184 			if ( ( ipmon_yychar < 0 ) && ( ( ipmon_yychar = YYLEX() ) < 0 ) )
1185 				ipmon_yychar = 0;		/* reached EOF */
1186 #if YYDEBUG
1187 			if ( ipmon_yydebug && ipmon_yytmp )
1188 			{
1189 				register int ipmon_yy_i;
1190 
1191 				printf( "Received token " );
1192 				if ( ipmon_yychar == 0 )
1193 					printf( "end-of-file\n" );
1194 				else if ( ipmon_yychar < 0 )
1195 					printf( "-none-\n" );
1196 				else
1197 				{
1198 					for ( ipmon_yy_i = 0;
1199 						ipmon_yytoks[ipmon_yy_i].t_val >= 0;
1200 						ipmon_yy_i++ )
1201 					{
1202 						if ( ipmon_yytoks[ipmon_yy_i].t_val
1203 							== ipmon_yychar )
1204 						{
1205 							break;
1206 						}
1207 					}
1208 					printf( "%s\n", ipmon_yytoks[ipmon_yy_i].t_name );
1209 				}
1210 			}
1211 #endif /* YYDEBUG */
1212 			/*
1213 			** look through exception table
1214 			*/
1215 			{
1216 				register YYCONST int *ipmon_yyxi = ipmon_yyexca;
1217 
1218 				while ( ( *ipmon_yyxi != -1 ) ||
1219 					( ipmon_yyxi[1] != ipmon_yy_state ) )
1220 				{
1221 					ipmon_yyxi += 2;
1222 				}
1223 				while ( ( *(ipmon_yyxi += 2) >= 0 ) &&
1224 					( *ipmon_yyxi != ipmon_yychar ) )
1225 					;
1226 				if ( ( ipmon_yy_n = ipmon_yyxi[1] ) < 0 )
1227 					YYACCEPT;
1228 			}
1229 		}
1230 
1231 		/*
1232 		** check for syntax error
1233 		*/
1234 		if ( ipmon_yy_n == 0 )	/* have an error */
1235 		{
1236 			/* no worry about speed here! */
1237 			switch ( ipmon_yyerrflag )
1238 			{
1239 			case 0:		/* new error */
1240 				ipmon_yyerror( "syntax error" );
1241 				goto skip_init;
1242 			ipmon_yyerrlab:
1243 				/*
1244 				** get globals into registers.
1245 				** we have a user generated syntax type error
1246 				*/
1247 				ipmon_yy_pv = ipmon_yypv;
1248 				ipmon_yy_ps = ipmon_yyps;
1249 				ipmon_yy_state = ipmon_yystate;
1250 			skip_init:
1251 				ipmon_yynerrs++;
1252 				/* FALLTHRU */
1253 			case 1:
1254 			case 2:		/* incompletely recovered error */
1255 					/* try again... */
1256 				ipmon_yyerrflag = 3;
1257 				/*
1258 				** find state where "error" is a legal
1259 				** shift action
1260 				*/
1261 				while ( ipmon_yy_ps >= ipmon_yys )
1262 				{
1263 					ipmon_yy_n = ipmon_yypact[ *ipmon_yy_ps ] + YYERRCODE;
1264 					if ( ipmon_yy_n >= 0 && ipmon_yy_n < YYLAST &&
1265 						ipmon_yychk[ipmon_yyact[ipmon_yy_n]] == YYERRCODE)					{
1266 						/*
1267 						** simulate shift of "error"
1268 						*/
1269 						ipmon_yy_state = ipmon_yyact[ ipmon_yy_n ];
1270 						goto ipmon_yy_stack;
1271 					}
1272 					/*
1273 					** current state has no shift on
1274 					** "error", pop stack
1275 					*/
1276 #if YYDEBUG
1277 #	define _POP_ "Error recovery pops state %d, uncovers state %d\n"
1278 					if ( ipmon_yydebug )
1279 						printf( _POP_, *ipmon_yy_ps,
1280 							ipmon_yy_ps[-1] );
1281 #	undef _POP_
1282 #endif
1283 					ipmon_yy_ps--;
1284 					ipmon_yy_pv--;
1285 				}
1286 				/*
1287 				** there is no state on stack with "error" as
1288 				** a valid shift.  give up.
1289 				*/
1290 				YYABORT;
1291 			case 3:		/* no shift yet; eat a token */
1292 #if YYDEBUG
1293 				/*
1294 				** if debugging, look up token in list of
1295 				** pairs.  0 and negative shouldn't occur,
1296 				** but since timing doesn't matter when
1297 				** debugging, it doesn't hurt to leave the
1298 				** tests here.
1299 				*/
1300 				if ( ipmon_yydebug )
1301 				{
1302 					register int ipmon_yy_i;
1303 
1304 					printf( "Error recovery discards " );
1305 					if ( ipmon_yychar == 0 )
1306 						printf( "token end-of-file\n" );
1307 					else if ( ipmon_yychar < 0 )
1308 						printf( "token -none-\n" );
1309 					else
1310 					{
1311 						for ( ipmon_yy_i = 0;
1312 							ipmon_yytoks[ipmon_yy_i].t_val >= 0;
1313 							ipmon_yy_i++ )
1314 						{
1315 							if ( ipmon_yytoks[ipmon_yy_i].t_val
1316 								== ipmon_yychar )
1317 							{
1318 								break;
1319 							}
1320 						}
1321 						printf( "token %s\n",
1322 							ipmon_yytoks[ipmon_yy_i].t_name );
1323 					}
1324 				}
1325 #endif /* YYDEBUG */
1326 				if ( ipmon_yychar == 0 )	/* reached EOF. quit */
1327 					YYABORT;
1328 				ipmon_yychar = -1;
1329 				goto ipmon_yy_newstate;
1330 			}
1331 		}/* end if ( ipmon_yy_n == 0 ) */
1332 		/*
1333 		** reduction by production ipmon_yy_n
1334 		** put stack tops, etc. so things right after switch
1335 		*/
1336 #if YYDEBUG
1337 		/*
1338 		** if debugging, print the string that is the user's
1339 		** specification of the reduction which is just about
1340 		** to be done.
1341 		*/
1342 		if ( ipmon_yydebug )
1343 			printf( "Reduce by (%d) \"%s\"\n",
1344 				ipmon_yy_n, ipmon_yyreds[ ipmon_yy_n ] );
1345 #endif
1346 		ipmon_yytmp = ipmon_yy_n;			/* value to switch over */
1347 		ipmon_yypvt = ipmon_yy_pv;			/* $vars top of value stack */
1348 		/*
1349 		** Look in goto table for next state
1350 		** Sorry about using ipmon_yy_state here as temporary
1351 		** register variable, but why not, if it works...
1352 		** If ipmon_yyr2[ ipmon_yy_n ] doesn't have the low order bit
1353 		** set, then there is no action to be done for
1354 		** this reduction.  So, no saving & unsaving of
1355 		** registers done.  The only difference between the
1356 		** code just after the if and the body of the if is
1357 		** the goto ipmon_yy_stack in the body.  This way the test
1358 		** can be made before the choice of what to do is needed.
1359 		*/
1360 		{
1361 			/* length of production doubled with extra bit */
1362 			register int ipmon_yy_len = ipmon_yyr2[ ipmon_yy_n ];
1363 
1364 			if ( !( ipmon_yy_len & 01 ) )
1365 			{
1366 				ipmon_yy_len >>= 1;
1367 				ipmon_yyval = ( ipmon_yy_pv -= ipmon_yy_len )[1];	/* $$ = $1 */
1368 				ipmon_yy_state = ipmon_yypgo[ ipmon_yy_n = ipmon_yyr1[ ipmon_yy_n ] ] +
1369 					*( ipmon_yy_ps -= ipmon_yy_len ) + 1;
1370 				if ( ipmon_yy_state >= YYLAST ||
1371 					ipmon_yychk[ ipmon_yy_state =
1372 					ipmon_yyact[ ipmon_yy_state ] ] != -ipmon_yy_n )
1373 				{
1374 					ipmon_yy_state = ipmon_yyact[ ipmon_yypgo[ ipmon_yy_n ] ];
1375 				}
1376 				goto ipmon_yy_stack;
1377 			}
1378 			ipmon_yy_len >>= 1;
1379 			ipmon_yyval = ( ipmon_yy_pv -= ipmon_yy_len )[1];	/* $$ = $1 */
1380 			ipmon_yy_state = ipmon_yypgo[ ipmon_yy_n = ipmon_yyr1[ ipmon_yy_n ] ] +
1381 				*( ipmon_yy_ps -= ipmon_yy_len ) + 1;
1382 			if ( ipmon_yy_state >= YYLAST ||
1383 				ipmon_yychk[ ipmon_yy_state = ipmon_yyact[ ipmon_yy_state ] ] != -ipmon_yy_n )
1384 			{
1385 				ipmon_yy_state = ipmon_yyact[ ipmon_yypgo[ ipmon_yy_n ] ];
1386 			}
1387 		}
1388 					/* save until reenter driver code */
1389 		ipmon_yystate = ipmon_yy_state;
1390 		ipmon_yyps = ipmon_yy_ps;
1391 		ipmon_yypv = ipmon_yy_pv;
1392 	}
1393 	/*
1394 	** code supplied by user is placed in this switch
1395 	*/
1396 	switch( ipmon_yytmp )
1397 	{
1398 
1399 case 5:
1400 # line 74 "../ipmon_y.y"
1401 { build_action(ipmon_yypvt[-6].opt); resetlexer(); } break;
1402 case 8:
1403 # line 79 "../ipmon_y.y"
1404 { set_variable(ipmon_yypvt[-3].str, ipmon_yypvt[-1].str);
1405 						  resetlexer();
1406 						  free(ipmon_yypvt[-3].str);
1407 						  free(ipmon_yypvt[-1].str);
1408 						} break;
1409 case 9:
1410 # line 87 "../ipmon_y.y"
1411 { ipmon_yyvarnext = 1; } break;
1412 case 10:
1413 # line 91 "../ipmon_y.y"
1414 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1415 case 11:
1416 # line 92 "../ipmon_y.y"
1417 { ipmon_yypvt[-2].opt->o_next = ipmon_yypvt[-0].opt; ipmon_yyval.opt = ipmon_yypvt[-2].opt; } break;
1418 case 12:
1419 # line 96 "../ipmon_y.y"
1420 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1421 case 13:
1422 # line 97 "../ipmon_y.y"
1423 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1424 case 14:
1425 # line 98 "../ipmon_y.y"
1426 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1427 case 15:
1428 # line 99 "../ipmon_y.y"
1429 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1430 case 16:
1431 # line 100 "../ipmon_y.y"
1432 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1433 case 17:
1434 # line 101 "../ipmon_y.y"
1435 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1436 case 18:
1437 # line 102 "../ipmon_y.y"
1438 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1439 case 19:
1440 # line 103 "../ipmon_y.y"
1441 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1442 case 20:
1443 # line 104 "../ipmon_y.y"
1444 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1445 case 21:
1446 # line 105 "../ipmon_y.y"
1447 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1448 case 22:
1449 # line 106 "../ipmon_y.y"
1450 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1451 case 23:
1452 # line 107 "../ipmon_y.y"
1453 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1454 case 24:
1455 # line 108 "../ipmon_y.y"
1456 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1457 case 25:
1458 # line 109 "../ipmon_y.y"
1459 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1460 case 26:
1461 # line 113 "../ipmon_y.y"
1462 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1463 case 27:
1464 # line 114 "../ipmon_y.y"
1465 { ipmon_yypvt[-2].opt->o_next = ipmon_yypvt[-0].opt; ipmon_yyval.opt = ipmon_yypvt[-2].opt; } break;
1466 case 28:
1467 # line 118 "../ipmon_y.y"
1468 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1469 case 29:
1470 # line 119 "../ipmon_y.y"
1471 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1472 case 30:
1473 # line 120 "../ipmon_y.y"
1474 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1475 case 31:
1476 # line 121 "../ipmon_y.y"
1477 { ipmon_yyval.opt = ipmon_yypvt[-0].opt; } break;
1478 case 32:
1479 # line 125 "../ipmon_y.y"
1480 { ipmon_yyval.opt = new_opt(IPM_DIRECTION);
1481 						  ipmon_yyval.opt->o_num = IPM_IN; } break;
1482 case 33:
1483 # line 127 "../ipmon_y.y"
1484 { ipmon_yyval.opt = new_opt(IPM_DIRECTION);
1485 						  ipmon_yyval.opt->o_num = IPM_OUT; } break;
1486 case 34:
1487 # line 131 "../ipmon_y.y"
1488 { ipmon_yyval.opt = new_opt(IPM_DSTIP);
1489 						  ipmon_yyval.opt->o_ip = ipmon_yypvt[-2].addr;
1490 						  ipmon_yyval.opt->o_num = ipmon_yypvt[-0].num; } break;
1491 case 35:
1492 # line 137 "../ipmon_y.y"
1493 { ipmon_yyval.opt = new_opt(IPM_DSTPORT);
1494 						  ipmon_yyval.opt->o_num = ipmon_yypvt[-0].num; } break;
1495 case 36:
1496 # line 139 "../ipmon_y.y"
1497 { ipmon_yyval.opt = new_opt(IPM_DSTPORT);
1498 						  ipmon_yyval.opt->o_str = ipmon_yypvt[-0].str; } break;
1499 case 37:
1500 # line 143 "../ipmon_y.y"
1501 { ipmon_yyval.opt = new_opt(IPM_SECOND);
1502 						  ipmon_yyval.opt->o_num = 1; } break;
1503 case 38:
1504 # line 145 "../ipmon_y.y"
1505 { ipmon_yyval.opt = new_opt(IPM_SECOND);
1506 						  ipmon_yyval.opt->o_num = ipmon_yypvt[-1].num; } break;
1507 case 39:
1508 # line 147 "../ipmon_y.y"
1509 { ipmon_yyval.opt = new_opt(IPM_PACKET);
1510 						  ipmon_yyval.opt->o_num = 1; } break;
1511 case 40:
1512 # line 149 "../ipmon_y.y"
1513 { ipmon_yyval.opt = new_opt(IPM_PACKET);
1514 						  ipmon_yyval.opt->o_num = ipmon_yypvt[-1].num; } break;
1515 case 41:
1516 # line 153 "../ipmon_y.y"
1517 { ipmon_yyval.opt = new_opt(IPM_GROUP);
1518 						  ipmon_yyval.opt->o_num = ipmon_yypvt[-0].num; } break;
1519 case 42:
1520 # line 155 "../ipmon_y.y"
1521 { ipmon_yyval.opt = new_opt(IPM_GROUP);
1522 						  ipmon_yyval.opt->o_str = ipmon_yypvt[-0].str; } break;
1523 case 43:
1524 # line 160 "../ipmon_y.y"
1525 { ipmon_yyval.opt = new_opt(IPM_INTERFACE);
1526 						  ipmon_yyval.opt->o_str = ipmon_yypvt[-0].str; } break;
1527 case 44:
1528 # line 164 "../ipmon_y.y"
1529 { ipmon_yyval.opt = new_opt(IPM_LOGTAG);
1530 						  ipmon_yyval.opt->o_num = ipmon_yypvt[-0].num; } break;
1531 case 45:
1532 # line 168 "../ipmon_y.y"
1533 { ipmon_yyval.opt = new_opt(IPM_NATTAG);
1534 						  ipmon_yyval.opt->o_str = ipmon_yypvt[-0].str; } break;
1535 case 46:
1536 # line 173 "../ipmon_y.y"
1537 { ipmon_yyval.opt = new_opt(IPM_PROTOCOL);
1538 						  ipmon_yyval.opt->o_num = ipmon_yypvt[-0].num; } break;
1539 case 47:
1540 # line 175 "../ipmon_y.y"
1541 { ipmon_yyval.opt = new_opt(IPM_PROTOCOL);
1542 						  ipmon_yyval.opt->o_num = getproto(ipmon_yypvt[-0].str);
1543 						  free(ipmon_yypvt[-0].str);
1544 						} break;
1545 case 48:
1546 # line 181 "../ipmon_y.y"
1547 { ipmon_yyval.opt = new_opt(IPM_RESULT);
1548 						  ipmon_yyval.opt->o_str = ipmon_yypvt[-0].str; } break;
1549 case 49:
1550 # line 185 "../ipmon_y.y"
1551 { ipmon_yyval.opt = new_opt(IPM_RULE);
1552 						  ipmon_yyval.opt->o_num = YY_NUMBER; } break;
1553 case 50:
1554 # line 189 "../ipmon_y.y"
1555 { ipmon_yyval.opt = new_opt(IPM_SRCIP);
1556 						  ipmon_yyval.opt->o_ip = ipmon_yypvt[-2].addr;
1557 						  ipmon_yyval.opt->o_num = ipmon_yypvt[-0].num; } break;
1558 case 51:
1559 # line 195 "../ipmon_y.y"
1560 { ipmon_yyval.opt = new_opt(IPM_SRCPORT);
1561 						  ipmon_yyval.opt->o_num = ipmon_yypvt[-0].num; } break;
1562 case 52:
1563 # line 197 "../ipmon_y.y"
1564 { ipmon_yyval.opt = new_opt(IPM_SRCPORT);
1565 						  ipmon_yyval.opt->o_str = ipmon_yypvt[-0].str; } break;
1566 case 53:
1567 # line 201 "../ipmon_y.y"
1568 { ipmon_yyval.opt = new_opt(IPM_TYPE);
1569 						  ipmon_yyval.opt->o_num = ipmon_yypvt[-0].num; } break;
1570 case 54:
1571 # line 206 "../ipmon_y.y"
1572 { ipmon_yyval.num = IPL_MAGIC; } break;
1573 case 55:
1574 # line 207 "../ipmon_y.y"
1575 { ipmon_yyval.num = IPL_MAGIC_NAT; } break;
1576 case 56:
1577 # line 208 "../ipmon_y.y"
1578 { ipmon_yyval.num = IPL_MAGIC_STATE; } break;
1579 case 57:
1580 # line 212 "../ipmon_y.y"
1581 { ipmon_yyval.opt = new_opt(IPM_EXECUTE);
1582 						  ipmon_yyval.opt->o_str = ipmon_yypvt[-0].str; } break;
1583 case 58:
1584 # line 216 "../ipmon_y.y"
1585 { ipmon_yyval.opt = new_opt(IPM_SAVE);
1586 						  ipmon_yyval.opt->o_num = ipmon_yypvt[-1].num;
1587 						  ipmon_yyval.opt->o_str = ipmon_yypvt[-0].str; } break;
1588 case 59:
1589 # line 221 "../ipmon_y.y"
1590 { ipmon_yyval.num = 0; } break;
1591 case 60:
1592 # line 222 "../ipmon_y.y"
1593 { ipmon_yyval.num = ipmon_yypvt[-0].num; } break;
1594 case 61:
1595 # line 223 "../ipmon_y.y"
1596 { ipmon_yyval.num = ipmon_yypvt[-2].num | ipmon_yypvt[-0].num; } break;
1597 case 62:
1598 # line 227 "../ipmon_y.y"
1599 { ipmon_yyval.num = IPMDO_SAVERAW; } break;
1600 case 63:
1601 # line 230 "../ipmon_y.y"
1602 { ipmon_yyval.opt = new_opt(IPM_SYSLOG); } break;
1603 case 64:
1604 # line 234 "../ipmon_y.y"
1605 { ipmon_yyval.opt = 0; } break;
1606 case 65:
1607 # line 238 "../ipmon_y.y"
1608 { if (ipmon_yypvt[-6].num > 255 || ipmon_yypvt[-4].num > 255 || ipmon_yypvt[-2].num > 255 || ipmon_yypvt[-0].num > 255) {
1609 			ipmon_yyerror("Invalid octet string for IP address");
1610 			return 0;
1611 		  }
1612 		  ipmon_yyval.addr.s_addr = (ipmon_yypvt[-6].num << 24) | (ipmon_yypvt[-4].num << 16) | (ipmon_yypvt[-2].num << 8) | ipmon_yypvt[-0].num;
1613 		  ipmon_yyval.addr.s_addr = htonl(ipmon_yyval.addr.s_addr);
1614 		} break;
1615 # line	556 "/usr/share/lib/ccs/yaccpar"
1616 	}
1617 	goto ipmon_yystack;		/* reset registers in driver code */
1618 }
1619 
1620