1 /* $OpenBSD: gencode.c,v 1.15 2002/02/19 19:39:37 millert Exp $ */ 2 3 /* 4 * Copyright (c) 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998 5 * The Regents of the University of California. All rights reserved. 6 * 7 * Redistribution and use in source and binary forms, with or without 8 * modification, are permitted provided that: (1) source code distributions 9 * retain the above copyright notice and this paragraph in its entirety, (2) 10 * distributions including binary code include the above copyright notice and 11 * this paragraph in its entirety in the documentation or other materials 12 * provided with the distribution, and (3) all advertising materials mentioning 13 * features or use of this software display the following acknowledgement: 14 * ``This product includes software developed by the University of California, 15 * Lawrence Berkeley Laboratory and its contributors.'' Neither the name of 16 * the University nor the names of its contributors may be used to endorse 17 * or promote products derived from this software without specific prior 18 * written permission. 19 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED 20 * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF 21 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. 22 */ 23 #ifndef lint 24 static const char rcsid[] = 25 "@(#) $Header: /home/cvs/src/lib/libpcap/gencode.c,v 1.15 2002/02/19 19:39:37 millert Exp $ (LBL)"; 26 #endif 27 28 #include <sys/types.h> 29 #include <sys/socket.h> 30 #include <sys/time.h> 31 32 struct mbuf; 33 struct rtentry; 34 35 #include <net/if.h> 36 37 #include <netinet/in.h> 38 #include <netinet/if_ether.h> 39 #include <netinet/if_arc.h> 40 41 #include <stdlib.h> 42 #include <memory.h> 43 #include <setjmp.h> 44 #include <stdarg.h> 45 46 #include "pcap-int.h" 47 48 #include "ethertype.h" 49 #include "gencode.h" 50 #include "ppp.h" 51 #include <pcap-namedb.h> 52 #ifdef INET6 53 #include <netdb.h> 54 #include <sys/socket.h> 55 #endif /*INET6*/ 56 57 #ifdef HAVE_OS_PROTO_H 58 #include "os-proto.h" 59 #endif 60 61 #define JMP(c) ((c)|BPF_JMP|BPF_K) 62 63 /* Locals */ 64 static jmp_buf top_ctx; 65 static pcap_t *bpf_pcap; 66 67 /* XXX */ 68 #ifdef PCAP_FDDIPAD 69 int pcap_fddipad = PCAP_FDDIPAD; 70 #else 71 int pcap_fddipad; 72 #endif 73 74 /* VARARGS */ 75 __dead void 76 bpf_error(const char *fmt, ...) 77 { 78 va_list ap; 79 80 va_start(ap, fmt); 81 if (bpf_pcap != NULL) 82 (void)vsnprintf(pcap_geterr(bpf_pcap), PCAP_ERRBUF_SIZE, 83 fmt, ap); 84 va_end(ap); 85 longjmp(top_ctx, 1); 86 /* NOTREACHED */ 87 } 88 89 static void init_linktype(int); 90 91 static int alloc_reg(void); 92 static void free_reg(int); 93 94 static struct block *root; 95 96 /* 97 * We divy out chunks of memory rather than call malloc each time so 98 * we don't have to worry about leaking memory. It's probably 99 * not a big deal if all this memory was wasted but it this ever 100 * goes into a library that would probably not be a good idea. 101 */ 102 #define NCHUNKS 16 103 #define CHUNK0SIZE 1024 104 struct chunk { 105 u_int n_left; 106 void *m; 107 }; 108 109 static struct chunk chunks[NCHUNKS]; 110 static int cur_chunk; 111 112 static void *newchunk(u_int); 113 static void freechunks(void); 114 static __inline struct block *new_block(int); 115 static __inline struct slist *new_stmt(int); 116 static struct block *gen_retblk(int); 117 static __inline void syntax(void); 118 119 static void backpatch(struct block *, struct block *); 120 static void merge(struct block *, struct block *); 121 static struct block *gen_cmp(u_int, u_int, bpf_int32); 122 static struct block *gen_mcmp(u_int, u_int, bpf_int32, bpf_u_int32); 123 static struct block *gen_bcmp(u_int, u_int, const u_char *); 124 static struct block *gen_uncond(int); 125 static __inline struct block *gen_true(void); 126 static __inline struct block *gen_false(void); 127 static struct block *gen_linktype(int); 128 static struct block *gen_hostop(bpf_u_int32, bpf_u_int32, int, int, u_int, u_int); 129 #ifdef INET6 130 static struct block *gen_hostop6(struct in6_addr *, struct in6_addr *, int, int, u_int, u_int); 131 #endif 132 static struct block *gen_ahostop(const u_char *, int); 133 static struct block *gen_ehostop(const u_char *, int); 134 static struct block *gen_fhostop(const u_char *, int); 135 static struct block *gen_dnhostop(bpf_u_int32, int, u_int); 136 static struct block *gen_host(bpf_u_int32, bpf_u_int32, int, int); 137 #ifdef INET6 138 static struct block *gen_host6(struct in6_addr *, struct in6_addr *, int, int); 139 #endif 140 #ifndef INET6 141 static struct block *gen_gateway(const u_char *, bpf_u_int32 **, int, int); 142 #endif 143 static struct block *gen_ipfrag(void); 144 static struct block *gen_portatom(int, bpf_int32); 145 #ifdef INET6 146 static struct block *gen_portatom6(int, bpf_int32); 147 #endif 148 struct block *gen_portop(int, int, int); 149 static struct block *gen_port(int, int, int); 150 #ifdef INET6 151 struct block *gen_portop6(int, int, int); 152 static struct block *gen_port6(int, int, int); 153 #endif 154 static int lookup_proto(const char *, int); 155 static struct block *gen_protochain(int, int, int); 156 static struct block *gen_proto(int, int, int); 157 static struct slist *xfer_to_x(struct arth *); 158 static struct slist *xfer_to_a(struct arth *); 159 static struct block *gen_len(int, int); 160 161 static void * 162 newchunk(n) 163 u_int n; 164 { 165 struct chunk *cp; 166 int k, size; 167 168 /* XXX Round to structure boundary. */ 169 n = ALIGN(n); 170 171 cp = &chunks[cur_chunk]; 172 if (n > cp->n_left) { 173 ++cp, k = ++cur_chunk; 174 if (k >= NCHUNKS) 175 bpf_error("out of memory"); 176 size = CHUNK0SIZE << k; 177 cp->m = (void *)malloc(size); 178 memset((char *)cp->m, 0, size); 179 cp->n_left = size; 180 if (n > size) 181 bpf_error("out of memory"); 182 } 183 cp->n_left -= n; 184 return (void *)((char *)cp->m + cp->n_left); 185 } 186 187 static void 188 freechunks() 189 { 190 int i; 191 192 cur_chunk = 0; 193 for (i = 0; i < NCHUNKS; ++i) 194 if (chunks[i].m != NULL) { 195 free(chunks[i].m); 196 chunks[i].m = NULL; 197 } 198 } 199 200 /* 201 * A strdup whose allocations are freed after code generation is over. 202 */ 203 char * 204 sdup(s) 205 register const char *s; 206 { 207 int n = strlen(s) + 1; 208 char *cp = newchunk(n); 209 210 strlcpy(cp, s, n); 211 return (cp); 212 } 213 214 static __inline struct block * 215 new_block(code) 216 int code; 217 { 218 struct block *p; 219 220 p = (struct block *)newchunk(sizeof(*p)); 221 p->s.code = code; 222 p->head = p; 223 224 return p; 225 } 226 227 static __inline struct slist * 228 new_stmt(code) 229 int code; 230 { 231 struct slist *p; 232 233 p = (struct slist *)newchunk(sizeof(*p)); 234 p->s.code = code; 235 236 return p; 237 } 238 239 static struct block * 240 gen_retblk(v) 241 int v; 242 { 243 struct block *b = new_block(BPF_RET|BPF_K); 244 245 b->s.k = v; 246 return b; 247 } 248 249 static __inline void 250 syntax() 251 { 252 bpf_error("syntax error in filter expression"); 253 } 254 255 static bpf_u_int32 netmask; 256 static int snaplen; 257 int no_optimize; 258 259 int 260 pcap_compile(pcap_t *p, struct bpf_program *program, 261 char *buf, int optimize, bpf_u_int32 mask) 262 { 263 extern int n_errors; 264 int len; 265 266 no_optimize = 0; 267 n_errors = 0; 268 root = NULL; 269 bpf_pcap = p; 270 if (setjmp(top_ctx)) { 271 freechunks(); 272 return (-1); 273 } 274 275 netmask = mask; 276 snaplen = pcap_snapshot(p); 277 278 lex_init(buf ? buf : ""); 279 init_linktype(pcap_datalink(p)); 280 (void)pcap_parse(); 281 282 if (n_errors) 283 syntax(); 284 285 if (root == NULL) 286 root = gen_retblk(snaplen); 287 288 if (optimize && !no_optimize) { 289 bpf_optimize(&root); 290 if (root == NULL || 291 (root->s.code == (BPF_RET|BPF_K) && root->s.k == 0)) 292 bpf_error("expression rejects all packets"); 293 } 294 program->bf_insns = icode_to_fcode(root, &len); 295 program->bf_len = len; 296 297 freechunks(); 298 return (0); 299 } 300 301 /* 302 * entry point for using the compiler with no pcap open 303 * pass in all the stuff that is needed explicitly instead. 304 */ 305 int 306 pcap_compile_nopcap(int snaplen_arg, int linktype_arg, 307 struct bpf_program *program, 308 char *buf, int optimize, bpf_u_int32 mask) 309 { 310 extern int n_errors; 311 int len; 312 313 n_errors = 0; 314 root = NULL; 315 bpf_pcap = NULL; 316 if (setjmp(top_ctx)) { 317 freechunks(); 318 return (-1); 319 } 320 321 netmask = mask; 322 323 /* XXX needed? I don't grok the use of globals here. */ 324 snaplen = snaplen_arg; 325 326 lex_init(buf ? buf : ""); 327 init_linktype(linktype_arg); 328 (void)pcap_parse(); 329 330 if (n_errors) 331 syntax(); 332 333 if (root == NULL) 334 root = gen_retblk(snaplen_arg); 335 336 if (optimize) { 337 bpf_optimize(&root); 338 if (root == NULL || 339 (root->s.code == (BPF_RET|BPF_K) && root->s.k == 0)) 340 bpf_error("expression rejects all packets"); 341 } 342 program->bf_insns = icode_to_fcode(root, &len); 343 program->bf_len = len; 344 345 freechunks(); 346 return (0); 347 } 348 349 /* 350 * Clean up a "struct bpf_program" by freeing all the memory allocated 351 * in it. 352 */ 353 void 354 pcap_freecode(struct bpf_program *program) 355 { 356 program->bf_len = 0; 357 if (program->bf_insns != NULL) { 358 free((char *)program->bf_insns); 359 program->bf_insns = NULL; 360 } 361 } 362 363 /* 364 * Backpatch the blocks in 'list' to 'target'. The 'sense' field indicates 365 * which of the jt and jf fields has been resolved and which is a pointer 366 * back to another unresolved block (or nil). At least one of the fields 367 * in each block is already resolved. 368 */ 369 static void 370 backpatch(list, target) 371 struct block *list, *target; 372 { 373 struct block *next; 374 375 while (list) { 376 if (!list->sense) { 377 next = JT(list); 378 JT(list) = target; 379 } else { 380 next = JF(list); 381 JF(list) = target; 382 } 383 list = next; 384 } 385 } 386 387 /* 388 * Merge the lists in b0 and b1, using the 'sense' field to indicate 389 * which of jt and jf is the link. 390 */ 391 static void 392 merge(b0, b1) 393 struct block *b0, *b1; 394 { 395 register struct block **p = &b0; 396 397 /* Find end of list. */ 398 while (*p) 399 p = !((*p)->sense) ? &JT(*p) : &JF(*p); 400 401 /* Concatenate the lists. */ 402 *p = b1; 403 } 404 405 void 406 finish_parse(p) 407 struct block *p; 408 { 409 backpatch(p, gen_retblk(snaplen)); 410 p->sense = !p->sense; 411 backpatch(p, gen_retblk(0)); 412 root = p->head; 413 } 414 415 void 416 gen_and(b0, b1) 417 struct block *b0, *b1; 418 { 419 backpatch(b0, b1->head); 420 b0->sense = !b0->sense; 421 b1->sense = !b1->sense; 422 merge(b1, b0); 423 b1->sense = !b1->sense; 424 b1->head = b0->head; 425 } 426 427 void 428 gen_or(b0, b1) 429 struct block *b0, *b1; 430 { 431 b0->sense = !b0->sense; 432 backpatch(b0, b1->head); 433 b0->sense = !b0->sense; 434 merge(b1, b0); 435 b1->head = b0->head; 436 } 437 438 void 439 gen_not(b) 440 struct block *b; 441 { 442 b->sense = !b->sense; 443 } 444 445 static struct block * 446 gen_cmp(offset, size, v) 447 u_int offset, size; 448 bpf_int32 v; 449 { 450 struct slist *s; 451 struct block *b; 452 453 s = new_stmt(BPF_LD|BPF_ABS|size); 454 s->s.k = offset; 455 456 b = new_block(JMP(BPF_JEQ)); 457 b->stmts = s; 458 b->s.k = v; 459 460 return b; 461 } 462 463 static struct block * 464 gen_mcmp(offset, size, v, mask) 465 u_int offset, size; 466 bpf_int32 v; 467 bpf_u_int32 mask; 468 { 469 struct block *b = gen_cmp(offset, size, v); 470 struct slist *s; 471 472 if (mask != 0xffffffff) { 473 s = new_stmt(BPF_ALU|BPF_AND|BPF_K); 474 s->s.k = mask; 475 b->stmts->next = s; 476 } 477 return b; 478 } 479 480 static struct block * 481 gen_bcmp(offset, size, v) 482 register u_int offset, size; 483 register const u_char *v; 484 { 485 register struct block *b, *tmp; 486 487 b = NULL; 488 while (size >= 4) { 489 register const u_char *p = &v[size - 4]; 490 bpf_int32 w = ((bpf_int32)p[0] << 24) | 491 ((bpf_int32)p[1] << 16) | ((bpf_int32)p[2] << 8) | p[3]; 492 493 tmp = gen_cmp(offset + size - 4, BPF_W, w); 494 if (b != NULL) 495 gen_and(b, tmp); 496 b = tmp; 497 size -= 4; 498 } 499 while (size >= 2) { 500 register const u_char *p = &v[size - 2]; 501 bpf_int32 w = ((bpf_int32)p[0] << 8) | p[1]; 502 503 tmp = gen_cmp(offset + size - 2, BPF_H, w); 504 if (b != NULL) 505 gen_and(b, tmp); 506 b = tmp; 507 size -= 2; 508 } 509 if (size > 0) { 510 tmp = gen_cmp(offset, BPF_B, (bpf_int32)v[0]); 511 if (b != NULL) 512 gen_and(b, tmp); 513 b = tmp; 514 } 515 return b; 516 } 517 518 /* 519 * Various code constructs need to know the layout of the data link 520 * layer. These variables give the necessary offsets. off_linktype 521 * is set to -1 for no encapsulation, in which case, IP is assumed. 522 */ 523 static u_int off_linktype; 524 static u_int off_nl; 525 static int linktype; 526 527 static void 528 init_linktype(type) 529 int type; 530 { 531 linktype = type; 532 533 switch (type) { 534 535 case DLT_ARCNET: 536 off_linktype = 2; 537 off_nl = 6; /* XXX in reality, variable! */ 538 return; 539 540 case DLT_EN10MB: 541 off_linktype = 12; 542 off_nl = 14; 543 return; 544 545 case DLT_SLIP: 546 /* 547 * SLIP doesn't have a link level type. The 16 byte 548 * header is hacked into our SLIP driver. 549 */ 550 off_linktype = -1; 551 off_nl = 16; 552 return; 553 554 case DLT_SLIP_BSDOS: 555 /* XXX this may be the same as the DLT_PPP_BSDOS case */ 556 off_linktype = -1; 557 /* XXX end */ 558 off_nl = 24; 559 return; 560 561 case DLT_NULL: 562 off_linktype = 0; 563 off_nl = 4; 564 return; 565 566 case DLT_PPP: 567 off_linktype = 2; 568 off_nl = 4; 569 return; 570 571 case DLT_PPP_BSDOS: 572 off_linktype = 5; 573 off_nl = 24; 574 return; 575 576 case DLT_FDDI: 577 /* 578 * FDDI doesn't really have a link-level type field. 579 * We assume that SSAP = SNAP is being used and pick 580 * out the encapsulated Ethernet type. 581 */ 582 off_linktype = 19; 583 #ifdef PCAP_FDDIPAD 584 off_linktype += pcap_fddipad; 585 #endif 586 off_nl = 21; 587 #ifdef PCAP_FDDIPAD 588 off_nl += pcap_fddipad; 589 #endif 590 return; 591 592 case DLT_IEEE802: 593 off_linktype = 20; 594 off_nl = 22; 595 return; 596 597 case DLT_ATM_RFC1483: 598 /* 599 * assume routed, non-ISO PDUs 600 * (i.e., LLC = 0xAA-AA-03, OUT = 0x00-00-00) 601 */ 602 off_linktype = 6; 603 off_nl = 8; 604 return; 605 606 case DLT_LOOP: 607 off_linktype = -1; 608 off_nl = 4; 609 return; 610 611 case DLT_ENC: 612 off_linktype = -1; 613 off_nl = 12; 614 return; 615 616 case DLT_PFLOG: 617 off_linktype = -1; 618 off_nl = 28; 619 return; 620 621 case DLT_RAW: 622 off_linktype = -1; 623 off_nl = 0; 624 return; 625 } 626 bpf_error("unknown data link type 0x%x", linktype); 627 /* NOTREACHED */ 628 } 629 630 static struct block * 631 gen_uncond(rsense) 632 int rsense; 633 { 634 struct block *b; 635 struct slist *s; 636 637 s = new_stmt(BPF_LD|BPF_IMM); 638 s->s.k = !rsense; 639 b = new_block(JMP(BPF_JEQ)); 640 b->stmts = s; 641 642 return b; 643 } 644 645 static __inline struct block * 646 gen_true() 647 { 648 return gen_uncond(1); 649 } 650 651 static __inline struct block * 652 gen_false() 653 { 654 return gen_uncond(0); 655 } 656 657 static struct block * 658 gen_linktype(proto) 659 register int proto; 660 { 661 struct block *b0, *b1; 662 663 /* If we're not using encapsulation and checking for IP, we're done */ 664 if (off_linktype == -1 && proto == ETHERTYPE_IP) 665 return gen_true(); 666 #ifdef INET6 667 /* this isn't the right thing to do, but sometimes necessary */ 668 if (off_linktype == -1 && proto == ETHERTYPE_IPV6) 669 return gen_true(); 670 #endif 671 672 switch (linktype) { 673 674 case DLT_SLIP: 675 return gen_false(); 676 677 case DLT_PPP: 678 if (proto == ETHERTYPE_IP) 679 proto = PPP_IP; /* XXX was 0x21 */ 680 #ifdef INET6 681 else if (proto == ETHERTYPE_IPV6) 682 proto = PPP_IPV6; 683 #endif 684 break; 685 686 case DLT_PPP_BSDOS: 687 switch (proto) { 688 689 case ETHERTYPE_IP: 690 b0 = gen_cmp(off_linktype, BPF_H, PPP_IP); 691 b1 = gen_cmp(off_linktype, BPF_H, PPP_VJC); 692 gen_or(b0, b1); 693 b0 = gen_cmp(off_linktype, BPF_H, PPP_VJNC); 694 gen_or(b1, b0); 695 return b0; 696 697 #ifdef INET6 698 case ETHERTYPE_IPV6: 699 proto = PPP_IPV6; 700 /* more to go? */ 701 break; 702 #endif /* INET6 */ 703 704 case ETHERTYPE_DN: 705 proto = PPP_DECNET; 706 break; 707 708 case ETHERTYPE_ATALK: 709 proto = PPP_APPLE; 710 break; 711 712 case ETHERTYPE_NS: 713 proto = PPP_NS; 714 break; 715 } 716 break; 717 718 case DLT_LOOP: 719 case DLT_ENC: 720 case DLT_PFLOG: 721 case DLT_NULL: 722 /* XXX */ 723 if (proto == ETHERTYPE_IP) 724 return (gen_cmp(0, BPF_W, (bpf_int32)htonl(AF_INET))); 725 #ifdef INET6 726 else if (proto == ETHERTYPE_IPV6) 727 return (gen_cmp(0, BPF_W, (bpf_int32)htonl(AF_INET6))); 728 #endif /* INET6 */ 729 else 730 return gen_false(); 731 break; 732 case DLT_ARCNET: 733 /* 734 * XXX should we check for first fragment if the protocol 735 * uses PHDS? 736 */ 737 switch(proto) { 738 default: 739 return gen_false(); 740 #ifdef INET6 741 case ETHERTYPE_IPV6: 742 return(gen_cmp(2, BPF_B, 743 (bpf_int32)htonl(ARCTYPE_INET6))); 744 #endif /* INET6 */ 745 case ETHERTYPE_IP: 746 b0 = gen_cmp(2, BPF_B, (bpf_int32)htonl(ARCTYPE_IP)); 747 b1 = gen_cmp(2, BPF_B, 748 (bpf_int32)htonl(ARCTYPE_IP_OLD)); 749 gen_or(b0, b1); 750 return(b1); 751 case ETHERTYPE_ARP: 752 b0 = gen_cmp(2, BPF_B, (bpf_int32)htonl(ARCTYPE_ARP)); 753 b1 = gen_cmp(2, BPF_B, 754 (bpf_int32)htonl(ARCTYPE_ARP_OLD)); 755 gen_or(b0, b1); 756 return(b1); 757 case ETHERTYPE_REVARP: 758 return(gen_cmp(2, BPF_B, 759 (bpf_int32)htonl(ARCTYPE_REVARP))); 760 case ETHERTYPE_ATALK: 761 return(gen_cmp(2, BPF_B, 762 (bpf_int32)htonl(ARCTYPE_ATALK))); 763 } 764 } 765 return gen_cmp(off_linktype, BPF_H, (bpf_int32)proto); 766 } 767 768 static struct block * 769 gen_hostop(addr, mask, dir, proto, src_off, dst_off) 770 bpf_u_int32 addr; 771 bpf_u_int32 mask; 772 int dir, proto; 773 u_int src_off, dst_off; 774 { 775 struct block *b0, *b1; 776 u_int offset; 777 778 switch (dir) { 779 780 case Q_SRC: 781 offset = src_off; 782 break; 783 784 case Q_DST: 785 offset = dst_off; 786 break; 787 788 case Q_AND: 789 b0 = gen_hostop(addr, mask, Q_SRC, proto, src_off, dst_off); 790 b1 = gen_hostop(addr, mask, Q_DST, proto, src_off, dst_off); 791 gen_and(b0, b1); 792 return b1; 793 794 case Q_OR: 795 case Q_DEFAULT: 796 b0 = gen_hostop(addr, mask, Q_SRC, proto, src_off, dst_off); 797 b1 = gen_hostop(addr, mask, Q_DST, proto, src_off, dst_off); 798 gen_or(b0, b1); 799 return b1; 800 801 default: 802 abort(); 803 } 804 b0 = gen_linktype(proto); 805 b1 = gen_mcmp(offset, BPF_W, (bpf_int32)addr, mask); 806 gen_and(b0, b1); 807 return b1; 808 } 809 810 #ifdef INET6 811 static struct block * 812 gen_hostop6(addr, mask, dir, proto, src_off, dst_off) 813 struct in6_addr *addr; 814 struct in6_addr *mask; 815 int dir, proto; 816 u_int src_off, dst_off; 817 { 818 struct block *b0, *b1; 819 u_int offset; 820 u_int32_t *a, *m; 821 822 switch (dir) { 823 824 case Q_SRC: 825 offset = src_off; 826 break; 827 828 case Q_DST: 829 offset = dst_off; 830 break; 831 832 case Q_AND: 833 b0 = gen_hostop6(addr, mask, Q_SRC, proto, src_off, dst_off); 834 b1 = gen_hostop6(addr, mask, Q_DST, proto, src_off, dst_off); 835 gen_and(b0, b1); 836 return b1; 837 838 case Q_OR: 839 case Q_DEFAULT: 840 b0 = gen_hostop6(addr, mask, Q_SRC, proto, src_off, dst_off); 841 b1 = gen_hostop6(addr, mask, Q_DST, proto, src_off, dst_off); 842 gen_or(b0, b1); 843 return b1; 844 845 default: 846 abort(); 847 } 848 /* this order is important */ 849 a = (u_int32_t *)addr; 850 m = (u_int32_t *)mask; 851 b1 = gen_mcmp(offset + 12, BPF_W, ntohl(a[3]), ntohl(m[3])); 852 b0 = gen_mcmp(offset + 8, BPF_W, ntohl(a[2]), ntohl(m[2])); 853 gen_and(b0, b1); 854 b0 = gen_mcmp(offset + 4, BPF_W, ntohl(a[1]), ntohl(m[1])); 855 gen_and(b0, b1); 856 b0 = gen_mcmp(offset + 0, BPF_W, ntohl(a[0]), ntohl(m[0])); 857 gen_and(b0, b1); 858 b0 = gen_linktype(proto); 859 gen_and(b0, b1); 860 return b1; 861 } 862 #endif /*INET6*/ 863 864 static struct block * 865 gen_ehostop(eaddr, dir) 866 register const u_char *eaddr; 867 register int dir; 868 { 869 struct block *b0, *b1; 870 871 switch (dir) { 872 case Q_SRC: 873 return gen_bcmp(6, 6, eaddr); 874 875 case Q_DST: 876 return gen_bcmp(0, 6, eaddr); 877 878 case Q_AND: 879 b0 = gen_ehostop(eaddr, Q_SRC); 880 b1 = gen_ehostop(eaddr, Q_DST); 881 gen_and(b0, b1); 882 return b1; 883 884 case Q_DEFAULT: 885 case Q_OR: 886 b0 = gen_ehostop(eaddr, Q_SRC); 887 b1 = gen_ehostop(eaddr, Q_DST); 888 gen_or(b0, b1); 889 return b1; 890 } 891 abort(); 892 /* NOTREACHED */ 893 } 894 895 /* 896 * Like gen_ehostop, but for DLT_FDDI 897 */ 898 static struct block * 899 gen_fhostop(eaddr, dir) 900 register const u_char *eaddr; 901 register int dir; 902 { 903 struct block *b0, *b1; 904 905 switch (dir) { 906 case Q_SRC: 907 #ifdef PCAP_FDDIPAD 908 return gen_bcmp(6 + 1 + pcap_fddipad, 6, eaddr); 909 #else 910 return gen_bcmp(6 + 1, 6, eaddr); 911 #endif 912 913 case Q_DST: 914 #ifdef PCAP_FDDIPAD 915 return gen_bcmp(0 + 1 + pcap_fddipad, 6, eaddr); 916 #else 917 return gen_bcmp(0 + 1, 6, eaddr); 918 #endif 919 920 case Q_AND: 921 b0 = gen_fhostop(eaddr, Q_SRC); 922 b1 = gen_fhostop(eaddr, Q_DST); 923 gen_and(b0, b1); 924 return b1; 925 926 case Q_DEFAULT: 927 case Q_OR: 928 b0 = gen_fhostop(eaddr, Q_SRC); 929 b1 = gen_fhostop(eaddr, Q_DST); 930 gen_or(b0, b1); 931 return b1; 932 } 933 abort(); 934 /* NOTREACHED */ 935 } 936 937 /* 938 * This is quite tricky because there may be pad bytes in front of the 939 * DECNET header, and then there are two possible data packet formats that 940 * carry both src and dst addresses, plus 5 packet types in a format that 941 * carries only the src node, plus 2 types that use a different format and 942 * also carry just the src node. 943 * 944 * Yuck. 945 * 946 * Instead of doing those all right, we just look for data packets with 947 * 0 or 1 bytes of padding. If you want to look at other packets, that 948 * will require a lot more hacking. 949 * 950 * To add support for filtering on DECNET "areas" (network numbers) 951 * one would want to add a "mask" argument to this routine. That would 952 * make the filter even more inefficient, although one could be clever 953 * and not generate masking instructions if the mask is 0xFFFF. 954 */ 955 static struct block * 956 gen_dnhostop(addr, dir, base_off) 957 bpf_u_int32 addr; 958 int dir; 959 u_int base_off; 960 { 961 struct block *b0, *b1, *b2, *tmp; 962 u_int offset_lh; /* offset if long header is received */ 963 u_int offset_sh; /* offset if short header is received */ 964 965 switch (dir) { 966 967 case Q_DST: 968 offset_sh = 1; /* follows flags */ 969 offset_lh = 7; /* flgs,darea,dsubarea,HIORD */ 970 break; 971 972 case Q_SRC: 973 offset_sh = 3; /* follows flags, dstnode */ 974 offset_lh = 15; /* flgs,darea,dsubarea,did,sarea,ssub,HIORD */ 975 break; 976 977 case Q_AND: 978 /* Inefficient because we do our Calvinball dance twice */ 979 b0 = gen_dnhostop(addr, Q_SRC, base_off); 980 b1 = gen_dnhostop(addr, Q_DST, base_off); 981 gen_and(b0, b1); 982 return b1; 983 984 case Q_OR: 985 case Q_DEFAULT: 986 /* Inefficient because we do our Calvinball dance twice */ 987 b0 = gen_dnhostop(addr, Q_SRC, base_off); 988 b1 = gen_dnhostop(addr, Q_DST, base_off); 989 gen_or(b0, b1); 990 return b1; 991 992 default: 993 abort(); 994 } 995 b0 = gen_linktype(ETHERTYPE_DN); 996 /* Check for pad = 1, long header case */ 997 tmp = gen_mcmp(base_off + 2, BPF_H, 998 (bpf_int32)ntohs(0x0681), (bpf_int32)ntohs(0x07FF)); 999 b1 = gen_cmp(base_off + 2 + 1 + offset_lh, 1000 BPF_H, (bpf_int32)ntohs(addr)); 1001 gen_and(tmp, b1); 1002 /* Check for pad = 0, long header case */ 1003 tmp = gen_mcmp(base_off + 2, BPF_B, (bpf_int32)0x06, (bpf_int32)0x7); 1004 b2 = gen_cmp(base_off + 2 + offset_lh, BPF_H, (bpf_int32)ntohs(addr)); 1005 gen_and(tmp, b2); 1006 gen_or(b2, b1); 1007 /* Check for pad = 1, short header case */ 1008 tmp = gen_mcmp(base_off + 2, BPF_H, 1009 (bpf_int32)ntohs(0x0281), (bpf_int32)ntohs(0x07FF)); 1010 b2 = gen_cmp(base_off + 2 + 1 + offset_sh, 1011 BPF_H, (bpf_int32)ntohs(addr)); 1012 gen_and(tmp, b2); 1013 gen_or(b2, b1); 1014 /* Check for pad = 0, short header case */ 1015 tmp = gen_mcmp(base_off + 2, BPF_B, (bpf_int32)0x02, (bpf_int32)0x7); 1016 b2 = gen_cmp(base_off + 2 + offset_sh, BPF_H, (bpf_int32)ntohs(addr)); 1017 gen_and(tmp, b2); 1018 gen_or(b2, b1); 1019 1020 /* Combine with test for linktype */ 1021 gen_and(b0, b1); 1022 return b1; 1023 } 1024 1025 static struct block * 1026 gen_host(addr, mask, proto, dir) 1027 bpf_u_int32 addr; 1028 bpf_u_int32 mask; 1029 int proto; 1030 int dir; 1031 { 1032 struct block *b0, *b1; 1033 1034 switch (proto) { 1035 1036 case Q_DEFAULT: 1037 b0 = gen_host(addr, mask, Q_IP, dir); 1038 b1 = gen_host(addr, mask, Q_ARP, dir); 1039 gen_or(b0, b1); 1040 b0 = gen_host(addr, mask, Q_RARP, dir); 1041 gen_or(b1, b0); 1042 return b0; 1043 1044 case Q_IP: 1045 return gen_hostop(addr, mask, dir, ETHERTYPE_IP, 1046 off_nl + 12, off_nl + 16); 1047 1048 case Q_RARP: 1049 return gen_hostop(addr, mask, dir, ETHERTYPE_REVARP, 1050 off_nl + 14, off_nl + 24); 1051 1052 case Q_ARP: 1053 return gen_hostop(addr, mask, dir, ETHERTYPE_ARP, 1054 off_nl + 14, off_nl + 24); 1055 1056 case Q_TCP: 1057 bpf_error("'tcp' modifier applied to host"); 1058 1059 case Q_UDP: 1060 bpf_error("'udp' modifier applied to host"); 1061 1062 case Q_ICMP: 1063 bpf_error("'icmp' modifier applied to host"); 1064 1065 case Q_IGMP: 1066 bpf_error("'igmp' modifier applied to host"); 1067 1068 case Q_IGRP: 1069 bpf_error("'igrp' modifier applied to host"); 1070 1071 case Q_PIM: 1072 bpf_error("'pim' modifier applied to host"); 1073 1074 case Q_ATALK: 1075 bpf_error("ATALK host filtering not implemented"); 1076 1077 case Q_DECNET: 1078 return gen_dnhostop(addr, dir, off_nl); 1079 1080 case Q_SCA: 1081 bpf_error("SCA host filtering not implemented"); 1082 1083 case Q_LAT: 1084 bpf_error("LAT host filtering not implemented"); 1085 1086 case Q_MOPDL: 1087 bpf_error("MOPDL host filtering not implemented"); 1088 1089 case Q_MOPRC: 1090 bpf_error("MOPRC host filtering not implemented"); 1091 1092 #ifdef INET6 1093 case Q_IPV6: 1094 bpf_error("'ip6' modifier applied to ip host"); 1095 1096 case Q_ICMPV6: 1097 bpf_error("'icmp6' modifier applied to host"); 1098 #endif /* INET6 */ 1099 1100 case Q_AH: 1101 bpf_error("'ah' modifier applied to host"); 1102 1103 case Q_ESP: 1104 bpf_error("'esp' modifier applied to host"); 1105 1106 default: 1107 abort(); 1108 } 1109 /* NOTREACHED */ 1110 } 1111 1112 #ifdef INET6 1113 static struct block * 1114 gen_host6(addr, mask, proto, dir) 1115 struct in6_addr *addr; 1116 struct in6_addr *mask; 1117 int proto; 1118 int dir; 1119 { 1120 switch (proto) { 1121 1122 case Q_DEFAULT: 1123 return gen_host6(addr, mask, Q_IPV6, dir); 1124 1125 case Q_IP: 1126 bpf_error("'ip' modifier applied to ip6 host"); 1127 1128 case Q_RARP: 1129 bpf_error("'rarp' modifier applied to ip6 host"); 1130 1131 case Q_ARP: 1132 bpf_error("'arp' modifier applied to ip6 host"); 1133 1134 case Q_TCP: 1135 bpf_error("'tcp' modifier applied to host"); 1136 1137 case Q_UDP: 1138 bpf_error("'udp' modifier applied to host"); 1139 1140 case Q_ICMP: 1141 bpf_error("'icmp' modifier applied to host"); 1142 1143 case Q_IGMP: 1144 bpf_error("'igmp' modifier applied to host"); 1145 1146 case Q_IGRP: 1147 bpf_error("'igrp' modifier applied to host"); 1148 1149 case Q_PIM: 1150 bpf_error("'pim' modifier applied to host"); 1151 1152 case Q_ATALK: 1153 bpf_error("ATALK host filtering not implemented"); 1154 1155 case Q_DECNET: 1156 bpf_error("'decnet' modifier applied to ip6 host"); 1157 1158 case Q_SCA: 1159 bpf_error("SCA host filtering not implemented"); 1160 1161 case Q_LAT: 1162 bpf_error("LAT host filtering not implemented"); 1163 1164 case Q_MOPDL: 1165 bpf_error("MOPDL host filtering not implemented"); 1166 1167 case Q_MOPRC: 1168 bpf_error("MOPRC host filtering not implemented"); 1169 1170 case Q_IPV6: 1171 return gen_hostop6(addr, mask, dir, ETHERTYPE_IPV6, 1172 off_nl + 8, off_nl + 24); 1173 1174 case Q_ICMPV6: 1175 bpf_error("'icmp6' modifier applied to host"); 1176 1177 case Q_AH: 1178 bpf_error("'ah' modifier applied to host"); 1179 1180 case Q_ESP: 1181 bpf_error("'esp' modifier applied to host"); 1182 1183 default: 1184 abort(); 1185 } 1186 /* NOTREACHED */ 1187 } 1188 #endif /*INET6*/ 1189 1190 #ifndef INET6 1191 static struct block * 1192 gen_gateway(eaddr, alist, proto, dir) 1193 const u_char *eaddr; 1194 bpf_u_int32 **alist; 1195 int proto; 1196 int dir; 1197 { 1198 struct block *b0, *b1, *tmp; 1199 1200 if (dir != 0) 1201 bpf_error("direction applied to 'gateway'"); 1202 1203 switch (proto) { 1204 case Q_DEFAULT: 1205 case Q_IP: 1206 case Q_ARP: 1207 case Q_RARP: 1208 if (linktype == DLT_EN10MB) 1209 b0 = gen_ehostop(eaddr, Q_OR); 1210 else if (linktype == DLT_FDDI) 1211 b0 = gen_fhostop(eaddr, Q_OR); 1212 else 1213 bpf_error( 1214 "'gateway' supported only on ethernet or FDDI"); 1215 1216 b1 = gen_host(**alist++, 0xffffffff, proto, Q_OR); 1217 while (*alist) { 1218 tmp = gen_host(**alist++, 0xffffffff, proto, Q_OR); 1219 gen_or(b1, tmp); 1220 b1 = tmp; 1221 } 1222 gen_not(b1); 1223 gen_and(b0, b1); 1224 return b1; 1225 } 1226 bpf_error("illegal modifier of 'gateway'"); 1227 /* NOTREACHED */ 1228 } 1229 #endif /*INET6*/ 1230 1231 struct block * 1232 gen_proto_abbrev(proto) 1233 int proto; 1234 { 1235 struct block *b0 = NULL, *b1; 1236 1237 switch (proto) { 1238 1239 case Q_TCP: 1240 b1 = gen_proto(IPPROTO_TCP, Q_IP, Q_DEFAULT); 1241 #ifdef INET6 1242 b0 = gen_proto(IPPROTO_TCP, Q_IPV6, Q_DEFAULT); 1243 gen_or(b0, b1); 1244 #endif 1245 break; 1246 1247 case Q_UDP: 1248 b1 = gen_proto(IPPROTO_UDP, Q_IP, Q_DEFAULT); 1249 #ifdef INET6 1250 b0 = gen_proto(IPPROTO_UDP, Q_IPV6, Q_DEFAULT); 1251 gen_or(b0, b1); 1252 #endif 1253 break; 1254 1255 case Q_ICMP: 1256 b1 = gen_proto(IPPROTO_ICMP, Q_IP, Q_DEFAULT); 1257 break; 1258 1259 #ifndef IPPROTO_IGMP 1260 #define IPPROTO_IGMP 2 1261 #endif 1262 1263 case Q_IGMP: 1264 b1 = gen_proto(IPPROTO_IGMP, Q_IP, Q_DEFAULT); 1265 break; 1266 1267 #ifndef IPPROTO_IGRP 1268 #define IPPROTO_IGRP 9 1269 #endif 1270 case Q_IGRP: 1271 b1 = gen_proto(IPPROTO_IGRP, Q_IP, Q_DEFAULT); 1272 break; 1273 1274 #ifndef IPPROTO_PIM 1275 #define IPPROTO_PIM 103 1276 #endif 1277 1278 case Q_PIM: 1279 b1 = gen_proto(IPPROTO_PIM, Q_IP, Q_DEFAULT); 1280 #ifdef INET6 1281 b0 = gen_proto(IPPROTO_PIM, Q_IPV6, Q_DEFAULT); 1282 gen_or(b0, b1); 1283 #endif 1284 break; 1285 1286 case Q_IP: 1287 b1 = gen_linktype(ETHERTYPE_IP); 1288 break; 1289 1290 case Q_ARP: 1291 b1 = gen_linktype(ETHERTYPE_ARP); 1292 break; 1293 1294 case Q_RARP: 1295 b1 = gen_linktype(ETHERTYPE_REVARP); 1296 break; 1297 1298 case Q_LINK: 1299 bpf_error("link layer applied in wrong context"); 1300 1301 case Q_ATALK: 1302 b1 = gen_linktype(ETHERTYPE_ATALK); 1303 break; 1304 1305 case Q_DECNET: 1306 b1 = gen_linktype(ETHERTYPE_DN); 1307 break; 1308 1309 case Q_SCA: 1310 b1 = gen_linktype(ETHERTYPE_SCA); 1311 break; 1312 1313 case Q_LAT: 1314 b1 = gen_linktype(ETHERTYPE_LAT); 1315 break; 1316 1317 case Q_MOPDL: 1318 b1 = gen_linktype(ETHERTYPE_MOPDL); 1319 break; 1320 1321 case Q_MOPRC: 1322 b1 = gen_linktype(ETHERTYPE_MOPRC); 1323 break; 1324 1325 #ifdef INET6 1326 case Q_IPV6: 1327 b1 = gen_linktype(ETHERTYPE_IPV6); 1328 break; 1329 1330 #ifndef IPPROTO_ICMPV6 1331 #define IPPROTO_ICMPV6 58 1332 #endif 1333 case Q_ICMPV6: 1334 b1 = gen_proto(IPPROTO_ICMPV6, Q_IPV6, Q_DEFAULT); 1335 break; 1336 #endif /* INET6 */ 1337 1338 #ifndef IPPROTO_AH 1339 #define IPPROTO_AH 51 1340 #endif 1341 case Q_AH: 1342 b1 = gen_proto(IPPROTO_AH, Q_IP, Q_DEFAULT); 1343 #ifdef INET6 1344 b0 = gen_proto(IPPROTO_AH, Q_IPV6, Q_DEFAULT); 1345 gen_or(b0, b1); 1346 #endif 1347 break; 1348 1349 #ifndef IPPROTO_ESP 1350 #define IPPROTO_ESP 50 1351 #endif 1352 case Q_ESP: 1353 b1 = gen_proto(IPPROTO_ESP, Q_IP, Q_DEFAULT); 1354 #ifdef INET6 1355 b0 = gen_proto(IPPROTO_ESP, Q_IPV6, Q_DEFAULT); 1356 gen_or(b0, b1); 1357 #endif 1358 break; 1359 1360 default: 1361 abort(); 1362 } 1363 return b1; 1364 } 1365 1366 static struct block * 1367 gen_ipfrag() 1368 { 1369 struct slist *s; 1370 struct block *b; 1371 1372 /* not ip frag */ 1373 s = new_stmt(BPF_LD|BPF_H|BPF_ABS); 1374 s->s.k = off_nl + 6; 1375 b = new_block(JMP(BPF_JSET)); 1376 b->s.k = 0x1fff; 1377 b->stmts = s; 1378 gen_not(b); 1379 1380 return b; 1381 } 1382 1383 static struct block * 1384 gen_portatom(off, v) 1385 int off; 1386 bpf_int32 v; 1387 { 1388 struct slist *s; 1389 struct block *b; 1390 1391 s = new_stmt(BPF_LDX|BPF_MSH|BPF_B); 1392 s->s.k = off_nl; 1393 1394 s->next = new_stmt(BPF_LD|BPF_IND|BPF_H); 1395 s->next->s.k = off_nl + off; 1396 1397 b = new_block(JMP(BPF_JEQ)); 1398 b->stmts = s; 1399 b->s.k = v; 1400 1401 return b; 1402 } 1403 1404 #ifdef INET6 1405 static struct block * 1406 gen_portatom6(off, v) 1407 int off; 1408 bpf_int32 v; 1409 { 1410 return gen_cmp(off_nl + 40 + off, BPF_H, v); 1411 } 1412 #endif/*INET6*/ 1413 1414 struct block * 1415 gen_portop(port, proto, dir) 1416 int port, proto, dir; 1417 { 1418 struct block *b0, *b1, *tmp; 1419 1420 /* ip proto 'proto' */ 1421 tmp = gen_cmp(off_nl + 9, BPF_B, (bpf_int32)proto); 1422 b0 = gen_ipfrag(); 1423 gen_and(tmp, b0); 1424 1425 switch (dir) { 1426 case Q_SRC: 1427 b1 = gen_portatom(0, (bpf_int32)port); 1428 break; 1429 1430 case Q_DST: 1431 b1 = gen_portatom(2, (bpf_int32)port); 1432 break; 1433 1434 case Q_OR: 1435 case Q_DEFAULT: 1436 tmp = gen_portatom(0, (bpf_int32)port); 1437 b1 = gen_portatom(2, (bpf_int32)port); 1438 gen_or(tmp, b1); 1439 break; 1440 1441 case Q_AND: 1442 tmp = gen_portatom(0, (bpf_int32)port); 1443 b1 = gen_portatom(2, (bpf_int32)port); 1444 gen_and(tmp, b1); 1445 break; 1446 1447 default: 1448 abort(); 1449 } 1450 gen_and(b0, b1); 1451 1452 return b1; 1453 } 1454 1455 static struct block * 1456 gen_port(port, ip_proto, dir) 1457 int port; 1458 int ip_proto; 1459 int dir; 1460 { 1461 struct block *b0, *b1, *tmp; 1462 1463 /* ether proto ip */ 1464 b0 = gen_linktype(ETHERTYPE_IP); 1465 1466 switch (ip_proto) { 1467 case IPPROTO_UDP: 1468 case IPPROTO_TCP: 1469 b1 = gen_portop(port, ip_proto, dir); 1470 break; 1471 1472 case PROTO_UNDEF: 1473 tmp = gen_portop(port, IPPROTO_TCP, dir); 1474 b1 = gen_portop(port, IPPROTO_UDP, dir); 1475 gen_or(tmp, b1); 1476 break; 1477 1478 default: 1479 abort(); 1480 } 1481 gen_and(b0, b1); 1482 return b1; 1483 } 1484 1485 #ifdef INET6 1486 struct block * 1487 gen_portop6(port, proto, dir) 1488 int port, proto, dir; 1489 { 1490 struct block *b0, *b1, *tmp; 1491 1492 /* ip proto 'proto' */ 1493 b0 = gen_cmp(off_nl + 6, BPF_B, (bpf_int32)proto); 1494 1495 switch (dir) { 1496 case Q_SRC: 1497 b1 = gen_portatom6(0, (bpf_int32)port); 1498 break; 1499 1500 case Q_DST: 1501 b1 = gen_portatom6(2, (bpf_int32)port); 1502 break; 1503 1504 case Q_OR: 1505 case Q_DEFAULT: 1506 tmp = gen_portatom6(0, (bpf_int32)port); 1507 b1 = gen_portatom6(2, (bpf_int32)port); 1508 gen_or(tmp, b1); 1509 break; 1510 1511 case Q_AND: 1512 tmp = gen_portatom6(0, (bpf_int32)port); 1513 b1 = gen_portatom6(2, (bpf_int32)port); 1514 gen_and(tmp, b1); 1515 break; 1516 1517 default: 1518 abort(); 1519 } 1520 gen_and(b0, b1); 1521 1522 return b1; 1523 } 1524 1525 static struct block * 1526 gen_port6(port, ip_proto, dir) 1527 int port; 1528 int ip_proto; 1529 int dir; 1530 { 1531 struct block *b0, *b1, *tmp; 1532 1533 /* ether proto ip */ 1534 b0 = gen_linktype(ETHERTYPE_IPV6); 1535 1536 switch (ip_proto) { 1537 case IPPROTO_UDP: 1538 case IPPROTO_TCP: 1539 b1 = gen_portop6(port, ip_proto, dir); 1540 break; 1541 1542 case PROTO_UNDEF: 1543 tmp = gen_portop6(port, IPPROTO_TCP, dir); 1544 b1 = gen_portop6(port, IPPROTO_UDP, dir); 1545 gen_or(tmp, b1); 1546 break; 1547 1548 default: 1549 abort(); 1550 } 1551 gen_and(b0, b1); 1552 return b1; 1553 } 1554 #endif /* INET6 */ 1555 1556 static int 1557 lookup_proto(name, proto) 1558 register const char *name; 1559 register int proto; 1560 { 1561 register int v; 1562 1563 switch (proto) { 1564 1565 case Q_DEFAULT: 1566 case Q_IP: 1567 v = pcap_nametoproto(name); 1568 if (v == PROTO_UNDEF) 1569 bpf_error("unknown ip proto '%s'", name); 1570 break; 1571 1572 case Q_LINK: 1573 /* XXX should look up h/w protocol type based on linktype */ 1574 v = pcap_nametoeproto(name); 1575 if (v == PROTO_UNDEF) 1576 bpf_error("unknown ether proto '%s'", name); 1577 break; 1578 1579 default: 1580 v = PROTO_UNDEF; 1581 break; 1582 } 1583 return v; 1584 } 1585 1586 static struct block * 1587 gen_protochain(v, proto, dir) 1588 int v; 1589 int proto; 1590 int dir; 1591 { 1592 struct block *b0, *b; 1593 struct slist *s[100]; 1594 int fix2, fix3, fix4, fix5; 1595 int ahcheck, again, end; 1596 int i, max; 1597 int reg1 = alloc_reg(); 1598 int reg2 = alloc_reg(); 1599 1600 memset(s, 0, sizeof(s)); 1601 fix2 = fix3 = fix4 = fix5 = 0; 1602 1603 switch (proto) { 1604 case Q_IP: 1605 case Q_IPV6: 1606 break; 1607 case Q_DEFAULT: 1608 b0 = gen_protochain(v, Q_IP, dir); 1609 b = gen_protochain(v, Q_IPV6, dir); 1610 gen_or(b0, b); 1611 return b; 1612 default: 1613 bpf_error("bad protocol applied for 'protochain'"); 1614 /*NOTREACHED*/ 1615 } 1616 1617 no_optimize = 1; /*this code is not compatible with optimzer yet */ 1618 1619 /* 1620 * s[0] is a dummy entry to protect other BPF insn from damaged 1621 * by s[fix] = foo with uninitialized variable "fix". It is somewhat 1622 * hard to find interdependency made by jump table fixup. 1623 */ 1624 i = 0; 1625 s[i] = new_stmt(0); /*dummy*/ 1626 i++; 1627 1628 switch (proto) { 1629 case Q_IP: 1630 b0 = gen_linktype(ETHERTYPE_IP); 1631 1632 /* A = ip->ip_p */ 1633 s[i] = new_stmt(BPF_LD|BPF_ABS|BPF_B); 1634 s[i]->s.k = off_nl + 9; 1635 i++; 1636 /* X = ip->ip_hl << 2 */ 1637 s[i] = new_stmt(BPF_LDX|BPF_MSH|BPF_B); 1638 s[i]->s.k = off_nl; 1639 i++; 1640 break; 1641 case Q_IPV6: 1642 b0 = gen_linktype(ETHERTYPE_IPV6); 1643 1644 /* A = ip6->ip_nxt */ 1645 s[i] = new_stmt(BPF_LD|BPF_ABS|BPF_B); 1646 s[i]->s.k = off_nl + 6; 1647 i++; 1648 /* X = sizeof(struct ip6_hdr) */ 1649 s[i] = new_stmt(BPF_LDX|BPF_IMM); 1650 s[i]->s.k = 40; 1651 i++; 1652 break; 1653 default: 1654 bpf_error("unsupported proto to gen_protochain"); 1655 /*NOTREACHED*/ 1656 } 1657 1658 /* again: if (A == v) goto end; else fall through; */ 1659 again = i; 1660 s[i] = new_stmt(BPF_JMP|BPF_JEQ|BPF_K); 1661 s[i]->s.k = v; 1662 s[i]->s.jt = NULL; /*later*/ 1663 s[i]->s.jf = NULL; /*update in next stmt*/ 1664 fix5 = i; 1665 i++; 1666 1667 /* if (A == IPPROTO_NONE) goto end */ 1668 s[i] = new_stmt(BPF_JMP|BPF_JEQ|BPF_K); 1669 s[i]->s.jt = NULL; /*later*/ 1670 s[i]->s.jf = NULL; /*update in next stmt*/ 1671 s[i]->s.k = IPPROTO_NONE; 1672 s[fix5]->s.jf = s[i]; 1673 fix2 = i; 1674 i++; 1675 1676 if (proto == Q_IPV6) { 1677 int v6start, v6end, v6advance, j; 1678 1679 v6start = i; 1680 /* if (A == IPPROTO_HOPOPTS) goto v6advance */ 1681 s[i] = new_stmt(BPF_JMP|BPF_JEQ|BPF_K); 1682 s[i]->s.jt = NULL; /*later*/ 1683 s[i]->s.jf = NULL; /*update in next stmt*/ 1684 s[i]->s.k = IPPROTO_HOPOPTS; 1685 s[fix2]->s.jf = s[i]; 1686 i++; 1687 /* if (A == IPPROTO_DSTOPTS) goto v6advance */ 1688 s[i - 1]->s.jf = s[i] = new_stmt(BPF_JMP|BPF_JEQ|BPF_K); 1689 s[i]->s.jt = NULL; /*later*/ 1690 s[i]->s.jf = NULL; /*update in next stmt*/ 1691 s[i]->s.k = IPPROTO_DSTOPTS; 1692 i++; 1693 /* if (A == IPPROTO_ROUTING) goto v6advance */ 1694 s[i - 1]->s.jf = s[i] = new_stmt(BPF_JMP|BPF_JEQ|BPF_K); 1695 s[i]->s.jt = NULL; /*later*/ 1696 s[i]->s.jf = NULL; /*update in next stmt*/ 1697 s[i]->s.k = IPPROTO_ROUTING; 1698 i++; 1699 /* if (A == IPPROTO_FRAGMENT) goto v6advance; else goto ahcheck; */ 1700 s[i - 1]->s.jf = s[i] = new_stmt(BPF_JMP|BPF_JEQ|BPF_K); 1701 s[i]->s.jt = NULL; /*later*/ 1702 s[i]->s.jf = NULL; /*later*/ 1703 s[i]->s.k = IPPROTO_FRAGMENT; 1704 fix3 = i; 1705 v6end = i; 1706 i++; 1707 1708 /* v6advance: */ 1709 v6advance = i; 1710 1711 /* 1712 * in short, 1713 * A = P[X + 1]; 1714 * X = X + (P[X] + 1) * 8; 1715 */ 1716 /* A = X */ 1717 s[i] = new_stmt(BPF_MISC|BPF_TXA); 1718 i++; 1719 /* MEM[reg1] = A */ 1720 s[i] = new_stmt(BPF_ST); 1721 s[i]->s.k = reg1; 1722 i++; 1723 /* A += 1 */ 1724 s[i] = new_stmt(BPF_ALU|BPF_ADD|BPF_K); 1725 s[i]->s.k = 1; 1726 i++; 1727 /* X = A */ 1728 s[i] = new_stmt(BPF_MISC|BPF_TAX); 1729 i++; 1730 /* A = P[X + packet head]; */ 1731 s[i] = new_stmt(BPF_LD|BPF_IND|BPF_B); 1732 s[i]->s.k = off_nl; 1733 i++; 1734 /* MEM[reg2] = A */ 1735 s[i] = new_stmt(BPF_ST); 1736 s[i]->s.k = reg2; 1737 i++; 1738 /* X = MEM[reg1] */ 1739 s[i] = new_stmt(BPF_LDX|BPF_MEM); 1740 s[i]->s.k = reg1; 1741 i++; 1742 /* A = P[X + packet head] */ 1743 s[i] = new_stmt(BPF_LD|BPF_IND|BPF_B); 1744 s[i]->s.k = off_nl; 1745 i++; 1746 /* A += 1 */ 1747 s[i] = new_stmt(BPF_ALU|BPF_ADD|BPF_K); 1748 s[i]->s.k = 1; 1749 i++; 1750 /* A *= 8 */ 1751 s[i] = new_stmt(BPF_ALU|BPF_MUL|BPF_K); 1752 s[i]->s.k = 8; 1753 i++; 1754 /* X = A; */ 1755 s[i] = new_stmt(BPF_MISC|BPF_TAX); 1756 i++; 1757 /* A = MEM[reg2] */ 1758 s[i] = new_stmt(BPF_LD|BPF_MEM); 1759 s[i]->s.k = reg2; 1760 i++; 1761 1762 /* goto again; (must use BPF_JA for backward jump) */ 1763 s[i] = new_stmt(BPF_JMP|BPF_JA); 1764 s[i]->s.k = again - i - 1; 1765 s[i - 1]->s.jf = s[i]; 1766 i++; 1767 1768 /* fixup */ 1769 for (j = v6start; j <= v6end; j++) 1770 s[j]->s.jt = s[v6advance]; 1771 } else { 1772 /* nop */ 1773 s[i] = new_stmt(BPF_ALU|BPF_ADD|BPF_K); 1774 s[i]->s.k = 0; 1775 s[fix2]->s.jf = s[i]; 1776 i++; 1777 } 1778 1779 /* ahcheck: */ 1780 ahcheck = i; 1781 /* if (A == IPPROTO_AH) then fall through; else goto end; */ 1782 s[i] = new_stmt(BPF_JMP|BPF_JEQ|BPF_K); 1783 s[i]->s.jt = NULL; /*later*/ 1784 s[i]->s.jf = NULL; /*later*/ 1785 s[i]->s.k = IPPROTO_AH; 1786 if (fix3) 1787 s[fix3]->s.jf = s[ahcheck]; 1788 fix4 = i; 1789 i++; 1790 1791 /* 1792 * in short, 1793 * A = P[X + 1]; 1794 * X = X + (P[X] + 2) * 4; 1795 */ 1796 /* A = X */ 1797 s[i - 1]->s.jt = s[i] = new_stmt(BPF_MISC|BPF_TXA); 1798 i++; 1799 /* MEM[reg1] = A */ 1800 s[i] = new_stmt(BPF_ST); 1801 s[i]->s.k = reg1; 1802 i++; 1803 /* A += 1 */ 1804 s[i] = new_stmt(BPF_ALU|BPF_ADD|BPF_K); 1805 s[i]->s.k = 1; 1806 i++; 1807 /* X = A */ 1808 s[i] = new_stmt(BPF_MISC|BPF_TAX); 1809 i++; 1810 /* A = P[X + packet head]; */ 1811 s[i] = new_stmt(BPF_LD|BPF_IND|BPF_B); 1812 s[i]->s.k = off_nl; 1813 i++; 1814 /* MEM[reg2] = A */ 1815 s[i] = new_stmt(BPF_ST); 1816 s[i]->s.k = reg2; 1817 i++; 1818 /* X = MEM[reg1] */ 1819 s[i] = new_stmt(BPF_LDX|BPF_MEM); 1820 s[i]->s.k = reg1; 1821 i++; 1822 /* A = P[X + packet head] */ 1823 s[i] = new_stmt(BPF_LD|BPF_IND|BPF_B); 1824 s[i]->s.k = off_nl; 1825 i++; 1826 /* A += 2 */ 1827 s[i] = new_stmt(BPF_ALU|BPF_ADD|BPF_K); 1828 s[i]->s.k = 2; 1829 i++; 1830 /* A *= 4 */ 1831 s[i] = new_stmt(BPF_ALU|BPF_MUL|BPF_K); 1832 s[i]->s.k = 4; 1833 i++; 1834 /* X = A; */ 1835 s[i] = new_stmt(BPF_MISC|BPF_TAX); 1836 i++; 1837 /* A = MEM[reg2] */ 1838 s[i] = new_stmt(BPF_LD|BPF_MEM); 1839 s[i]->s.k = reg2; 1840 i++; 1841 1842 /* goto again; (must use BPF_JA for backward jump) */ 1843 s[i] = new_stmt(BPF_JMP|BPF_JA); 1844 s[i]->s.k = again - i - 1; 1845 i++; 1846 1847 /* end: nop */ 1848 end = i; 1849 s[i] = new_stmt(BPF_ALU|BPF_ADD|BPF_K); 1850 s[i]->s.k = 0; 1851 s[fix2]->s.jt = s[end]; 1852 s[fix4]->s.jf = s[end]; 1853 s[fix5]->s.jt = s[end]; 1854 i++; 1855 1856 /* 1857 * make slist chain 1858 */ 1859 max = i; 1860 for (i = 0; i < max - 1; i++) 1861 s[i]->next = s[i + 1]; 1862 s[max - 1]->next = NULL; 1863 1864 /* 1865 * emit final check 1866 */ 1867 b = new_block(JMP(BPF_JEQ)); 1868 b->stmts = s[1]; /*remember, s[0] is dummy*/ 1869 b->s.k = v; 1870 1871 free_reg(reg1); 1872 free_reg(reg2); 1873 1874 gen_and(b0, b); 1875 return b; 1876 } 1877 1878 static struct block * 1879 gen_proto(v, proto, dir) 1880 int v; 1881 int proto; 1882 int dir; 1883 { 1884 struct block *b0, *b1; 1885 1886 if (dir != Q_DEFAULT) 1887 bpf_error("direction applied to 'proto'"); 1888 1889 switch (proto) { 1890 case Q_DEFAULT: 1891 #ifdef INET6 1892 b0 = gen_proto(v, Q_IP, dir); 1893 b1 = gen_proto(v, Q_IPV6, dir); 1894 gen_or(b0, b1); 1895 return b1; 1896 #else 1897 /*FALLTHROUGH*/ 1898 #endif 1899 case Q_IP: 1900 b0 = gen_linktype(ETHERTYPE_IP); 1901 #ifndef CHASE_CHAIN 1902 b1 = gen_cmp(off_nl + 9, BPF_B, (bpf_int32)v); 1903 #else 1904 b1 = gen_protochain(v, Q_IP); 1905 #endif 1906 gen_and(b0, b1); 1907 return b1; 1908 1909 case Q_ARP: 1910 bpf_error("arp does not encapsulate another protocol"); 1911 /* NOTREACHED */ 1912 1913 case Q_RARP: 1914 bpf_error("rarp does not encapsulate another protocol"); 1915 /* NOTREACHED */ 1916 1917 case Q_ATALK: 1918 bpf_error("atalk encapsulation is not specifiable"); 1919 /* NOTREACHED */ 1920 1921 case Q_DECNET: 1922 bpf_error("decnet encapsulation is not specifiable"); 1923 /* NOTREACHED */ 1924 1925 case Q_SCA: 1926 bpf_error("sca does not encapsulate another protocol"); 1927 /* NOTREACHED */ 1928 1929 case Q_LAT: 1930 bpf_error("lat does not encapsulate another protocol"); 1931 /* NOTREACHED */ 1932 1933 case Q_MOPRC: 1934 bpf_error("moprc does not encapsulate another protocol"); 1935 /* NOTREACHED */ 1936 1937 case Q_MOPDL: 1938 bpf_error("mopdl does not encapsulate another protocol"); 1939 /* NOTREACHED */ 1940 1941 case Q_LINK: 1942 return gen_linktype(v); 1943 1944 case Q_UDP: 1945 bpf_error("'udp proto' is bogus"); 1946 /* NOTREACHED */ 1947 1948 case Q_TCP: 1949 bpf_error("'tcp proto' is bogus"); 1950 /* NOTREACHED */ 1951 1952 case Q_ICMP: 1953 bpf_error("'icmp proto' is bogus"); 1954 /* NOTREACHED */ 1955 1956 case Q_IGMP: 1957 bpf_error("'igmp proto' is bogus"); 1958 /* NOTREACHED */ 1959 1960 case Q_IGRP: 1961 bpf_error("'igrp proto' is bogus"); 1962 /* NOTREACHED */ 1963 1964 case Q_PIM: 1965 bpf_error("'pim proto' is bogus"); 1966 /* NOTREACHED */ 1967 1968 #ifdef INET6 1969 case Q_IPV6: 1970 b0 = gen_linktype(ETHERTYPE_IPV6); 1971 #ifndef CHASE_CHAIN 1972 b1 = gen_cmp(off_nl + 6, BPF_B, (bpf_int32)v); 1973 #else 1974 b1 = gen_protochain(v, Q_IPV6); 1975 #endif 1976 gen_and(b0, b1); 1977 return b1; 1978 1979 case Q_ICMPV6: 1980 bpf_error("'icmp6 proto' is bogus"); 1981 #endif /* INET6 */ 1982 1983 case Q_AH: 1984 bpf_error("'ah proto' is bogus"); 1985 1986 case Q_ESP: 1987 bpf_error("'ah proto' is bogus"); 1988 1989 default: 1990 abort(); 1991 /* NOTREACHED */ 1992 } 1993 /* NOTREACHED */ 1994 } 1995 1996 struct block * 1997 gen_scode(name, q) 1998 register const char *name; 1999 struct qual q; 2000 { 2001 int proto = q.proto; 2002 int dir = q.dir; 2003 int tproto; 2004 u_char *eaddr; 2005 bpf_u_int32 mask, addr; 2006 #ifndef INET6 2007 bpf_u_int32 **alist; 2008 #else 2009 int tproto6; 2010 struct sockaddr_in *sin; 2011 struct sockaddr_in6 *sin6; 2012 struct addrinfo *res, *res0; 2013 struct in6_addr mask128; 2014 #endif /*INET6*/ 2015 struct block *b, *tmp; 2016 int port, real_proto; 2017 2018 switch (q.addr) { 2019 2020 case Q_NET: 2021 addr = pcap_nametonetaddr(name); 2022 if (addr == 0) 2023 bpf_error("unknown network '%s'", name); 2024 /* Left justify network addr and calculate its network mask */ 2025 mask = 0xffffffff; 2026 while (addr && (addr & 0xff000000) == 0) { 2027 addr <<= 8; 2028 mask <<= 8; 2029 } 2030 return gen_host(addr, mask, proto, dir); 2031 2032 case Q_DEFAULT: 2033 case Q_HOST: 2034 if (proto == Q_LINK) { 2035 switch (linktype) { 2036 2037 case DLT_EN10MB: 2038 eaddr = pcap_ether_hostton(name); 2039 if (eaddr == NULL) 2040 bpf_error( 2041 "unknown ether host '%s'", name); 2042 return gen_ehostop(eaddr, dir); 2043 2044 case DLT_FDDI: 2045 eaddr = pcap_ether_hostton(name); 2046 if (eaddr == NULL) 2047 bpf_error( 2048 "unknown FDDI host '%s'", name); 2049 return gen_fhostop(eaddr, dir); 2050 2051 default: 2052 bpf_error( 2053 "only ethernet/FDDI supports link-level host name"); 2054 break; 2055 } 2056 } else if (proto == Q_DECNET) { 2057 unsigned short dn_addr = __pcap_nametodnaddr(name); 2058 /* 2059 * I don't think DECNET hosts can be multihomed, so 2060 * there is no need to build up a list of addresses 2061 */ 2062 return (gen_host(dn_addr, 0, proto, dir)); 2063 } else { 2064 #ifndef INET6 2065 alist = pcap_nametoaddr(name); 2066 if (alist == NULL || *alist == NULL) 2067 bpf_error("unknown host '%s'", name); 2068 tproto = proto; 2069 if (off_linktype == -1 && tproto == Q_DEFAULT) 2070 tproto = Q_IP; 2071 b = gen_host(**alist++, 0xffffffff, tproto, dir); 2072 while (*alist) { 2073 tmp = gen_host(**alist++, 0xffffffff, 2074 tproto, dir); 2075 gen_or(b, tmp); 2076 b = tmp; 2077 } 2078 return b; 2079 #else 2080 memset(&mask128, 0xff, sizeof(mask128)); 2081 res0 = res = pcap_nametoaddrinfo(name); 2082 if (res == NULL) 2083 bpf_error("unknown host '%s'", name); 2084 b = tmp = NULL; 2085 tproto = tproto6 = proto; 2086 if (off_linktype == -1 && tproto == Q_DEFAULT) { 2087 tproto = Q_IP; 2088 tproto6 = Q_IPV6; 2089 } 2090 for (res = res0; res; res = res->ai_next) { 2091 switch (res->ai_family) { 2092 case AF_INET: 2093 if (tproto == Q_IPV6) 2094 continue; 2095 2096 sin = (struct sockaddr_in *) 2097 res->ai_addr; 2098 tmp = gen_host(ntohl(sin->sin_addr.s_addr), 2099 0xffffffff, tproto, dir); 2100 break; 2101 case AF_INET6: 2102 if (tproto6 == Q_IP) 2103 continue; 2104 2105 sin6 = (struct sockaddr_in6 *) 2106 res->ai_addr; 2107 tmp = gen_host6(&sin6->sin6_addr, 2108 &mask128, tproto6, dir); 2109 break; 2110 } 2111 if (b) 2112 gen_or(b, tmp); 2113 b = tmp; 2114 } 2115 freeaddrinfo(res0); 2116 if (b == NULL) { 2117 bpf_error("unknown host '%s'%s", name, 2118 (proto == Q_DEFAULT) 2119 ? "" 2120 : " for specified address family"); 2121 } 2122 return b; 2123 #endif /*INET6*/ 2124 } 2125 2126 case Q_PORT: 2127 if (proto != Q_DEFAULT && proto != Q_UDP && proto != Q_TCP) 2128 bpf_error("illegal qualifier of 'port'"); 2129 if (pcap_nametoport(name, &port, &real_proto) == 0) 2130 bpf_error("unknown port '%s'", name); 2131 if (proto == Q_UDP) { 2132 if (real_proto == IPPROTO_TCP) 2133 bpf_error("port '%s' is tcp", name); 2134 else 2135 /* override PROTO_UNDEF */ 2136 real_proto = IPPROTO_UDP; 2137 } 2138 if (proto == Q_TCP) { 2139 if (real_proto == IPPROTO_UDP) 2140 bpf_error("port '%s' is udp", name); 2141 else 2142 /* override PROTO_UNDEF */ 2143 real_proto = IPPROTO_TCP; 2144 } 2145 #ifndef INET6 2146 return gen_port(port, real_proto, dir); 2147 #else 2148 { 2149 struct block *b; 2150 b = gen_port(port, real_proto, dir); 2151 gen_or(gen_port6(port, real_proto, dir), b); 2152 return b; 2153 } 2154 #endif /* INET6 */ 2155 2156 case Q_GATEWAY: 2157 #ifndef INET6 2158 eaddr = pcap_ether_hostton(name); 2159 if (eaddr == NULL) 2160 bpf_error("unknown ether host: %s", name); 2161 2162 alist = pcap_nametoaddr(name); 2163 if (alist == NULL || *alist == NULL) 2164 bpf_error("unknown host '%s'", name); 2165 return gen_gateway(eaddr, alist, proto, dir); 2166 #else 2167 bpf_error("'gateway' not supported in this configuration"); 2168 #endif /*INET6*/ 2169 2170 case Q_PROTO: 2171 real_proto = lookup_proto(name, proto); 2172 if (real_proto >= 0) 2173 return gen_proto(real_proto, proto, dir); 2174 else 2175 bpf_error("unknown protocol: %s", name); 2176 2177 case Q_PROTOCHAIN: 2178 real_proto = lookup_proto(name, proto); 2179 if (real_proto >= 0) 2180 return gen_protochain(real_proto, proto, dir); 2181 else 2182 bpf_error("unknown protocol: %s", name); 2183 2184 2185 case Q_UNDEF: 2186 syntax(); 2187 /* NOTREACHED */ 2188 } 2189 abort(); 2190 /* NOTREACHED */ 2191 } 2192 2193 struct block * 2194 gen_mcode(s1, s2, masklen, q) 2195 register const char *s1, *s2; 2196 register int masklen; 2197 struct qual q; 2198 { 2199 register int nlen, mlen; 2200 bpf_u_int32 n, m; 2201 2202 nlen = __pcap_atoin(s1, &n); 2203 /* Promote short ipaddr */ 2204 n <<= 32 - nlen; 2205 2206 if (s2 != NULL) { 2207 mlen = __pcap_atoin(s2, &m); 2208 /* Promote short ipaddr */ 2209 m <<= 32 - mlen; 2210 if ((n & ~m) != 0) 2211 bpf_error("non-network bits set in \"%s mask %s\"", 2212 s1, s2); 2213 } else { 2214 /* Convert mask len to mask */ 2215 if (masklen > 32) 2216 bpf_error("mask length must be <= 32"); 2217 m = 0xffffffff << (32 - masklen); 2218 if ((n & ~m) != 0) 2219 bpf_error("non-network bits set in \"%s/%d\"", 2220 s1, masklen); 2221 } 2222 2223 switch (q.addr) { 2224 2225 case Q_NET: 2226 return gen_host(n, m, q.proto, q.dir); 2227 2228 default: 2229 bpf_error("Mask syntax for networks only"); 2230 /* NOTREACHED */ 2231 } 2232 } 2233 2234 struct block * 2235 gen_ncode(s, v, q) 2236 register const char *s; 2237 bpf_u_int32 v; 2238 struct qual q; 2239 { 2240 bpf_u_int32 mask; 2241 int proto = q.proto; 2242 int dir = q.dir; 2243 register int vlen; 2244 2245 if (s == NULL) 2246 vlen = 32; 2247 else if (q.proto == Q_DECNET) 2248 vlen = __pcap_atodn(s, &v); 2249 else 2250 vlen = __pcap_atoin(s, &v); 2251 2252 switch (q.addr) { 2253 2254 case Q_DEFAULT: 2255 case Q_HOST: 2256 case Q_NET: 2257 if (proto == Q_DECNET) 2258 return gen_host(v, 0, proto, dir); 2259 else if (proto == Q_LINK) { 2260 bpf_error("illegal link layer address"); 2261 } else { 2262 mask = 0xffffffff; 2263 if (s == NULL && q.addr == Q_NET) { 2264 /* Promote short net number */ 2265 while (v && (v & 0xff000000) == 0) { 2266 v <<= 8; 2267 mask <<= 8; 2268 } 2269 } else { 2270 /* Promote short ipaddr */ 2271 v <<= 32 - vlen; 2272 mask <<= 32 - vlen; 2273 } 2274 return gen_host(v, mask, proto, dir); 2275 } 2276 2277 case Q_PORT: 2278 if (proto == Q_UDP) 2279 proto = IPPROTO_UDP; 2280 else if (proto == Q_TCP) 2281 proto = IPPROTO_TCP; 2282 else if (proto == Q_DEFAULT) 2283 proto = PROTO_UNDEF; 2284 else 2285 bpf_error("illegal qualifier of 'port'"); 2286 2287 #ifndef INET6 2288 return gen_port((int)v, proto, dir); 2289 #else 2290 { 2291 struct block *b; 2292 b = gen_port((int)v, proto, dir); 2293 gen_or(gen_port6((int)v, proto, dir), b); 2294 return b; 2295 } 2296 #endif /* INET6 */ 2297 2298 case Q_GATEWAY: 2299 bpf_error("'gateway' requires a name"); 2300 /* NOTREACHED */ 2301 2302 case Q_PROTO: 2303 return gen_proto((int)v, proto, dir); 2304 2305 case Q_PROTOCHAIN: 2306 return gen_protochain((int)v, proto, dir); 2307 2308 case Q_UNDEF: 2309 syntax(); 2310 /* NOTREACHED */ 2311 2312 default: 2313 abort(); 2314 /* NOTREACHED */ 2315 } 2316 /* NOTREACHED */ 2317 } 2318 2319 #ifdef INET6 2320 struct block * 2321 gen_mcode6(s1, s2, masklen, q) 2322 register const char *s1, *s2; 2323 register int masklen; 2324 struct qual q; 2325 { 2326 struct addrinfo *res; 2327 struct in6_addr *addr; 2328 struct in6_addr mask; 2329 struct block *b; 2330 u_int32_t *a, *m; 2331 2332 if (s2) 2333 bpf_error("no mask %s supported", s2); 2334 2335 res = pcap_nametoaddrinfo(s1); 2336 if (!res) 2337 bpf_error("invalid ip6 address %s", s1); 2338 if (res->ai_next) 2339 bpf_error("%s resolved to multiple address", s1); 2340 addr = &((struct sockaddr_in6 *)res->ai_addr)->sin6_addr; 2341 2342 if (sizeof(mask) * 8 < masklen) 2343 bpf_error("mask length must be <= %u", (unsigned int)(sizeof(mask) * 8)); 2344 memset(&mask, 0xff, masklen / 8); 2345 if (masklen % 8) { 2346 mask.s6_addr[masklen / 8] = 2347 (0xff << (8 - masklen % 8)) & 0xff; 2348 } 2349 2350 a = (u_int32_t *)addr; 2351 m = (u_int32_t *)&mask; 2352 if ((a[0] & ~m[0]) || (a[1] & ~m[1]) 2353 || (a[2] & ~m[2]) || (a[3] & ~m[3])) { 2354 bpf_error("non-network bits set in \"%s/%d\"", s1, masklen); 2355 } 2356 2357 switch (q.addr) { 2358 2359 case Q_DEFAULT: 2360 case Q_HOST: 2361 if (masklen != 128) 2362 bpf_error("Mask syntax for networks only"); 2363 /* FALLTHROUGH */ 2364 2365 case Q_NET: 2366 b = gen_host6(addr, &mask, q.proto, q.dir); 2367 freeaddrinfo(res); 2368 return b; 2369 2370 default: 2371 bpf_error("invalid qualifier against IPv6 address"); 2372 /* NOTREACHED */ 2373 } 2374 } 2375 #endif /*INET6*/ 2376 2377 struct block * 2378 gen_ecode(eaddr, q) 2379 register const u_char *eaddr; 2380 struct qual q; 2381 { 2382 if ((q.addr == Q_HOST || q.addr == Q_DEFAULT) && q.proto == Q_LINK) { 2383 if (linktype == DLT_EN10MB) 2384 return gen_ehostop(eaddr, (int)q.dir); 2385 if (linktype == DLT_FDDI) 2386 return gen_fhostop(eaddr, (int)q.dir); 2387 } 2388 bpf_error("ethernet address used in non-ether expression"); 2389 /* NOTREACHED */ 2390 } 2391 2392 void 2393 sappend(s0, s1) 2394 struct slist *s0, *s1; 2395 { 2396 /* 2397 * This is definitely not the best way to do this, but the 2398 * lists will rarely get long. 2399 */ 2400 while (s0->next) 2401 s0 = s0->next; 2402 s0->next = s1; 2403 } 2404 2405 static struct slist * 2406 xfer_to_x(a) 2407 struct arth *a; 2408 { 2409 struct slist *s; 2410 2411 s = new_stmt(BPF_LDX|BPF_MEM); 2412 s->s.k = a->regno; 2413 return s; 2414 } 2415 2416 static struct slist * 2417 xfer_to_a(a) 2418 struct arth *a; 2419 { 2420 struct slist *s; 2421 2422 s = new_stmt(BPF_LD|BPF_MEM); 2423 s->s.k = a->regno; 2424 return s; 2425 } 2426 2427 struct arth * 2428 gen_load(proto, index, size) 2429 int proto; 2430 struct arth *index; 2431 int size; 2432 { 2433 struct slist *s, *tmp; 2434 struct block *b; 2435 int regno = alloc_reg(); 2436 2437 free_reg(index->regno); 2438 switch (size) { 2439 2440 default: 2441 bpf_error("data size must be 1, 2, or 4"); 2442 2443 case 1: 2444 size = BPF_B; 2445 break; 2446 2447 case 2: 2448 size = BPF_H; 2449 break; 2450 2451 case 4: 2452 size = BPF_W; 2453 break; 2454 } 2455 switch (proto) { 2456 default: 2457 bpf_error("unsupported index operation"); 2458 2459 case Q_LINK: 2460 s = xfer_to_x(index); 2461 tmp = new_stmt(BPF_LD|BPF_IND|size); 2462 sappend(s, tmp); 2463 sappend(index->s, s); 2464 break; 2465 2466 case Q_IP: 2467 case Q_ARP: 2468 case Q_RARP: 2469 case Q_ATALK: 2470 case Q_DECNET: 2471 case Q_SCA: 2472 case Q_LAT: 2473 case Q_MOPRC: 2474 case Q_MOPDL: 2475 #ifdef INET6 2476 case Q_IPV6: 2477 #endif 2478 /* XXX Note that we assume a fixed link header here. */ 2479 s = xfer_to_x(index); 2480 tmp = new_stmt(BPF_LD|BPF_IND|size); 2481 tmp->s.k = off_nl; 2482 sappend(s, tmp); 2483 sappend(index->s, s); 2484 2485 b = gen_proto_abbrev(proto); 2486 if (index->b) 2487 gen_and(index->b, b); 2488 index->b = b; 2489 break; 2490 2491 case Q_TCP: 2492 case Q_UDP: 2493 case Q_ICMP: 2494 case Q_IGMP: 2495 case Q_IGRP: 2496 case Q_PIM: 2497 s = new_stmt(BPF_LDX|BPF_MSH|BPF_B); 2498 s->s.k = off_nl; 2499 sappend(s, xfer_to_a(index)); 2500 sappend(s, new_stmt(BPF_ALU|BPF_ADD|BPF_X)); 2501 sappend(s, new_stmt(BPF_MISC|BPF_TAX)); 2502 sappend(s, tmp = new_stmt(BPF_LD|BPF_IND|size)); 2503 tmp->s.k = off_nl; 2504 sappend(index->s, s); 2505 2506 gen_and(gen_proto_abbrev(proto), b = gen_ipfrag()); 2507 if (index->b) 2508 gen_and(index->b, b); 2509 #ifdef INET6 2510 gen_and(gen_proto_abbrev(Q_IP), b); 2511 #endif 2512 index->b = b; 2513 break; 2514 #ifdef INET6 2515 case Q_ICMPV6: 2516 bpf_error("IPv6 upper-layer protocol is not supported by proto[x]"); 2517 /*NOTREACHED*/ 2518 #endif 2519 } 2520 index->regno = regno; 2521 s = new_stmt(BPF_ST); 2522 s->s.k = regno; 2523 sappend(index->s, s); 2524 2525 return index; 2526 } 2527 2528 struct block * 2529 gen_relation(code, a0, a1, reversed) 2530 int code; 2531 struct arth *a0, *a1; 2532 int reversed; 2533 { 2534 struct slist *s0, *s1, *s2; 2535 struct block *b, *tmp; 2536 2537 s0 = xfer_to_x(a1); 2538 s1 = xfer_to_a(a0); 2539 s2 = new_stmt(BPF_ALU|BPF_SUB|BPF_X); 2540 b = new_block(JMP(code)); 2541 if (code == BPF_JGT || code == BPF_JGE) { 2542 reversed = !reversed; 2543 b->s.k = 0x80000000; 2544 } 2545 if (reversed) 2546 gen_not(b); 2547 2548 sappend(s1, s2); 2549 sappend(s0, s1); 2550 sappend(a1->s, s0); 2551 sappend(a0->s, a1->s); 2552 2553 b->stmts = a0->s; 2554 2555 free_reg(a0->regno); 2556 free_reg(a1->regno); 2557 2558 /* 'and' together protocol checks */ 2559 if (a0->b) { 2560 if (a1->b) { 2561 gen_and(a0->b, tmp = a1->b); 2562 } 2563 else 2564 tmp = a0->b; 2565 } else 2566 tmp = a1->b; 2567 2568 if (tmp) 2569 gen_and(tmp, b); 2570 2571 return b; 2572 } 2573 2574 struct arth * 2575 gen_loadlen() 2576 { 2577 int regno = alloc_reg(); 2578 struct arth *a = (struct arth *)newchunk(sizeof(*a)); 2579 struct slist *s; 2580 2581 s = new_stmt(BPF_LD|BPF_LEN); 2582 s->next = new_stmt(BPF_ST); 2583 s->next->s.k = regno; 2584 a->s = s; 2585 a->regno = regno; 2586 2587 return a; 2588 } 2589 2590 struct arth * 2591 gen_loadi(val) 2592 int val; 2593 { 2594 struct arth *a; 2595 struct slist *s; 2596 int reg; 2597 2598 a = (struct arth *)newchunk(sizeof(*a)); 2599 2600 reg = alloc_reg(); 2601 2602 s = new_stmt(BPF_LD|BPF_IMM); 2603 s->s.k = val; 2604 s->next = new_stmt(BPF_ST); 2605 s->next->s.k = reg; 2606 a->s = s; 2607 a->regno = reg; 2608 2609 return a; 2610 } 2611 2612 struct arth * 2613 gen_neg(a) 2614 struct arth *a; 2615 { 2616 struct slist *s; 2617 2618 s = xfer_to_a(a); 2619 sappend(a->s, s); 2620 s = new_stmt(BPF_ALU|BPF_NEG); 2621 s->s.k = 0; 2622 sappend(a->s, s); 2623 s = new_stmt(BPF_ST); 2624 s->s.k = a->regno; 2625 sappend(a->s, s); 2626 2627 return a; 2628 } 2629 2630 struct arth * 2631 gen_arth(code, a0, a1) 2632 int code; 2633 struct arth *a0, *a1; 2634 { 2635 struct slist *s0, *s1, *s2; 2636 2637 s0 = xfer_to_x(a1); 2638 s1 = xfer_to_a(a0); 2639 s2 = new_stmt(BPF_ALU|BPF_X|code); 2640 2641 sappend(s1, s2); 2642 sappend(s0, s1); 2643 sappend(a1->s, s0); 2644 sappend(a0->s, a1->s); 2645 2646 free_reg(a1->regno); 2647 2648 s0 = new_stmt(BPF_ST); 2649 a0->regno = s0->s.k = alloc_reg(); 2650 sappend(a0->s, s0); 2651 2652 return a0; 2653 } 2654 2655 /* 2656 * Here we handle simple allocation of the scratch registers. 2657 * If too many registers are alloc'd, the allocator punts. 2658 */ 2659 static int regused[BPF_MEMWORDS]; 2660 static int curreg; 2661 2662 /* 2663 * Return the next free register. 2664 */ 2665 static int 2666 alloc_reg() 2667 { 2668 int n = BPF_MEMWORDS; 2669 2670 while (--n >= 0) { 2671 if (regused[curreg]) 2672 curreg = (curreg + 1) % BPF_MEMWORDS; 2673 else { 2674 regused[curreg] = 1; 2675 return curreg; 2676 } 2677 } 2678 bpf_error("too many registers needed to evaluate expression"); 2679 /* NOTREACHED */ 2680 } 2681 2682 /* 2683 * Return a register to the table so it can 2684 * be used later. 2685 */ 2686 static void 2687 free_reg(n) 2688 int n; 2689 { 2690 regused[n] = 0; 2691 } 2692 2693 static struct block * 2694 gen_len(jmp, n) 2695 int jmp, n; 2696 { 2697 struct slist *s; 2698 struct block *b; 2699 2700 s = new_stmt(BPF_LD|BPF_LEN); 2701 b = new_block(JMP(jmp)); 2702 b->stmts = s; 2703 b->s.k = n; 2704 2705 return b; 2706 } 2707 2708 struct block * 2709 gen_greater(n) 2710 int n; 2711 { 2712 return gen_len(BPF_JGE, n); 2713 } 2714 2715 struct block * 2716 gen_less(n) 2717 int n; 2718 { 2719 struct block *b; 2720 2721 b = gen_len(BPF_JGT, n); 2722 gen_not(b); 2723 2724 return b; 2725 } 2726 2727 struct block * 2728 gen_byteop(op, idx, val) 2729 int op, idx, val; 2730 { 2731 struct block *b; 2732 struct slist *s; 2733 2734 switch (op) { 2735 default: 2736 abort(); 2737 2738 case '=': 2739 return gen_cmp((u_int)idx, BPF_B, (bpf_int32)val); 2740 2741 case '<': 2742 b = gen_cmp((u_int)idx, BPF_B, (bpf_int32)val); 2743 b->s.code = JMP(BPF_JGE); 2744 gen_not(b); 2745 return b; 2746 2747 case '>': 2748 b = gen_cmp((u_int)idx, BPF_B, (bpf_int32)val); 2749 b->s.code = JMP(BPF_JGT); 2750 return b; 2751 2752 case '|': 2753 s = new_stmt(BPF_ALU|BPF_OR|BPF_K); 2754 break; 2755 2756 case '&': 2757 s = new_stmt(BPF_ALU|BPF_AND|BPF_K); 2758 break; 2759 } 2760 s->s.k = val; 2761 b = new_block(JMP(BPF_JEQ)); 2762 b->stmts = s; 2763 gen_not(b); 2764 2765 return b; 2766 } 2767 2768 static u_char abroadcast[] = { 0x0 }; 2769 2770 struct block * 2771 gen_broadcast(proto) 2772 int proto; 2773 { 2774 bpf_u_int32 hostmask; 2775 struct block *b0, *b1, *b2; 2776 static u_char ebroadcast[] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff }; 2777 2778 switch (proto) { 2779 2780 case Q_DEFAULT: 2781 case Q_LINK: 2782 if (linktype == DLT_ARCNET) 2783 return gen_ahostop(abroadcast, Q_DST); 2784 if (linktype == DLT_EN10MB) 2785 return gen_ehostop(ebroadcast, Q_DST); 2786 if (linktype == DLT_FDDI) 2787 return gen_fhostop(ebroadcast, Q_DST); 2788 bpf_error("not a broadcast link"); 2789 break; 2790 2791 case Q_IP: 2792 b0 = gen_linktype(ETHERTYPE_IP); 2793 hostmask = ~netmask; 2794 b1 = gen_mcmp(off_nl + 16, BPF_W, (bpf_int32)0, hostmask); 2795 b2 = gen_mcmp(off_nl + 16, BPF_W, 2796 (bpf_int32)(~0 & hostmask), hostmask); 2797 gen_or(b1, b2); 2798 gen_and(b0, b2); 2799 return b2; 2800 } 2801 bpf_error("only ether/ip broadcast filters supported"); 2802 } 2803 2804 struct block * 2805 gen_multicast(proto) 2806 int proto; 2807 { 2808 register struct block *b0, *b1; 2809 register struct slist *s; 2810 2811 switch (proto) { 2812 2813 case Q_DEFAULT: 2814 case Q_LINK: 2815 if (linktype == DLT_ARCNET) 2816 /* all ARCnet multicasts use the same address */ 2817 return gen_ahostop(abroadcast, Q_DST); 2818 2819 if (linktype == DLT_EN10MB) { 2820 /* ether[0] & 1 != 0 */ 2821 s = new_stmt(BPF_LD|BPF_B|BPF_ABS); 2822 s->s.k = 0; 2823 b0 = new_block(JMP(BPF_JSET)); 2824 b0->s.k = 1; 2825 b0->stmts = s; 2826 return b0; 2827 } 2828 2829 if (linktype == DLT_FDDI) { 2830 /* XXX TEST THIS: MIGHT NOT PORT PROPERLY XXX */ 2831 /* fddi[1] & 1 != 0 */ 2832 s = new_stmt(BPF_LD|BPF_B|BPF_ABS); 2833 s->s.k = 1; 2834 b0 = new_block(JMP(BPF_JSET)); 2835 b0->s.k = 1; 2836 b0->stmts = s; 2837 return b0; 2838 } 2839 /* Link not known to support multicasts */ 2840 break; 2841 2842 case Q_IP: 2843 b0 = gen_linktype(ETHERTYPE_IP); 2844 b1 = gen_cmp(off_nl + 16, BPF_B, (bpf_int32)224); 2845 b1->s.code = JMP(BPF_JGE); 2846 gen_and(b0, b1); 2847 return b1; 2848 2849 #ifdef INET6 2850 case Q_IPV6: 2851 b0 = gen_linktype(ETHERTYPE_IPV6); 2852 b1 = gen_cmp(off_nl + 24, BPF_B, (bpf_int32)255); 2853 gen_and(b0, b1); 2854 return b1; 2855 #endif /* INET6 */ 2856 } 2857 bpf_error("only IP multicast filters supported on ethernet/FDDI"); 2858 } 2859 2860 /* 2861 * generate command for inbound/outbound. It's here so we can 2862 * make it link-type specific. 'dir' = 0 implies "inbound", 2863 * = 1 implies "outbound". 2864 */ 2865 struct block * 2866 gen_inbound(dir) 2867 int dir; 2868 { 2869 register struct block *b0; 2870 2871 /* 2872 * Only SLIP and old-style PPP data link types support 2873 * inbound/outbound qualifiers. 2874 */ 2875 switch (linktype) { 2876 case DLT_SLIP: 2877 case DLT_PPP: 2878 /* These are okay. */ 2879 break; 2880 2881 default: 2882 bpf_error("inbound/outbound not supported on linktype 0x%x\n", 2883 linktype); 2884 /* NOTREACHED */ 2885 } 2886 2887 b0 = gen_relation(BPF_JEQ, 2888 gen_load(Q_LINK, gen_loadi(0), 1), 2889 gen_loadi(0), 2890 dir); 2891 return (b0); 2892 } 2893 2894 struct block * 2895 gen_acode(eaddr, q) 2896 register const u_char *eaddr; 2897 struct qual q; 2898 { 2899 if ((q.addr == Q_HOST || q.addr == Q_DEFAULT) && q.proto == Q_LINK) { 2900 if (linktype == DLT_ARCNET) 2901 return gen_ahostop(eaddr, (int)q.dir); 2902 } 2903 bpf_error("ARCnet address used in non-arc expression"); 2904 /* NOTREACHED */ 2905 } 2906 2907 static struct block * 2908 gen_ahostop(eaddr, dir) 2909 register const u_char *eaddr; 2910 register int dir; 2911 { 2912 register struct block *b0, *b1; 2913 2914 switch (dir) { 2915 /* src comes first, different from Ethernet */ 2916 case Q_SRC: 2917 return gen_bcmp(0, 1, eaddr); 2918 2919 case Q_DST: 2920 return gen_bcmp(1, 1, eaddr); 2921 2922 case Q_AND: 2923 b0 = gen_ahostop(eaddr, Q_SRC); 2924 b1 = gen_ahostop(eaddr, Q_DST); 2925 gen_and(b0, b1); 2926 return b1; 2927 2928 case Q_DEFAULT: 2929 case Q_OR: 2930 b0 = gen_ahostop(eaddr, Q_SRC); 2931 b1 = gen_ahostop(eaddr, Q_DST); 2932 gen_or(b0, b1); 2933 return b1; 2934 } 2935 abort(); 2936 /* NOTREACHED */ 2937 } 2938