1145519Sdarrenr/* $FreeBSD: stable/10/contrib/ipfilter/tools/ipf_y.y 317314 2017-04-23 03:16:38Z cy $ */ 2145510Sdarrenr 3170268Sdarrenr/* 4255332Scy * Copyright (C) 2012 by Darren Reed. 5170268Sdarrenr * 6170268Sdarrenr * See the IPFILTER.LICENCE file for details on licencing. 7170268Sdarrenr */ 8145510Sdarrenr%{ 9145510Sdarrenr#include "ipf.h" 10145510Sdarrenr#include <sys/ioctl.h> 11145510Sdarrenr#include <syslog.h> 12317314Scy#include <err.h> 13145510Sdarrenr#ifdef IPFILTER_BPF 14145510Sdarrenr# include <pcap.h> 15145510Sdarrenr#endif 16145510Sdarrenr#include "netinet/ip_pool.h" 17145510Sdarrenr#include "netinet/ip_htable.h" 18145510Sdarrenr#include "netinet/ipl.h" 19145510Sdarrenr#include "ipf_l.h" 20145510Sdarrenr 21145510Sdarrenr#define YYDEBUG 1 22145510Sdarrenr#define DOALL(x) for (fr = frc; fr != NULL; fr = fr->fr_next) { x } 23145510Sdarrenr#define DOREM(x) for (; fr != NULL; fr = fr->fr_next) { x } 24145510Sdarrenr 25145510Sdarrenrextern void yyerror __P((char *)); 26145510Sdarrenrextern int yyparse __P((void)); 27145510Sdarrenrextern int yylex __P((void)); 28145510Sdarrenrextern int yydebug; 29145510Sdarrenrextern FILE *yyin; 30145510Sdarrenrextern int yylineNum; 31145510Sdarrenr 32255332Scystatic int addname __P((frentry_t **, char *)); 33255332Scystatic frentry_t *addrule __P((void)); 34255332Scystatic frentry_t *allocfr __P((void)); 35255332Scystatic void build_dstaddr_af __P((frentry_t *, void *)); 36255332Scystatic void build_srcaddr_af __P((frentry_t *, void *)); 37145510Sdarrenrstatic void dobpf __P((int, char *)); 38255332Scystatic void doipfexpr __P((char *)); 39255332Scystatic void do_tuneint __P((char *, int)); 40255332Scystatic void do_tunestr __P((char *, char *)); 41255332Scystatic void fillgroup __P((frentry_t *)); 42255332Scystatic int lookuphost __P((char *, i6addr_t *)); 43145510Sdarrenrstatic u_int makehash __P((struct alist_s *)); 44145510Sdarrenrstatic int makepool __P((struct alist_s *)); 45255332Scystatic struct alist_s *newalist __P((struct alist_s *)); 46255332Scystatic void newrule __P((void)); 47255332Scystatic void resetaddr __P((void)); 48255332Scystatic void setgroup __P((frentry_t **, char *)); 49255332Scystatic void setgrhead __P((frentry_t **, char *)); 50255332Scystatic void seticmphead __P((frentry_t **, char *)); 51255332Scystatic void setifname __P((frentry_t **, int, char *)); 52255332Scystatic void setipftype __P((void)); 53145510Sdarrenrstatic void setsyslog __P((void)); 54145510Sdarrenrstatic void unsetsyslog __P((void)); 55145510Sdarrenr 56145510Sdarrenrfrentry_t *fr = NULL, *frc = NULL, *frtop = NULL, *frold = NULL; 57145510Sdarrenr 58145510Sdarrenrstatic int ifpflag = 0; 59145510Sdarrenrstatic int nowith = 0; 60145510Sdarrenrstatic int dynamic = -1; 61145510Sdarrenrstatic int pooled = 0; 62145510Sdarrenrstatic int hashed = 0; 63145510Sdarrenrstatic int nrules = 0; 64145510Sdarrenrstatic int newlist = 0; 65145510Sdarrenrstatic int added = 0; 66145510Sdarrenrstatic int ipffd = -1; 67255332Scystatic int *yycont = NULL; 68255332Scystatic ioctlfunc_t ipfioctls[IPL_LOGSIZE]; 69145510Sdarrenrstatic addfunc_t ipfaddfunc = NULL; 70145510Sdarrenr 71145510Sdarrenr%} 72145510Sdarrenr%union { 73145510Sdarrenr char *str; 74145510Sdarrenr u_32_t num; 75145510Sdarrenr frentry_t fr; 76145510Sdarrenr frtuc_t *frt; 77145510Sdarrenr struct alist_s *alist; 78145510Sdarrenr u_short port; 79255332Scy struct in_addr ip4; 80145510Sdarrenr struct { 81145510Sdarrenr u_short p1; 82145510Sdarrenr u_short p2; 83145510Sdarrenr int pc; 84145510Sdarrenr } pc; 85255332Scy struct ipp_s { 86255332Scy int type; 87255332Scy int ifpos; 88255332Scy int f; 89255332Scy int v; 90255332Scy int lif; 91145510Sdarrenr union i6addr a; 92145510Sdarrenr union i6addr m; 93255332Scy char *name; 94145510Sdarrenr } ipp; 95161357Sguido struct { 96255332Scy i6addr_t adr; 97255332Scy int f; 98255332Scy } adr; 99255332Scy i6addr_t ip6; 100255332Scy struct { 101161357Sguido char *if1; 102161357Sguido char *if2; 103161357Sguido } ifs; 104255332Scy char gname[FR_GROUPLEN]; 105145510Sdarrenr}; 106145510Sdarrenr 107145510Sdarrenr%type <port> portnum 108145510Sdarrenr%type <num> facility priority icmpcode seclevel secname icmptype 109145510Sdarrenr%type <num> opt compare range opttype flagset optlist ipv6hdrlist ipv6hdr 110255332Scy%type <num> portc porteq ipmask maskopts 111255332Scy%type <ip4> ipv4 ipv4_16 ipv4_24 112255332Scy%type <adr> hostname 113145510Sdarrenr%type <ipp> addr ipaddr 114255332Scy%type <str> servicename name interfacename groupname 115145510Sdarrenr%type <pc> portrange portcomp 116145510Sdarrenr%type <alist> addrlist poollist 117161357Sguido%type <ifs> onname 118145510Sdarrenr 119145510Sdarrenr%token <num> YY_NUMBER YY_HEX 120145510Sdarrenr%token <str> YY_STR 121145510Sdarrenr%token YY_COMMENT 122145510Sdarrenr%token YY_CMP_EQ YY_CMP_NE YY_CMP_LE YY_CMP_GE YY_CMP_LT YY_CMP_GT 123145510Sdarrenr%token YY_RANGE_OUT YY_RANGE_IN 124145510Sdarrenr%token <ip6> YY_IPV6 125145510Sdarrenr 126255332Scy%token IPFY_SET 127161357Sguido%token IPFY_PASS IPFY_BLOCK IPFY_COUNT IPFY_CALL IPFY_NOMATCH 128145510Sdarrenr%token IPFY_RETICMP IPFY_RETRST IPFY_RETICMPASDST 129145510Sdarrenr%token IPFY_IN IPFY_OUT 130145510Sdarrenr%token IPFY_QUICK IPFY_ON IPFY_OUTVIA IPFY_INVIA 131145510Sdarrenr%token IPFY_DUPTO IPFY_TO IPFY_FROUTE IPFY_REPLY_TO IPFY_ROUTETO 132255332Scy%token IPFY_TOS IPFY_TTL IPFY_PROTO IPFY_INET IPFY_INET6 133145510Sdarrenr%token IPFY_HEAD IPFY_GROUP 134145510Sdarrenr%token IPFY_AUTH IPFY_PREAUTH 135255332Scy%token IPFY_LOG IPFY_BODY IPFY_FIRST IPFY_LEVEL IPFY_ORBLOCK IPFY_L5AS 136255332Scy%token IPFY_LOGTAG IPFY_MATCHTAG IPFY_SETTAG IPFY_SKIP IPFY_DECAPS 137145510Sdarrenr%token IPFY_FROM IPFY_ALL IPFY_ANY IPFY_BPFV4 IPFY_BPFV6 IPFY_POOL IPFY_HASH 138255332Scy%token IPFY_IPFEXPR IPFY_PPS IPFY_FAMILY IPFY_DSTLIST 139145510Sdarrenr%token IPFY_ESP IPFY_AH 140145510Sdarrenr%token IPFY_WITH IPFY_AND IPFY_NOT IPFY_NO IPFY_OPT 141145510Sdarrenr%token IPFY_TCPUDP IPFY_TCP IPFY_UDP 142145510Sdarrenr%token IPFY_FLAGS IPFY_MULTICAST 143145510Sdarrenr%token IPFY_MASK IPFY_BROADCAST IPFY_NETWORK IPFY_NETMASKED IPFY_PEER 144255332Scy%token IPFY_RPC IPFY_PORT 145255332Scy%token IPFY_NOW IPFY_COMMENT IPFY_RULETTL 146145510Sdarrenr%token IPFY_ICMP IPFY_ICMPTYPE IPFY_ICMPCODE 147145510Sdarrenr%token IPFY_IPOPTS IPFY_SHORT IPFY_NAT IPFY_BADSRC IPFY_LOWTTL IPFY_FRAG 148145510Sdarrenr%token IPFY_MBCAST IPFY_BAD IPFY_BADNAT IPFY_OOW IPFY_NEWISN IPFY_NOICMPERR 149145510Sdarrenr%token IPFY_KEEP IPFY_STATE IPFY_FRAGS IPFY_LIMIT IPFY_STRICT IPFY_AGE 150255332Scy%token IPFY_SYNC IPFY_FRAGBODY IPFY_ICMPHEAD IPFY_NOLOG IPFY_LOOSE 151255332Scy%token IPFY_MAX_SRCS IPFY_MAX_PER_SRC 152145510Sdarrenr%token IPFY_IPOPT_NOP IPFY_IPOPT_RR IPFY_IPOPT_ZSU IPFY_IPOPT_MTUP 153145510Sdarrenr%token IPFY_IPOPT_MTUR IPFY_IPOPT_ENCODE IPFY_IPOPT_TS IPFY_IPOPT_TR 154145510Sdarrenr%token IPFY_IPOPT_SEC IPFY_IPOPT_LSRR IPFY_IPOPT_ESEC IPFY_IPOPT_CIPSO 155145510Sdarrenr%token IPFY_IPOPT_SATID IPFY_IPOPT_SSRR IPFY_IPOPT_ADDEXT IPFY_IPOPT_VISA 156145510Sdarrenr%token IPFY_IPOPT_IMITD IPFY_IPOPT_EIP IPFY_IPOPT_FINN IPFY_IPOPT_DPS 157145510Sdarrenr%token IPFY_IPOPT_SDB IPFY_IPOPT_NSAPA IPFY_IPOPT_RTRALRT IPFY_IPOPT_UMP 158145510Sdarrenr%token IPFY_SECCLASS IPFY_SEC_UNC IPFY_SEC_CONF IPFY_SEC_RSV1 IPFY_SEC_RSV2 159255332Scy%token IPFY_SEC_RSV4 IPFY_SEC_SEC IPFY_SEC_TS IPFY_SEC_RSV3 IPFY_DOI 160145510Sdarrenr 161255332Scy%token IPFY_V6HDRS IPFY_IPV6OPT IPFY_IPV6OPT_DSTOPTS IPFY_IPV6OPT_HOPOPTS 162255332Scy%token IPFY_IPV6OPT_IPV6 IPFY_IPV6OPT_NONE IPFY_IPV6OPT_ROUTING IPFY_V6HDR 163153881Sguido%token IPFY_IPV6OPT_MOBILITY IPFY_IPV6OPT_ESP IPFY_IPV6OPT_FRAG 164145510Sdarrenr 165145510Sdarrenr%token IPFY_ICMPT_UNR IPFY_ICMPT_ECHO IPFY_ICMPT_ECHOR IPFY_ICMPT_SQUENCH 166145510Sdarrenr%token IPFY_ICMPT_REDIR IPFY_ICMPT_TIMEX IPFY_ICMPT_PARAMP IPFY_ICMPT_TIMEST 167145510Sdarrenr%token IPFY_ICMPT_TIMESTREP IPFY_ICMPT_INFOREQ IPFY_ICMPT_INFOREP 168145510Sdarrenr%token IPFY_ICMPT_MASKREQ IPFY_ICMPT_MASKREP IPFY_ICMPT_ROUTERAD 169145510Sdarrenr%token IPFY_ICMPT_ROUTERSOL 170145510Sdarrenr 171145510Sdarrenr%token IPFY_ICMPC_NETUNR IPFY_ICMPC_HSTUNR IPFY_ICMPC_PROUNR IPFY_ICMPC_PORUNR 172145510Sdarrenr%token IPFY_ICMPC_NEEDF IPFY_ICMPC_SRCFAIL IPFY_ICMPC_NETUNK IPFY_ICMPC_HSTUNK 173145510Sdarrenr%token IPFY_ICMPC_ISOLATE IPFY_ICMPC_NETPRO IPFY_ICMPC_HSTPRO 174145510Sdarrenr%token IPFY_ICMPC_NETTOS IPFY_ICMPC_HSTTOS IPFY_ICMPC_FLTPRO IPFY_ICMPC_HSTPRE 175145510Sdarrenr%token IPFY_ICMPC_CUTPRE 176145510Sdarrenr 177145510Sdarrenr%token IPFY_FAC_KERN IPFY_FAC_USER IPFY_FAC_MAIL IPFY_FAC_DAEMON IPFY_FAC_AUTH 178145510Sdarrenr%token IPFY_FAC_SYSLOG IPFY_FAC_LPR IPFY_FAC_NEWS IPFY_FAC_UUCP IPFY_FAC_CRON 179145510Sdarrenr%token IPFY_FAC_LOCAL0 IPFY_FAC_LOCAL1 IPFY_FAC_LOCAL2 IPFY_FAC_LOCAL3 180145510Sdarrenr%token IPFY_FAC_LOCAL4 IPFY_FAC_LOCAL5 IPFY_FAC_LOCAL6 IPFY_FAC_LOCAL7 181145510Sdarrenr%token IPFY_FAC_SECURITY IPFY_FAC_FTP IPFY_FAC_AUTHPRIV IPFY_FAC_AUDIT 182145510Sdarrenr%token IPFY_FAC_LFMT IPFY_FAC_CONSOLE 183145510Sdarrenr 184145510Sdarrenr%token IPFY_PRI_EMERG IPFY_PRI_ALERT IPFY_PRI_CRIT IPFY_PRI_ERR IPFY_PRI_WARN 185145510Sdarrenr%token IPFY_PRI_NOTICE IPFY_PRI_INFO IPFY_PRI_DEBUG 186145510Sdarrenr%% 187255332Scyfile: settings rules 188255332Scy | rules 189255332Scy ; 190255332Scy 191255332Scysettings: 192255332Scy YY_COMMENT 193255332Scy | setting 194255332Scy | settings setting 195255332Scy ; 196255332Scy 197255332Scyrules: line 198145510Sdarrenr | assign 199255332Scy | rules line 200255332Scy | rules assign 201145510Sdarrenr ; 202145510Sdarrenr 203255332Scysetting: 204255332Scy IPFY_SET YY_STR YY_NUMBER ';' { do_tuneint($2, $3); } 205255332Scy | IPFY_SET YY_STR YY_HEX ';' { do_tuneint($2, $3); } 206255332Scy | IPFY_SET YY_STR YY_STR ';' { do_tunestr($2, $3); } 207255332Scy ; 208255332Scy 209170268Sdarrenrline: rule { while ((fr = frtop) != NULL) { 210145510Sdarrenr frtop = fr->fr_next; 211145510Sdarrenr fr->fr_next = NULL; 212255332Scy if ((fr->fr_type == FR_T_IPF) && 213255332Scy (fr->fr_ip.fi_v == 0)) 214255332Scy fr->fr_mip.fi_v = 0; 215255332Scy /* XXX validate ? */ 216255332Scy (*ipfaddfunc)(ipffd, ipfioctls[IPL_LOGIPF], fr); 217145510Sdarrenr fr->fr_next = frold; 218145510Sdarrenr frold = fr; 219145510Sdarrenr } 220145510Sdarrenr resetlexer(); 221145510Sdarrenr } 222145510Sdarrenr | YY_COMMENT 223145510Sdarrenr ; 224145510Sdarrenr 225161357Sguidoxx: { newrule(); } 226145510Sdarrenr ; 227145510Sdarrenr 228145510Sdarrenrassign: YY_STR assigning YY_STR ';' { set_variable($1, $3); 229145510Sdarrenr resetlexer(); 230145510Sdarrenr free($1); 231145510Sdarrenr free($3); 232170268Sdarrenr yyvarnext = 0; 233145510Sdarrenr } 234145510Sdarrenr ; 235145510Sdarrenr 236145510Sdarrenrassigning: 237145510Sdarrenr '=' { yyvarnext = 1; } 238145510Sdarrenr ; 239145510Sdarrenr 240145510Sdarrenrrule: inrule eol 241145510Sdarrenr | outrule eol 242145510Sdarrenr ; 243145510Sdarrenr 244145510Sdarrenreol: | ';' 245145510Sdarrenr ; 246145510Sdarrenr 247145510Sdarrenrinrule: 248145510Sdarrenr rulehead markin inopts rulemain ruletail intag ruletail2 249145510Sdarrenr ; 250145510Sdarrenr 251145510Sdarrenroutrule: 252145510Sdarrenr rulehead markout outopts rulemain ruletail outtag ruletail2 253145510Sdarrenr ; 254145510Sdarrenr 255145510Sdarrenrrulehead: 256170268Sdarrenr xx collection action 257170268Sdarrenr | xx insert collection action 258145510Sdarrenr ; 259145510Sdarrenr 260145510Sdarrenrmarkin: IPFY_IN { fr->fr_flags |= FR_INQUE; } 261145510Sdarrenr ; 262145510Sdarrenr 263145510Sdarrenrmarkout: 264145510Sdarrenr IPFY_OUT { fr->fr_flags |= FR_OUTQUE; } 265145510Sdarrenr ; 266145510Sdarrenr 267145510Sdarrenrrulemain: 268145510Sdarrenr ipfrule 269145510Sdarrenr | bpfrule 270255332Scy | exprrule 271145510Sdarrenr ; 272145510Sdarrenr 273145510Sdarrenripfrule: 274255332Scy family tos ttl proto ip 275145510Sdarrenr ; 276145510Sdarrenr 277255332Scyfamily: | IPFY_FAMILY IPFY_INET { if (use_inet6 == 1) { 278255332Scy YYERROR; 279255332Scy } else { 280255332Scy frc->fr_family = AF_INET; 281255332Scy } 282255332Scy } 283255332Scy | IPFY_INET { if (use_inet6 == 1) { 284255332Scy YYERROR; 285255332Scy } else { 286255332Scy frc->fr_family = AF_INET; 287255332Scy } 288255332Scy } 289255332Scy | IPFY_FAMILY IPFY_INET6 { if (use_inet6 == -1) { 290255332Scy YYERROR; 291255332Scy } else { 292255332Scy frc->fr_family = AF_INET6; 293255332Scy } 294255332Scy } 295255332Scy | IPFY_INET6 { if (use_inet6 == -1) { 296255332Scy YYERROR; 297255332Scy } else { 298255332Scy frc->fr_family = AF_INET6; 299255332Scy } 300255332Scy } 301255332Scy ; 302255332Scy 303145510Sdarrenrbpfrule: 304145510Sdarrenr IPFY_BPFV4 '{' YY_STR '}' { dobpf(4, $3); free($3); } 305145510Sdarrenr | IPFY_BPFV6 '{' YY_STR '}' { dobpf(6, $3); free($3); } 306145510Sdarrenr ; 307145510Sdarrenr 308255332Scyexprrule: 309255332Scy IPFY_IPFEXPR '{' YY_STR '}' { doipfexpr($3); } 310255332Scy ; 311255332Scy 312145510Sdarrenrruletail: 313145510Sdarrenr with keep head group 314145510Sdarrenr ; 315145510Sdarrenr 316145510Sdarrenrruletail2: 317255332Scy pps age new rulettl comment 318145510Sdarrenr ; 319145510Sdarrenr 320145510Sdarrenrintag: settagin matchtagin 321145510Sdarrenr ; 322145510Sdarrenr 323145510Sdarrenrouttag: settagout matchtagout 324145510Sdarrenr ; 325145510Sdarrenr 326145510Sdarrenrinsert: 327145510Sdarrenr '@' YY_NUMBER { fr->fr_hits = (U_QUAD_T)$2 + 1; } 328145510Sdarrenr ; 329145510Sdarrenr 330145510Sdarrenrcollection: 331145510Sdarrenr | YY_NUMBER { fr->fr_collect = $1; } 332145510Sdarrenr ; 333145510Sdarrenr 334145510Sdarrenraction: block 335145510Sdarrenr | IPFY_PASS { fr->fr_flags |= FR_PASS; } 336161357Sguido | IPFY_NOMATCH { fr->fr_flags |= FR_NOMATCH; } 337145510Sdarrenr | log 338145510Sdarrenr | IPFY_COUNT { fr->fr_flags |= FR_ACCOUNT; } 339255332Scy | decaps { fr->fr_flags |= FR_DECAPSULATE; } 340145510Sdarrenr | auth 341145510Sdarrenr | IPFY_SKIP YY_NUMBER { fr->fr_flags |= FR_SKIP; 342145510Sdarrenr fr->fr_arg = $2; } 343145510Sdarrenr | IPFY_CALL func 344145510Sdarrenr | IPFY_CALL IPFY_NOW func { fr->fr_flags |= FR_CALLNOW; } 345145510Sdarrenr ; 346145510Sdarrenr 347145510Sdarrenrblock: blocked 348145510Sdarrenr | blocked blockreturn 349145510Sdarrenr ; 350145510Sdarrenr 351145510Sdarrenrblocked: 352145510Sdarrenr IPFY_BLOCK { fr->fr_flags = FR_BLOCK; } 353145510Sdarrenr ; 354145510Sdarrenrblockreturn: 355145510Sdarrenr IPFY_RETICMP { fr->fr_flags |= FR_RETICMP; } 356145510Sdarrenr | IPFY_RETICMP returncode { fr->fr_flags |= FR_RETICMP; } 357145510Sdarrenr | IPFY_RETICMPASDST { fr->fr_flags |= FR_FAKEICMP; } 358145510Sdarrenr | IPFY_RETICMPASDST returncode { fr->fr_flags |= FR_FAKEICMP; } 359145510Sdarrenr | IPFY_RETRST { fr->fr_flags |= FR_RETRST; } 360145510Sdarrenr ; 361145510Sdarrenr 362255332Scydecaps: IPFY_DECAPS 363255332Scy | IPFY_DECAPS IPFY_L5AS '(' YY_STR ')' 364255332Scy { fr->fr_icode = atoi($4); } 365255332Scy ; 366255332Scy 367145510Sdarrenrlog: IPFY_LOG { fr->fr_flags |= FR_LOG; } 368145510Sdarrenr | IPFY_LOG logoptions { fr->fr_flags |= FR_LOG; } 369145510Sdarrenr ; 370145510Sdarrenr 371145510Sdarrenrauth: IPFY_AUTH { fr->fr_flags |= FR_AUTH; } 372161357Sguido | IPFY_AUTH blockreturn { fr->fr_flags |= FR_AUTH;} 373145510Sdarrenr | IPFY_PREAUTH { fr->fr_flags |= FR_PREAUTH; } 374145510Sdarrenr ; 375145510Sdarrenr 376255332Scyfunc: YY_STR '/' YY_NUMBER 377255332Scy { fr->fr_func = nametokva($1, ipfioctls[IPL_LOGIPF]); 378255332Scy fr->fr_arg = $3; 379255332Scy free($1); 380255332Scy } 381145510Sdarrenr ; 382145510Sdarrenr 383145510Sdarrenrinopts: 384145510Sdarrenr | inopts inopt 385145510Sdarrenr ; 386145510Sdarrenr 387145510Sdarrenrinopt: 388145510Sdarrenr logopt 389145510Sdarrenr | quick 390145510Sdarrenr | on 391145510Sdarrenr | dup 392145510Sdarrenr | froute 393145510Sdarrenr | proute 394145510Sdarrenr | replyto 395145510Sdarrenr ; 396145510Sdarrenr 397145510Sdarrenroutopts: 398145510Sdarrenr | outopts outopt 399145510Sdarrenr ; 400145510Sdarrenr 401145510Sdarrenroutopt: 402145510Sdarrenr logopt 403145510Sdarrenr | quick 404145510Sdarrenr | on 405145510Sdarrenr | dup 406145510Sdarrenr | proute 407255332Scy | froute 408145510Sdarrenr | replyto 409145510Sdarrenr ; 410145510Sdarrenr 411145510Sdarrenrtos: | settos YY_NUMBER { DOALL(fr->fr_tos = $2; fr->fr_mtos = 0xff;) } 412145510Sdarrenr | settos YY_HEX { DOALL(fr->fr_tos = $2; fr->fr_mtos = 0xff;) } 413145510Sdarrenr | settos lstart toslist lend 414145510Sdarrenr ; 415145510Sdarrenr 416145510Sdarrenrsettos: IPFY_TOS { setipftype(); } 417145510Sdarrenr ; 418145510Sdarrenr 419145510Sdarrenrtoslist: 420145510Sdarrenr YY_NUMBER { DOALL(fr->fr_tos = $1; fr->fr_mtos = 0xff;) } 421145510Sdarrenr | YY_HEX { DOREM(fr->fr_tos = $1; fr->fr_mtos = 0xff;) } 422145510Sdarrenr | toslist lmore YY_NUMBER 423145510Sdarrenr { DOREM(fr->fr_tos = $3; fr->fr_mtos = 0xff;) } 424255332Scy | toslist lmore YY_HEX 425145510Sdarrenr { DOREM(fr->fr_tos = $3; fr->fr_mtos = 0xff;) } 426145510Sdarrenr ; 427145510Sdarrenr 428145510Sdarrenrttl: | setttl YY_NUMBER 429145510Sdarrenr { DOALL(fr->fr_ttl = $2; fr->fr_mttl = 0xff;) } 430145510Sdarrenr | setttl lstart ttllist lend 431145510Sdarrenr ; 432145510Sdarrenr 433255332Scylstart: '{' { newlist = 1; fr = frc; added = 0; } 434145510Sdarrenr ; 435145510Sdarrenr 436255332Scylend: '}' { nrules += added; } 437145510Sdarrenr ; 438145510Sdarrenr 439145510Sdarrenrlmore: lanother { if (newlist == 1) { 440145510Sdarrenr newlist = 0; 441145510Sdarrenr } 442145510Sdarrenr fr = addrule(); 443145510Sdarrenr if (yycont != NULL) 444145510Sdarrenr *yycont = 1; 445145510Sdarrenr } 446145510Sdarrenr ; 447145510Sdarrenr 448145510Sdarrenrlanother: 449145510Sdarrenr | ',' 450145510Sdarrenr ; 451145510Sdarrenr 452145510Sdarrenrsetttl: IPFY_TTL { setipftype(); } 453145510Sdarrenr ; 454145510Sdarrenr 455145510Sdarrenrttllist: 456145510Sdarrenr YY_NUMBER { DOREM(fr->fr_ttl = $1; fr->fr_mttl = 0xff;) } 457145510Sdarrenr | ttllist lmore YY_NUMBER 458145510Sdarrenr { DOREM(fr->fr_ttl = $3; fr->fr_mttl = 0xff;) } 459145510Sdarrenr ; 460145510Sdarrenr 461145510Sdarrenrproto: | protox protocol { yyresetdict(); } 462145510Sdarrenr ; 463145510Sdarrenr 464145510Sdarrenrprotox: IPFY_PROTO { setipftype(); 465145510Sdarrenr fr = frc; 466145510Sdarrenr yysetdict(NULL); } 467145510Sdarrenr ; 468145510Sdarrenr 469145510Sdarrenrip: srcdst flags icmp 470145510Sdarrenr ; 471145510Sdarrenr 472255332Scygroup: | IPFY_GROUP groupname { DOALL(setgroup(&fr, $2); \ 473255332Scy fillgroup(fr);); 474255332Scy free($2); 475255332Scy } 476145510Sdarrenr ; 477145510Sdarrenr 478255332Scyhead: | IPFY_HEAD groupname { DOALL(setgrhead(&fr, $2);); 479255332Scy free($2); 480255332Scy } 481145510Sdarrenr ; 482145510Sdarrenr 483255332Scygroupname: 484255332Scy YY_STR { $$ = $1; 485255332Scy if (strlen($$) >= FR_GROUPLEN) 486255332Scy $$[FR_GROUPLEN - 1] = '\0'; 487255332Scy } 488255332Scy | YY_NUMBER { $$ = malloc(16); 489255332Scy sprintf($$, "%d", $1); 490255332Scy } 491255332Scy ; 492255332Scy 493145510Sdarrenrsettagin: 494145510Sdarrenr | IPFY_SETTAG '(' taginlist ')' 495145510Sdarrenr ; 496145510Sdarrenr 497145510Sdarrenrtaginlist: 498145510Sdarrenr taginspec 499145510Sdarrenr | taginlist ',' taginspec 500145510Sdarrenr ; 501145510Sdarrenr 502145510Sdarrenrtaginspec: 503145510Sdarrenr logtag 504145510Sdarrenr ; 505145510Sdarrenr 506145510Sdarrenrnattag: IPFY_NAT '=' YY_STR { DOALL(strncpy(fr->fr_nattag.ipt_tag,\ 507145510Sdarrenr $3, IPFTAG_LEN);); 508145510Sdarrenr free($3); } 509145510Sdarrenr | IPFY_NAT '=' YY_NUMBER { DOALL(sprintf(fr->fr_nattag.ipt_tag,\ 510145510Sdarrenr "%d", $3 & 0xffffffff);) } 511145510Sdarrenr ; 512145510Sdarrenr 513145510Sdarrenrlogtag: IPFY_LOG '=' YY_NUMBER { DOALL(fr->fr_logtag = $3;) } 514145510Sdarrenr ; 515145510Sdarrenr 516145510Sdarrenrsettagout: 517145510Sdarrenr | IPFY_SETTAG '(' tagoutlist ')' 518145510Sdarrenr ; 519145510Sdarrenr 520145510Sdarrenrtagoutlist: 521145510Sdarrenr tagoutspec 522145510Sdarrenr | tagoutlist ',' tagoutspec 523145510Sdarrenr ; 524145510Sdarrenr 525145510Sdarrenrtagoutspec: 526145510Sdarrenr logtag 527145510Sdarrenr | nattag 528145510Sdarrenr ; 529145510Sdarrenr 530145510Sdarrenrmatchtagin: 531145510Sdarrenr | IPFY_MATCHTAG '(' tagoutlist ')' 532145510Sdarrenr ; 533145510Sdarrenr 534145510Sdarrenrmatchtagout: 535145510Sdarrenr | IPFY_MATCHTAG '(' taginlist ')' 536145510Sdarrenr ; 537145510Sdarrenr 538145510Sdarrenrpps: | IPFY_PPS YY_NUMBER { DOALL(fr->fr_pps = $2;) } 539145510Sdarrenr ; 540145510Sdarrenr 541145510Sdarrenrnew: | savegroup file restoregroup 542145510Sdarrenr ; 543145510Sdarrenr 544255332Scyrulettl: 545255332Scy | IPFY_RULETTL YY_NUMBER { DOALL(fr->fr_die = $2;) } 546255332Scy ; 547255332Scy 548255332Scycomment: 549255332Scy | IPFY_COMMENT YY_STR { DOALL(fr->fr_comment = addname(&fr, \ 550255332Scy $2);) } 551255332Scy ; 552255332Scy 553145510Sdarrenrsavegroup: 554145510Sdarrenr '{' 555145510Sdarrenr ; 556145510Sdarrenr 557145510Sdarrenrrestoregroup: 558145510Sdarrenr '}' 559145510Sdarrenr ; 560145510Sdarrenr 561145510Sdarrenrlogopt: log 562145510Sdarrenr ; 563145510Sdarrenr 564255332Scyquick: IPFY_QUICK { fr->fr_flags |= FR_QUICK; } 565145510Sdarrenr ; 566145510Sdarrenr 567255332Scyon: IPFY_ON onname { setifname(&fr, 0, $2.if1); 568255332Scy free($2.if1); 569255332Scy if ($2.if2 != NULL) { 570255332Scy setifname(&fr, 1, 571255332Scy $2.if2); 572255332Scy free($2.if2); 573255332Scy } 574255332Scy } 575161357Sguido | IPFY_ON lstart onlist lend 576255332Scy | IPFY_ON onname IPFY_INVIA vianame { setifname(&fr, 0, $2.if1); 577255332Scy free($2.if1); 578255332Scy if ($2.if2 != NULL) { 579255332Scy setifname(&fr, 1, 580255332Scy $2.if2); 581255332Scy free($2.if2); 582255332Scy } 583255332Scy } 584255332Scy | IPFY_ON onname IPFY_OUTVIA vianame { setifname(&fr, 0, $2.if1); 585255332Scy free($2.if1); 586255332Scy if ($2.if2 != NULL) { 587255332Scy setifname(&fr, 1, 588255332Scy $2.if2); 589255332Scy free($2.if2); 590255332Scy } 591255332Scy } 592145510Sdarrenr ; 593145510Sdarrenr 594255332Scyonlist: onname { DOREM(setifname(&fr, 0, $1.if1); \ 595255332Scy if ($1.if2 != NULL) \ 596255332Scy setifname(&fr, 1, $1.if2); \ 597255332Scy ) 598255332Scy free($1.if1); 599255332Scy if ($1.if2 != NULL) 600255332Scy free($1.if2); 601255332Scy } 602255332Scy | onlist lmore onname { DOREM(setifname(&fr, 0, $3.if1); \ 603255332Scy if ($3.if2 != NULL) \ 604255332Scy setifname(&fr, 1, $3.if2); \ 605255332Scy ) 606255332Scy free($3.if1); 607255332Scy if ($3.if2 != NULL) 608255332Scy free($3.if2); 609255332Scy } 610161357Sguido ; 611161357Sguido 612255332Scyonname: interfacename { $$.if1 = $1; 613255332Scy $$.if2 = NULL; 614255332Scy } 615145510Sdarrenr | interfacename ',' interfacename 616255332Scy { $$.if1 = $1; 617255332Scy $$.if2 = $3; 618255332Scy } 619145510Sdarrenr ; 620145510Sdarrenr 621145510Sdarrenrvianame: 622255332Scy name { setifname(&fr, 2, $1); 623255332Scy free($1); 624255332Scy } 625255332Scy | name ',' name { setifname(&fr, 2, $1); 626255332Scy free($1); 627255332Scy setifname(&fr, 3, $3); 628255332Scy free($3); 629255332Scy } 630145510Sdarrenr ; 631145510Sdarrenr 632145510Sdarrenrdup: IPFY_DUPTO name 633255332Scy { int idx = addname(&fr, $2); 634255332Scy fr->fr_dif.fd_name = idx; 635145510Sdarrenr free($2); 636145510Sdarrenr } 637255332Scy | IPFY_DUPTO IPFY_DSTLIST '/' name 638255332Scy { int idx = addname(&fr, $4); 639255332Scy fr->fr_dif.fd_name = idx; 640255332Scy fr->fr_dif.fd_type = FRD_DSTLIST; 641255332Scy free($4); 642255332Scy } 643145510Sdarrenr | IPFY_DUPTO name duptoseparator hostname 644255332Scy { int idx = addname(&fr, $2); 645255332Scy fr->fr_dif.fd_name = idx; 646255332Scy fr->fr_dif.fd_ptr = (void *)-1; 647255332Scy fr->fr_dif.fd_ip6 = $4.adr; 648255332Scy if (fr->fr_family == AF_UNSPEC && $4.f != AF_UNSPEC) 649255332Scy fr->fr_family = $4.f; 650145510Sdarrenr yyexpectaddr = 0; 651145510Sdarrenr free($2); 652145510Sdarrenr } 653145510Sdarrenr ; 654145510Sdarrenr 655145510Sdarrenrduptoseparator: 656145510Sdarrenr ':' { yyexpectaddr = 1; yycont = &yyexpectaddr; resetaddr(); } 657145510Sdarrenr ; 658145510Sdarrenr 659145510Sdarrenrfroute: IPFY_FROUTE { fr->fr_flags |= FR_FASTROUTE; } 660145510Sdarrenr ; 661145510Sdarrenr 662145510Sdarrenrproute: routeto name 663255332Scy { int idx = addname(&fr, $2); 664255332Scy fr->fr_tif.fd_name = idx; 665145510Sdarrenr free($2); 666145510Sdarrenr } 667255332Scy | routeto IPFY_DSTLIST '/' name 668255332Scy { int idx = addname(&fr, $4); 669255332Scy fr->fr_tif.fd_name = idx; 670255332Scy fr->fr_tif.fd_type = FRD_DSTLIST; 671255332Scy free($4); 672255332Scy } 673145510Sdarrenr | routeto name duptoseparator hostname 674255332Scy { int idx = addname(&fr, $2); 675255332Scy fr->fr_tif.fd_name = idx; 676255332Scy fr->fr_tif.fd_ptr = (void *)-1; 677255332Scy fr->fr_tif.fd_ip6 = $4.adr; 678255332Scy if (fr->fr_family == AF_UNSPEC && $4.f != AF_UNSPEC) 679255332Scy fr->fr_family = $4.f; 680145510Sdarrenr yyexpectaddr = 0; 681145510Sdarrenr free($2); 682145510Sdarrenr } 683145510Sdarrenr ; 684145510Sdarrenr 685145510Sdarrenrrouteto: 686145510Sdarrenr IPFY_TO 687145510Sdarrenr | IPFY_ROUTETO 688145510Sdarrenr ; 689145510Sdarrenr 690145510Sdarrenrreplyto: 691145510Sdarrenr IPFY_REPLY_TO name 692255332Scy { int idx = addname(&fr, $2); 693255332Scy fr->fr_rif.fd_name = idx; 694145510Sdarrenr free($2); 695145510Sdarrenr } 696255332Scy | IPFY_REPLY_TO IPFY_DSTLIST '/' name 697255332Scy { fr->fr_rif.fd_name = addname(&fr, $4); 698255332Scy fr->fr_rif.fd_type = FRD_DSTLIST; 699255332Scy free($4); 700255332Scy } 701145510Sdarrenr | IPFY_REPLY_TO name duptoseparator hostname 702255332Scy { int idx = addname(&fr, $2); 703255332Scy fr->fr_rif.fd_name = idx; 704255332Scy fr->fr_rif.fd_ptr = (void *)-1; 705255332Scy fr->fr_rif.fd_ip6 = $4.adr; 706255332Scy if (fr->fr_family == AF_UNSPEC && $4.f != AF_UNSPEC) 707255332Scy fr->fr_family = $4.f; 708145510Sdarrenr free($2); 709145510Sdarrenr } 710145510Sdarrenr ; 711145510Sdarrenr 712145510Sdarrenrlogoptions: 713145510Sdarrenr logoption 714145510Sdarrenr | logoptions logoption 715145510Sdarrenr ; 716145510Sdarrenr 717145510Sdarrenrlogoption: 718145510Sdarrenr IPFY_BODY { fr->fr_flags |= FR_LOGBODY; } 719145510Sdarrenr | IPFY_FIRST { fr->fr_flags |= FR_LOGFIRST; } 720145510Sdarrenr | IPFY_ORBLOCK { fr->fr_flags |= FR_LOGORBLOCK; } 721145510Sdarrenr | level loglevel { unsetsyslog(); } 722145510Sdarrenr ; 723145510Sdarrenr 724145510Sdarrenrreturncode: 725145510Sdarrenr starticmpcode icmpcode ')' { fr->fr_icode = $2; yyresetdict(); } 726145510Sdarrenr ; 727145510Sdarrenr 728145510Sdarrenrstarticmpcode: 729145510Sdarrenr '(' { yysetdict(icmpcodewords); } 730145510Sdarrenr ; 731145510Sdarrenr 732145510Sdarrenrsrcdst: | IPFY_ALL 733145510Sdarrenr | fromto 734145510Sdarrenr ; 735145510Sdarrenr 736145510Sdarrenrprotocol: 737255332Scy YY_NUMBER { DOALL(fr->fr_proto = $1; \ 738255332Scy fr->fr_mproto = 0xff;) 739255332Scy } 740145510Sdarrenr | YY_STR { if (!strcmp($1, "tcp-udp")) { 741255332Scy DOALL(fr->fr_flx |= FI_TCPUDP; \ 742145510Sdarrenr fr->fr_mflx |= FI_TCPUDP;) 743145510Sdarrenr } else { 744145510Sdarrenr int p = getproto($1); 745145510Sdarrenr if (p == -1) 746145510Sdarrenr yyerror("protocol unknown"); 747255332Scy DOALL(fr->fr_proto = p; \ 748145510Sdarrenr fr->fr_mproto = 0xff;) 749145510Sdarrenr } 750145510Sdarrenr free($1); 751255332Scy } 752145510Sdarrenr | YY_STR nextstring YY_STR 753145510Sdarrenr { if (!strcmp($1, "tcp") && 754145510Sdarrenr !strcmp($3, "udp")) { 755145510Sdarrenr DOREM(fr->fr_flx |= FI_TCPUDP; \ 756145510Sdarrenr fr->fr_mflx |= FI_TCPUDP;) 757255332Scy } else { 758145510Sdarrenr YYERROR; 759255332Scy } 760145510Sdarrenr free($1); 761145510Sdarrenr free($3); 762145510Sdarrenr } 763145510Sdarrenr ; 764145510Sdarrenr 765145510Sdarrenrnextstring: 766145510Sdarrenr '/' { yysetdict(NULL); } 767145510Sdarrenr ; 768145510Sdarrenr 769145510Sdarrenrfromto: from srcobject to dstobject { yyexpectaddr = 0; yycont = NULL; } 770145510Sdarrenr | to dstobject { yyexpectaddr = 0; yycont = NULL; } 771145510Sdarrenr | from srcobject { yyexpectaddr = 0; yycont = NULL; } 772145510Sdarrenr ; 773145510Sdarrenr 774145510Sdarrenrfrom: IPFY_FROM { setipftype(); 775145510Sdarrenr if (fr == NULL) 776145510Sdarrenr fr = frc; 777145510Sdarrenr yyexpectaddr = 1; 778145510Sdarrenr if (yydebug) 779145510Sdarrenr printf("set yyexpectaddr\n"); 780145510Sdarrenr yycont = &yyexpectaddr; 781145510Sdarrenr yysetdict(addrwords); 782145510Sdarrenr resetaddr(); } 783145510Sdarrenr ; 784145510Sdarrenr 785145510Sdarrenrto: IPFY_TO { if (fr == NULL) 786145510Sdarrenr fr = frc; 787145510Sdarrenr yyexpectaddr = 1; 788145510Sdarrenr if (yydebug) 789145510Sdarrenr printf("set yyexpectaddr\n"); 790145510Sdarrenr yycont = &yyexpectaddr; 791145510Sdarrenr yysetdict(addrwords); 792255332Scy resetaddr(); 793255332Scy } 794145510Sdarrenr ; 795145510Sdarrenr 796145510Sdarrenrwith: | andwith withlist 797145510Sdarrenr ; 798145510Sdarrenr 799145510Sdarrenrandwith: 800145510Sdarrenr IPFY_WITH { nowith = 0; setipftype(); } 801145510Sdarrenr | IPFY_AND { nowith = 0; setipftype(); } 802145510Sdarrenr ; 803145510Sdarrenr 804255332Scyflags: | startflags flagset 805145510Sdarrenr { DOALL(fr->fr_tcpf = $2; fr->fr_tcpfm = FR_TCPFMAX;) } 806145510Sdarrenr | startflags flagset '/' flagset 807145510Sdarrenr { DOALL(fr->fr_tcpf = $2; fr->fr_tcpfm = $4;) } 808145510Sdarrenr | startflags '/' flagset 809145510Sdarrenr { DOALL(fr->fr_tcpf = 0; fr->fr_tcpfm = $3;) } 810145510Sdarrenr | startflags YY_NUMBER 811145510Sdarrenr { DOALL(fr->fr_tcpf = $2; fr->fr_tcpfm = FR_TCPFMAX;) } 812145510Sdarrenr | startflags '/' YY_NUMBER 813145510Sdarrenr { DOALL(fr->fr_tcpf = 0; fr->fr_tcpfm = $3;) } 814145510Sdarrenr | startflags YY_NUMBER '/' YY_NUMBER 815145510Sdarrenr { DOALL(fr->fr_tcpf = $2; fr->fr_tcpfm = $4;) } 816145510Sdarrenr | startflags flagset '/' YY_NUMBER 817145510Sdarrenr { DOALL(fr->fr_tcpf = $2; fr->fr_tcpfm = $4;) } 818145510Sdarrenr | startflags YY_NUMBER '/' flagset 819145510Sdarrenr { DOALL(fr->fr_tcpf = $2; fr->fr_tcpfm = $4;) } 820145510Sdarrenr ; 821145510Sdarrenr 822145510Sdarrenrstartflags: 823145510Sdarrenr IPFY_FLAGS { if (frc->fr_type != FR_T_IPF) 824145510Sdarrenr yyerror("flags with non-ipf type rule"); 825145510Sdarrenr if (frc->fr_proto != IPPROTO_TCP) 826145510Sdarrenr yyerror("flags with non-TCP rule"); 827145510Sdarrenr } 828145510Sdarrenr ; 829145510Sdarrenr 830145510Sdarrenrflagset: 831145510Sdarrenr YY_STR { $$ = tcpflags($1); free($1); } 832145510Sdarrenr | YY_HEX { $$ = $1; } 833145510Sdarrenr ; 834145510Sdarrenr 835145510Sdarrenrsrcobject: 836145510Sdarrenr { yyresetdict(); } fromport 837145510Sdarrenr | srcaddr srcport 838145510Sdarrenr | '!' srcaddr srcport 839145510Sdarrenr { DOALL(fr->fr_flags |= FR_NOTSRCIP;) } 840145510Sdarrenr ; 841145510Sdarrenr 842145510Sdarrenrsrcaddr: 843255332Scy addr { build_srcaddr_af(fr, &$1); } 844145510Sdarrenr | lstart srcaddrlist lend 845145510Sdarrenr ; 846145510Sdarrenr 847145510Sdarrenrsrcaddrlist: 848255332Scy addr { build_srcaddr_af(fr, &$1); } 849145510Sdarrenr | srcaddrlist lmore addr 850255332Scy { build_srcaddr_af(fr, &$3); } 851145510Sdarrenr ; 852145510Sdarrenr 853145510Sdarrenrsrcport: 854145510Sdarrenr | portcomp 855145510Sdarrenr { DOALL(fr->fr_scmp = $1.pc; fr->fr_sport = $1.p1;) } 856145510Sdarrenr | portrange 857145510Sdarrenr { DOALL(fr->fr_scmp = $1.pc; fr->fr_sport = $1.p1; \ 858145510Sdarrenr fr->fr_stop = $1.p2;) } 859145510Sdarrenr | porteq lstart srcportlist lend 860145510Sdarrenr { yyresetdict(); } 861145510Sdarrenr ; 862145510Sdarrenr 863145510Sdarrenrfromport: 864145510Sdarrenr portcomp 865145510Sdarrenr { DOALL(fr->fr_scmp = $1.pc; fr->fr_sport = $1.p1;) } 866145510Sdarrenr | portrange 867145510Sdarrenr { DOALL(fr->fr_scmp = $1.pc; fr->fr_sport = $1.p1; \ 868145510Sdarrenr fr->fr_stop = $1.p2;) } 869145510Sdarrenr | porteq lstart srcportlist lend 870145510Sdarrenr { yyresetdict(); } 871145510Sdarrenr ; 872145510Sdarrenr 873145510Sdarrenrsrcportlist: 874145510Sdarrenr portnum { DOREM(fr->fr_scmp = FR_EQUAL; fr->fr_sport = $1;) } 875255332Scy | portnum ':' portnum 876172776Sdarrenr { DOREM(fr->fr_scmp = FR_INCRANGE; fr->fr_sport = $1; \ 877172776Sdarrenr fr->fr_stop = $3;) } 878255332Scy | portnum YY_RANGE_IN portnum 879172776Sdarrenr { DOREM(fr->fr_scmp = FR_INRANGE; fr->fr_sport = $1; \ 880172776Sdarrenr fr->fr_stop = $3;) } 881145510Sdarrenr | srcportlist lmore portnum 882145510Sdarrenr { DOREM(fr->fr_scmp = FR_EQUAL; fr->fr_sport = $3;) } 883172776Sdarrenr | srcportlist lmore portnum ':' portnum 884172776Sdarrenr { DOREM(fr->fr_scmp = FR_INCRANGE; fr->fr_sport = $3; \ 885172776Sdarrenr fr->fr_stop = $5;) } 886172776Sdarrenr | srcportlist lmore portnum YY_RANGE_IN portnum 887172776Sdarrenr { DOREM(fr->fr_scmp = FR_INRANGE; fr->fr_sport = $3; \ 888172776Sdarrenr fr->fr_stop = $5;) } 889145510Sdarrenr ; 890145510Sdarrenr 891145510Sdarrenrdstobject: 892145510Sdarrenr { yyresetdict(); } toport 893145510Sdarrenr | dstaddr dstport 894145510Sdarrenr | '!' dstaddr dstport 895145510Sdarrenr { DOALL(fr->fr_flags |= FR_NOTDSTIP;) } 896145510Sdarrenr ; 897145510Sdarrenr 898145510Sdarrenrdstaddr: 899255332Scy addr { if (($1.f != AF_UNSPEC) && (frc->fr_family != AF_UNSPEC) && 900255332Scy ($1.f != frc->fr_family)) 901255332Scy yyerror("1.src/dst address family mismatch"); 902255332Scy build_dstaddr_af(fr, &$1); 903145510Sdarrenr } 904145510Sdarrenr | lstart dstaddrlist lend 905145510Sdarrenr ; 906145510Sdarrenr 907145510Sdarrenrdstaddrlist: 908255332Scy addr { if (($1.f != AF_UNSPEC) && (frc->fr_family != AF_UNSPEC) && 909255332Scy ($1.f != frc->fr_family)) 910255332Scy yyerror("2.src/dst address family mismatch"); 911255332Scy build_dstaddr_af(fr, &$1); 912145510Sdarrenr } 913145510Sdarrenr | dstaddrlist lmore addr 914255332Scy { if (($3.f != AF_UNSPEC) && (frc->fr_family != AF_UNSPEC) && 915255332Scy ($3.f != frc->fr_family)) 916255332Scy yyerror("3.src/dst address family mismatch"); 917255332Scy build_dstaddr_af(fr, &$3); 918145510Sdarrenr } 919145510Sdarrenr ; 920145510Sdarrenr 921145510Sdarrenr 922145510Sdarrenrdstport: 923145510Sdarrenr | portcomp 924145510Sdarrenr { DOALL(fr->fr_dcmp = $1.pc; fr->fr_dport = $1.p1;) } 925145510Sdarrenr | portrange 926145510Sdarrenr { DOALL(fr->fr_dcmp = $1.pc; fr->fr_dport = $1.p1; \ 927145510Sdarrenr fr->fr_dtop = $1.p2;) } 928145510Sdarrenr | porteq lstart dstportlist lend 929145510Sdarrenr { yyresetdict(); } 930145510Sdarrenr ; 931145510Sdarrenr 932145510Sdarrenrtoport: 933145510Sdarrenr portcomp 934145510Sdarrenr { DOALL(fr->fr_dcmp = $1.pc; fr->fr_dport = $1.p1;) } 935145510Sdarrenr | portrange 936145510Sdarrenr { DOALL(fr->fr_dcmp = $1.pc; fr->fr_dport = $1.p1; \ 937145510Sdarrenr fr->fr_dtop = $1.p2;) } 938145510Sdarrenr | porteq lstart dstportlist lend 939145510Sdarrenr { yyresetdict(); } 940145510Sdarrenr ; 941145510Sdarrenr 942145510Sdarrenrdstportlist: 943145510Sdarrenr portnum { DOREM(fr->fr_dcmp = FR_EQUAL; fr->fr_dport = $1;) } 944255332Scy | portnum ':' portnum 945172776Sdarrenr { DOREM(fr->fr_dcmp = FR_INCRANGE; fr->fr_dport = $1; \ 946172776Sdarrenr fr->fr_dtop = $3;) } 947255332Scy | portnum YY_RANGE_IN portnum 948172776Sdarrenr { DOREM(fr->fr_dcmp = FR_INRANGE; fr->fr_dport = $1; \ 949172776Sdarrenr fr->fr_dtop = $3;) } 950145510Sdarrenr | dstportlist lmore portnum 951145510Sdarrenr { DOREM(fr->fr_dcmp = FR_EQUAL; fr->fr_dport = $3;) } 952172776Sdarrenr | dstportlist lmore portnum ':' portnum 953172776Sdarrenr { DOREM(fr->fr_dcmp = FR_INCRANGE; fr->fr_dport = $3; \ 954172776Sdarrenr fr->fr_dtop = $5;) } 955172776Sdarrenr | dstportlist lmore portnum YY_RANGE_IN portnum 956172776Sdarrenr { DOREM(fr->fr_dcmp = FR_INRANGE; fr->fr_dport = $3; \ 957172776Sdarrenr fr->fr_dtop = $5;) } 958145510Sdarrenr ; 959145510Sdarrenr 960145510Sdarrenraddr: pool '/' YY_NUMBER { pooled = 1; 961255332Scy yyexpectaddr = 0; 962255332Scy $$.type = FRI_LOOKUP; 963255332Scy $$.v = 0; 964255332Scy $$.ifpos = -1; 965255332Scy $$.f = AF_UNSPEC; 966145510Sdarrenr $$.a.iplookuptype = IPLT_POOL; 967170268Sdarrenr $$.a.iplookupsubtype = 0; 968145510Sdarrenr $$.a.iplookupnum = $3; } 969170268Sdarrenr | pool '/' YY_STR { pooled = 1; 970255332Scy $$.ifpos = -1; 971255332Scy $$.f = AF_UNSPEC; 972255332Scy $$.type = FRI_LOOKUP; 973170268Sdarrenr $$.a.iplookuptype = IPLT_POOL; 974170268Sdarrenr $$.a.iplookupsubtype = 1; 975255332Scy $$.a.iplookupname = addname(&fr, $3); 976170268Sdarrenr } 977255332Scy | pool '=' '(' { yyexpectaddr = 1; 978255332Scy pooled = 1; 979255332Scy } 980255332Scy poollist ')' { yyexpectaddr = 0; 981255332Scy $$.v = 0; 982255332Scy $$.ifpos = -1; 983255332Scy $$.f = AF_UNSPEC; 984255332Scy $$.type = FRI_LOOKUP; 985145510Sdarrenr $$.a.iplookuptype = IPLT_POOL; 986170268Sdarrenr $$.a.iplookupsubtype = 0; 987255332Scy $$.a.iplookupnum = makepool($5); 988255332Scy } 989145510Sdarrenr | hash '/' YY_NUMBER { hashed = 1; 990255332Scy yyexpectaddr = 0; 991255332Scy $$.v = 0; 992255332Scy $$.ifpos = -1; 993255332Scy $$.f = AF_UNSPEC; 994255332Scy $$.type = FRI_LOOKUP; 995145510Sdarrenr $$.a.iplookuptype = IPLT_HASH; 996170268Sdarrenr $$.a.iplookupsubtype = 0; 997255332Scy $$.a.iplookupnum = $3; 998255332Scy } 999255332Scy | hash '/' YY_STR { hashed = 1; 1000255332Scy $$.type = FRI_LOOKUP; 1001255332Scy $$.v = 0; 1002255332Scy $$.ifpos = -1; 1003255332Scy $$.f = AF_UNSPEC; 1004170268Sdarrenr $$.a.iplookuptype = IPLT_HASH; 1005170268Sdarrenr $$.a.iplookupsubtype = 1; 1006255332Scy $$.a.iplookupname = addname(&fr, $3); 1007170268Sdarrenr } 1008255332Scy | hash '=' '(' { hashed = 1; 1009255332Scy yyexpectaddr = 1; 1010255332Scy } 1011255332Scy addrlist ')' { yyexpectaddr = 0; 1012255332Scy $$.v = 0; 1013255332Scy $$.ifpos = -1; 1014255332Scy $$.f = AF_UNSPEC; 1015255332Scy $$.type = FRI_LOOKUP; 1016145510Sdarrenr $$.a.iplookuptype = IPLT_HASH; 1017170268Sdarrenr $$.a.iplookupsubtype = 0; 1018255332Scy $$.a.iplookupnum = makehash($5); 1019255332Scy } 1020255332Scy | ipaddr { $$ = $1; 1021145510Sdarrenr yyexpectaddr = 0; } 1022145510Sdarrenr ; 1023145510Sdarrenr 1024272988Scyipaddr: IPFY_ANY { memset(&($$), 0, sizeof($$)); 1025255332Scy $$.type = FRI_NORMAL; 1026255332Scy $$.ifpos = -1; 1027255332Scy yyexpectaddr = 0; 1028255332Scy } 1029272988Scy | hostname { memset(&($$), 0, sizeof($$)); 1030272988Scy $$.a = $1.adr; 1031255332Scy $$.f = $1.f; 1032255332Scy if ($1.f == AF_INET6) 1033255332Scy fill6bits(128, $$.m.i6); 1034255332Scy else if ($1.f == AF_INET) 1035255332Scy fill6bits(32, $$.m.i6); 1036255332Scy $$.v = ftov($1.f); 1037255332Scy $$.ifpos = dynamic; 1038255332Scy $$.type = FRI_NORMAL; 1039255332Scy } 1040255332Scy | hostname { yyresetdict(); } 1041255332Scy maskspace { yysetdict(maskwords); 1042255332Scy yyexpectaddr = 2; } 1043272988Scy ipmask { memset(&($$), 0, sizeof($$)); 1044272988Scy ntomask($1.f, $5, $$.m.i6); 1045255332Scy $$.a = $1.adr; 1046255332Scy $$.a.i6[0] &= $$.m.i6[0]; 1047255332Scy $$.a.i6[1] &= $$.m.i6[1]; 1048255332Scy $$.a.i6[2] &= $$.m.i6[2]; 1049255332Scy $$.a.i6[3] &= $$.m.i6[3]; 1050255332Scy $$.f = $1.f; 1051255332Scy $$.v = ftov($1.f); 1052255332Scy $$.type = ifpflag; 1053255332Scy $$.ifpos = dynamic; 1054255332Scy if (ifpflag != 0 && $$.v == 0) { 1055255332Scy if (frc->fr_family == AF_INET6){ 1056255332Scy $$.v = 6; 1057255332Scy $$.f = AF_INET6; 1058255332Scy } else { 1059255332Scy $$.v = 4; 1060255332Scy $$.f = AF_INET; 1061255332Scy } 1062255332Scy } 1063145510Sdarrenr yyresetdict(); 1064255332Scy yyexpectaddr = 0; 1065255332Scy } 1066272988Scy | '(' YY_STR ')' { memset(&($$), 0, sizeof($$)); 1067272988Scy $$.type = FRI_DYNAMIC; 1068255332Scy ifpflag = FRI_DYNAMIC; 1069255332Scy $$.ifpos = addname(&fr, $2); 1070255332Scy $$.lif = 0; 1071255332Scy } 1072255332Scy | '(' YY_STR ')' '/' 1073255332Scy { ifpflag = FRI_DYNAMIC; yysetdict(maskwords); } 1074255332Scy maskopts 1075272988Scy { memset(&($$), 0, sizeof($$)); 1076272988Scy $$.type = ifpflag; 1077255332Scy $$.ifpos = addname(&fr, $2); 1078255332Scy $$.lif = 0; 1079255332Scy if (frc->fr_family == AF_UNSPEC) 1080255332Scy frc->fr_family = AF_INET; 1081255332Scy if (ifpflag == FRI_DYNAMIC) { 1082255332Scy ntomask(frc->fr_family, 1083255332Scy $6, $$.m.i6); 1084255332Scy } 1085145510Sdarrenr yyresetdict(); 1086255332Scy yyexpectaddr = 0; 1087255332Scy } 1088255332Scy | '(' YY_STR ':' YY_NUMBER ')' '/' 1089255332Scy { ifpflag = FRI_DYNAMIC; yysetdict(maskwords); } 1090255332Scy maskopts 1091272988Scy { memset(&($$), 0, sizeof($$)); 1092272988Scy $$.type = ifpflag; 1093255332Scy $$.ifpos = addname(&fr, $2); 1094255332Scy $$.lif = $4; 1095255332Scy if (frc->fr_family == AF_UNSPEC) 1096255332Scy frc->fr_family = AF_INET; 1097255332Scy if (ifpflag == FRI_DYNAMIC) { 1098255332Scy ntomask(frc->fr_family, 1099255332Scy $8, $$.m.i6); 1100255332Scy } 1101145510Sdarrenr yyresetdict(); 1102255332Scy yyexpectaddr = 0; 1103255332Scy } 1104145510Sdarrenr ; 1105255332Scy 1106145510Sdarrenrmaskspace: 1107145510Sdarrenr '/' 1108145510Sdarrenr | IPFY_MASK 1109145510Sdarrenr ; 1110145510Sdarrenr 1111255332Scyipmask: ipv4 { $$ = count4bits($1.s_addr); } 1112255332Scy | YY_HEX { $$ = count4bits(htonl($1)); } 1113255332Scy | YY_NUMBER { $$ = $1; } 1114255332Scy | YY_IPV6 { $$ = count6bits($1.i6); } 1115255332Scy | maskopts { $$ = $1; } 1116255332Scy ; 1117255332Scy 1118255332Scymaskopts: 1119255332Scy IPFY_BROADCAST { if (ifpflag == FRI_DYNAMIC) { 1120145510Sdarrenr ifpflag = FRI_BROADCAST; 1121255332Scy } else { 1122145510Sdarrenr YYERROR; 1123255332Scy } 1124255332Scy $$ = 0; 1125145510Sdarrenr } 1126145510Sdarrenr | IPFY_NETWORK { if (ifpflag == FRI_DYNAMIC) { 1127145510Sdarrenr ifpflag = FRI_NETWORK; 1128255332Scy } else { 1129145510Sdarrenr YYERROR; 1130255332Scy } 1131255332Scy $$ = 0; 1132145510Sdarrenr } 1133145510Sdarrenr | IPFY_NETMASKED { if (ifpflag == FRI_DYNAMIC) { 1134145510Sdarrenr ifpflag = FRI_NETMASKED; 1135255332Scy } else { 1136145510Sdarrenr YYERROR; 1137255332Scy } 1138255332Scy $$ = 0; 1139145510Sdarrenr } 1140145510Sdarrenr | IPFY_PEER { if (ifpflag == FRI_DYNAMIC) { 1141145510Sdarrenr ifpflag = FRI_PEERADDR; 1142255332Scy } else { 1143145510Sdarrenr YYERROR; 1144255332Scy } 1145255332Scy $$ = 0; 1146145510Sdarrenr } 1147255332Scy | YY_NUMBER { $$ = $1; } 1148145510Sdarrenr ; 1149145510Sdarrenr 1150255332Scyhostname: 1151272988Scy ipv4 { memset(&($$), 0, sizeof($$)); 1152272988Scy $$.adr.in4 = $1; 1153255332Scy if (frc->fr_family == AF_INET6) 1154145510Sdarrenr YYERROR; 1155255332Scy $$.f = AF_INET; 1156255332Scy yyexpectaddr = 2; 1157145510Sdarrenr } 1158272988Scy | YY_NUMBER { memset(&($$), 0, sizeof($$)); 1159272988Scy if (frc->fr_family == AF_INET6) 1160145510Sdarrenr YYERROR; 1161255332Scy $$.adr.in4_addr = $1; 1162255332Scy $$.f = AF_INET; 1163255332Scy yyexpectaddr = 2; 1164145510Sdarrenr } 1165272988Scy | YY_HEX { memset(&($$), 0, sizeof($$)); 1166272988Scy if (frc->fr_family == AF_INET6) 1167145510Sdarrenr YYERROR; 1168255332Scy $$.adr.in4_addr = $1; 1169255332Scy $$.f = AF_INET; 1170255332Scy yyexpectaddr = 2; 1171145510Sdarrenr } 1172272988Scy | YY_STR { memset(&($$), 0, sizeof($$)); 1173272988Scy if (lookuphost($1, &$$.adr) == 0) 1174255332Scy $$.f = AF_INET; 1175255332Scy free($1); 1176255332Scy yyexpectaddr = 2; 1177255332Scy } 1178272988Scy | YY_IPV6 { memset(&($$), 0, sizeof($$)); 1179272988Scy if (frc->fr_family == AF_INET) 1180145510Sdarrenr YYERROR; 1181255332Scy $$.adr = $1; 1182255332Scy $$.f = AF_INET6; 1183255332Scy yyexpectaddr = 2; 1184145510Sdarrenr } 1185145510Sdarrenr ; 1186145510Sdarrenr 1187145510Sdarrenraddrlist: 1188145510Sdarrenr ipaddr { $$ = newalist(NULL); 1189255332Scy $$->al_family = $1.f; 1190255332Scy $$->al_i6addr = $1.a; 1191255332Scy $$->al_i6mask = $1.m; 1192255332Scy } 1193255332Scy | ipaddr ',' { yyexpectaddr = 1; } addrlist 1194255332Scy { $$ = newalist($4); 1195255332Scy $$->al_family = $1.f; 1196255332Scy $$->al_i6addr = $1.a; 1197255332Scy $$->al_i6mask = $1.m; 1198255332Scy } 1199145510Sdarrenr ; 1200145510Sdarrenr 1201145510Sdarrenrpool: IPFY_POOL { yyexpectaddr = 0; yycont = NULL; yyresetdict(); } 1202145510Sdarrenr ; 1203145510Sdarrenr 1204145510Sdarrenrhash: IPFY_HASH { yyexpectaddr = 0; yycont = NULL; yyresetdict(); } 1205145510Sdarrenr ; 1206145510Sdarrenr 1207145510Sdarrenrpoollist: 1208145510Sdarrenr ipaddr { $$ = newalist(NULL); 1209255332Scy $$->al_family = $1.f; 1210255332Scy $$->al_i6addr = $1.a; 1211255332Scy $$->al_i6mask = $1.m; 1212255332Scy } 1213145510Sdarrenr | '!' ipaddr { $$ = newalist(NULL); 1214145510Sdarrenr $$->al_not = 1; 1215255332Scy $$->al_family = $2.f; 1216255332Scy $$->al_i6addr = $2.a; 1217255332Scy $$->al_i6mask = $2.m; 1218255332Scy } 1219145510Sdarrenr | poollist ',' ipaddr 1220145510Sdarrenr { $$ = newalist($1); 1221255332Scy $$->al_family = $3.f; 1222255332Scy $$->al_i6addr = $3.a; 1223255332Scy $$->al_i6mask = $3.m; 1224255332Scy } 1225145510Sdarrenr | poollist ',' '!' ipaddr 1226145510Sdarrenr { $$ = newalist($1); 1227145510Sdarrenr $$->al_not = 1; 1228255332Scy $$->al_family = $4.f; 1229255332Scy $$->al_i6addr = $4.a; 1230255332Scy $$->al_i6mask = $4.m; 1231255332Scy } 1232145510Sdarrenr ; 1233145510Sdarrenr 1234145510Sdarrenrport: IPFY_PORT { yyexpectaddr = 0; 1235145510Sdarrenr yycont = NULL; 1236255332Scy if (frc->fr_proto != 0 && 1237255332Scy frc->fr_proto != IPPROTO_UDP && 1238255332Scy frc->fr_proto != IPPROTO_TCP) 1239255332Scy yyerror("port use incorrect"); 1240145510Sdarrenr } 1241145510Sdarrenr ; 1242145510Sdarrenr 1243145510Sdarrenrportc: port compare { $$ = $2; 1244255332Scy yysetdict(NULL); 1245255332Scy } 1246145510Sdarrenr | porteq { $$ = $1; } 1247145510Sdarrenr ; 1248145510Sdarrenr 1249145510Sdarrenrporteq: port '=' { $$ = FR_EQUAL; 1250255332Scy yysetdict(NULL); 1251255332Scy } 1252145510Sdarrenr ; 1253145510Sdarrenr 1254145510Sdarrenrportr: IPFY_PORT { yyexpectaddr = 0; 1255145510Sdarrenr yycont = NULL; 1256255332Scy yysetdict(NULL); 1257255332Scy } 1258145510Sdarrenr ; 1259145510Sdarrenr 1260145510Sdarrenrportcomp: 1261145510Sdarrenr portc portnum { $$.pc = $1; 1262145510Sdarrenr $$.p1 = $2; 1263255332Scy yyresetdict(); 1264255332Scy } 1265145510Sdarrenr ; 1266145510Sdarrenr 1267145510Sdarrenrportrange: 1268145510Sdarrenr portr portnum range portnum { $$.p1 = $2; 1269145510Sdarrenr $$.pc = $3; 1270145510Sdarrenr $$.p2 = $4; 1271255332Scy yyresetdict(); 1272255332Scy } 1273145510Sdarrenr ; 1274145510Sdarrenr 1275145510Sdarrenricmp: | itype icode 1276145510Sdarrenr ; 1277145510Sdarrenr 1278145510Sdarrenritype: seticmptype icmptype 1279145510Sdarrenr { DOALL(fr->fr_icmp = htons($2 << 8); fr->fr_icmpm = htons(0xff00);); 1280145510Sdarrenr yyresetdict(); 1281145510Sdarrenr } 1282145510Sdarrenr | seticmptype lstart typelist lend { yyresetdict(); } 1283145510Sdarrenr ; 1284145510Sdarrenr 1285145510Sdarrenrseticmptype: 1286255332Scy IPFY_ICMPTYPE { if (frc->fr_family == AF_UNSPEC) 1287255332Scy frc->fr_family = AF_INET; 1288255332Scy if (frc->fr_family == AF_INET && 1289255332Scy frc->fr_type == FR_T_IPF && 1290255332Scy frc->fr_proto != IPPROTO_ICMP) { 1291255332Scy yyerror("proto not icmp"); 1292255332Scy } 1293255332Scy if (frc->fr_family == AF_INET6 && 1294255332Scy frc->fr_type == FR_T_IPF && 1295255332Scy frc->fr_proto != IPPROTO_ICMPV6) { 1296255332Scy yyerror("proto not ipv6-icmp"); 1297255332Scy } 1298255332Scy setipftype(); 1299255332Scy DOALL(if (fr->fr_family == AF_INET) { \ 1300255332Scy fr->fr_ip.fi_v = 4; \ 1301255332Scy fr->fr_mip.fi_v = 0xf; \ 1302255332Scy } 1303255332Scy if (fr->fr_family == AF_INET6) { \ 1304255332Scy fr->fr_ip.fi_v = 6; \ 1305255332Scy fr->fr_mip.fi_v = 0xf; \ 1306255332Scy } 1307255332Scy ) 1308255332Scy yysetdict(NULL); 1309255332Scy } 1310145510Sdarrenr ; 1311145510Sdarrenr 1312145510Sdarrenricode: | seticmpcode icmpcode 1313145510Sdarrenr { DOALL(fr->fr_icmp |= htons($2); fr->fr_icmpm |= htons(0xff);); 1314145510Sdarrenr yyresetdict(); 1315145510Sdarrenr } 1316145510Sdarrenr | seticmpcode lstart codelist lend { yyresetdict(); } 1317145510Sdarrenr ; 1318145510Sdarrenr 1319145510Sdarrenrseticmpcode: 1320145510Sdarrenr IPFY_ICMPCODE { yysetdict(icmpcodewords); } 1321145510Sdarrenr ; 1322145510Sdarrenr 1323145510Sdarrenrtypelist: 1324145510Sdarrenr icmptype 1325145510Sdarrenr { DOREM(fr->fr_icmp = htons($1 << 8); fr->fr_icmpm = htons(0xff00);) } 1326145510Sdarrenr | typelist lmore icmptype 1327145510Sdarrenr { DOREM(fr->fr_icmp = htons($3 << 8); fr->fr_icmpm = htons(0xff00);) } 1328145510Sdarrenr ; 1329145510Sdarrenr 1330145510Sdarrenrcodelist: 1331145510Sdarrenr icmpcode 1332145510Sdarrenr { DOREM(fr->fr_icmp |= htons($1); fr->fr_icmpm |= htons(0xff);) } 1333145510Sdarrenr | codelist lmore icmpcode 1334161357Sguido { DOREM(fr->fr_icmp &= htons(0xff00); fr->fr_icmp |= htons($3); \ 1335161357Sguido fr->fr_icmpm |= htons(0xff);) } 1336145510Sdarrenr ; 1337145510Sdarrenr 1338145510Sdarrenrage: | IPFY_AGE YY_NUMBER { DOALL(fr->fr_age[0] = $2; \ 1339145510Sdarrenr fr->fr_age[1] = $2;) } 1340145510Sdarrenr | IPFY_AGE YY_NUMBER '/' YY_NUMBER 1341145510Sdarrenr { DOALL(fr->fr_age[0] = $2; \ 1342145510Sdarrenr fr->fr_age[1] = $4;) } 1343145510Sdarrenr ; 1344145510Sdarrenr 1345145510Sdarrenrkeep: | IPFY_KEEP keepstate keep 1346145510Sdarrenr | IPFY_KEEP keepfrag keep 1347145510Sdarrenr ; 1348145510Sdarrenr 1349145510Sdarrenrkeepstate: 1350145510Sdarrenr IPFY_STATE stateoptlist { DOALL(fr->fr_flags |= FR_KEEPSTATE;)} 1351145510Sdarrenr ; 1352145510Sdarrenr 1353145510Sdarrenrkeepfrag: 1354145510Sdarrenr IPFY_FRAGS fragoptlist { DOALL(fr->fr_flags |= FR_KEEPFRAG;) } 1355145510Sdarrenr | IPFY_FRAG fragoptlist { DOALL(fr->fr_flags |= FR_KEEPFRAG;) } 1356145510Sdarrenr ; 1357145510Sdarrenr 1358145510Sdarrenrfragoptlist: 1359145510Sdarrenr | '(' fragopts ')' 1360145510Sdarrenr ; 1361145510Sdarrenr 1362145510Sdarrenrfragopts: 1363145510Sdarrenr fragopt lanother fragopts 1364145510Sdarrenr | fragopt 1365145510Sdarrenr ; 1366145510Sdarrenr 1367145510Sdarrenrfragopt: 1368145510Sdarrenr IPFY_STRICT { DOALL(fr->fr_flags |= FR_FRSTRICT;) } 1369145510Sdarrenr ; 1370145510Sdarrenr 1371145510Sdarrenrstateoptlist: 1372145510Sdarrenr | '(' stateopts ')' 1373145510Sdarrenr ; 1374145510Sdarrenr 1375145510Sdarrenrstateopts: 1376145510Sdarrenr stateopt lanother stateopts 1377145510Sdarrenr | stateopt 1378145510Sdarrenr ; 1379145510Sdarrenr 1380145510Sdarrenrstateopt: 1381145510Sdarrenr IPFY_LIMIT YY_NUMBER { DOALL(fr->fr_statemax = $2;) } 1382145510Sdarrenr | IPFY_STRICT { DOALL(if (fr->fr_proto != IPPROTO_TCP) { \ 1383145510Sdarrenr YYERROR; \ 1384255332Scy } else if (fr->fr_flags & FR_STLOOSE) {\ 1385255332Scy YYERROR; \ 1386255332Scy } else \ 1387145510Sdarrenr fr->fr_flags |= FR_STSTRICT;) 1388145510Sdarrenr } 1389255332Scy | IPFY_LOOSE { DOALL(if (fr->fr_proto != IPPROTO_TCP) { \ 1390255332Scy YYERROR; \ 1391255332Scy } else if (fr->fr_flags & FR_STSTRICT){\ 1392255332Scy YYERROR; \ 1393255332Scy } else \ 1394255332Scy fr->fr_flags |= FR_STLOOSE;) 1395255332Scy } 1396145510Sdarrenr | IPFY_NEWISN { DOALL(if (fr->fr_proto != IPPROTO_TCP) { \ 1397145510Sdarrenr YYERROR; \ 1398145510Sdarrenr } else \ 1399145510Sdarrenr fr->fr_flags |= FR_NEWISN;) 1400145510Sdarrenr } 1401145510Sdarrenr | IPFY_NOICMPERR { DOALL(fr->fr_flags |= FR_NOICMPERR;) } 1402145510Sdarrenr 1403145510Sdarrenr | IPFY_SYNC { DOALL(fr->fr_flags |= FR_STATESYNC;) } 1404161357Sguido | IPFY_AGE YY_NUMBER { DOALL(fr->fr_age[0] = $2; \ 1405161357Sguido fr->fr_age[1] = $2;) } 1406161357Sguido | IPFY_AGE YY_NUMBER '/' YY_NUMBER 1407161357Sguido { DOALL(fr->fr_age[0] = $2; \ 1408161357Sguido fr->fr_age[1] = $4;) } 1409255332Scy | IPFY_ICMPHEAD groupname 1410255332Scy { DOALL(seticmphead(&fr, $2);) 1411255332Scy free($2); 1412255332Scy } 1413255332Scy | IPFY_NOLOG 1414255332Scy { DOALL(fr->fr_nostatelog = 1;) } 1415255332Scy | IPFY_RPC 1416255332Scy { DOALL(fr->fr_rpc = 1;) } 1417255332Scy | IPFY_RPC IPFY_IN YY_STR 1418255332Scy { DOALL(fr->fr_rpc = 1;) } 1419255332Scy | IPFY_MAX_SRCS YY_NUMBER 1420255332Scy { DOALL(fr->fr_srctrack.ht_max_nodes = $2;) } 1421255332Scy | IPFY_MAX_PER_SRC YY_NUMBER 1422255332Scy { DOALL(fr->fr_srctrack.ht_max_per_node = $2; \ 1423255332Scy fr->fr_srctrack.ht_netmask = \ 1424255332Scy fr->fr_family == AF_INET ? 32: 128;) 1425255332Scy } 1426255332Scy | IPFY_MAX_PER_SRC YY_NUMBER '/' YY_NUMBER 1427255332Scy { DOALL(fr->fr_srctrack.ht_max_per_node = $2; \ 1428255332Scy fr->fr_srctrack.ht_netmask = $4;) 1429255332Scy } 1430145510Sdarrenr ; 1431145510Sdarrenr 1432145510Sdarrenrportnum: 1433255332Scy servicename { if (getport(frc, $1, 1434255332Scy &($$), NULL) == -1) 1435145510Sdarrenr yyerror("service unknown"); 1436145510Sdarrenr $$ = ntohs($$); 1437145510Sdarrenr free($1); 1438145510Sdarrenr } 1439145510Sdarrenr | YY_NUMBER { if ($1 > 65535) /* Unsigned */ 1440145510Sdarrenr yyerror("invalid port number"); 1441145510Sdarrenr else 1442145510Sdarrenr $$ = $1; 1443145510Sdarrenr } 1444145510Sdarrenr ; 1445145510Sdarrenr 1446145510Sdarrenrwithlist: 1447153881Sguido withopt { nowith = 0; } 1448153881Sguido | withlist withopt { nowith = 0; } 1449153881Sguido | withlist ',' withopt { nowith = 0; } 1450145510Sdarrenr ; 1451145510Sdarrenr 1452145510Sdarrenrwithopt: 1453145510Sdarrenr opttype { DOALL(fr->fr_flx |= $1; fr->fr_mflx |= $1;) } 1454153881Sguido | notwith opttype { DOALL(fr->fr_mflx |= $2;) } 1455145510Sdarrenr | ipopt ipopts { yyresetdict(); } 1456145510Sdarrenr | notwith ipopt ipopts { yyresetdict(); } 1457255332Scy | startv6hdr ipv6hdrs { yyresetdict(); } 1458145510Sdarrenr ; 1459145510Sdarrenr 1460145510Sdarrenripopt: IPFY_OPT { yysetdict(ipv4optwords); } 1461145510Sdarrenr ; 1462145510Sdarrenr 1463255332Scystartv6hdr: 1464255332Scy IPFY_V6HDR { if (frc->fr_family != AF_INET6) 1465145510Sdarrenr yyerror("only available with IPv6"); 1466145510Sdarrenr yysetdict(ipv6optwords); 1467145510Sdarrenr } 1468145510Sdarrenr ; 1469145510Sdarrenr 1470145510Sdarrenrnotwith: 1471145510Sdarrenr IPFY_NOT { nowith = 1; } 1472145510Sdarrenr | IPFY_NO { nowith = 1; } 1473145510Sdarrenr ; 1474145510Sdarrenr 1475145510Sdarrenropttype: 1476145510Sdarrenr IPFY_IPOPTS { $$ = FI_OPTIONS; } 1477145510Sdarrenr | IPFY_SHORT { $$ = FI_SHORT; } 1478145510Sdarrenr | IPFY_NAT { $$ = FI_NATED; } 1479145510Sdarrenr | IPFY_BAD { $$ = FI_BAD; } 1480145510Sdarrenr | IPFY_BADNAT { $$ = FI_BADNAT; } 1481145510Sdarrenr | IPFY_BADSRC { $$ = FI_BADSRC; } 1482145510Sdarrenr | IPFY_LOWTTL { $$ = FI_LOWTTL; } 1483145510Sdarrenr | IPFY_FRAG { $$ = FI_FRAG; } 1484145510Sdarrenr | IPFY_FRAGBODY { $$ = FI_FRAGBODY; } 1485145510Sdarrenr | IPFY_FRAGS { $$ = FI_FRAG; } 1486145510Sdarrenr | IPFY_MBCAST { $$ = FI_MBCAST; } 1487145510Sdarrenr | IPFY_MULTICAST { $$ = FI_MULTICAST; } 1488145510Sdarrenr | IPFY_BROADCAST { $$ = FI_BROADCAST; } 1489145510Sdarrenr | IPFY_STATE { $$ = FI_STATE; } 1490145510Sdarrenr | IPFY_OOW { $$ = FI_OOW; } 1491255332Scy | IPFY_AH { $$ = FI_AH; } 1492255332Scy | IPFY_V6HDRS { $$ = FI_V6EXTHDR; } 1493145510Sdarrenr ; 1494145510Sdarrenr 1495145510Sdarrenripopts: optlist { DOALL(fr->fr_mip.fi_optmsk |= $1; 1496255332Scy if (fr->fr_family == AF_UNSPEC) { 1497255332Scy fr->fr_family = AF_INET; 1498255332Scy fr->fr_ip.fi_v = 4; 1499255332Scy fr->fr_mip.fi_v = 0xf; 1500255332Scy } else if (fr->fr_family != AF_INET) { 1501255332Scy YYERROR; 1502255332Scy } 1503145510Sdarrenr if (!nowith) 1504145510Sdarrenr fr->fr_ip.fi_optmsk |= $1;) 1505145510Sdarrenr } 1506145510Sdarrenr ; 1507145510Sdarrenr 1508145510Sdarrenroptlist: 1509145510Sdarrenr opt { $$ |= $1; } 1510145510Sdarrenr | optlist ',' opt { $$ |= $1 | $3; } 1511145510Sdarrenr ; 1512145510Sdarrenr 1513145510Sdarrenripv6hdrs: 1514145510Sdarrenr ipv6hdrlist { DOALL(fr->fr_mip.fi_optmsk |= $1; 1515145510Sdarrenr if (!nowith) 1516145510Sdarrenr fr->fr_ip.fi_optmsk |= $1;) 1517145510Sdarrenr } 1518145510Sdarrenr ; 1519145510Sdarrenr 1520145510Sdarrenripv6hdrlist: 1521145510Sdarrenr ipv6hdr { $$ |= $1; } 1522145510Sdarrenr | ipv6hdrlist ',' ipv6hdr { $$ |= $1 | $3; } 1523145510Sdarrenr ; 1524145510Sdarrenr 1525145510Sdarrenrsecname: 1526145510Sdarrenr seclevel { $$ |= $1; } 1527145510Sdarrenr | secname ',' seclevel { $$ |= $1 | $3; } 1528145510Sdarrenr ; 1529145510Sdarrenr 1530145510Sdarrenrseclevel: 1531145510Sdarrenr IPFY_SEC_UNC { $$ = secbit(IPSO_CLASS_UNCL); } 1532145510Sdarrenr | IPFY_SEC_CONF { $$ = secbit(IPSO_CLASS_CONF); } 1533145510Sdarrenr | IPFY_SEC_RSV1 { $$ = secbit(IPSO_CLASS_RES1); } 1534145510Sdarrenr | IPFY_SEC_RSV2 { $$ = secbit(IPSO_CLASS_RES2); } 1535145510Sdarrenr | IPFY_SEC_RSV3 { $$ = secbit(IPSO_CLASS_RES3); } 1536145510Sdarrenr | IPFY_SEC_RSV4 { $$ = secbit(IPSO_CLASS_RES4); } 1537145510Sdarrenr | IPFY_SEC_SEC { $$ = secbit(IPSO_CLASS_SECR); } 1538145510Sdarrenr | IPFY_SEC_TS { $$ = secbit(IPSO_CLASS_TOPS); } 1539145510Sdarrenr ; 1540145510Sdarrenr 1541145510Sdarrenricmptype: 1542255332Scy YY_NUMBER { $$ = $1; } 1543255332Scy | YY_STR { $$ = geticmptype(frc->fr_family, $1); 1544255332Scy if ($$ == -1) 1545255332Scy yyerror("unrecognised icmp type"); 1546255332Scy } 1547145510Sdarrenr ; 1548145510Sdarrenr 1549145510Sdarrenricmpcode: 1550145510Sdarrenr YY_NUMBER { $$ = $1; } 1551145510Sdarrenr | IPFY_ICMPC_NETUNR { $$ = ICMP_UNREACH_NET; } 1552145510Sdarrenr | IPFY_ICMPC_HSTUNR { $$ = ICMP_UNREACH_HOST; } 1553145510Sdarrenr | IPFY_ICMPC_PROUNR { $$ = ICMP_UNREACH_PROTOCOL; } 1554145510Sdarrenr | IPFY_ICMPC_PORUNR { $$ = ICMP_UNREACH_PORT; } 1555145510Sdarrenr | IPFY_ICMPC_NEEDF { $$ = ICMP_UNREACH_NEEDFRAG; } 1556145510Sdarrenr | IPFY_ICMPC_SRCFAIL { $$ = ICMP_UNREACH_SRCFAIL; } 1557145510Sdarrenr | IPFY_ICMPC_NETUNK { $$ = ICMP_UNREACH_NET_UNKNOWN; } 1558145510Sdarrenr | IPFY_ICMPC_HSTUNK { $$ = ICMP_UNREACH_HOST_UNKNOWN; } 1559145510Sdarrenr | IPFY_ICMPC_ISOLATE { $$ = ICMP_UNREACH_ISOLATED; } 1560145510Sdarrenr | IPFY_ICMPC_NETPRO { $$ = ICMP_UNREACH_NET_PROHIB; } 1561145510Sdarrenr | IPFY_ICMPC_HSTPRO { $$ = ICMP_UNREACH_HOST_PROHIB; } 1562145510Sdarrenr | IPFY_ICMPC_NETTOS { $$ = ICMP_UNREACH_TOSNET; } 1563145510Sdarrenr | IPFY_ICMPC_HSTTOS { $$ = ICMP_UNREACH_TOSHOST; } 1564145510Sdarrenr | IPFY_ICMPC_FLTPRO { $$ = ICMP_UNREACH_ADMIN_PROHIBIT; } 1565145510Sdarrenr | IPFY_ICMPC_HSTPRE { $$ = 14; } 1566145510Sdarrenr | IPFY_ICMPC_CUTPRE { $$ = 15; } 1567145510Sdarrenr ; 1568145510Sdarrenr 1569145510Sdarrenropt: 1570145510Sdarrenr IPFY_IPOPT_NOP { $$ = getoptbyvalue(IPOPT_NOP); } 1571145510Sdarrenr | IPFY_IPOPT_RR { $$ = getoptbyvalue(IPOPT_RR); } 1572145510Sdarrenr | IPFY_IPOPT_ZSU { $$ = getoptbyvalue(IPOPT_ZSU); } 1573145510Sdarrenr | IPFY_IPOPT_MTUP { $$ = getoptbyvalue(IPOPT_MTUP); } 1574145510Sdarrenr | IPFY_IPOPT_MTUR { $$ = getoptbyvalue(IPOPT_MTUR); } 1575145510Sdarrenr | IPFY_IPOPT_ENCODE { $$ = getoptbyvalue(IPOPT_ENCODE); } 1576145510Sdarrenr | IPFY_IPOPT_TS { $$ = getoptbyvalue(IPOPT_TS); } 1577145510Sdarrenr | IPFY_IPOPT_TR { $$ = getoptbyvalue(IPOPT_TR); } 1578145510Sdarrenr | IPFY_IPOPT_SEC { $$ = getoptbyvalue(IPOPT_SECURITY); } 1579145510Sdarrenr | IPFY_IPOPT_LSRR { $$ = getoptbyvalue(IPOPT_LSRR); } 1580145510Sdarrenr | IPFY_IPOPT_ESEC { $$ = getoptbyvalue(IPOPT_E_SEC); } 1581255332Scy | IPFY_IPOPT_CIPSO { $$ = getoptbyvalue(IPOPT_CIPSO); } 1582255332Scy | IPFY_IPOPT_CIPSO doi { $$ = getoptbyvalue(IPOPT_CIPSO); } 1583145510Sdarrenr | IPFY_IPOPT_SATID { $$ = getoptbyvalue(IPOPT_SATID); } 1584145510Sdarrenr | IPFY_IPOPT_SSRR { $$ = getoptbyvalue(IPOPT_SSRR); } 1585145510Sdarrenr | IPFY_IPOPT_ADDEXT { $$ = getoptbyvalue(IPOPT_ADDEXT); } 1586145510Sdarrenr | IPFY_IPOPT_VISA { $$ = getoptbyvalue(IPOPT_VISA); } 1587145510Sdarrenr | IPFY_IPOPT_IMITD { $$ = getoptbyvalue(IPOPT_IMITD); } 1588145510Sdarrenr | IPFY_IPOPT_EIP { $$ = getoptbyvalue(IPOPT_EIP); } 1589145510Sdarrenr | IPFY_IPOPT_FINN { $$ = getoptbyvalue(IPOPT_FINN); } 1590145510Sdarrenr | IPFY_IPOPT_DPS { $$ = getoptbyvalue(IPOPT_DPS); } 1591145510Sdarrenr | IPFY_IPOPT_SDB { $$ = getoptbyvalue(IPOPT_SDB); } 1592145510Sdarrenr | IPFY_IPOPT_NSAPA { $$ = getoptbyvalue(IPOPT_NSAPA); } 1593145510Sdarrenr | IPFY_IPOPT_RTRALRT { $$ = getoptbyvalue(IPOPT_RTRALRT); } 1594145510Sdarrenr | IPFY_IPOPT_UMP { $$ = getoptbyvalue(IPOPT_UMP); } 1595145510Sdarrenr | setsecclass secname 1596145510Sdarrenr { DOALL(fr->fr_mip.fi_secmsk |= $2; 1597255332Scy if (fr->fr_family == AF_UNSPEC) { 1598255332Scy fr->fr_family = AF_INET; 1599255332Scy fr->fr_ip.fi_v = 4; 1600255332Scy fr->fr_mip.fi_v = 0xf; 1601255332Scy } else if (fr->fr_family != AF_INET) { 1602255332Scy YYERROR; 1603255332Scy } 1604145510Sdarrenr if (!nowith) 1605145510Sdarrenr fr->fr_ip.fi_secmsk |= $2;) 1606145510Sdarrenr $$ = 0; 1607145510Sdarrenr yyresetdict(); 1608145510Sdarrenr } 1609145510Sdarrenr ; 1610145510Sdarrenr 1611145510Sdarrenrsetsecclass: 1612255332Scy IPFY_SECCLASS { yysetdict(ipv4secwords); } 1613145510Sdarrenr ; 1614145510Sdarrenr 1615255332Scydoi: IPFY_DOI YY_NUMBER { DOALL(fr->fr_doimask = 0xffffffff; \ 1616255332Scy if (!nowith) \ 1617255332Scy fr->fr_doi = $2;) } 1618255332Scy | IPFY_DOI YY_HEX { DOALL(fr->fr_doimask = 0xffffffff; \ 1619255332Scy if (!nowith) \ 1620255332Scy fr->fr_doi = $2;) } 1621255332Scy ; 1622255332Scy 1623145510Sdarrenripv6hdr: 1624145510Sdarrenr IPFY_AH { $$ = getv6optbyvalue(IPPROTO_AH); } 1625145510Sdarrenr | IPFY_IPV6OPT_DSTOPTS { $$ = getv6optbyvalue(IPPROTO_DSTOPTS); } 1626153881Sguido | IPFY_IPV6OPT_ESP { $$ = getv6optbyvalue(IPPROTO_ESP); } 1627145510Sdarrenr | IPFY_IPV6OPT_HOPOPTS { $$ = getv6optbyvalue(IPPROTO_HOPOPTS); } 1628145510Sdarrenr | IPFY_IPV6OPT_IPV6 { $$ = getv6optbyvalue(IPPROTO_IPV6); } 1629145510Sdarrenr | IPFY_IPV6OPT_NONE { $$ = getv6optbyvalue(IPPROTO_NONE); } 1630145510Sdarrenr | IPFY_IPV6OPT_ROUTING { $$ = getv6optbyvalue(IPPROTO_ROUTING); } 1631153881Sguido | IPFY_IPV6OPT_FRAG { $$ = getv6optbyvalue(IPPROTO_FRAGMENT); } 1632153881Sguido | IPFY_IPV6OPT_MOBILITY { $$ = getv6optbyvalue(IPPROTO_MOBILITY); } 1633145510Sdarrenr ; 1634145510Sdarrenr 1635145510Sdarrenrlevel: IPFY_LEVEL { setsyslog(); } 1636145510Sdarrenr ; 1637145510Sdarrenr 1638145510Sdarrenrloglevel: 1639145510Sdarrenr priority { fr->fr_loglevel = LOG_LOCAL0|$1; } 1640145510Sdarrenr | facility '.' priority { fr->fr_loglevel = $1 | $3; } 1641145510Sdarrenr ; 1642145510Sdarrenr 1643145510Sdarrenrfacility: 1644145510Sdarrenr IPFY_FAC_KERN { $$ = LOG_KERN; } 1645145510Sdarrenr | IPFY_FAC_USER { $$ = LOG_USER; } 1646145510Sdarrenr | IPFY_FAC_MAIL { $$ = LOG_MAIL; } 1647145510Sdarrenr | IPFY_FAC_DAEMON { $$ = LOG_DAEMON; } 1648145510Sdarrenr | IPFY_FAC_AUTH { $$ = LOG_AUTH; } 1649145510Sdarrenr | IPFY_FAC_SYSLOG { $$ = LOG_SYSLOG; } 1650145510Sdarrenr | IPFY_FAC_LPR { $$ = LOG_LPR; } 1651145510Sdarrenr | IPFY_FAC_NEWS { $$ = LOG_NEWS; } 1652145510Sdarrenr | IPFY_FAC_UUCP { $$ = LOG_UUCP; } 1653145510Sdarrenr | IPFY_FAC_CRON { $$ = LOG_CRON; } 1654145510Sdarrenr | IPFY_FAC_FTP { $$ = LOG_FTP; } 1655145510Sdarrenr | IPFY_FAC_AUTHPRIV { $$ = LOG_AUTHPRIV; } 1656145510Sdarrenr | IPFY_FAC_AUDIT { $$ = LOG_AUDIT; } 1657145510Sdarrenr | IPFY_FAC_LFMT { $$ = LOG_LFMT; } 1658145510Sdarrenr | IPFY_FAC_LOCAL0 { $$ = LOG_LOCAL0; } 1659145510Sdarrenr | IPFY_FAC_LOCAL1 { $$ = LOG_LOCAL1; } 1660145510Sdarrenr | IPFY_FAC_LOCAL2 { $$ = LOG_LOCAL2; } 1661145510Sdarrenr | IPFY_FAC_LOCAL3 { $$ = LOG_LOCAL3; } 1662145510Sdarrenr | IPFY_FAC_LOCAL4 { $$ = LOG_LOCAL4; } 1663145510Sdarrenr | IPFY_FAC_LOCAL5 { $$ = LOG_LOCAL5; } 1664145510Sdarrenr | IPFY_FAC_LOCAL6 { $$ = LOG_LOCAL6; } 1665145510Sdarrenr | IPFY_FAC_LOCAL7 { $$ = LOG_LOCAL7; } 1666145510Sdarrenr | IPFY_FAC_SECURITY { $$ = LOG_SECURITY; } 1667145510Sdarrenr ; 1668145510Sdarrenr 1669145510Sdarrenrpriority: 1670145510Sdarrenr IPFY_PRI_EMERG { $$ = LOG_EMERG; } 1671145510Sdarrenr | IPFY_PRI_ALERT { $$ = LOG_ALERT; } 1672145510Sdarrenr | IPFY_PRI_CRIT { $$ = LOG_CRIT; } 1673145510Sdarrenr | IPFY_PRI_ERR { $$ = LOG_ERR; } 1674145510Sdarrenr | IPFY_PRI_WARN { $$ = LOG_WARNING; } 1675145510Sdarrenr | IPFY_PRI_NOTICE { $$ = LOG_NOTICE; } 1676145510Sdarrenr | IPFY_PRI_INFO { $$ = LOG_INFO; } 1677145510Sdarrenr | IPFY_PRI_DEBUG { $$ = LOG_DEBUG; } 1678145510Sdarrenr ; 1679145510Sdarrenr 1680145510Sdarrenrcompare: 1681145510Sdarrenr YY_CMP_EQ { $$ = FR_EQUAL; } 1682145510Sdarrenr | YY_CMP_NE { $$ = FR_NEQUAL; } 1683145510Sdarrenr | YY_CMP_LT { $$ = FR_LESST; } 1684145510Sdarrenr | YY_CMP_LE { $$ = FR_LESSTE; } 1685145510Sdarrenr | YY_CMP_GT { $$ = FR_GREATERT; } 1686145510Sdarrenr | YY_CMP_GE { $$ = FR_GREATERTE; } 1687145510Sdarrenr ; 1688145510Sdarrenr 1689145510Sdarrenrrange: YY_RANGE_IN { $$ = FR_INRANGE; } 1690145510Sdarrenr | YY_RANGE_OUT { $$ = FR_OUTRANGE; } 1691145510Sdarrenr | ':' { $$ = FR_INCRANGE; } 1692145510Sdarrenr ; 1693145510Sdarrenr 1694145510Sdarrenrservicename: 1695145510Sdarrenr YY_STR { $$ = $1; } 1696145510Sdarrenr ; 1697145510Sdarrenr 1698170268Sdarrenrinterfacename: name { $$ = $1; } 1699170268Sdarrenr | name ':' YY_NUMBER 1700145510Sdarrenr { $$ = $1; 1701145510Sdarrenr fprintf(stderr, "%d: Logical interface %s:%d unsupported, " 1702145510Sdarrenr "use the physical interface %s instead.\n", 1703145510Sdarrenr yylineNum, $1, $3, $1); 1704145510Sdarrenr } 1705145510Sdarrenr ; 1706145510Sdarrenr 1707145510Sdarrenrname: YY_STR { $$ = $1; } 1708170268Sdarrenr | '-' { $$ = strdup("-"); } 1709145510Sdarrenr ; 1710145510Sdarrenr 1711145510Sdarrenripv4_16: 1712145510Sdarrenr YY_NUMBER '.' YY_NUMBER 1713145510Sdarrenr { if ($1 > 255 || $3 > 255) { 1714145510Sdarrenr yyerror("Invalid octet string for IP address"); 1715145510Sdarrenr return 0; 1716145510Sdarrenr } 1717145510Sdarrenr $$.s_addr = ($1 << 24) | ($3 << 16); 1718145510Sdarrenr $$.s_addr = htonl($$.s_addr); 1719145510Sdarrenr } 1720145510Sdarrenr ; 1721145510Sdarrenr 1722145510Sdarrenripv4_24: 1723145510Sdarrenr ipv4_16 '.' YY_NUMBER 1724145510Sdarrenr { if ($3 > 255) { 1725145510Sdarrenr yyerror("Invalid octet string for IP address"); 1726145510Sdarrenr return 0; 1727145510Sdarrenr } 1728145510Sdarrenr $$.s_addr |= htonl($3 << 8); 1729145510Sdarrenr } 1730145510Sdarrenr ; 1731145510Sdarrenr 1732145510Sdarrenripv4: ipv4_24 '.' YY_NUMBER 1733145510Sdarrenr { if ($3 > 255) { 1734145510Sdarrenr yyerror("Invalid octet string for IP address"); 1735145510Sdarrenr return 0; 1736145510Sdarrenr } 1737145510Sdarrenr $$.s_addr |= htonl($3); 1738145510Sdarrenr } 1739145510Sdarrenr | ipv4_24 1740145510Sdarrenr | ipv4_16 1741145510Sdarrenr ; 1742145510Sdarrenr 1743145510Sdarrenr%% 1744145510Sdarrenr 1745145510Sdarrenr 1746255332Scystatic struct wordtab ipfwords[] = { 1747145510Sdarrenr { "age", IPFY_AGE }, 1748145510Sdarrenr { "ah", IPFY_AH }, 1749145510Sdarrenr { "all", IPFY_ALL }, 1750145510Sdarrenr { "and", IPFY_AND }, 1751145510Sdarrenr { "auth", IPFY_AUTH }, 1752145510Sdarrenr { "bad", IPFY_BAD }, 1753145510Sdarrenr { "bad-nat", IPFY_BADNAT }, 1754145510Sdarrenr { "bad-src", IPFY_BADSRC }, 1755145510Sdarrenr { "bcast", IPFY_BROADCAST }, 1756145510Sdarrenr { "block", IPFY_BLOCK }, 1757145510Sdarrenr { "body", IPFY_BODY }, 1758145510Sdarrenr { "bpf-v4", IPFY_BPFV4 }, 1759145510Sdarrenr#ifdef USE_INET6 1760145510Sdarrenr { "bpf-v6", IPFY_BPFV6 }, 1761145510Sdarrenr#endif 1762145510Sdarrenr { "call", IPFY_CALL }, 1763145510Sdarrenr { "code", IPFY_ICMPCODE }, 1764255332Scy { "comment", IPFY_COMMENT }, 1765145510Sdarrenr { "count", IPFY_COUNT }, 1766255332Scy { "decapsulate", IPFY_DECAPS }, 1767255332Scy { "dstlist", IPFY_DSTLIST }, 1768255332Scy { "doi", IPFY_DOI }, 1769145510Sdarrenr { "dup-to", IPFY_DUPTO }, 1770145510Sdarrenr { "eq", YY_CMP_EQ }, 1771145510Sdarrenr { "esp", IPFY_ESP }, 1772255332Scy { "exp", IPFY_IPFEXPR }, 1773255332Scy { "family", IPFY_FAMILY }, 1774145510Sdarrenr { "fastroute", IPFY_FROUTE }, 1775145510Sdarrenr { "first", IPFY_FIRST }, 1776145510Sdarrenr { "flags", IPFY_FLAGS }, 1777145510Sdarrenr { "frag", IPFY_FRAG }, 1778145510Sdarrenr { "frag-body", IPFY_FRAGBODY }, 1779145510Sdarrenr { "frags", IPFY_FRAGS }, 1780145510Sdarrenr { "from", IPFY_FROM }, 1781145510Sdarrenr { "ge", YY_CMP_GE }, 1782145510Sdarrenr { "group", IPFY_GROUP }, 1783145510Sdarrenr { "gt", YY_CMP_GT }, 1784145510Sdarrenr { "head", IPFY_HEAD }, 1785145510Sdarrenr { "icmp", IPFY_ICMP }, 1786255332Scy { "icmp-head", IPFY_ICMPHEAD }, 1787145510Sdarrenr { "icmp-type", IPFY_ICMPTYPE }, 1788145510Sdarrenr { "in", IPFY_IN }, 1789145510Sdarrenr { "in-via", IPFY_INVIA }, 1790255332Scy { "inet", IPFY_INET }, 1791255332Scy { "inet6", IPFY_INET6 }, 1792145510Sdarrenr { "ipopt", IPFY_IPOPTS }, 1793145510Sdarrenr { "ipopts", IPFY_IPOPTS }, 1794145510Sdarrenr { "keep", IPFY_KEEP }, 1795255332Scy { "l5-as", IPFY_L5AS }, 1796145510Sdarrenr { "le", YY_CMP_LE }, 1797145510Sdarrenr { "level", IPFY_LEVEL }, 1798145510Sdarrenr { "limit", IPFY_LIMIT }, 1799145510Sdarrenr { "log", IPFY_LOG }, 1800255332Scy { "loose", IPFY_LOOSE }, 1801145510Sdarrenr { "lowttl", IPFY_LOWTTL }, 1802145510Sdarrenr { "lt", YY_CMP_LT }, 1803145510Sdarrenr { "mask", IPFY_MASK }, 1804145510Sdarrenr { "match-tag", IPFY_MATCHTAG }, 1805255332Scy { "max-per-src", IPFY_MAX_PER_SRC }, 1806255332Scy { "max-srcs", IPFY_MAX_SRCS }, 1807145510Sdarrenr { "mbcast", IPFY_MBCAST }, 1808153881Sguido { "mcast", IPFY_MULTICAST }, 1809145510Sdarrenr { "multicast", IPFY_MULTICAST }, 1810145510Sdarrenr { "nat", IPFY_NAT }, 1811145510Sdarrenr { "ne", YY_CMP_NE }, 1812145510Sdarrenr { "net", IPFY_NETWORK }, 1813145510Sdarrenr { "newisn", IPFY_NEWISN }, 1814145510Sdarrenr { "no", IPFY_NO }, 1815145510Sdarrenr { "no-icmp-err", IPFY_NOICMPERR }, 1816255332Scy { "nolog", IPFY_NOLOG }, 1817161357Sguido { "nomatch", IPFY_NOMATCH }, 1818145510Sdarrenr { "now", IPFY_NOW }, 1819145510Sdarrenr { "not", IPFY_NOT }, 1820145510Sdarrenr { "oow", IPFY_OOW }, 1821145510Sdarrenr { "on", IPFY_ON }, 1822145510Sdarrenr { "opt", IPFY_OPT }, 1823145510Sdarrenr { "or-block", IPFY_ORBLOCK }, 1824145510Sdarrenr { "out", IPFY_OUT }, 1825145510Sdarrenr { "out-via", IPFY_OUTVIA }, 1826145510Sdarrenr { "pass", IPFY_PASS }, 1827145510Sdarrenr { "port", IPFY_PORT }, 1828145510Sdarrenr { "pps", IPFY_PPS }, 1829145510Sdarrenr { "preauth", IPFY_PREAUTH }, 1830145510Sdarrenr { "proto", IPFY_PROTO }, 1831145510Sdarrenr { "quick", IPFY_QUICK }, 1832145510Sdarrenr { "reply-to", IPFY_REPLY_TO }, 1833145510Sdarrenr { "return-icmp", IPFY_RETICMP }, 1834145510Sdarrenr { "return-icmp-as-dest", IPFY_RETICMPASDST }, 1835145510Sdarrenr { "return-rst", IPFY_RETRST }, 1836145510Sdarrenr { "route-to", IPFY_ROUTETO }, 1837255332Scy { "rule-ttl", IPFY_RULETTL }, 1838255332Scy { "rpc", IPFY_RPC }, 1839145510Sdarrenr { "sec-class", IPFY_SECCLASS }, 1840255332Scy { "set", IPFY_SET }, 1841145510Sdarrenr { "set-tag", IPFY_SETTAG }, 1842145510Sdarrenr { "skip", IPFY_SKIP }, 1843145510Sdarrenr { "short", IPFY_SHORT }, 1844145510Sdarrenr { "state", IPFY_STATE }, 1845145510Sdarrenr { "state-age", IPFY_AGE }, 1846145510Sdarrenr { "strict", IPFY_STRICT }, 1847145510Sdarrenr { "sync", IPFY_SYNC }, 1848145510Sdarrenr { "tcp", IPFY_TCP }, 1849145510Sdarrenr { "tcp-udp", IPFY_TCPUDP }, 1850145510Sdarrenr { "tos", IPFY_TOS }, 1851145510Sdarrenr { "to", IPFY_TO }, 1852145510Sdarrenr { "ttl", IPFY_TTL }, 1853145510Sdarrenr { "udp", IPFY_UDP }, 1854255332Scy { "v6hdr", IPFY_V6HDR }, 1855255332Scy { "v6hdrs", IPFY_V6HDRS }, 1856145510Sdarrenr { "with", IPFY_WITH }, 1857145510Sdarrenr { NULL, 0 } 1858145510Sdarrenr}; 1859145510Sdarrenr 1860255332Scystatic struct wordtab addrwords[] = { 1861145510Sdarrenr { "any", IPFY_ANY }, 1862145510Sdarrenr { "hash", IPFY_HASH }, 1863145510Sdarrenr { "pool", IPFY_POOL }, 1864145510Sdarrenr { NULL, 0 } 1865145510Sdarrenr}; 1866145510Sdarrenr 1867255332Scystatic struct wordtab maskwords[] = { 1868145510Sdarrenr { "broadcast", IPFY_BROADCAST }, 1869145510Sdarrenr { "netmasked", IPFY_NETMASKED }, 1870145510Sdarrenr { "network", IPFY_NETWORK }, 1871145510Sdarrenr { "peer", IPFY_PEER }, 1872145510Sdarrenr { NULL, 0 } 1873145510Sdarrenr}; 1874145510Sdarrenr 1875255332Scystatic struct wordtab icmpcodewords[] = { 1876145510Sdarrenr { "cutoff-preced", IPFY_ICMPC_CUTPRE }, 1877145510Sdarrenr { "filter-prohib", IPFY_ICMPC_FLTPRO }, 1878145510Sdarrenr { "isolate", IPFY_ICMPC_ISOLATE }, 1879145510Sdarrenr { "needfrag", IPFY_ICMPC_NEEDF }, 1880145510Sdarrenr { "net-prohib", IPFY_ICMPC_NETPRO }, 1881145510Sdarrenr { "net-tos", IPFY_ICMPC_NETTOS }, 1882145510Sdarrenr { "host-preced", IPFY_ICMPC_HSTPRE }, 1883145510Sdarrenr { "host-prohib", IPFY_ICMPC_HSTPRO }, 1884145510Sdarrenr { "host-tos", IPFY_ICMPC_HSTTOS }, 1885145510Sdarrenr { "host-unk", IPFY_ICMPC_HSTUNK }, 1886145510Sdarrenr { "host-unr", IPFY_ICMPC_HSTUNR }, 1887145510Sdarrenr { "net-unk", IPFY_ICMPC_NETUNK }, 1888145510Sdarrenr { "net-unr", IPFY_ICMPC_NETUNR }, 1889145510Sdarrenr { "port-unr", IPFY_ICMPC_PORUNR }, 1890145510Sdarrenr { "proto-unr", IPFY_ICMPC_PROUNR }, 1891145510Sdarrenr { "srcfail", IPFY_ICMPC_SRCFAIL }, 1892145510Sdarrenr { NULL, 0 }, 1893145510Sdarrenr}; 1894145510Sdarrenr 1895255332Scystatic struct wordtab ipv4optwords[] = { 1896145510Sdarrenr { "addext", IPFY_IPOPT_ADDEXT }, 1897145510Sdarrenr { "cipso", IPFY_IPOPT_CIPSO }, 1898145510Sdarrenr { "dps", IPFY_IPOPT_DPS }, 1899145510Sdarrenr { "e-sec", IPFY_IPOPT_ESEC }, 1900145510Sdarrenr { "eip", IPFY_IPOPT_EIP }, 1901145510Sdarrenr { "encode", IPFY_IPOPT_ENCODE }, 1902145510Sdarrenr { "finn", IPFY_IPOPT_FINN }, 1903145510Sdarrenr { "imitd", IPFY_IPOPT_IMITD }, 1904145510Sdarrenr { "lsrr", IPFY_IPOPT_LSRR }, 1905145510Sdarrenr { "mtup", IPFY_IPOPT_MTUP }, 1906145510Sdarrenr { "mtur", IPFY_IPOPT_MTUR }, 1907145510Sdarrenr { "nop", IPFY_IPOPT_NOP }, 1908145510Sdarrenr { "nsapa", IPFY_IPOPT_NSAPA }, 1909145510Sdarrenr { "rr", IPFY_IPOPT_RR }, 1910145510Sdarrenr { "rtralrt", IPFY_IPOPT_RTRALRT }, 1911145510Sdarrenr { "satid", IPFY_IPOPT_SATID }, 1912145510Sdarrenr { "sdb", IPFY_IPOPT_SDB }, 1913145510Sdarrenr { "sec", IPFY_IPOPT_SEC }, 1914145510Sdarrenr { "ssrr", IPFY_IPOPT_SSRR }, 1915145510Sdarrenr { "tr", IPFY_IPOPT_TR }, 1916145510Sdarrenr { "ts", IPFY_IPOPT_TS }, 1917145510Sdarrenr { "ump", IPFY_IPOPT_UMP }, 1918145510Sdarrenr { "visa", IPFY_IPOPT_VISA }, 1919145510Sdarrenr { "zsu", IPFY_IPOPT_ZSU }, 1920145510Sdarrenr { NULL, 0 }, 1921145510Sdarrenr}; 1922145510Sdarrenr 1923255332Scystatic struct wordtab ipv4secwords[] = { 1924145510Sdarrenr { "confid", IPFY_SEC_CONF }, 1925145510Sdarrenr { "reserv-1", IPFY_SEC_RSV1 }, 1926145510Sdarrenr { "reserv-2", IPFY_SEC_RSV2 }, 1927145510Sdarrenr { "reserv-3", IPFY_SEC_RSV3 }, 1928145510Sdarrenr { "reserv-4", IPFY_SEC_RSV4 }, 1929145510Sdarrenr { "secret", IPFY_SEC_SEC }, 1930145510Sdarrenr { "topsecret", IPFY_SEC_TS }, 1931145510Sdarrenr { "unclass", IPFY_SEC_UNC }, 1932145510Sdarrenr { NULL, 0 }, 1933145510Sdarrenr}; 1934145510Sdarrenr 1935255332Scystatic struct wordtab ipv6optwords[] = { 1936145510Sdarrenr { "dstopts", IPFY_IPV6OPT_DSTOPTS }, 1937153881Sguido { "esp", IPFY_IPV6OPT_ESP }, 1938153881Sguido { "frag", IPFY_IPV6OPT_FRAG }, 1939145510Sdarrenr { "hopopts", IPFY_IPV6OPT_HOPOPTS }, 1940145510Sdarrenr { "ipv6", IPFY_IPV6OPT_IPV6 }, 1941153881Sguido { "mobility", IPFY_IPV6OPT_MOBILITY }, 1942145510Sdarrenr { "none", IPFY_IPV6OPT_NONE }, 1943145510Sdarrenr { "routing", IPFY_IPV6OPT_ROUTING }, 1944145510Sdarrenr { NULL, 0 }, 1945145510Sdarrenr}; 1946145510Sdarrenr 1947255332Scystatic struct wordtab logwords[] = { 1948145510Sdarrenr { "kern", IPFY_FAC_KERN }, 1949145510Sdarrenr { "user", IPFY_FAC_USER }, 1950145510Sdarrenr { "mail", IPFY_FAC_MAIL }, 1951145510Sdarrenr { "daemon", IPFY_FAC_DAEMON }, 1952145510Sdarrenr { "auth", IPFY_FAC_AUTH }, 1953145510Sdarrenr { "syslog", IPFY_FAC_SYSLOG }, 1954145510Sdarrenr { "lpr", IPFY_FAC_LPR }, 1955145510Sdarrenr { "news", IPFY_FAC_NEWS }, 1956145510Sdarrenr { "uucp", IPFY_FAC_UUCP }, 1957145510Sdarrenr { "cron", IPFY_FAC_CRON }, 1958145510Sdarrenr { "ftp", IPFY_FAC_FTP }, 1959145510Sdarrenr { "authpriv", IPFY_FAC_AUTHPRIV }, 1960145510Sdarrenr { "audit", IPFY_FAC_AUDIT }, 1961145510Sdarrenr { "logalert", IPFY_FAC_LFMT }, 1962145510Sdarrenr { "console", IPFY_FAC_CONSOLE }, 1963145510Sdarrenr { "security", IPFY_FAC_SECURITY }, 1964145510Sdarrenr { "local0", IPFY_FAC_LOCAL0 }, 1965145510Sdarrenr { "local1", IPFY_FAC_LOCAL1 }, 1966145510Sdarrenr { "local2", IPFY_FAC_LOCAL2 }, 1967145510Sdarrenr { "local3", IPFY_FAC_LOCAL3 }, 1968145510Sdarrenr { "local4", IPFY_FAC_LOCAL4 }, 1969145510Sdarrenr { "local5", IPFY_FAC_LOCAL5 }, 1970145510Sdarrenr { "local6", IPFY_FAC_LOCAL6 }, 1971145510Sdarrenr { "local7", IPFY_FAC_LOCAL7 }, 1972145510Sdarrenr { "emerg", IPFY_PRI_EMERG }, 1973145510Sdarrenr { "alert", IPFY_PRI_ALERT }, 1974145510Sdarrenr { "crit", IPFY_PRI_CRIT }, 1975145510Sdarrenr { "err", IPFY_PRI_ERR }, 1976145510Sdarrenr { "warn", IPFY_PRI_WARN }, 1977145510Sdarrenr { "notice", IPFY_PRI_NOTICE }, 1978145510Sdarrenr { "info", IPFY_PRI_INFO }, 1979145510Sdarrenr { "debug", IPFY_PRI_DEBUG }, 1980145510Sdarrenr { NULL, 0 }, 1981145510Sdarrenr}; 1982145510Sdarrenr 1983145510Sdarrenr 1984145510Sdarrenr 1985145510Sdarrenr 1986145510Sdarrenrint ipf_parsefile(fd, addfunc, iocfuncs, filename) 1987145510Sdarrenrint fd; 1988145510Sdarrenraddfunc_t addfunc; 1989145510Sdarrenrioctlfunc_t *iocfuncs; 1990145510Sdarrenrchar *filename; 1991145510Sdarrenr{ 1992145510Sdarrenr FILE *fp = NULL; 1993145510Sdarrenr char *s; 1994145510Sdarrenr 1995145510Sdarrenr yylineNum = 1; 1996145510Sdarrenr yysettab(ipfwords); 1997145510Sdarrenr 1998145510Sdarrenr s = getenv("YYDEBUG"); 1999145510Sdarrenr if (s != NULL) 2000145510Sdarrenr yydebug = atoi(s); 2001145510Sdarrenr else 2002145510Sdarrenr yydebug = 0; 2003145510Sdarrenr 2004145510Sdarrenr if (strcmp(filename, "-")) { 2005145510Sdarrenr fp = fopen(filename, "r"); 2006145510Sdarrenr if (fp == NULL) { 2007145510Sdarrenr fprintf(stderr, "fopen(%s) failed: %s\n", filename, 2008145510Sdarrenr STRERROR(errno)); 2009145510Sdarrenr return -1; 2010145510Sdarrenr } 2011145510Sdarrenr } else 2012145510Sdarrenr fp = stdin; 2013145510Sdarrenr 2014145510Sdarrenr while (ipf_parsesome(fd, addfunc, iocfuncs, fp) == 1) 2015145510Sdarrenr ; 2016145510Sdarrenr if (fp != NULL) 2017145510Sdarrenr fclose(fp); 2018145510Sdarrenr return 0; 2019145510Sdarrenr} 2020145510Sdarrenr 2021145510Sdarrenr 2022145510Sdarrenrint ipf_parsesome(fd, addfunc, iocfuncs, fp) 2023145510Sdarrenrint fd; 2024145510Sdarrenraddfunc_t addfunc; 2025145510Sdarrenrioctlfunc_t *iocfuncs; 2026145510SdarrenrFILE *fp; 2027145510Sdarrenr{ 2028145510Sdarrenr char *s; 2029145510Sdarrenr int i; 2030145510Sdarrenr 2031145510Sdarrenr ipffd = fd; 2032145510Sdarrenr for (i = 0; i <= IPL_LOGMAX; i++) 2033255332Scy ipfioctls[i] = iocfuncs[i]; 2034145510Sdarrenr ipfaddfunc = addfunc; 2035145510Sdarrenr 2036145510Sdarrenr if (feof(fp)) 2037145510Sdarrenr return 0; 2038145510Sdarrenr i = fgetc(fp); 2039145510Sdarrenr if (i == EOF) 2040145510Sdarrenr return 0; 2041145510Sdarrenr if (ungetc(i, fp) == 0) 2042145510Sdarrenr return 0; 2043145510Sdarrenr if (feof(fp)) 2044145510Sdarrenr return 0; 2045145510Sdarrenr s = getenv("YYDEBUG"); 2046145510Sdarrenr if (s != NULL) 2047145510Sdarrenr yydebug = atoi(s); 2048145510Sdarrenr else 2049145510Sdarrenr yydebug = 0; 2050145510Sdarrenr 2051145510Sdarrenr yyin = fp; 2052145510Sdarrenr yyparse(); 2053145510Sdarrenr return 1; 2054145510Sdarrenr} 2055145510Sdarrenr 2056145510Sdarrenr 2057145510Sdarrenrstatic void newrule() 2058145510Sdarrenr{ 2059145510Sdarrenr frentry_t *frn; 2060145510Sdarrenr 2061255332Scy frn = allocfr(); 2062145510Sdarrenr for (fr = frtop; fr != NULL && fr->fr_next != NULL; fr = fr->fr_next) 2063145510Sdarrenr ; 2064255332Scy if (fr != NULL) { 2065145510Sdarrenr fr->fr_next = frn; 2066255332Scy frn->fr_pnext = &fr->fr_next; 2067255332Scy } 2068255332Scy if (frtop == NULL) { 2069145510Sdarrenr frtop = frn; 2070255332Scy frn->fr_pnext = &frtop; 2071255332Scy } 2072145510Sdarrenr fr = frn; 2073145510Sdarrenr frc = frn; 2074145510Sdarrenr fr->fr_loglevel = 0xffff; 2075145510Sdarrenr fr->fr_isc = (void *)-1; 2076145510Sdarrenr fr->fr_logtag = FR_NOLOGTAG; 2077145510Sdarrenr fr->fr_type = FR_T_NONE; 2078255332Scy fr->fr_flineno = yylineNum; 2079145510Sdarrenr 2080255332Scy if (use_inet6 == 1) 2081255332Scy fr->fr_family = AF_INET6; 2082255332Scy else if (use_inet6 == -1) 2083255332Scy fr->fr_family = AF_INET; 2084255332Scy 2085145510Sdarrenr nrules = 1; 2086145510Sdarrenr} 2087145510Sdarrenr 2088145510Sdarrenr 2089145510Sdarrenrstatic void setipftype() 2090145510Sdarrenr{ 2091145510Sdarrenr for (fr = frc; fr != NULL; fr = fr->fr_next) { 2092145510Sdarrenr if (fr->fr_type == FR_T_NONE) { 2093145510Sdarrenr fr->fr_type = FR_T_IPF; 2094145510Sdarrenr fr->fr_data = (void *)calloc(sizeof(fripf_t), 1); 2095145510Sdarrenr fr->fr_dsize = sizeof(fripf_t); 2096255332Scy fr->fr_family = frc->fr_family; 2097255332Scy if (fr->fr_family == AF_INET) { 2098255332Scy fr->fr_ip.fi_v = 4; 2099255332Scy } 2100255332Scy else if (fr->fr_family == AF_INET6) { 2101255332Scy fr->fr_ip.fi_v = 6; 2102255332Scy } 2103145510Sdarrenr fr->fr_mip.fi_v = 0xf; 2104145510Sdarrenr fr->fr_ipf->fri_sifpidx = -1; 2105145510Sdarrenr fr->fr_ipf->fri_difpidx = -1; 2106145510Sdarrenr } 2107145510Sdarrenr if (fr->fr_type != FR_T_IPF) { 2108145510Sdarrenr fprintf(stderr, "IPF Type not set\n"); 2109145510Sdarrenr } 2110145510Sdarrenr } 2111145510Sdarrenr} 2112145510Sdarrenr 2113145510Sdarrenr 2114145510Sdarrenrstatic frentry_t *addrule() 2115145510Sdarrenr{ 2116145510Sdarrenr frentry_t *f, *f1, *f2; 2117145510Sdarrenr int count; 2118145510Sdarrenr 2119145510Sdarrenr for (f2 = frc; f2->fr_next != NULL; f2 = f2->fr_next) 2120145510Sdarrenr ; 2121145510Sdarrenr 2122145510Sdarrenr count = nrules; 2123145510Sdarrenr f = f2; 2124145510Sdarrenr for (f1 = frc; count > 0; count--, f1 = f1->fr_next) { 2125255332Scy f->fr_next = allocfr(); 2126255332Scy if (f->fr_next == NULL) 2127255332Scy return NULL; 2128255332Scy f->fr_next->fr_pnext = &f->fr_next; 2129145510Sdarrenr added++; 2130145510Sdarrenr f = f->fr_next; 2131255332Scy *f = *f1; 2132145510Sdarrenr f->fr_next = NULL; 2133145510Sdarrenr if (f->fr_caddr != NULL) { 2134145510Sdarrenr f->fr_caddr = malloc(f->fr_dsize); 2135145510Sdarrenr bcopy(f1->fr_caddr, f->fr_caddr, f->fr_dsize); 2136145510Sdarrenr } 2137145510Sdarrenr } 2138145510Sdarrenr 2139145510Sdarrenr return f2->fr_next; 2140145510Sdarrenr} 2141145510Sdarrenr 2142145510Sdarrenr 2143255332Scystatic int 2144255332Scylookuphost(name, addrp) 2145255332Scy char *name; 2146255332Scy i6addr_t *addrp; 2147145510Sdarrenr{ 2148145510Sdarrenr int i; 2149145510Sdarrenr 2150145510Sdarrenr hashed = 0; 2151145510Sdarrenr pooled = 0; 2152145510Sdarrenr dynamic = -1; 2153145510Sdarrenr 2154145510Sdarrenr for (i = 0; i < 4; i++) { 2155255332Scy if (fr->fr_ifnames[i] == -1) 2156255332Scy continue; 2157255332Scy if (strcmp(name, fr->fr_names + fr->fr_ifnames[i]) == 0) { 2158145510Sdarrenr ifpflag = FRI_DYNAMIC; 2159255332Scy dynamic = addname(&fr, name); 2160255332Scy return 1; 2161145510Sdarrenr } 2162145510Sdarrenr } 2163145510Sdarrenr 2164255332Scy if (gethost(AF_INET, name, addrp) == -1) { 2165145510Sdarrenr fprintf(stderr, "unknown name \"%s\"\n", name); 2166255332Scy return -1; 2167145510Sdarrenr } 2168255332Scy return 0; 2169145510Sdarrenr} 2170145510Sdarrenr 2171145510Sdarrenr 2172145510Sdarrenrstatic void dobpf(v, phrase) 2173145510Sdarrenrint v; 2174145510Sdarrenrchar *phrase; 2175145510Sdarrenr{ 2176145510Sdarrenr#ifdef IPFILTER_BPF 2177145510Sdarrenr struct bpf_program bpf; 2178145510Sdarrenr struct pcap *p; 2179145510Sdarrenr#endif 2180145510Sdarrenr fakebpf_t *fb; 2181145510Sdarrenr u_32_t l; 2182145510Sdarrenr char *s; 2183145510Sdarrenr int i; 2184145510Sdarrenr 2185145510Sdarrenr for (fr = frc; fr != NULL; fr = fr->fr_next) { 2186145510Sdarrenr if (fr->fr_type != FR_T_NONE) { 2187145510Sdarrenr fprintf(stderr, "cannot mix IPF and BPF matching\n"); 2188145510Sdarrenr return; 2189145510Sdarrenr } 2190255332Scy fr->fr_family = vtof(v); 2191145510Sdarrenr fr->fr_type = FR_T_BPFOPC; 2192145510Sdarrenr 2193153881Sguido if (!strncmp(phrase, "0x", 2)) { 2194145510Sdarrenr fb = malloc(sizeof(fakebpf_t)); 2195145510Sdarrenr 2196145510Sdarrenr for (i = 0, s = strtok(phrase, " \r\n\t"); s != NULL; 2197145510Sdarrenr s = strtok(NULL, " \r\n\t"), i++) { 2198145510Sdarrenr fb = realloc(fb, (i / 4 + 1) * sizeof(*fb)); 2199317314Scy if (fb == NULL) { 2200317314Scy warnx("memory allocation error at %d in %s in %s", __LINE__, __FUNCTION__, __FILE__); 2201317314Scy abort(); 2202317314Scy } 2203145510Sdarrenr l = (u_32_t)strtol(s, NULL, 0); 2204145510Sdarrenr switch (i & 3) 2205145510Sdarrenr { 2206145510Sdarrenr case 0 : 2207145510Sdarrenr fb[i / 4].fb_c = l & 0xffff; 2208145510Sdarrenr break; 2209145510Sdarrenr case 1 : 2210145510Sdarrenr fb[i / 4].fb_t = l & 0xff; 2211145510Sdarrenr break; 2212145510Sdarrenr case 2 : 2213145510Sdarrenr fb[i / 4].fb_f = l & 0xff; 2214145510Sdarrenr break; 2215145510Sdarrenr case 3 : 2216145510Sdarrenr fb[i / 4].fb_k = l; 2217145510Sdarrenr break; 2218145510Sdarrenr } 2219145510Sdarrenr } 2220145510Sdarrenr if ((i & 3) != 0) { 2221145510Sdarrenr fprintf(stderr, 2222145510Sdarrenr "Odd number of bytes in BPF code\n"); 2223145510Sdarrenr exit(1); 2224145510Sdarrenr } 2225145510Sdarrenr i--; 2226145510Sdarrenr fr->fr_dsize = (i / 4 + 1) * sizeof(*fb); 2227145510Sdarrenr fr->fr_data = fb; 2228145510Sdarrenr return; 2229145510Sdarrenr } 2230145510Sdarrenr 2231145510Sdarrenr#ifdef IPFILTER_BPF 2232145510Sdarrenr bzero((char *)&bpf, sizeof(bpf)); 2233145510Sdarrenr p = pcap_open_dead(DLT_RAW, 1); 2234145510Sdarrenr if (!p) { 2235145510Sdarrenr fprintf(stderr, "pcap_open_dead failed\n"); 2236145510Sdarrenr return; 2237145510Sdarrenr } 2238145510Sdarrenr 2239145510Sdarrenr if (pcap_compile(p, &bpf, phrase, 1, 0xffffffff)) { 2240145510Sdarrenr pcap_perror(p, "ipf"); 2241145510Sdarrenr pcap_close(p); 2242145510Sdarrenr fprintf(stderr, "pcap parsing failed (%s)\n", phrase); 2243145510Sdarrenr return; 2244145510Sdarrenr } 2245145510Sdarrenr pcap_close(p); 2246145510Sdarrenr 2247145510Sdarrenr fr->fr_dsize = bpf.bf_len * sizeof(struct bpf_insn); 2248145510Sdarrenr fr->fr_data = malloc(fr->fr_dsize); 2249145510Sdarrenr bcopy((char *)bpf.bf_insns, fr->fr_data, fr->fr_dsize); 2250145510Sdarrenr if (!bpf_validate(fr->fr_data, bpf.bf_len)) { 2251145510Sdarrenr fprintf(stderr, "BPF validation failed\n"); 2252145510Sdarrenr return; 2253145510Sdarrenr } 2254145510Sdarrenr#endif 2255145510Sdarrenr } 2256145510Sdarrenr 2257145510Sdarrenr#ifdef IPFILTER_BPF 2258145510Sdarrenr if (opts & OPT_DEBUG) 2259145510Sdarrenr bpf_dump(&bpf, 0); 2260145510Sdarrenr#else 2261145510Sdarrenr fprintf(stderr, "BPF filter expressions not supported\n"); 2262145510Sdarrenr exit(1); 2263145510Sdarrenr#endif 2264145510Sdarrenr} 2265145510Sdarrenr 2266145510Sdarrenr 2267145510Sdarrenrstatic void resetaddr() 2268145510Sdarrenr{ 2269145510Sdarrenr hashed = 0; 2270145510Sdarrenr pooled = 0; 2271145510Sdarrenr dynamic = -1; 2272145510Sdarrenr} 2273145510Sdarrenr 2274145510Sdarrenr 2275145510Sdarrenrstatic alist_t *newalist(ptr) 2276145510Sdarrenralist_t *ptr; 2277145510Sdarrenr{ 2278145510Sdarrenr alist_t *al; 2279145510Sdarrenr 2280145510Sdarrenr al = malloc(sizeof(*al)); 2281145510Sdarrenr if (al == NULL) 2282145510Sdarrenr return NULL; 2283145510Sdarrenr al->al_not = 0; 2284145510Sdarrenr al->al_next = ptr; 2285145510Sdarrenr return al; 2286145510Sdarrenr} 2287145510Sdarrenr 2288145510Sdarrenr 2289255332Scystatic int 2290255332Scymakepool(list) 2291255332Scy alist_t *list; 2292145510Sdarrenr{ 2293145510Sdarrenr ip_pool_node_t *n, *top; 2294145510Sdarrenr ip_pool_t pool; 2295145510Sdarrenr alist_t *a; 2296145510Sdarrenr int num; 2297145510Sdarrenr 2298145510Sdarrenr if (list == NULL) 2299145510Sdarrenr return 0; 2300145510Sdarrenr top = calloc(1, sizeof(*top)); 2301145510Sdarrenr if (top == NULL) 2302145510Sdarrenr return 0; 2303255332Scy 2304145510Sdarrenr for (n = top, a = list; (n != NULL) && (a != NULL); a = a->al_next) { 2305255332Scy if (use_inet6 == 1) { 2306255332Scy#ifdef AF_INET6 2307255332Scy n->ipn_addr.adf_family = AF_INET6; 2308255332Scy n->ipn_addr.adf_addr = a->al_i6addr; 2309255332Scy n->ipn_addr.adf_len = offsetof(addrfamily_t, 2310255332Scy adf_addr) + 16; 2311255332Scy n->ipn_mask.adf_family = AF_INET6; 2312255332Scy n->ipn_mask.adf_addr = a->al_i6mask; 2313255332Scy n->ipn_mask.adf_len = offsetof(addrfamily_t, 2314255332Scy adf_addr) + 16; 2315255332Scy 2316255332Scy#endif 2317255332Scy } else { 2318255332Scy n->ipn_addr.adf_family = AF_INET; 2319255332Scy n->ipn_addr.adf_addr.in4.s_addr = a->al_1; 2320255332Scy n->ipn_addr.adf_len = offsetof(addrfamily_t, 2321255332Scy adf_addr) + 4; 2322255332Scy n->ipn_mask.adf_family = AF_INET; 2323255332Scy n->ipn_mask.adf_addr.in4.s_addr = a->al_2; 2324255332Scy n->ipn_mask.adf_len = offsetof(addrfamily_t, 2325255332Scy adf_addr) + 4; 2326255332Scy } 2327145510Sdarrenr n->ipn_info = a->al_not; 2328145510Sdarrenr if (a->al_next != NULL) { 2329145510Sdarrenr n->ipn_next = calloc(1, sizeof(*n)); 2330145510Sdarrenr n = n->ipn_next; 2331145510Sdarrenr } 2332145510Sdarrenr } 2333145510Sdarrenr 2334145510Sdarrenr bzero((char *)&pool, sizeof(pool)); 2335145510Sdarrenr pool.ipo_unit = IPL_LOGIPF; 2336145510Sdarrenr pool.ipo_list = top; 2337255332Scy num = load_pool(&pool, ipfioctls[IPL_LOGLOOKUP]); 2338145510Sdarrenr 2339145510Sdarrenr while ((n = top) != NULL) { 2340145510Sdarrenr top = n->ipn_next; 2341145510Sdarrenr free(n); 2342145510Sdarrenr } 2343145510Sdarrenr return num; 2344145510Sdarrenr} 2345145510Sdarrenr 2346145510Sdarrenr 2347145510Sdarrenrstatic u_int makehash(list) 2348145510Sdarrenralist_t *list; 2349145510Sdarrenr{ 2350145510Sdarrenr iphtent_t *n, *top; 2351145510Sdarrenr iphtable_t iph; 2352145510Sdarrenr alist_t *a; 2353145510Sdarrenr int num; 2354145510Sdarrenr 2355145510Sdarrenr if (list == NULL) 2356145510Sdarrenr return 0; 2357145510Sdarrenr top = calloc(1, sizeof(*top)); 2358145510Sdarrenr if (top == NULL) 2359145510Sdarrenr return 0; 2360255332Scy 2361145510Sdarrenr for (n = top, a = list; (n != NULL) && (a != NULL); a = a->al_next) { 2362255332Scy if (a->al_family == AF_INET6) { 2363255332Scy n->ipe_family = AF_INET6; 2364255332Scy n->ipe_addr = a->al_i6addr; 2365255332Scy n->ipe_mask = a->al_i6mask; 2366255332Scy } else { 2367255332Scy n->ipe_family = AF_INET; 2368255332Scy n->ipe_addr.in4_addr = a->al_1; 2369255332Scy n->ipe_mask.in4_addr = a->al_2; 2370255332Scy } 2371145510Sdarrenr n->ipe_value = 0; 2372145510Sdarrenr if (a->al_next != NULL) { 2373145510Sdarrenr n->ipe_next = calloc(1, sizeof(*n)); 2374145510Sdarrenr n = n->ipe_next; 2375145510Sdarrenr } 2376145510Sdarrenr } 2377145510Sdarrenr 2378145510Sdarrenr bzero((char *)&iph, sizeof(iph)); 2379145510Sdarrenr iph.iph_unit = IPL_LOGIPF; 2380145510Sdarrenr iph.iph_type = IPHASH_LOOKUP; 2381145510Sdarrenr *iph.iph_name = '\0'; 2382145510Sdarrenr 2383255332Scy if (load_hash(&iph, top, ipfioctls[IPL_LOGLOOKUP]) == 0) 2384145510Sdarrenr sscanf(iph.iph_name, "%u", &num); 2385145510Sdarrenr else 2386145510Sdarrenr num = 0; 2387145510Sdarrenr 2388145510Sdarrenr while ((n = top) != NULL) { 2389145510Sdarrenr top = n->ipe_next; 2390145510Sdarrenr free(n); 2391145510Sdarrenr } 2392145510Sdarrenr return num; 2393145510Sdarrenr} 2394145510Sdarrenr 2395145510Sdarrenr 2396255332Scyint ipf_addrule(fd, ioctlfunc, ptr) 2397145510Sdarrenrint fd; 2398145510Sdarrenrioctlfunc_t ioctlfunc; 2399145510Sdarrenrvoid *ptr; 2400145510Sdarrenr{ 2401145510Sdarrenr ioctlcmd_t add, del; 2402145510Sdarrenr frentry_t *fr; 2403145510Sdarrenr ipfobj_t obj; 2404145510Sdarrenr 2405170268Sdarrenr if (ptr == NULL) 2406255332Scy return 0; 2407170268Sdarrenr 2408145510Sdarrenr fr = ptr; 2409145510Sdarrenr add = 0; 2410145510Sdarrenr del = 0; 2411145510Sdarrenr 2412145510Sdarrenr bzero((char *)&obj, sizeof(obj)); 2413145510Sdarrenr obj.ipfo_rev = IPFILTER_VERSION; 2414255332Scy obj.ipfo_size = fr->fr_size; 2415145510Sdarrenr obj.ipfo_type = IPFOBJ_FRENTRY; 2416145510Sdarrenr obj.ipfo_ptr = ptr; 2417145510Sdarrenr 2418145510Sdarrenr if ((opts & OPT_DONOTHING) != 0) 2419145510Sdarrenr fd = -1; 2420145510Sdarrenr 2421145510Sdarrenr if (opts & OPT_ZERORULEST) { 2422145510Sdarrenr add = SIOCZRLST; 2423145510Sdarrenr } else if (opts & OPT_INACTIVE) { 2424145510Sdarrenr add = (u_int)fr->fr_hits ? SIOCINIFR : 2425145510Sdarrenr SIOCADIFR; 2426145510Sdarrenr del = SIOCRMIFR; 2427145510Sdarrenr } else { 2428145510Sdarrenr add = (u_int)fr->fr_hits ? SIOCINAFR : 2429145510Sdarrenr SIOCADAFR; 2430145510Sdarrenr del = SIOCRMAFR; 2431145510Sdarrenr } 2432145510Sdarrenr 2433161357Sguido if ((opts & OPT_OUTQUE) != 0) 2434145510Sdarrenr fr->fr_flags |= FR_OUTQUE; 2435145510Sdarrenr if (fr->fr_hits) 2436145510Sdarrenr fr->fr_hits--; 2437170268Sdarrenr if ((opts & OPT_VERBOSE) != 0) 2438145510Sdarrenr printfr(fr, ioctlfunc); 2439145510Sdarrenr 2440170268Sdarrenr if ((opts & OPT_DEBUG) != 0) { 2441145510Sdarrenr binprint(fr, sizeof(*fr)); 2442145510Sdarrenr if (fr->fr_data != NULL) 2443145510Sdarrenr binprint(fr->fr_data, fr->fr_dsize); 2444145510Sdarrenr } 2445145510Sdarrenr 2446145510Sdarrenr if ((opts & OPT_ZERORULEST) != 0) { 2447145510Sdarrenr if ((*ioctlfunc)(fd, add, (void *)&obj) == -1) { 2448145510Sdarrenr if ((opts & OPT_DONOTHING) == 0) { 2449255332Scy char msg[80]; 2450255332Scy 2451255332Scy sprintf(msg, "%d:ioctl(zero rule)", 2452255332Scy fr->fr_flineno); 2453255332Scy return ipf_perror_fd(fd, ioctlfunc, msg); 2454145510Sdarrenr } 2455145510Sdarrenr } else { 2456145510Sdarrenr#ifdef USE_QUAD_T 2457145510Sdarrenr printf("hits %qd bytes %qd ", 2458145510Sdarrenr (long long)fr->fr_hits, 2459145510Sdarrenr (long long)fr->fr_bytes); 2460145510Sdarrenr#else 2461145510Sdarrenr printf("hits %ld bytes %ld ", 2462145510Sdarrenr fr->fr_hits, fr->fr_bytes); 2463145510Sdarrenr#endif 2464145510Sdarrenr printfr(fr, ioctlfunc); 2465145510Sdarrenr } 2466145510Sdarrenr } else if ((opts & OPT_REMOVE) != 0) { 2467145510Sdarrenr if ((*ioctlfunc)(fd, del, (void *)&obj) == -1) { 2468255332Scy if ((opts & OPT_DONOTHING) == 0) { 2469255332Scy char msg[80]; 2470255332Scy 2471255332Scy sprintf(msg, "%d:ioctl(delete rule)", 2472255332Scy fr->fr_flineno); 2473255332Scy return ipf_perror_fd(fd, ioctlfunc, msg); 2474145510Sdarrenr } 2475145510Sdarrenr } 2476145510Sdarrenr } else { 2477145510Sdarrenr if ((*ioctlfunc)(fd, add, (void *)&obj) == -1) { 2478255332Scy if ((opts & OPT_DONOTHING) == 0) { 2479255332Scy char msg[80]; 2480255332Scy 2481255332Scy sprintf(msg, "%d:ioctl(add/insert rule)", 2482255332Scy fr->fr_flineno); 2483255332Scy return ipf_perror_fd(fd, ioctlfunc, msg); 2484145510Sdarrenr } 2485145510Sdarrenr } 2486145510Sdarrenr } 2487255332Scy return 0; 2488145510Sdarrenr} 2489145510Sdarrenr 2490145510Sdarrenrstatic void setsyslog() 2491145510Sdarrenr{ 2492145510Sdarrenr yysetdict(logwords); 2493145510Sdarrenr yybreakondot = 1; 2494145510Sdarrenr} 2495145510Sdarrenr 2496145510Sdarrenr 2497145510Sdarrenrstatic void unsetsyslog() 2498145510Sdarrenr{ 2499145510Sdarrenr yyresetdict(); 2500145510Sdarrenr yybreakondot = 0; 2501145510Sdarrenr} 2502145510Sdarrenr 2503145510Sdarrenr 2504145510Sdarrenrstatic void fillgroup(fr) 2505145510Sdarrenrfrentry_t *fr; 2506145510Sdarrenr{ 2507145510Sdarrenr frentry_t *f; 2508145510Sdarrenr 2509255332Scy for (f = frold; f != NULL; f = f->fr_next) { 2510255332Scy if (f->fr_grhead == -1 && fr->fr_group == -1) 2511145510Sdarrenr break; 2512255332Scy if (f->fr_grhead == -1 || fr->fr_group == -1) 2513255332Scy continue; 2514255332Scy if (strcmp(f->fr_names + f->fr_grhead, 2515255332Scy fr->fr_names + fr->fr_group) == 0) 2516255332Scy break; 2517255332Scy } 2518255332Scy 2519145510Sdarrenr if (f == NULL) 2520145510Sdarrenr return; 2521145510Sdarrenr 2522145510Sdarrenr /* 2523145510Sdarrenr * Only copy down matching fields if the rules are of the same type 2524145510Sdarrenr * and are of ipf type. The only fields that are copied are those 2525145510Sdarrenr * that impact the rule parsing itself, eg. need for knowing what the 2526145510Sdarrenr * protocol should be for rules with port comparisons in them. 2527145510Sdarrenr */ 2528145510Sdarrenr if (f->fr_type != fr->fr_type || f->fr_type != FR_T_IPF) 2529145510Sdarrenr return; 2530145510Sdarrenr 2531255332Scy if (fr->fr_family == 0 && f->fr_family != 0) 2532255332Scy fr->fr_family = f->fr_family; 2533145510Sdarrenr 2534145510Sdarrenr if (fr->fr_mproto == 0 && f->fr_mproto != 0) 2535145510Sdarrenr fr->fr_mproto = f->fr_mproto; 2536145510Sdarrenr if (fr->fr_proto == 0 && f->fr_proto != 0) 2537145510Sdarrenr fr->fr_proto = f->fr_proto; 2538145510Sdarrenr 2539145510Sdarrenr if ((fr->fr_mproto == 0) && ((fr->fr_flx & FI_TCPUDP) == 0) && 2540255332Scy ((f->fr_flx & FI_TCPUDP) != 0)) { 2541145510Sdarrenr fr->fr_flx |= FI_TCPUDP; 2542255332Scy fr->fr_mflx |= FI_TCPUDP; 2543255332Scy } 2544145510Sdarrenr} 2545255332Scy 2546255332Scy 2547255332Scystatic void doipfexpr(line) 2548255332Scychar *line; 2549255332Scy{ 2550255332Scy int *array; 2551255332Scy char *error; 2552255332Scy 2553255332Scy array = parseipfexpr(line, &error); 2554255332Scy if (array == NULL) { 2555255332Scy fprintf(stderr, "%s:", error); 2556255332Scy yyerror("error parsing ipf matching expression"); 2557255332Scy return; 2558255332Scy } 2559255332Scy 2560255332Scy fr->fr_type = FR_T_IPFEXPR; 2561255332Scy fr->fr_data = array; 2562255332Scy fr->fr_dsize = array[0] * sizeof(*array); 2563255332Scy} 2564255332Scy 2565255332Scy 2566255332Scystatic void do_tuneint(varname, value) 2567255332Scychar *varname; 2568255332Scyint value; 2569255332Scy{ 2570255332Scy char buffer[80]; 2571255332Scy 2572255332Scy strncpy(buffer, varname, 60); 2573255332Scy buffer[59] = '\0'; 2574255332Scy strcat(buffer, "="); 2575255332Scy sprintf(buffer, "%u", value); 2576255332Scy ipf_dotuning(ipffd, buffer, ioctl); 2577255332Scy} 2578255332Scy 2579255332Scy 2580255332Scystatic void do_tunestr(varname, value) 2581255332Scychar *varname, *value; 2582255332Scy{ 2583255332Scy 2584255332Scy if (!strcasecmp(value, "true")) { 2585255332Scy do_tuneint(varname, 1); 2586255332Scy } else if (!strcasecmp(value, "false")) { 2587255332Scy do_tuneint(varname, 0); 2588255332Scy } else { 2589255332Scy yyerror("did not find true/false where expected"); 2590255332Scy } 2591255332Scy} 2592255332Scy 2593255332Scy 2594255332Scystatic void setifname(frp, idx, name) 2595255332Scyfrentry_t **frp; 2596255332Scyint idx; 2597255332Scychar *name; 2598255332Scy{ 2599255332Scy int pos; 2600255332Scy 2601255332Scy pos = addname(frp, name); 2602255332Scy if (pos == -1) 2603255332Scy return; 2604255332Scy (*frp)->fr_ifnames[idx] = pos; 2605255332Scy} 2606255332Scy 2607255332Scy 2608255332Scystatic int addname(frp, name) 2609255332Scyfrentry_t **frp; 2610255332Scychar *name; 2611255332Scy{ 2612255332Scy frentry_t *f; 2613255332Scy int nlen; 2614255332Scy int pos; 2615255332Scy 2616255332Scy nlen = strlen(name) + 1; 2617255332Scy f = realloc(*frp, (*frp)->fr_size + nlen); 2618255332Scy if (*frp == frc) 2619255332Scy frc = f; 2620255332Scy *frp = f; 2621255332Scy if (f == NULL) 2622255332Scy return -1; 2623255332Scy if (f->fr_pnext != NULL) 2624255332Scy *f->fr_pnext = f; 2625255332Scy f->fr_size += nlen; 2626255332Scy pos = f->fr_namelen; 2627255332Scy f->fr_namelen += nlen; 2628255332Scy strcpy(f->fr_names + pos, name); 2629255332Scy f->fr_names[f->fr_namelen] = '\0'; 2630255332Scy return pos; 2631255332Scy} 2632255332Scy 2633255332Scy 2634255332Scystatic frentry_t *allocfr() 2635255332Scy{ 2636255332Scy frentry_t *fr; 2637255332Scy 2638255332Scy fr = calloc(1, sizeof(*fr)); 2639255332Scy if (fr != NULL) { 2640255332Scy fr->fr_size = sizeof(*fr); 2641255332Scy fr->fr_comment = -1; 2642255332Scy fr->fr_group = -1; 2643255332Scy fr->fr_grhead = -1; 2644255332Scy fr->fr_icmphead = -1; 2645255332Scy fr->fr_ifnames[0] = -1; 2646255332Scy fr->fr_ifnames[1] = -1; 2647255332Scy fr->fr_ifnames[2] = -1; 2648255332Scy fr->fr_ifnames[3] = -1; 2649255332Scy fr->fr_tif.fd_name = -1; 2650255332Scy fr->fr_rif.fd_name = -1; 2651255332Scy fr->fr_dif.fd_name = -1; 2652255332Scy } 2653255332Scy return fr; 2654255332Scy} 2655255332Scy 2656255332Scy 2657255332Scystatic void setgroup(frp, name) 2658255332Scyfrentry_t **frp; 2659255332Scychar *name; 2660255332Scy{ 2661255332Scy int pos; 2662255332Scy 2663255332Scy pos = addname(frp, name); 2664255332Scy if (pos == -1) 2665255332Scy return; 2666255332Scy (*frp)->fr_group = pos; 2667255332Scy} 2668255332Scy 2669255332Scy 2670255332Scystatic void setgrhead(frp, name) 2671255332Scyfrentry_t **frp; 2672255332Scychar *name; 2673255332Scy{ 2674255332Scy int pos; 2675255332Scy 2676255332Scy pos = addname(frp, name); 2677255332Scy if (pos == -1) 2678255332Scy return; 2679255332Scy (*frp)->fr_grhead = pos; 2680255332Scy} 2681255332Scy 2682255332Scy 2683255332Scystatic void seticmphead(frp, name) 2684255332Scyfrentry_t **frp; 2685255332Scychar *name; 2686255332Scy{ 2687255332Scy int pos; 2688255332Scy 2689255332Scy pos = addname(frp, name); 2690255332Scy if (pos == -1) 2691255332Scy return; 2692255332Scy (*frp)->fr_icmphead = pos; 2693255332Scy} 2694255332Scy 2695255332Scy 2696255332Scystatic void 2697255332Scybuild_dstaddr_af(fp, ptr) 2698255332Scy frentry_t *fp; 2699255332Scy void *ptr; 2700255332Scy{ 2701255332Scy struct ipp_s *ipp = ptr; 2702255332Scy frentry_t *f = fp; 2703255332Scy 2704255332Scy if (f->fr_family != AF_UNSPEC && ipp->f == AF_UNSPEC) { 2705255332Scy ipp->f = f->fr_family; 2706255332Scy ipp->v = f->fr_ip.fi_v; 2707255332Scy } 2708255332Scy if (ipp->f == AF_INET) 2709255332Scy ipp->v = 4; 2710255332Scy else if (ipp->f == AF_INET6) 2711255332Scy ipp->v = 6; 2712255332Scy 2713255332Scy for (; f != NULL; f = f->fr_next) { 2714255332Scy f->fr_ip.fi_dst = ipp->a; 2715255332Scy f->fr_mip.fi_dst = ipp->m; 2716255332Scy f->fr_family = ipp->f; 2717255332Scy f->fr_ip.fi_v = ipp->v; 2718255332Scy f->fr_mip.fi_v = 0xf; 2719255332Scy f->fr_datype = ipp->type; 2720255332Scy if (ipp->ifpos != -1) 2721255332Scy f->fr_ipf->fri_difpidx = ipp->ifpos; 2722255332Scy } 2723255332Scy fr = NULL; 2724255332Scy} 2725255332Scy 2726255332Scy 2727255332Scystatic void 2728255332Scybuild_srcaddr_af(fp, ptr) 2729255332Scy frentry_t *fp; 2730255332Scy void *ptr; 2731255332Scy{ 2732255332Scy struct ipp_s *ipp = ptr; 2733255332Scy frentry_t *f = fp; 2734255332Scy 2735255332Scy if (f->fr_family != AF_UNSPEC && ipp->f == AF_UNSPEC) { 2736255332Scy ipp->f = f->fr_family; 2737255332Scy ipp->v = f->fr_ip.fi_v; 2738255332Scy } 2739255332Scy if (ipp->f == AF_INET) 2740255332Scy ipp->v = 4; 2741255332Scy else if (ipp->f == AF_INET6) 2742255332Scy ipp->v = 6; 2743255332Scy 2744255332Scy for (; f != NULL; f = f->fr_next) { 2745255332Scy f->fr_ip.fi_src = ipp->a; 2746255332Scy f->fr_mip.fi_src = ipp->m; 2747255332Scy f->fr_family = ipp->f; 2748255332Scy f->fr_ip.fi_v = ipp->v; 2749255332Scy f->fr_mip.fi_v = 0xf; 2750255332Scy f->fr_satype = ipp->type; 2751255332Scy f->fr_ipf->fri_sifpidx = ipp->ifpos; 2752255332Scy } 2753255332Scy fr = NULL; 2754255332Scy} 2755