gencode.c revision 511eca30a483e912c274e1d8ba3a0f8f081e2227
1478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/*#define CHASE_CHAIN*/ 2478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 3478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Copyright (c) 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 1998 4478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * The Regents of the University of California. All rights reserved. 5478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 6478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Redistribution and use in source and binary forms, with or without 7478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * modification, are permitted provided that: (1) source code distributions 8478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * retain the above copyright notice and this paragraph in its entirety, (2) 9478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * distributions including binary code include the above copyright notice and 10478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * this paragraph in its entirety in the documentation or other materials 11478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * provided with the distribution, and (3) all advertising materials mentioning 12478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * features or use of this software display the following acknowledgement: 13478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * ``This product includes software developed by the University of California, 14478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Lawrence Berkeley Laboratory and its contributors.'' Neither the name of 15478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the University nor the names of its contributors may be used to endorse 16478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * or promote products derived from this software without specific prior 17478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * written permission. 18478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED 19478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF 20478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. 21478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 22478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef lint 23478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic const char rcsid[] _U_ = 24511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall "@(#) $Header: /tcpdump/master/libpcap/gencode.c,v 1.309 2008-12-23 20:13:29 guy Exp $ (LBL)"; 25478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 26478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 27478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef HAVE_CONFIG_H 28478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include "config.h" 29478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 30478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 31478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef WIN32 32478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include <pcap-stdinc.h> 33478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#else /* WIN32 */ 34511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#if HAVE_INTTYPES_H 35511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#include <inttypes.h> 36511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#elif HAVE_STDINT_H 37511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#include <stdint.h> 38511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif 39511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#ifdef HAVE_SYS_BITYPES_H 40511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#include <sys/bitypes.h> 41511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif 42478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include <sys/types.h> 43478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include <sys/socket.h> 44478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif /* WIN32 */ 45478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 46478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 47478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - why was this included even on UNIX? 48478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 49478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef __MINGW32__ 50511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#include "ip6_misc.h" 51478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 52478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 53478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef WIN32 54478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 55478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef __NetBSD__ 56478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include <sys/param.h> 57478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 58478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 59478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include <netinet/in.h> 60511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#include <arpa/inet.h> 61478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 62478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif /* WIN32 */ 63478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 64478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include <stdlib.h> 65478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include <string.h> 66478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include <memory.h> 67478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include <setjmp.h> 68478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include <stdarg.h> 69478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 70478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef MSDOS 71478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include "pcap-dos.h" 72478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 73478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 74478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include "pcap-int.h" 75478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 76478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include "ethertype.h" 77478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include "nlpid.h" 78478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include "llc.h" 79478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include "gencode.h" 80511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#include "ieee80211.h" 81478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include "atmuni31.h" 82478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include "sunatmpos.h" 83478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include "ppp.h" 84511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#include "pcap/sll.h" 85511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#include "pcap/ipnet.h" 86478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include "arcnet.h" 87511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#if defined(linux) && defined(PF_PACKET) && defined(SO_ATTACH_FILTER) 88511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#include <linux/types.h> 89511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#include <linux/if_packet.h> 90511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#include <linux/filter.h> 91511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif 92478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef HAVE_NET_PFVAR_H 93478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include <sys/socket.h> 94478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include <net/if.h> 95478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include <net/pfvar.h> 96478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include <net/if_pflog.h> 97478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 98478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef offsetof 99478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#define offsetof(s, e) ((size_t)&((s *)0)->e) 100478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 101478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef INET6 102478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef WIN32 103478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include <netdb.h> /* for "struct addrinfo" */ 104478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif /* WIN32 */ 105478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif /*INET6*/ 106511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#include <pcap/namedb.h> 107478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 108478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#define ETHERMTU 1500 109478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 110511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#ifndef IPPROTO_HOPOPTS 111511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#define IPPROTO_HOPOPTS 0 112511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif 113511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#ifndef IPPROTO_ROUTING 114511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#define IPPROTO_ROUTING 43 115511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif 116511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#ifndef IPPROTO_FRAGMENT 117511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#define IPPROTO_FRAGMENT 44 118511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif 119511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#ifndef IPPROTO_DSTOPTS 120511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#define IPPROTO_DSTOPTS 60 121511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif 122478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef IPPROTO_SCTP 123478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#define IPPROTO_SCTP 132 124478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 125478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 126478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef HAVE_OS_PROTO_H 127478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#include "os-proto.h" 128478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 129478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 130478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#define JMP(c) ((c)|BPF_JMP|BPF_K) 131478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 132478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* Locals */ 133478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic jmp_buf top_ctx; 134478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic pcap_t *bpf_pcap; 135478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 136478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* Hack for updating VLAN, MPLS, and PPPoE offsets. */ 137511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#ifdef WIN32 138478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int orig_linktype = (u_int)-1, orig_nl = (u_int)-1, label_stack_depth = (u_int)-1; 139478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#else 140478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int orig_linktype = -1U, orig_nl = -1U, label_stack_depth = -1U; 141478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 142478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 143478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* XXX */ 144478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic int pcap_fddipad; 145478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 146478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* VARARGS */ 147478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectvoid 148478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectbpf_error(const char *fmt, ...) 149478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 150478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project va_list ap; 151478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 152478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project va_start(ap, fmt); 153478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (bpf_pcap != NULL) 154478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (void)vsnprintf(pcap_geterr(bpf_pcap), PCAP_ERRBUF_SIZE, 155478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project fmt, ap); 156478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project va_end(ap); 157478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project longjmp(top_ctx, 1); 158478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 159478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 160478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 161478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic void init_linktype(pcap_t *); 162478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 163511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic void init_regs(void); 164478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic int alloc_reg(void); 165478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic void free_reg(int); 166478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 167478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *root; 168478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 169478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 170478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Value passed to gen_load_a() to indicate what the offset argument 171478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * is relative to. 172478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 173478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectenum e_offrel { 174478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project OR_PACKET, /* relative to the beginning of the packet */ 175511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall OR_LINK, /* relative to the beginning of the link-layer header */ 176511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall OR_MACPL, /* relative to the end of the MAC-layer header */ 177478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project OR_NET, /* relative to the network-layer header */ 178478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project OR_NET_NOSNAP, /* relative to the network-layer header, with no SNAP header at the link layer */ 179478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project OR_TRAN_IPV4, /* relative to the transport-layer header, with IPv4 network layer */ 180478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project OR_TRAN_IPV6 /* relative to the transport-layer header, with IPv6 network layer */ 181478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project}; 182478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 183511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#ifdef INET6 184511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall/* 185511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * As errors are handled by a longjmp, anything allocated must be freed 186511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * in the longjmp handler, so it must be reachable from that handler. 187511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * One thing that's allocated is the result of pcap_nametoaddrinfo(); 188511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * it must be freed with freeaddrinfo(). This variable points to any 189511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * addrinfo structure that would need to be freed. 190511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 191511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct addrinfo *ai; 192511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif 193511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 194478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 195478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * We divy out chunks of memory rather than call malloc each time so 196478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * we don't have to worry about leaking memory. It's probably 197478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * not a big deal if all this memory was wasted but if this ever 198478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * goes into a library that would probably not be a good idea. 199478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 200478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - this *is* in a library.... 201478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 202478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#define NCHUNKS 16 203478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#define CHUNK0SIZE 1024 204478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct chunk { 205478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int n_left; 206478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project void *m; 207478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project}; 208478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 209478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct chunk chunks[NCHUNKS]; 210478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic int cur_chunk; 211478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 212478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic void *newchunk(u_int); 213478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic void freechunks(void); 214478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic inline struct block *new_block(int); 215478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic inline struct slist *new_stmt(int); 216478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_retblk(int); 217478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic inline void syntax(void); 218478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 219478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic void backpatch(struct block *, struct block *); 220478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic void merge(struct block *, struct block *); 221478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_cmp(enum e_offrel, u_int, u_int, bpf_int32); 222478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_cmp_gt(enum e_offrel, u_int, u_int, bpf_int32); 223478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_cmp_ge(enum e_offrel, u_int, u_int, bpf_int32); 224478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_cmp_lt(enum e_offrel, u_int, u_int, bpf_int32); 225478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_cmp_le(enum e_offrel, u_int, u_int, bpf_int32); 226478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_mcmp(enum e_offrel, u_int, u_int, bpf_int32, 227478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32); 228478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_bcmp(enum e_offrel, u_int, u_int, const u_char *); 229478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_ncmp(enum e_offrel, bpf_u_int32, bpf_u_int32, 230478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32, bpf_u_int32, int, bpf_int32); 231478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct slist *gen_load_llrel(u_int, u_int); 232511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct slist *gen_load_macplrel(u_int, u_int); 233478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct slist *gen_load_a(enum e_offrel, u_int, u_int); 234478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct slist *gen_loadx_iphdrlen(void); 235478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_uncond(int); 236478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic inline struct block *gen_true(void); 237478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic inline struct block *gen_false(void); 238478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_ether_linktype(int); 239511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct block *gen_ipnet_linktype(int); 240478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_linux_sll_linktype(int); 241511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct slist *gen_load_prism_llprefixlen(void); 242511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct slist *gen_load_avs_llprefixlen(void); 243511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct slist *gen_load_radiotap_llprefixlen(void); 244511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct slist *gen_load_ppi_llprefixlen(void); 245511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic void insert_compute_vloffsets(struct block *); 246478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct slist *gen_llprefixlen(void); 247511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct slist *gen_off_macpl(void); 248511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic int ethertype_to_ppptype(int); 249478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_linktype(int); 250511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct block *gen_snap(bpf_u_int32, bpf_u_int32); 251478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_llc_linktype(int); 252478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_hostop(bpf_u_int32, bpf_u_int32, int, int, u_int, u_int); 253478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef INET6 254478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_hostop6(struct in6_addr *, struct in6_addr *, int, int, u_int, u_int); 255478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 256478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_ahostop(const u_char *, int); 257478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_ehostop(const u_char *, int); 258478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_fhostop(const u_char *, int); 259478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_thostop(const u_char *, int); 260478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_wlanhostop(const u_char *, int); 261478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_ipfchostop(const u_char *, int); 262478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_dnhostop(bpf_u_int32, int); 263478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_mpls_linktype(int); 264478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_host(bpf_u_int32, bpf_u_int32, int, int, int); 265478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef INET6 266478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_host6(struct in6_addr *, struct in6_addr *, int, int, int); 267478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 268478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef INET6 269478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_gateway(const u_char *, bpf_u_int32 **, int, int); 270478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 271478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_ipfrag(void); 272478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_portatom(int, bpf_int32); 273478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_portrangeatom(int, bpf_int32, bpf_int32); 274478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_portatom6(int, bpf_int32); 275478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_portrangeatom6(int, bpf_int32, bpf_int32); 276478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block *gen_portop(int, int, int); 277478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_port(int, int, int); 278478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block *gen_portrangeop(int, int, int, int); 279478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_portrange(int, int, int, int); 280478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block *gen_portop6(int, int, int); 281478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_port6(int, int, int); 282478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block *gen_portrangeop6(int, int, int, int); 283478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_portrange6(int, int, int, int); 284478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic int lookup_proto(const char *, int); 285478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_protochain(int, int, int); 286478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_proto(int, int, int); 287478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct slist *xfer_to_x(struct arth *); 288478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct slist *xfer_to_a(struct arth *); 289478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_mac_multicast(int); 290478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_len(int, int); 291511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct block *gen_check_802_11_data_frame(void); 292478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 293478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_ppi_dlt_check(void); 294478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block *gen_msg_abbrev(int type); 295478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 296478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic void * 297478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectnewchunk(n) 298478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int n; 299478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 300478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct chunk *cp; 301478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int k; 302478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project size_t size; 303478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 304478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef __NetBSD__ 305478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* XXX Round up to nearest long. */ 306478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project n = (n + sizeof(long) - 1) & ~(sizeof(long) - 1); 307478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#else 308478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* XXX Round up to structure boundary. */ 309478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project n = ALIGN(n); 310478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 311478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 312478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project cp = &chunks[cur_chunk]; 313478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (n > cp->n_left) { 314478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project ++cp, k = ++cur_chunk; 315478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (k >= NCHUNKS) 316478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("out of memory"); 317478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project size = CHUNK0SIZE << k; 318478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project cp->m = (void *)malloc(size); 319478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (cp->m == NULL) 320478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("out of memory"); 321478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project memset((char *)cp->m, 0, size); 322478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project cp->n_left = size; 323478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (n > size) 324478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("out of memory"); 325478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 326478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project cp->n_left -= n; 327478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (void *)((char *)cp->m + cp->n_left); 328478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 329478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 330478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic void 331478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectfreechunks() 332478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 333478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int i; 334478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 335478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project cur_chunk = 0; 336478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project for (i = 0; i < NCHUNKS; ++i) 337478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (chunks[i].m != NULL) { 338478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project free(chunks[i].m); 339478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project chunks[i].m = NULL; 340478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 341478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 342478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 343478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 344478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * A strdup whose allocations are freed after code generation is over. 345478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 346478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectchar * 347478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectsdup(s) 348478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const char *s; 349478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 350478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int n = strlen(s) + 1; 351478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project char *cp = newchunk(n); 352478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 353478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project strlcpy(cp, s, n); 354478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (cp); 355478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 356478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 357478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic inline struct block * 358478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectnew_block(code) 359478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int code; 360478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 361478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *p; 362478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 363478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project p = (struct block *)newchunk(sizeof(*p)); 364478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project p->s.code = code; 365478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project p->head = p; 366478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 367478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return p; 368478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 369478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 370478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic inline struct slist * 371478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectnew_stmt(code) 372478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int code; 373478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 374478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *p; 375478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 376478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project p = (struct slist *)newchunk(sizeof(*p)); 377478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project p->s.code = code; 378478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 379478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return p; 380478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 381478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 382478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 383478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_retblk(v) 384478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int v; 385478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 386478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b = new_block(BPF_RET|BPF_K); 387478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 388478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b->s.k = v; 389478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 390478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 391478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 392478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic inline void 393478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectsyntax() 394478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 395478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("syntax error in filter expression"); 396478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 397478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 398478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic bpf_u_int32 netmask; 399478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic int snaplen; 400478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectint no_optimize; 401511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#ifdef WIN32 402511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic int 403511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallpcap_compile_unsafe(pcap_t *p, struct bpf_program *program, 404511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall const char *buf, int optimize, bpf_u_int32 mask); 405511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 406511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallint 407511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallpcap_compile(pcap_t *p, struct bpf_program *program, 408511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall const char *buf, int optimize, bpf_u_int32 mask) 409511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall{ 410511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall int result; 411511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 412511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall EnterCriticalSection(&g_PcapCompileCriticalSection); 413511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 414511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall result = pcap_compile_unsafe(p, program, buf, optimize, mask); 415478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 416511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall LeaveCriticalSection(&g_PcapCompileCriticalSection); 417511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 418511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return result; 419511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall} 420511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 421511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic int 422511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallpcap_compile_unsafe(pcap_t *p, struct bpf_program *program, 423511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall const char *buf, int optimize, bpf_u_int32 mask) 424511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#else /* WIN32 */ 425478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectint 426478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectpcap_compile(pcap_t *p, struct bpf_program *program, 427478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project const char *buf, int optimize, bpf_u_int32 mask) 428511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif /* WIN32 */ 429478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 430478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project extern int n_errors; 431478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project const char * volatile xbuf = buf; 432511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall u_int len; 433478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 434511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 435511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If this pcap_t hasn't been activated, it doesn't have a 436511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * link-layer type, so we can't use it. 437511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 438511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (!p->activated) { 439511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall snprintf(p->errbuf, PCAP_ERRBUF_SIZE, 440511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall "not-yet-activated pcap_t passed to pcap_compile"); 441511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (-1); 442511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 443478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project no_optimize = 0; 444478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project n_errors = 0; 445478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project root = NULL; 446478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_pcap = p; 447511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall init_regs(); 448478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (setjmp(top_ctx)) { 449511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#ifdef INET6 450511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (ai != NULL) { 451511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall freeaddrinfo(ai); 452511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall ai = NULL; 453511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 454511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif 455478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project lex_cleanup(); 456478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project freechunks(); 457478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (-1); 458478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 459478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 460478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project netmask = mask; 461478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 462478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project snaplen = pcap_snapshot(p); 463478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (snaplen == 0) { 464478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project snprintf(p->errbuf, PCAP_ERRBUF_SIZE, 465478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project "snaplen of 0 rejects all packets"); 466478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return -1; 467478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 468478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 469478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project lex_init(xbuf ? xbuf : ""); 470478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project init_linktype(p); 471478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (void)pcap_parse(); 472478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 473478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (n_errors) 474478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project syntax(); 475478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 476478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (root == NULL) 477478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project root = gen_retblk(snaplen); 478478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 479478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (optimize && !no_optimize) { 480478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_optimize(&root); 481478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (root == NULL || 482478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (root->s.code == (BPF_RET|BPF_K) && root->s.k == 0)) 483478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("expression rejects all packets"); 484478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 485478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project program->bf_insns = icode_to_fcode(root, &len); 486478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project program->bf_len = len; 487478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 488478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project lex_cleanup(); 489478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project freechunks(); 490478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (0); 491478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 492478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 493478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 494478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * entry point for using the compiler with no pcap open 495478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * pass in all the stuff that is needed explicitly instead. 496478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 497478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectint 498478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectpcap_compile_nopcap(int snaplen_arg, int linktype_arg, 499478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct bpf_program *program, 500478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project const char *buf, int optimize, bpf_u_int32 mask) 501478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 502478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project pcap_t *p; 503478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int ret; 504478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 505478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project p = pcap_open_dead(linktype_arg, snaplen_arg); 506478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (p == NULL) 507478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (-1); 508478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project ret = pcap_compile(p, program, buf, optimize, mask); 509478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project pcap_close(p); 510478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (ret); 511478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 512478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 513478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 514478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Clean up a "struct bpf_program" by freeing all the memory allocated 515478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * in it. 516478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 517478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectvoid 518478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectpcap_freecode(struct bpf_program *program) 519478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 520478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project program->bf_len = 0; 521478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (program->bf_insns != NULL) { 522478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project free((char *)program->bf_insns); 523478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project program->bf_insns = NULL; 524478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 525478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 526478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 527478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 528478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Backpatch the blocks in 'list' to 'target'. The 'sense' field indicates 529478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * which of the jt and jf fields has been resolved and which is a pointer 530478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * back to another unresolved block (or nil). At least one of the fields 531478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * in each block is already resolved. 532478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 533478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic void 534478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectbackpatch(list, target) 535478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *list, *target; 536478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 537478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *next; 538478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 539478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project while (list) { 540478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!list->sense) { 541478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project next = JT(list); 542478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project JT(list) = target; 543478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else { 544478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project next = JF(list); 545478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project JF(list) = target; 546478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 547478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project list = next; 548478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 549478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 550478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 551478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 552478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Merge the lists in b0 and b1, using the 'sense' field to indicate 553478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * which of jt and jf is the link. 554478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 555478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic void 556478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectmerge(b0, b1) 557478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1; 558478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 559478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register struct block **p = &b0; 560478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 561478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Find end of list. */ 562478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project while (*p) 563478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project p = !((*p)->sense) ? &JT(*p) : &JF(*p); 564478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 565478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Concatenate the lists. */ 566478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project *p = b1; 567478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 568478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 569478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectvoid 570478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectfinish_parse(p) 571478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *p; 572478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 573478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *ppi_dlt_check; 574478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 575478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 576478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Insert before the statements of the first (root) block any 577478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * statements needed to load the lengths of any variable-length 578478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * headers into registers. 579478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 580478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - a fancier strategy would be to insert those before the 581478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * statements of all blocks that use those lengths and that 582478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * have no predecessors that use them, so that we only compute 583478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the lengths if we need them. There might be even better 584511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * approaches than that. 585511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 586511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * However, those strategies would be more complicated, and 587511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * as we don't generate code to compute a length if the 588511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * program has no tests that use the length, and as most 589511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * tests will probably use those lengths, we would just 590511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * postpone computing the lengths so that it's not done 591511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * for tests that fail early, and it's not clear that's 592511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * worth the effort. 593511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 594511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall insert_compute_vloffsets(p->head); 595511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 596511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 597511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * For DLT_PPI captures, generate a check of the per-packet 598511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * DLT value to make sure it's DLT_IEEE802_11. 599478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 600511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall ppi_dlt_check = gen_ppi_dlt_check(); 601511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (ppi_dlt_check != NULL) 602511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(ppi_dlt_check, p); 603478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 604511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall backpatch(p, gen_retblk(snaplen)); 605511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall p->sense = !p->sense; 606511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall backpatch(p, gen_retblk(0)); 607511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall root = p->head; 608478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 609478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 610478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectvoid 611478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_and(b0, b1) 612478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1; 613478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 614478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project backpatch(b0, b1->head); 615478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0->sense = !b0->sense; 616478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->sense = !b1->sense; 617478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project merge(b1, b0); 618478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->sense = !b1->sense; 619478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->head = b0->head; 620478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 621478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 622478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectvoid 623478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_or(b0, b1) 624478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1; 625478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 626478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0->sense = !b0->sense; 627478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project backpatch(b0, b1->head); 628478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0->sense = !b0->sense; 629478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project merge(b1, b0); 630478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->head = b0->head; 631478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 632478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 633478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectvoid 634478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_not(b) 635478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b; 636478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 637478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b->sense = !b->sense; 638478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 639478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 640478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 641478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_cmp(offrel, offset, size, v) 642478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project enum e_offrel offrel; 643478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int offset, size; 644478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 v; 645478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 646478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_ncmp(offrel, offset, size, 0xffffffff, BPF_JEQ, 0, v); 647478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 648478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 649478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 650478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_cmp_gt(offrel, offset, size, v) 651478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project enum e_offrel offrel; 652478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int offset, size; 653478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 v; 654478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 655478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_ncmp(offrel, offset, size, 0xffffffff, BPF_JGT, 0, v); 656478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 657478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 658478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 659478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_cmp_ge(offrel, offset, size, v) 660478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project enum e_offrel offrel; 661478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int offset, size; 662478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 v; 663478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 664478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_ncmp(offrel, offset, size, 0xffffffff, BPF_JGE, 0, v); 665478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 666478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 667478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 668478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_cmp_lt(offrel, offset, size, v) 669478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project enum e_offrel offrel; 670478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int offset, size; 671478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 v; 672478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 673478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_ncmp(offrel, offset, size, 0xffffffff, BPF_JGE, 1, v); 674478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 675478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 676478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 677478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_cmp_le(offrel, offset, size, v) 678478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project enum e_offrel offrel; 679478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int offset, size; 680478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 v; 681478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 682478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_ncmp(offrel, offset, size, 0xffffffff, BPF_JGT, 1, v); 683478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 684478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 685478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 686478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_mcmp(offrel, offset, size, v, mask) 687478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project enum e_offrel offrel; 688478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int offset, size; 689478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 v; 690478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 mask; 691478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 692478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_ncmp(offrel, offset, size, mask, BPF_JEQ, 0, v); 693478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 694478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 695478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 696478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_bcmp(offrel, offset, size, v) 697478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project enum e_offrel offrel; 698478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register u_int offset, size; 699478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const u_char *v; 700478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 701478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register struct block *b, *tmp; 702478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 703478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = NULL; 704478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project while (size >= 4) { 705478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const u_char *p = &v[size - 4]; 706478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 w = ((bpf_int32)p[0] << 24) | 707478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project ((bpf_int32)p[1] << 16) | ((bpf_int32)p[2] << 8) | p[3]; 708478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 709478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_cmp(offrel, offset + size - 4, BPF_W, w); 710478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (b != NULL) 711478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b, tmp); 712478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = tmp; 713478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project size -= 4; 714478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 715478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project while (size >= 2) { 716478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const u_char *p = &v[size - 2]; 717478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 w = ((bpf_int32)p[0] << 8) | p[1]; 718478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 719478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_cmp(offrel, offset + size - 2, BPF_H, w); 720478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (b != NULL) 721478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b, tmp); 722478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = tmp; 723478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project size -= 2; 724478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 725478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (size > 0) { 726478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_cmp(offrel, offset, BPF_B, (bpf_int32)v[0]); 727478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (b != NULL) 728478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b, tmp); 729478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = tmp; 730478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 731478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 732478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 733478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 734478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 735478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * AND the field of size "size" at offset "offset" relative to the header 736478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * specified by "offrel" with "mask", and compare it with the value "v" 737478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * with the test specified by "jtype"; if "reverse" is true, the test 738478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * should test the opposite of "jtype". 739478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 740478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 741478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_ncmp(offrel, offset, size, mask, jtype, reverse, v) 742478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project enum e_offrel offrel; 743478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 v; 744478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 offset, size, mask, jtype; 745478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int reverse; 746478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 747478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s, *s2; 748478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b; 749478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 750478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_load_a(offrel, offset, size); 751478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 752478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (mask != 0xffffffff) { 753478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_ALU|BPF_AND|BPF_K); 754478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2->s.k = mask; 755478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, s2); 756478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 757478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 758478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = new_block(JMP(jtype)); 759478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b->stmts = s; 760478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b->s.k = v; 761478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (reverse && (jtype == BPF_JGT || jtype == BPF_JGE)) 762478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b); 763478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 764478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 765478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 766478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 767478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Various code constructs need to know the layout of the data link 768478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * layer. These variables give the necessary offsets from the beginning 769478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of the packet data. 770478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 771478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 772478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 773478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This is the offset of the beginning of the link-layer header from 774478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the beginning of the raw packet data. 775478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 776478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * It's usually 0, except for 802.11 with a fixed-length radio header. 777478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (For 802.11 with a variable-length radio header, we have to generate 778478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * code to compute that offset; off_ll is 0 in that case.) 779478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 780478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int off_ll; 781478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 782478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 783511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If there's a variable-length header preceding the link-layer header, 784511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * "reg_off_ll" is the register number for a register containing the 785511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * length of that header, and therefore the offset of the link-layer 786511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * header from the beginning of the raw packet data. Otherwise, 787511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * "reg_off_ll" is -1. 788511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 789511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic int reg_off_ll; 790511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 791511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall/* 792511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * This is the offset of the beginning of the MAC-layer header from 793511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the beginning of the link-layer header. 794478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * It's usually 0, except for ATM LANE, where it's the offset, relative 795511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * to the beginning of the raw packet data, of the Ethernet header, and 796511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * for Ethernet with various additional information. 797478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 798478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int off_mac; 799478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 800478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 801511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * This is the offset of the beginning of the MAC-layer payload, 802511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * from the beginning of the raw packet data. 803511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 804511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * I.e., it's the sum of the length of the link-layer header (without, 805511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * for example, any 802.2 LLC header, so it's the MAC-layer 806511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * portion of that header), plus any prefix preceding the 807511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * link-layer header. 808511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 809511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic u_int off_macpl; 810511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 811511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall/* 812511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * This is 1 if the offset of the beginning of the MAC-layer payload 813511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * from the beginning of the link-layer header is variable-length. 814511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 815511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic int off_macpl_is_variable; 816511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 817511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall/* 818511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If the link layer has variable_length headers, "reg_off_macpl" 819511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * is the register number for a register containing the length of the 820511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * link-layer header plus the length of any variable-length header 821511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * preceding the link-layer header. Otherwise, "reg_off_macpl" 822511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * is -1. 823511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 824511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic int reg_off_macpl; 825511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 826511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall/* 827478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "off_linktype" is the offset to information in the link-layer header 828478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * giving the packet type. This offset is relative to the beginning 829478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of the link-layer header (i.e., it doesn't include off_ll). 830478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 831478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For Ethernet, it's the offset of the Ethernet type field. 832478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 833478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For link-layer types that always use 802.2 headers, it's the 834478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * offset of the LLC header. 835478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 836478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For PPP, it's the offset of the PPP type field. 837478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 838478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For Cisco HDLC, it's the offset of the CHDLC type field. 839478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 840478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For BSD loopback, it's the offset of the AF_ value. 841478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 842478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For Linux cooked sockets, it's the offset of the type field. 843478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 844478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * It's set to -1 for no encapsulation, in which case, IP is assumed. 845478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 846478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int off_linktype; 847478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 848478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 849511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * TRUE if "pppoes" appeared in the filter; it causes link-layer type 850511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * checks to check the PPP header, assumed to follow a LAN-style link- 851511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * layer header and a PPPoE session header. 852511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 853511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic int is_pppoes = 0; 854511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 855511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall/* 856478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * TRUE if the link layer includes an ATM pseudo-header. 857478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 858478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic int is_atm = 0; 859478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 860478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 861478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * TRUE if "lane" appeared in the filter; it causes us to generate 862478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * code that assumes LANE rather than LLC-encapsulated traffic in SunATM. 863478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 864478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic int is_lane = 0; 865478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 866478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 867478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * These are offsets for the ATM pseudo-header. 868478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 869478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int off_vpi; 870478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int off_vci; 871478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int off_proto; 872478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 873478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 874478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * These are offsets for the MTP2 fields. 875478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 876478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int off_li; 877511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic u_int off_li_hsl; 878478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 879478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 880478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * These are offsets for the MTP3 fields. 881478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 882478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int off_sio; 883478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int off_opc; 884478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int off_dpc; 885478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int off_sls; 886478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 887478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 888478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This is the offset of the first byte after the ATM pseudo_header, 889478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * or -1 if there is no ATM pseudo-header. 890478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 891478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int off_payload; 892478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 893478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 894478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * These are offsets to the beginning of the network-layer header. 895511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * They are relative to the beginning of the MAC-layer payload (i.e., 896511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * they don't include off_ll or off_macpl). 897478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 898478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If the link layer never uses 802.2 LLC: 899478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 900478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "off_nl" and "off_nl_nosnap" are the same. 901478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 902478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If the link layer always uses 802.2 LLC: 903478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 904478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "off_nl" is the offset if there's a SNAP header following 905478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the 802.2 header; 906478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 907478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "off_nl_nosnap" is the offset if there's no SNAP header. 908478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 909478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If the link layer is Ethernet: 910478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 911478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "off_nl" is the offset if the packet is an Ethernet II packet 912478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (we assume no 802.3+802.2+SNAP); 913478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 914478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "off_nl_nosnap" is the offset if the packet is an 802.3 packet 915478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * with an 802.2 header following it. 916478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 917478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int off_nl; 918478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_int off_nl_nosnap; 919478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 920478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic int linktype; 921478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 922478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic void 923478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectinit_linktype(p) 924478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project pcap_t *p; 925478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 926478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project linktype = pcap_datalink(p); 927478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project pcap_fddipad = p->fddipad; 928478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 929478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 930478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Assume it's not raw ATM with a pseudo-header, for now. 931478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 932478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_mac = 0; 933478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project is_atm = 0; 934478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project is_lane = 0; 935478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_vpi = -1; 936478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_vci = -1; 937478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_proto = -1; 938478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_payload = -1; 939478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 940478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 941511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * And that we're not doing PPPoE. 942511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 943511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall is_pppoes = 0; 944511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 945511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 946478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * And assume we're not doing SS7. 947478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 948478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_li = -1; 949511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_li_hsl = -1; 950478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_sio = -1; 951478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_opc = -1; 952478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_dpc = -1; 953478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_sls = -1; 954478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 955478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 956511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Also assume it's not 802.11. 957478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 958478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_ll = 0; 959511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 0; 960511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl_is_variable = 0; 961478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 962478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project orig_linktype = -1; 963478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project orig_nl = -1; 964478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project label_stack_depth = 0; 965478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 966511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall reg_off_ll = -1; 967511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall reg_off_macpl = -1; 968478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 969478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (linktype) { 970478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 971478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_ARCNET: 972478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 2; 973511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 6; 974511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; /* XXX in reality, variable! */ 975511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 0; /* no 802.2 LLC */ 976478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 977478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 978478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_ARCNET_LINUX: 979478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 4; 980511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 8; 981511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; /* XXX in reality, variable! */ 982511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 0; /* no 802.2 LLC */ 983478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 984478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 985478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_EN10MB: 986478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 12; 987511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 14; /* Ethernet header length */ 988511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; /* Ethernet II */ 989511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 3; /* 802.3+802.2 */ 990478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 991478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 992478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_SLIP: 993478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 994478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * SLIP doesn't have a link level type. The 16 byte 995478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * header is hacked into our SLIP driver. 996478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 997478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = -1; 998511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 16; 999511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1000511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 0; /* no 802.2 LLC */ 1001478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1002478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1003478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_SLIP_BSDOS: 1004478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* XXX this may be the same as the DLT_PPP_BSDOS case */ 1005478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = -1; 1006478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* XXX end */ 1007511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 24; 1008511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1009511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 0; /* no 802.2 LLC */ 1010478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1011478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1012478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_NULL: 1013478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_LOOP: 1014478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 0; 1015511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 4; 1016511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1017511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 0; /* no 802.2 LLC */ 1018478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1019478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1020478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_ENC: 1021478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 0; 1022511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 12; 1023511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1024511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 0; /* no 802.2 LLC */ 1025478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1026478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1027478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PPP: 1028478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PPP_PPPD: 1029478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_C_HDLC: /* BSD/OS Cisco HDLC */ 1030478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PPP_SERIAL: /* NetBSD sync/async serial PPP */ 1031478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 2; 1032511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 4; 1033511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1034511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 0; /* no 802.2 LLC */ 1035478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1036478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1037478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PPP_ETHER: 1038478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1039478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This does no include the Ethernet header, and 1040478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * only covers session state. 1041478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1042478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 6; 1043511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 8; 1044511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1045511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 0; /* no 802.2 LLC */ 1046478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1047478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1048478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PPP_BSDOS: 1049478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 5; 1050511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 24; 1051511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1052511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 0; /* no 802.2 LLC */ 1053478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1054478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1055478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_FDDI: 1056478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1057478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * FDDI doesn't really have a link-level type field. 1058478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * We set "off_linktype" to the offset of the LLC header. 1059478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1060478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * To check for Ethernet types, we assume that SSAP = SNAP 1061478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * is being used and pick out the encapsulated Ethernet type. 1062478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - should we generate code to check for SNAP? 1063478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1064478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 13; 1065478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype += pcap_fddipad; 1066511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 13; /* FDDI MAC header length */ 1067511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl += pcap_fddipad; 1068511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 8; /* 802.2+SNAP */ 1069511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 3; /* 802.2 */ 1070478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1071478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1072478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IEEE802: 1073478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1074478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Token Ring doesn't really have a link-level type field. 1075478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * We set "off_linktype" to the offset of the LLC header. 1076478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1077478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * To check for Ethernet types, we assume that SSAP = SNAP 1078478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * is being used and pick out the encapsulated Ethernet type. 1079478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - should we generate code to check for SNAP? 1080478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1081478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - the header is actually variable-length. 1082478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Some various Linux patched versions gave 38 1083478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * as "off_linktype" and 40 as "off_nl"; however, 1084478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * if a token ring packet has *no* routing 1085478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * information, i.e. is not source-routed, the correct 1086478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * values are 20 and 22, as they are in the vanilla code. 1087478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1088478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * A packet is source-routed iff the uppermost bit 1089478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of the first byte of the source address, at an 1090478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * offset of 8, has the uppermost bit set. If the 1091478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * packet is source-routed, the total number of bytes 1092478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of routing information is 2 plus bits 0x1F00 of 1093478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the 16-bit value at an offset of 14 (shifted right 1094478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 8 - figure out which byte that is). 1095478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1096478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 14; 1097511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 14; /* Token Ring MAC header length */ 1098511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 8; /* 802.2+SNAP */ 1099511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 3; /* 802.2 */ 1100478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1101478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1102478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IEEE802_11: 1103511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PRISM_HEADER: 1104511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO_AVS: 1105511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO: 1106478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1107478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 802.11 doesn't really have a link-level type field. 1108478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * We set "off_linktype" to the offset of the LLC header. 1109478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1110478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * To check for Ethernet types, we assume that SSAP = SNAP 1111478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * is being used and pick out the encapsulated Ethernet type. 1112478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - should we generate code to check for SNAP? 1113478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1114511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * We also handle variable-length radio headers here. 1115511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * The Prism header is in theory variable-length, but in 1116511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * practice it's always 144 bytes long. However, some 1117511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * drivers on Linux use ARPHRD_IEEE80211_PRISM, but 1118511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * sometimes or always supply an AVS header, so we 1119511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * have to check whether the radio header is a Prism 1120511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * header or an AVS header, so, in practice, it's 1121511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * variable-length. 1122478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1123478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 24; 1124511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 0; /* link-layer header is variable-length */ 1125511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl_is_variable = 1; 1126511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 8; /* 802.2+SNAP */ 1127511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 3; /* 802.2 */ 1128478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1129478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1130478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PPI: 1131511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 1132511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * At the moment we treat PPI the same way that we treat 1133511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * normal Radiotap encoded packets. The difference is in 1134511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the function that generates the code at the beginning 1135511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * to compute the header length. Since this code generator 1136511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * of PPI supports bare 802.11 encapsulation only (i.e. 1137511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the encapsulated DLT should be DLT_IEEE802_11) we 1138511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * generate code to check for this too. 1139478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1140478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 24; 1141511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 0; /* link-layer header is variable-length */ 1142511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl_is_variable = 1; 1143511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 8; /* 802.2+SNAP */ 1144511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 3; /* 802.2 */ 1145478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1146478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1147478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_ATM_RFC1483: 1148478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_ATM_CLIP: /* Linux ATM defines this */ 1149478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1150478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * assume routed, non-ISO PDUs 1151478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (i.e., LLC = 0xAA-AA-03, OUT = 0x00-00-00) 1152478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1153478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - what about ISO PDUs, e.g. CLNP, ISIS, ESIS, 1154478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * or PPP with the PPP NLPID (e.g., PPPoA)? The 1155478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * latter would presumably be treated the way PPPoE 1156478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * should be, so you can do "pppoe and udp port 2049" 1157478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * or "pppoa and tcp port 80" and have it check for 1158478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * PPPo{A,E} and a PPP protocol of IP and.... 1159478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1160478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 0; 1161511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 0; /* packet begins with LLC header */ 1162478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl = 8; /* 802.2+SNAP */ 1163478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap = 3; /* 802.2 */ 1164478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1165478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1166478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_SUNATM: 1167478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1168478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Full Frontal ATM; you get AALn PDUs with an ATM 1169478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * pseudo-header. 1170478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1171478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project is_atm = 1; 1172478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_vpi = SUNATM_VPI_POS; 1173478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_vci = SUNATM_VCI_POS; 1174478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_proto = PROTO_POS; 1175511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_mac = -1; /* assume LLC-encapsulated, so no MAC-layer header */ 1176478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_payload = SUNATM_PKT_BEGIN_POS; 1177478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = off_payload; 1178511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = off_payload; /* if LLC-encapsulated */ 1179511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 8; /* 802.2+SNAP */ 1180511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 3; /* 802.2 */ 1181478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1182478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1183478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_RAW: 1184511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IPV4: 1185511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IPV6: 1186478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = -1; 1187511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 0; 1188478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl = 0; 1189478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap = 0; /* no 802.2 LLC */ 1190478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1191478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1192478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_LINUX_SLL: /* fake header for Linux cooked socket */ 1193478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 14; 1194511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 16; 1195511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1196511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 0; /* no 802.2 LLC */ 1197478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1198478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1199478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_LTALK: 1200478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1201478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * LocalTalk does have a 1-byte type field in the LLAP header, 1202478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * but really it just indicates whether there is a "short" or 1203478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "long" DDP packet following. 1204478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1205478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = -1; 1206511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 0; 1207478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl = 0; 1208478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap = 0; /* no 802.2 LLC */ 1209478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1210478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1211478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IP_OVER_FC: 1212478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1213478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * RFC 2625 IP-over-Fibre-Channel doesn't really have a 1214478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * link-level type field. We set "off_linktype" to the 1215478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * offset of the LLC header. 1216478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1217478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * To check for Ethernet types, we assume that SSAP = SNAP 1218478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * is being used and pick out the encapsulated Ethernet type. 1219478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - should we generate code to check for SNAP? RFC 1220478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 2625 says SNAP should be used. 1221478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1222478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 16; 1223511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 16; 1224511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 8; /* 802.2+SNAP */ 1225511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 3; /* 802.2 */ 1226478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1227478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1228478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_FRELAY: 1229478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1230478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - we should set this to handle SNAP-encapsulated 1231478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frames (NLPID of 0x80). 1232478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1233478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = -1; 1234511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 0; 1235478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl = 0; 1236478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap = 0; /* no 802.2 LLC */ 1237478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1238478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1239478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1240478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the only BPF-interesting FRF.16 frames are non-control frames; 1241478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Frame Relay has a variable length link-layer 1242478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * so lets start with offset 4 for now and increments later on (FIXME); 1243478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1244478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_MFR: 1245478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = -1; 1246511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 0; 1247478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl = 4; 1248478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap = 0; /* XXX - for now -> no 802.2 LLC */ 1249478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1250478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1251478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_APPLE_IP_OVER_IEEE1394: 1252478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 16; 1253511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 18; 1254511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1255511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 0; /* no 802.2 LLC */ 1256478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1257478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1258478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_SYMANTEC_FIREWALL: 1259478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 6; 1260511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 44; 1261511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; /* Ethernet II */ 1262511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 0; /* XXX - what does it do with 802.3 packets? */ 1263478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1264478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1265478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef HAVE_NET_PFVAR_H 1266478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PFLOG: 1267478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 0; 1268511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = PFLOG_HDRLEN; 1269511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1270511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 0; /* no 802.2 LLC */ 1271478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1272478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 1273478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1274478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_MFR: 1275478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_MLFR: 1276478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_MLPPP: 1277478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_PPP: 1278478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_CHDLC: 1279478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_FRELAY: 1280478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 4; 1281511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 4; 1282511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1283478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap = -1; /* no 802.2 LLC */ 1284478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1285478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1286478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_ATM1: 1287511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_linktype = 4; /* in reality variable between 4-8 */ 1288511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 4; /* in reality variable between 4-8 */ 1289511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1290511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 10; 1291478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1292478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1293478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_ATM2: 1294511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_linktype = 8; /* in reality variable between 8-12 */ 1295511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 8; /* in reality variable between 8-12 */ 1296511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1297511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 10; 1298478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1299478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1300478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* frames captured on a Juniper PPPoE service PIC 1301478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * contain raw ethernet frames */ 1302478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_PPPOE: 1303478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_ETHER: 1304511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 14; 1305478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 16; 1306478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl = 18; /* Ethernet II */ 1307478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap = 21; /* 802.3+802.2 */ 1308478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1309478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1310478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_PPPOE_ATM: 1311478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 4; 1312511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 6; 1313511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1314511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = -1; /* no 802.2 LLC */ 1315478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1316478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1317478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_GGSN: 1318478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 6; 1319511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 12; 1320511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1321511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = -1; /* no 802.2 LLC */ 1322478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1323478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1324478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_ES: 1325478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 6; 1326511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = -1; /* not really a network layer but raw IP addresses */ 1327511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = -1; /* not really a network layer but raw IP addresses */ 1328478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap = -1; /* no 802.2 LLC */ 1329478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1330478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1331478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_MONITOR: 1332478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 12; 1333511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 12; 1334511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; /* raw IP/IP6 header */ 1335478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap = -1; /* no 802.2 LLC */ 1336478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1337478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1338511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_BACNET_MS_TP: 1339511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_linktype = -1; 1340511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = -1; 1341511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = -1; 1342511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = -1; 1343511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return; 1344511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1345478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_SERVICES: 1346478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 12; 1347511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = -1; /* L3 proto location dep. on cookie type */ 1348478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl = -1; /* L3 proto location dep. on cookie type */ 1349478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap = -1; /* no 802.2 LLC */ 1350478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1351478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1352478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_VP: 1353478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = 18; 1354511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = -1; 1355511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = -1; 1356511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = -1; 1357511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return; 1358511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1359511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_ST: 1360511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_linktype = 18; 1361511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = -1; 1362511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = -1; 1363511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = -1; 1364511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return; 1365511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1366511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_ISM: 1367511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_linktype = 8; 1368511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = -1; 1369511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = -1; 1370511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = -1; 1371511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return; 1372511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1373511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_VS: 1374511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_SRX_E2E: 1375511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_FIBRECHANNEL: 1376511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_ATM_CEMIC: 1377511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_linktype = 8; 1378511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = -1; 1379478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl = -1; 1380478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap = -1; 1381478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1382478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1383478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_MTP2: 1384478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_li = 2; 1385511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_li_hsl = 4; 1386478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_sio = 3; 1387478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_opc = 4; 1388478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_dpc = 4; 1389478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_sls = 7; 1390478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = -1; 1391511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = -1; 1392478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl = -1; 1393478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap = -1; 1394478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1395478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1396478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_MTP2_WITH_PHDR: 1397478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_li = 6; 1398511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_li_hsl = 8; 1399478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_sio = 7; 1400478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_opc = 8; 1401478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_dpc = 8; 1402478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_sls = 11; 1403478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = -1; 1404511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = -1; 1405478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl = -1; 1406478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap = -1; 1407478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1408478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1409511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_ERF: 1410511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_li = 22; 1411511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_li_hsl = 24; 1412511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_sio = 23; 1413511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_opc = 24; 1414511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_dpc = 24; 1415511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_sls = 27; 1416478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = -1; 1417511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = -1; 1418511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = -1; 1419511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = -1; 1420478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1421478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1422511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PFSYNC: 1423478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = -1; 1424511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 4; 1425511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1426511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 0; 1427478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1428478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1429511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_AX25_KISS: 1430478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1431478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Currently, only raw "link[N:M]" filtering is supported. 1432478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1433511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_linktype = -1; /* variable, min 15, max 71 steps of 7 */ 1434511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = -1; 1435511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = -1; /* variable, min 16, max 71 steps of 7 */ 1436511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = -1; /* no 802.2 LLC */ 1437511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_mac = 1; /* step over the kiss length byte */ 1438511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return; 1439511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1440511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IPNET: 1441511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_linktype = 1; 1442511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 24; /* ipnet header length */ 1443511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; 1444478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap = -1; 1445478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return; 1446478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1447511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER: 1448511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_mac = 4; /* MAC header is past 4-byte pseudo-header */ 1449511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_linktype = 16; /* includes 4-byte pseudo-header */ 1450511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 18; /* pseudo-header+Ethernet header length */ 1451511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; /* Ethernet II */ 1452511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 3; /* 802.3+802.2 */ 1453511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return; 1454511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1455511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER_TRANSPARENT: 1456511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_mac = 12; /* MAC header is past 4-byte pseudo-header, preamble, and SFD */ 1457511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_linktype = 24; /* includes 4-byte pseudo-header+preamble+SFD */ 1458511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = 26; /* pseudo-header+preamble+SFD+Ethernet header length */ 1459511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; /* Ethernet II */ 1460511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 3; /* 802.3+802.2 */ 1461511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return; 1462511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1463511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall default: 1464478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1465511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * For values in the range in which we've assigned new 1466511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * DLT_ values, only raw "link[N:M]" filtering is supported. 1467478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1468511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (linktype >= DLT_MATCHING_MIN && 1469511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall linktype <= DLT_MATCHING_MAX) { 1470511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_linktype = -1; 1471511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = -1; 1472511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = -1; 1473511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = -1; 1474511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return; 1475511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 1476511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1477478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 1478478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unknown data link type %d", linktype); 1479478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 1480478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 1481478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1482478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 1483478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Load a value relative to the beginning of the link-layer header. 1484478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * The link-layer header doesn't necessarily begin at the beginning 1485478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of the packet data; there might be a variable-length prefix containing 1486478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * radio information. 1487478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1488478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct slist * 1489478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_load_llrel(offset, size) 1490478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int offset, size; 1491478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 1492478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s, *s2; 1493478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1494478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_llprefixlen(); 1495478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1496478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1497478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If "s" is non-null, it has code to arrange that the X register 1498478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * contains the length of the prefix preceding the link-layer 1499478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * header. 1500478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1501478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Otherwise, the length of the prefix preceding the link-layer 1502478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * header is "off_ll". 1503478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1504478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (s != NULL) { 1505478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1506478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * There's a variable-length prefix preceding the 1507478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * link-layer header. "s" points to a list of statements 1508478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * that put the length of that prefix into the X register. 1509478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * do an indirect load, to use the X register as an offset. 1510478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1511478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_LD|BPF_IND|size); 1512478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2->s.k = offset; 1513478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, s2); 1514478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else { 1515478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1516478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * There is no variable-length header preceding the 1517478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * link-layer header; add in off_ll, which, if there's 1518478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * a fixed-length header preceding the link-layer header, 1519478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * is the length of that header. 1520478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1521478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_LD|BPF_ABS|size); 1522478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s->s.k = offset + off_ll; 1523478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 1524478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return s; 1525478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 1526478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1527511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall/* 1528511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Load a value relative to the beginning of the MAC-layer payload. 1529511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 1530511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct slist * 1531511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallgen_load_macplrel(offset, size) 1532511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall u_int offset, size; 1533511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall{ 1534511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *s, *s2; 1535511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1536511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_off_macpl(); 1537511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1538511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 1539511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If s is non-null, the offset of the MAC-layer payload is 1540511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * variable, and s points to a list of instructions that 1541511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * arrange that the X register contains that offset. 1542511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 1543511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Otherwise, the offset of the MAC-layer payload is constant, 1544511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * and is in off_macpl. 1545511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 1546511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (s != NULL) { 1547511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 1548511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * The offset of the MAC-layer payload is in the X 1549511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * register. Do an indirect load, to use the X register 1550511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * as an offset. 1551511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 1552511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_LD|BPF_IND|size); 1553511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = offset; 1554511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, s2); 1555511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } else { 1556511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 1557511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * The offset of the MAC-layer payload is constant, 1558511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * and is in off_macpl; load the value at that offset 1559511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * plus the specified offset. 1560511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 1561511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = new_stmt(BPF_LD|BPF_ABS|size); 1562511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s->s.k = off_macpl + offset; 1563511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 1564511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return s; 1565511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall} 1566478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1567478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 1568478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Load a value relative to the beginning of the specified header. 1569478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1570478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct slist * 1571478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_load_a(offrel, offset, size) 1572478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project enum e_offrel offrel; 1573478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int offset, size; 1574478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 1575478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s, *s2; 1576478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1577478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (offrel) { 1578478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1579478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case OR_PACKET: 1580478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_LD|BPF_ABS|size); 1581478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s->s.k = offset; 1582478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 1583478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1584478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case OR_LINK: 1585478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_load_llrel(offset, size); 1586478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 1587478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1588511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case OR_MACPL: 1589511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_macplrel(offset, size); 1590511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 1591511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1592511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case OR_NET: 1593511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_macplrel(off_nl + offset, size); 1594478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 1595478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1596478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case OR_NET_NOSNAP: 1597511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_macplrel(off_nl_nosnap + offset, size); 1598478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 1599478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1600478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case OR_TRAN_IPV4: 1601478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1602478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Load the X register with the length of the IPv4 header 1603478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (plus the offset of the link-layer header, if it's 1604478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * preceded by a variable-length header such as a radio 1605478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * header), in bytes. 1606478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1607478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_loadx_iphdrlen(); 1608478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1609478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1610511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Load the item at {offset of the MAC-layer payload} + 1611511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * {offset, relative to the start of the MAC-layer 1612511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * paylod, of the IPv4 header} + {length of the IPv4 header} + 1613478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * {specified offset}. 1614478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1615511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * (If the offset of the MAC-layer payload is variable, 1616511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * it's included in the value in the X register, and 1617511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * off_macpl is 0.) 1618478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1619478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_LD|BPF_IND|size); 1620511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = off_macpl + off_nl + offset; 1621478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, s2); 1622478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 1623478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1624478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case OR_TRAN_IPV6: 1625511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_macplrel(off_nl + 40 + offset, size); 1626478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 1627478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1628478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 1629478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 1630478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return NULL; 1631478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 1632478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return s; 1633478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 1634478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1635478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 1636478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Generate code to load into the X register the sum of the length of 1637478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the IPv4 header and any variable-length header preceding the link-layer 1638478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * header. 1639478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1640478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct slist * 1641478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_loadx_iphdrlen() 1642478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 1643478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s, *s2; 1644478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1645511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_off_macpl(); 1646478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (s != NULL) { 1647478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1648478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * There's a variable-length prefix preceding the 1649511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * link-layer header, or the link-layer header is itself 1650511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * variable-length. "s" points to a list of statements 1651511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * that put the offset of the MAC-layer payload into 1652511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the X register. 1653511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 1654478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * The 4*([k]&0xf) addressing mode can't be used, as we 1655478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * don't have a constant offset, so we have to load the 1656478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * value in question into the A register and add to it 1657478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the value from the X register. 1658478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1659478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_LD|BPF_IND|BPF_B); 1660478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2->s.k = off_nl; 1661478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, s2); 1662478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_ALU|BPF_AND|BPF_K); 1663478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2->s.k = 0xf; 1664478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, s2); 1665478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_ALU|BPF_LSH|BPF_K); 1666478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2->s.k = 2; 1667478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, s2); 1668478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1669478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1670478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * The A register now contains the length of the 1671511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * IP header. We need to add to it the offset of 1672511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the MAC-layer payload, which is still in the X 1673511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * register, and move the result into the X register. 1674478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1675478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, new_stmt(BPF_ALU|BPF_ADD|BPF_X)); 1676478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, new_stmt(BPF_MISC|BPF_TAX)); 1677478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else { 1678478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1679478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * There is no variable-length header preceding the 1680511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * link-layer header, and the link-layer header is 1681511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * fixed-length; load the length of the IPv4 header, 1682511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * which is at an offset of off_nl from the beginning 1683511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * of the MAC-layer payload, and thus at an offset 1684511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * of off_mac_pl + off_nl from the beginning of the 1685511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * raw packet data. 1686478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1687478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_LDX|BPF_MSH|BPF_B); 1688511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s->s.k = off_macpl + off_nl; 1689478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 1690478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return s; 1691478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 1692478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1693478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 1694478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_uncond(rsense) 1695478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int rsense; 1696478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 1697478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b; 1698478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s; 1699478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1700478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_LD|BPF_IMM); 1701478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s->s.k = !rsense; 1702478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = new_block(JMP(BPF_JEQ)); 1703478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b->stmts = s; 1704478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1705478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 1706478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 1707478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1708478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic inline struct block * 1709478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_true() 1710478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 1711478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_uncond(1); 1712478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 1713478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1714478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic inline struct block * 1715478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_false() 1716478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 1717478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_uncond(0); 1718478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 1719478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1720478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 1721478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Byte-swap a 32-bit number. 1722478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * ("htonl()" or "ntohl()" won't work - we want to byte-swap even on 1723478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * big-endian platforms.) 1724478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1725478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#define SWAPLONG(y) \ 1726478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project((((y)&0xff)<<24) | (((y)&0xff00)<<8) | (((y)&0xff0000)>>8) | (((y)>>24)&0xff)) 1727478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1728478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 1729478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Generate code to match a particular packet type. 1730478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1731478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "proto" is an Ethernet type value, if > ETHERMTU, or an LLC SAP 1732478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * value, if <= ETHERMTU. We use that to determine whether to 1733478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * match the type/length field or to check the type/length field for 1734478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * a value <= ETHERMTU to see whether it's a type field and then do 1735478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the appropriate test. 1736478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1737478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 1738478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_ether_linktype(proto) 1739478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register int proto; 1740478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 1741478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1; 1742478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1743478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 1744478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1745478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case LLCSAP_ISONS: 1746478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case LLCSAP_IP: 1747478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case LLCSAP_NETBEUI: 1748478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1749478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * OSI protocols and NetBEUI always use 802.2 encapsulation, 1750478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * so we check the DSAP and SSAP. 1751478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1752478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * LLCSAP_IP checks for IP-over-802.2, rather 1753478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * than IP-over-Ethernet or IP-over-SNAP. 1754478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1755478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - should we check both the DSAP and the 1756478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * SSAP, like this, or should we check just the 1757478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * DSAP, as we do for other types <= ETHERMTU 1758478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (i.e., other SAP values)? 1759478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1760478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp_gt(OR_LINK, off_linktype, BPF_H, ETHERMTU); 1761478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b0); 1762511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_cmp(OR_MACPL, 0, BPF_H, (bpf_int32) 1763478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project ((proto << 8) | proto)); 1764478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 1765478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 1766478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1767478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case LLCSAP_IPX: 1768478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1769478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Check for; 1770478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1771478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Ethernet_II frames, which are Ethernet 1772478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frames with a frame type of ETHERTYPE_IPX; 1773478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1774478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Ethernet_802.3 frames, which are 802.3 1775478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frames (i.e., the type/length field is 1776478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * a length field, <= ETHERMTU, rather than 1777478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * a type field) with the first two bytes 1778478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * after the Ethernet/802.3 header being 1779478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 0xFFFF; 1780478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1781478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Ethernet_802.2 frames, which are 802.3 1782478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frames with an 802.2 LLC header and 1783478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * with the IPX LSAP as the DSAP in the LLC 1784478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * header; 1785478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1786478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Ethernet_SNAP frames, which are 802.3 1787478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frames with an LLC header and a SNAP 1788478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * header and with an OUI of 0x000000 1789478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (encapsulated Ethernet) and a protocol 1790478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * ID of ETHERTYPE_IPX in the SNAP header. 1791478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1792478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - should we generate the same code both 1793478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * for tests for LLCSAP_IPX and for ETHERTYPE_IPX? 1794478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1795478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1796478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1797478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This generates code to check both for the 1798478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * IPX LSAP (Ethernet_802.2) and for Ethernet_802.3. 1799478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1800511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_cmp(OR_MACPL, 0, BPF_B, (bpf_int32)LLCSAP_IPX); 1801511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_cmp(OR_MACPL, 0, BPF_H, (bpf_int32)0xFFFF); 1802478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 1803478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1804478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1805478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now we add code to check for SNAP frames with 1806478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * ETHERTYPE_IPX, i.e. Ethernet_SNAP. 1807478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1808511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_snap(0x000000, ETHERTYPE_IPX); 1809478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 1810478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1811478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1812478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now we generate code to check for 802.3 1813478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frames in general. 1814478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1815478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp_gt(OR_LINK, off_linktype, BPF_H, ETHERMTU); 1816478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b0); 1817478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1818478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1819478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now add the check for 802.3 frames before the 1820478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * check for Ethernet_802.2 and Ethernet_802.3, 1821478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * as those checks should only be done on 802.3 1822478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frames, not on Ethernet frames. 1823478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1824478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 1825478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1826478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1827478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now add the check for Ethernet_II frames, and 1828478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * do that before checking for the other frame 1829478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * types. 1830478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1831478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, off_linktype, BPF_H, 1832478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)ETHERTYPE_IPX); 1833478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 1834478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 1835478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1836478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_ATALK: 1837478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_AARP: 1838478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1839478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * EtherTalk (AppleTalk protocols on Ethernet link 1840478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * layer) may use 802.2 encapsulation. 1841478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1842478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1843478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1844478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Check for 802.2 encapsulation (EtherTalk phase 2?); 1845478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * we check for an Ethernet type field less than 1846478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1500, which means it's an 802.3 length field. 1847478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1848478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp_gt(OR_LINK, off_linktype, BPF_H, ETHERMTU); 1849478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b0); 1850478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1851478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1852478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 802.2-encapsulated ETHERTYPE_ATALK packets are 1853478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * SNAP packets with an organization code of 1854478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 0x080007 (Apple, for Appletalk) and a protocol 1855478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * type of ETHERTYPE_ATALK (Appletalk). 1856478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1857478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 802.2-encapsulated ETHERTYPE_AARP packets are 1858478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * SNAP packets with an organization code of 1859478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 0x000000 (encapsulated Ethernet) and a protocol 1860478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * type of ETHERTYPE_AARP (Appletalk ARP). 1861478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1862478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto == ETHERTYPE_ATALK) 1863511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_snap(0x080007, ETHERTYPE_ATALK); 1864478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else /* proto == ETHERTYPE_AARP */ 1865511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_snap(0x000000, ETHERTYPE_AARP); 1866478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 1867478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1868478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1869478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Check for Ethernet encapsulation (Ethertalk 1870478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * phase 1?); we just check for the Ethernet 1871478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * protocol type. 1872478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1873478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, off_linktype, BPF_H, (bpf_int32)proto); 1874478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1875478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 1876478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 1877478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1878478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 1879478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto <= ETHERMTU) { 1880478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1881478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This is an LLC SAP value, so the frames 1882478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * that match would be 802.2 frames. 1883478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Check that the frame is an 802.2 frame 1884478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (i.e., that the length/type field is 1885478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * a length field, <= ETHERMTU) and 1886478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * then check the DSAP. 1887478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1888478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp_gt(OR_LINK, off_linktype, BPF_H, ETHERMTU); 1889478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b0); 1890478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_cmp(OR_LINK, off_linktype + 2, BPF_B, 1891478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)proto); 1892478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 1893478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 1894478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else { 1895478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1896478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This is an Ethernet type, so compare 1897478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the length/type field with it (if 1898478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the frame is an 802.2 frame, the length 1899478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * field will be <= ETHERMTU, and, as 1900478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "proto" is > ETHERMTU, this test 1901478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * will fail and the frame won't match, 1902478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * which is what we want). 1903478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1904478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_cmp(OR_LINK, off_linktype, BPF_H, 1905478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)proto); 1906478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 1907478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 1908478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 1909478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1910478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 1911511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * "proto" is an Ethernet type value and for IPNET, if it is not IPv4 1912511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * or IPv6 then we have an error. 1913511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 1914511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct block * 1915511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallgen_ipnet_linktype(proto) 1916511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall register int proto; 1917511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall{ 1918511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall switch (proto) { 1919511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1920511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case ETHERTYPE_IP: 1921511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_cmp(OR_LINK, off_linktype, BPF_B, 1922511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (bpf_int32)IPH_AF_INET); 1923511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* NOTREACHED */ 1924511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1925511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case ETHERTYPE_IPV6: 1926511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_cmp(OR_LINK, off_linktype, BPF_B, 1927511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (bpf_int32)IPH_AF_INET6); 1928511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* NOTREACHED */ 1929511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1930511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall default: 1931511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 1932511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 1933511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1934511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_false(); 1935511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall} 1936511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 1937511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall/* 1938478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Generate code to match a particular packet type. 1939478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1940478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "proto" is an Ethernet type value, if > ETHERMTU, or an LLC SAP 1941478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * value, if <= ETHERMTU. We use that to determine whether to 1942478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * match the type field or to check the type field for the special 1943478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * LINUX_SLL_P_802_2 value and then do the appropriate test. 1944478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1945478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 1946478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_linux_sll_linktype(proto) 1947478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register int proto; 1948478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 1949478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1; 1950478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1951478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 1952478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1953478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case LLCSAP_ISONS: 1954478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case LLCSAP_IP: 1955478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case LLCSAP_NETBEUI: 1956478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1957478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * OSI protocols and NetBEUI always use 802.2 encapsulation, 1958478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * so we check the DSAP and SSAP. 1959478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1960478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * LLCSAP_IP checks for IP-over-802.2, rather 1961478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * than IP-over-Ethernet or IP-over-SNAP. 1962478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1963478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - should we check both the DSAP and the 1964478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * SSAP, like this, or should we check just the 1965478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * DSAP, as we do for other types <= ETHERMTU 1966478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (i.e., other SAP values)? 1967478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 1968478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, off_linktype, BPF_H, LINUX_SLL_P_802_2); 1969511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_cmp(OR_MACPL, 0, BPF_H, (bpf_int32) 1970478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project ((proto << 8) | proto)); 1971478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 1972478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 1973478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 1974478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case LLCSAP_IPX: 1975478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 1976478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Ethernet_II frames, which are Ethernet 1977478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frames with a frame type of ETHERTYPE_IPX; 1978478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1979478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Ethernet_802.3 frames, which have a frame 1980478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * type of LINUX_SLL_P_802_3; 1981478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1982478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Ethernet_802.2 frames, which are 802.3 1983478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frames with an 802.2 LLC header (i.e, have 1984478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * a frame type of LINUX_SLL_P_802_2) and 1985478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * with the IPX LSAP as the DSAP in the LLC 1986478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * header; 1987478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1988478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Ethernet_SNAP frames, which are 802.3 1989478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frames with an LLC header and a SNAP 1990478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * header and with an OUI of 0x000000 1991478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (encapsulated Ethernet) and a protocol 1992478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * ID of ETHERTYPE_IPX in the SNAP header. 1993478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 1994478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * First, do the checks on LINUX_SLL_P_802_2 1995478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frames; generate the check for either 1996478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Ethernet_802.2 or Ethernet_SNAP frames, and 1997478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * then put a check for LINUX_SLL_P_802_2 frames 1998478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * before it. 1999478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2000511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_cmp(OR_MACPL, 0, BPF_B, (bpf_int32)LLCSAP_IPX); 2001511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_snap(0x000000, ETHERTYPE_IPX); 2002478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 2003478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, off_linktype, BPF_H, LINUX_SLL_P_802_2); 2004478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 2005478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2006478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2007478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now check for 802.3 frames and OR that with 2008478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the previous test. 2009478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2010478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, off_linktype, BPF_H, LINUX_SLL_P_802_3); 2011478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 2012478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2013478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2014478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now add the check for Ethernet_II frames, and 2015478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * do that before checking for the other frame 2016478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * types. 2017478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2018478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, off_linktype, BPF_H, 2019478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)ETHERTYPE_IPX); 2020478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 2021478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 2022478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2023478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_ATALK: 2024478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_AARP: 2025478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2026478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * EtherTalk (AppleTalk protocols on Ethernet link 2027478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * layer) may use 802.2 encapsulation. 2028478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2029478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2030478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2031478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Check for 802.2 encapsulation (EtherTalk phase 2?); 2032478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * we check for the 802.2 protocol type in the 2033478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "Ethernet type" field. 2034478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2035478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, off_linktype, BPF_H, LINUX_SLL_P_802_2); 2036478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2037478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2038478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 802.2-encapsulated ETHERTYPE_ATALK packets are 2039478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * SNAP packets with an organization code of 2040478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 0x080007 (Apple, for Appletalk) and a protocol 2041478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * type of ETHERTYPE_ATALK (Appletalk). 2042478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 2043478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 802.2-encapsulated ETHERTYPE_AARP packets are 2044478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * SNAP packets with an organization code of 2045478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 0x000000 (encapsulated Ethernet) and a protocol 2046478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * type of ETHERTYPE_AARP (Appletalk ARP). 2047478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2048478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto == ETHERTYPE_ATALK) 2049511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_snap(0x080007, ETHERTYPE_ATALK); 2050478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else /* proto == ETHERTYPE_AARP */ 2051511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_snap(0x000000, ETHERTYPE_AARP); 2052478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 2053478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2054478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2055478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Check for Ethernet encapsulation (Ethertalk 2056478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * phase 1?); we just check for the Ethernet 2057478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * protocol type. 2058478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2059478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, off_linktype, BPF_H, (bpf_int32)proto); 2060478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2061478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 2062478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 2063478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2064478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 2065478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto <= ETHERMTU) { 2066478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2067478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This is an LLC SAP value, so the frames 2068478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * that match would be 802.2 frames. 2069478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Check for the 802.2 protocol type 2070478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * in the "Ethernet type" field, and 2071478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * then check the DSAP. 2072478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2073478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, off_linktype, BPF_H, 2074478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project LINUX_SLL_P_802_2); 2075511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_cmp(OR_LINK, off_macpl, BPF_B, 2076478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)proto); 2077478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 2078478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 2079478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else { 2080478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2081478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This is an Ethernet type, so compare 2082478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the length/type field with it (if 2083478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the frame is an 802.2 frame, the length 2084478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * field will be <= ETHERMTU, and, as 2085478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "proto" is > ETHERMTU, this test 2086478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * will fail and the frame won't match, 2087478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * which is what we want). 2088478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2089478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_cmp(OR_LINK, off_linktype, BPF_H, 2090478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)proto); 2091478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 2092478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 2093478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 2094478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2095511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct slist * 2096511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallgen_load_prism_llprefixlen() 2097511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall{ 2098511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *s1, *s2; 2099511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *sjeq_avs_cookie; 2100511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *sjcommon; 2101511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2102511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2103511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * This code is not compatible with the optimizer, as 2104511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * we are generating jmp instructions within a normal 2105511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * slist of instructions 2106511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2107511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall no_optimize = 1; 2108511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2109511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2110511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Generate code to load the length of the radio header into 2111511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the register assigned to hold that length, if one has been 2112511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * assigned. (If one hasn't been assigned, no code we've 2113511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * generated uses that prefix, so we don't need to generate any 2114511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * code to load it.) 2115511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 2116511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Some Linux drivers use ARPHRD_IEEE80211_PRISM but sometimes 2117511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * or always use the AVS header rather than the Prism header. 2118511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * We load a 4-byte big-endian value at the beginning of the 2119511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * raw packet data, and see whether, when masked with 0xFFFFF000, 2120511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * it's equal to 0x80211000. If so, that indicates that it's 2121511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * an AVS header (the masked-out bits are the version number). 2122511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Otherwise, it's a Prism header. 2123511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 2124511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * XXX - the Prism header is also, in theory, variable-length, 2125511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * but no known software generates headers that aren't 144 2126511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * bytes long. 2127511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2128511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (reg_off_ll != -1) { 2129511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2130511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Load the cookie. 2131511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2132511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s1 = new_stmt(BPF_LD|BPF_W|BPF_ABS); 2133511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s1->s.k = 0; 2134511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2135511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2136511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * AND it with 0xFFFFF000. 2137511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2138511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_ALU|BPF_AND|BPF_K); 2139511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = 0xFFFFF000; 2140511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s1, s2); 2141511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2142511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2143511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Compare with 0x80211000. 2144511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2145511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjeq_avs_cookie = new_stmt(JMP(BPF_JEQ)); 2146511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjeq_avs_cookie->s.k = 0x80211000; 2147511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s1, sjeq_avs_cookie); 2148511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2149511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2150511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If it's AVS: 2151511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 2152511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * The 4 bytes at an offset of 4 from the beginning of 2153511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the AVS header are the length of the AVS header. 2154511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * That field is big-endian. 2155511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2156511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_LD|BPF_W|BPF_ABS); 2157511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = 4; 2158511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s1, s2); 2159511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjeq_avs_cookie->s.jt = s2; 2160511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2161511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2162511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Now jump to the code to allocate a register 2163511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * into which to save the header length and 2164511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * store the length there. (The "jump always" 2165511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * instruction needs to have the k field set; 2166511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * it's added to the PC, so, as we're jumping 2167511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * over a single instruction, it should be 1.) 2168511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2169511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjcommon = new_stmt(JMP(BPF_JA)); 2170511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjcommon->s.k = 1; 2171511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s1, sjcommon); 2172511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2173511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2174511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Now for the code that handles the Prism header. 2175511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Just load the length of the Prism header (144) 2176511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * into the A register. Have the test for an AVS 2177511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * header branch here if we don't have an AVS header. 2178511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2179511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_LD|BPF_W|BPF_IMM); 2180511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = 144; 2181511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s1, s2); 2182511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjeq_avs_cookie->s.jf = s2; 2183511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2184511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2185511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Now allocate a register to hold that value and store 2186511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * it. The code for the AVS header will jump here after 2187511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * loading the length of the AVS header. 2188511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2189511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_ST); 2190511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = reg_off_ll; 2191511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s1, s2); 2192511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjcommon->s.jf = s2; 2193511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2194511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2195511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Now move it into the X register. 2196511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2197511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_MISC|BPF_TAX); 2198511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s1, s2); 2199511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2200511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (s1); 2201511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } else 2202511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (NULL); 2203511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall} 2204511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2205511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct slist * 2206511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallgen_load_avs_llprefixlen() 2207478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 2208478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s1, *s2; 2209478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2210478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2211511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Generate code to load the length of the AVS header into 2212511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the register assigned to hold that length, if one has been 2213511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * assigned. (If one hasn't been assigned, no code we've 2214511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * generated uses that prefix, so we don't need to generate any 2215511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * code to load it.) 2216478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2217511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (reg_off_ll != -1) { 2218511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2219511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * The 4 bytes at an offset of 4 from the beginning of 2220511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the AVS header are the length of the AVS header. 2221511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * That field is big-endian. 2222511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2223511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s1 = new_stmt(BPF_LD|BPF_W|BPF_ABS); 2224511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s1->s.k = 4; 2225511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2226511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2227511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Now allocate a register to hold that value and store 2228511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * it. 2229511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2230511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_ST); 2231511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = reg_off_ll; 2232511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s1, s2); 2233511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2234511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2235511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Now move it into the X register. 2236511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2237511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_MISC|BPF_TAX); 2238511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s1, s2); 2239511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2240511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (s1); 2241511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } else 2242511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (NULL); 2243511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall} 2244511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2245511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct slist * 2246511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallgen_load_radiotap_llprefixlen() 2247511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall{ 2248511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *s1, *s2; 2249511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2250511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2251511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Generate code to load the length of the radiotap header into 2252511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the register assigned to hold that length, if one has been 2253511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * assigned. (If one hasn't been assigned, no code we've 2254511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * generated uses that prefix, so we don't need to generate any 2255511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * code to load it.) 2256511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2257511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (reg_off_ll != -1) { 2258478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2259478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * The 2 bytes at offsets of 2 and 3 from the beginning 2260478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of the radiotap header are the length of the radiotap 2261478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * header; unfortunately, it's little-endian, so we have 2262478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * to load it a byte at a time and construct the value. 2263478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2264478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2265478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2266478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Load the high-order byte, at an offset of 3, shift it 2267478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * left a byte, and put the result in the X register. 2268478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2269478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s1 = new_stmt(BPF_LD|BPF_B|BPF_ABS); 2270478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s1->s.k = 3; 2271478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_ALU|BPF_LSH|BPF_K); 2272478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s1, s2); 2273478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2->s.k = 8; 2274478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_MISC|BPF_TAX); 2275478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s1, s2); 2276478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2277478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2278478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Load the next byte, at an offset of 2, and OR the 2279478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * value from the X register into it. 2280478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2281478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_LD|BPF_B|BPF_ABS); 2282478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s1, s2); 2283478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2->s.k = 2; 2284478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_ALU|BPF_OR|BPF_X); 2285478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s1, s2); 2286478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2287478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2288478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now allocate a register to hold that value and store 2289478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * it. 2290478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2291478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_ST); 2292511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = reg_off_ll; 2293478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s1, s2); 2294478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2295478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2296478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now move it into the X register. 2297478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2298478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_MISC|BPF_TAX); 2299478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s1, s2); 2300478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2301511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (s1); 2302511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } else 2303511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (NULL); 2304478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 2305478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2306478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 2307478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * At the moment we treat PPI as normal Radiotap encoded 2308478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * packets. The difference is in the function that generates 2309478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the code at the beginning to compute the header length. 2310478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Since this code generator of PPI supports bare 802.11 2311478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * encapsulation only (i.e. the encapsulated DLT should be 2312511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * DLT_IEEE802_11) we generate code to check for this too; 2313511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * that's done in finish_parse(). 2314478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2315511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct slist * 2316511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallgen_load_ppi_llprefixlen() 2317478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 2318478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s1, *s2; 2319478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2320478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2321511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Generate code to load the length of the radiotap header 2322511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * into the register assigned to hold that length, if one has 2323511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * been assigned. 2324478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2325511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (reg_off_ll != -1) { 2326511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2327478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * The 2 bytes at offsets of 2 and 3 from the beginning 2328478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of the radiotap header are the length of the radiotap 2329478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * header; unfortunately, it's little-endian, so we have 2330478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * to load it a byte at a time and construct the value. 2331478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2332478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2333478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2334478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Load the high-order byte, at an offset of 3, shift it 2335478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * left a byte, and put the result in the X register. 2336478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2337478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s1 = new_stmt(BPF_LD|BPF_B|BPF_ABS); 2338478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s1->s.k = 3; 2339478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_ALU|BPF_LSH|BPF_K); 2340478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s1, s2); 2341478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2->s.k = 8; 2342478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_MISC|BPF_TAX); 2343478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s1, s2); 2344478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2345478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2346478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Load the next byte, at an offset of 2, and OR the 2347478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * value from the X register into it. 2348478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2349478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_LD|BPF_B|BPF_ABS); 2350478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s1, s2); 2351478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2->s.k = 2; 2352478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_ALU|BPF_OR|BPF_X); 2353478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s1, s2); 2354478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2355478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2356478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now allocate a register to hold that value and store 2357478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * it. 2358478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2359478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_ST); 2360511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = reg_off_ll; 2361478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s1, s2); 2362478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2363478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2364478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now move it into the X register. 2365478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2366478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_MISC|BPF_TAX); 2367478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s1, s2); 2368478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2369511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (s1); 2370511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } else 2371511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (NULL); 2372511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall} 2373511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2374511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall/* 2375511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Load a value relative to the beginning of the link-layer header after the 802.11 2376511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * header, i.e. LLC_SNAP. 2377511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * The link-layer header doesn't necessarily begin at the beginning 2378511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * of the packet data; there might be a variable-length prefix containing 2379511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * radio information. 2380511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2381511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct slist * 2382511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallgen_load_802_11_header_len(struct slist *s, struct slist *snext) 2383511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall{ 2384511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *s2; 2385511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *sjset_data_frame_1; 2386511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *sjset_data_frame_2; 2387511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *sjset_qos; 2388511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *sjset_radiotap_flags; 2389511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *sjset_radiotap_tsft; 2390511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *sjset_tsft_datapad, *sjset_notsft_datapad; 2391511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *s_roundup; 2392511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2393511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (reg_off_macpl == -1) { 2394511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2395511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * No register has been assigned to the offset of 2396511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the MAC-layer payload, which means nobody needs 2397511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * it; don't bother computing it - just return 2398511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * what we already have. 2399511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2400511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (s); 2401511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 2402511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2403511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2404511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * This code is not compatible with the optimizer, as 2405511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * we are generating jmp instructions within a normal 2406511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * slist of instructions 2407511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2408511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall no_optimize = 1; 2409511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2410511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2411511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If "s" is non-null, it has code to arrange that the X register 2412511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * contains the length of the prefix preceding the link-layer 2413511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * header. 2414511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 2415511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Otherwise, the length of the prefix preceding the link-layer 2416511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * header is "off_ll". 2417511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2418511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (s == NULL) { 2419511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2420511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * There is no variable-length header preceding the 2421511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * link-layer header. 2422511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 2423511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Load the length of the fixed-length prefix preceding 2424511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the link-layer header (if any) into the X register, 2425511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * and store it in the reg_off_macpl register. 2426511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * That length is off_ll. 2427511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2428511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = new_stmt(BPF_LDX|BPF_IMM); 2429511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s->s.k = off_ll; 2430511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 2431511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2432511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2433511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * The X register contains the offset of the beginning of the 2434511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * link-layer header; add 24, which is the minimum length 2435511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * of the MAC header for a data frame, to that, and store it 2436511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * in reg_off_macpl, and then load the Frame Control field, 2437511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * which is at the offset in the X register, with an indexed load. 2438511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2439511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_MISC|BPF_TXA); 2440511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, s2); 2441511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_ALU|BPF_ADD|BPF_K); 2442511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = 24; 2443511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, s2); 2444511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_ST); 2445511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = reg_off_macpl; 2446511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, s2); 2447511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2448511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_LD|BPF_IND|BPF_B); 2449511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = 0; 2450511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, s2); 2451511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2452511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2453511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Check the Frame Control field to see if this is a data frame; 2454511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * a data frame has the 0x08 bit (b3) in that field set and the 2455511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 0x04 bit (b2) clear. 2456511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2457511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_data_frame_1 = new_stmt(JMP(BPF_JSET)); 2458511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_data_frame_1->s.k = 0x08; 2459511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, sjset_data_frame_1); 2460511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2461511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2462511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If b3 is set, test b2, otherwise go to the first statement of 2463511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the rest of the program. 2464511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2465511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_data_frame_1->s.jt = sjset_data_frame_2 = new_stmt(JMP(BPF_JSET)); 2466511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_data_frame_2->s.k = 0x04; 2467511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, sjset_data_frame_2); 2468511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_data_frame_1->s.jf = snext; 2469511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2470511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2471511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If b2 is not set, this is a data frame; test the QoS bit. 2472511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Otherwise, go to the first statement of the rest of the 2473511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * program. 2474511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2475511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_data_frame_2->s.jt = snext; 2476511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_data_frame_2->s.jf = sjset_qos = new_stmt(JMP(BPF_JSET)); 2477511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_qos->s.k = 0x80; /* QoS bit */ 2478511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, sjset_qos); 2479511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2480511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2481511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If it's set, add 2 to reg_off_macpl, to skip the QoS 2482511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * field. 2483511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Otherwise, go to the first statement of the rest of the 2484511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * program. 2485511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2486511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_qos->s.jt = s2 = new_stmt(BPF_LD|BPF_MEM); 2487511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = reg_off_macpl; 2488511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, s2); 2489511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_ALU|BPF_ADD|BPF_IMM); 2490511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = 2; 2491511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, s2); 2492511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_ST); 2493511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = reg_off_macpl; 2494511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, s2); 2495511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2496511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2497511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If we have a radiotap header, look at it to see whether 2498511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * there's Atheros padding between the MAC-layer header 2499511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * and the payload. 2500511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 2501511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Note: all of the fields in the radiotap header are 2502511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * little-endian, so we byte-swap all of the values 2503511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * we test against, as they will be loaded as big-endian 2504511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * values. 2505511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2506511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (linktype == DLT_IEEE802_11_RADIO) { 2507511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2508511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Is the IEEE80211_RADIOTAP_FLAGS bit (0x0000002) set 2509511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * in the presence flag? 2510511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2511511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_qos->s.jf = s2 = new_stmt(BPF_LD|BPF_ABS|BPF_W); 2512511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = 4; 2513511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, s2); 2514511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2515511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_radiotap_flags = new_stmt(JMP(BPF_JSET)); 2516511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_radiotap_flags->s.k = SWAPLONG(0x00000002); 2517511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, sjset_radiotap_flags); 2518511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2519511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2520511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If not, skip all of this. 2521511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2522511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_radiotap_flags->s.jf = snext; 2523511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2524511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2525511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Otherwise, is the IEEE80211_RADIOTAP_TSFT bit set? 2526511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2527511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_radiotap_tsft = sjset_radiotap_flags->s.jt = 2528511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall new_stmt(JMP(BPF_JSET)); 2529511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_radiotap_tsft->s.k = SWAPLONG(0x00000001); 2530511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, sjset_radiotap_tsft); 2531511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2532511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2533511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If IEEE80211_RADIOTAP_TSFT is set, the flags field is 2534511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * at an offset of 16 from the beginning of the raw packet 2535511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * data (8 bytes for the radiotap header and 8 bytes for 2536511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the TSFT field). 2537511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 2538511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Test whether the IEEE80211_RADIOTAP_F_DATAPAD bit (0x20) 2539511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * is set. 2540511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2541511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_radiotap_tsft->s.jt = s2 = new_stmt(BPF_LD|BPF_ABS|BPF_B); 2542511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = 16; 2543511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, s2); 2544511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2545511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_tsft_datapad = new_stmt(JMP(BPF_JSET)); 2546511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_tsft_datapad->s.k = 0x20; 2547511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, sjset_tsft_datapad); 2548511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2549511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2550511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If IEEE80211_RADIOTAP_TSFT is not set, the flags field is 2551511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * at an offset of 8 from the beginning of the raw packet 2552511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * data (8 bytes for the radiotap header). 2553511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 2554511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Test whether the IEEE80211_RADIOTAP_F_DATAPAD bit (0x20) 2555511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * is set. 2556511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2557511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_radiotap_tsft->s.jf = s2 = new_stmt(BPF_LD|BPF_ABS|BPF_B); 2558511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = 8; 2559511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, s2); 2560511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2561511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_notsft_datapad = new_stmt(JMP(BPF_JSET)); 2562511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_notsft_datapad->s.k = 0x20; 2563511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, sjset_notsft_datapad); 2564511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2565478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2566511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * In either case, if IEEE80211_RADIOTAP_F_DATAPAD is 2567511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * set, round the length of the 802.11 header to 2568511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * a multiple of 4. Do that by adding 3 and then 2569511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * dividing by and multiplying by 4, which we do by 2570511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * ANDing with ~3. 2571478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2572511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s_roundup = new_stmt(BPF_LD|BPF_MEM); 2573511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s_roundup->s.k = reg_off_macpl; 2574511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, s_roundup); 2575511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_ALU|BPF_ADD|BPF_IMM); 2576511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = 3; 2577511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, s2); 2578511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_ALU|BPF_AND|BPF_IMM); 2579511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = ~3; 2580511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, s2); 2581511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2 = new_stmt(BPF_ST); 2582511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s2->s.k = reg_off_macpl; 2583511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, s2); 2584511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2585511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_tsft_datapad->s.jt = s_roundup; 2586511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_tsft_datapad->s.jf = snext; 2587511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_notsft_datapad->s.jt = s_roundup; 2588511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_notsft_datapad->s.jf = snext; 2589511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } else 2590511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sjset_qos->s.jf = snext; 2591511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2592511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return s; 2593511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall} 2594511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2595511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic void 2596511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallinsert_compute_vloffsets(b) 2597511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct block *b; 2598511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall{ 2599511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *s; 2600511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2601511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2602511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * For link-layer types that have a variable-length header 2603511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * preceding the link-layer header, generate code to load 2604511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the offset of the link-layer header into the register 2605511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * assigned to that offset, if any. 2606511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2607511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall switch (linktype) { 2608511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2609511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PRISM_HEADER: 2610511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_prism_llprefixlen(); 2611511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2612511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2613511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO_AVS: 2614511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_avs_llprefixlen(); 2615511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2616511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2617511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO: 2618511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_radiotap_llprefixlen(); 2619511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2620511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2621511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PPI: 2622511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_ppi_llprefixlen(); 2623511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2624478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2625511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall default: 2626511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = NULL; 2627511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2628511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 2629511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2630511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2631511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * For link-layer types that have a variable-length link-layer 2632511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * header, generate code to load the offset of the MAC-layer 2633511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * payload into the register assigned to that offset, if any. 2634511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2635511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall switch (linktype) { 2636511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2637511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11: 2638511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PRISM_HEADER: 2639511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO_AVS: 2640511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO: 2641511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PPI: 2642511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_802_11_header_len(s, b->stmts); 2643511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2644511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 2645511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2646511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2647511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If we have any offset-loading code, append all the 2648511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * existing statements in the block to those statements, 2649511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * and make the resulting list the list of statements 2650511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * for the block. 2651511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2652511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (s != NULL) { 2653511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall sappend(s, b->stmts); 2654511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b->stmts = s; 2655478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 2656478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 2657511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2658478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 2659478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_ppi_dlt_check(void) 2660478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 2661478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s_load_dlt; 2662478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b; 2663478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2664478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (linktype == DLT_PPI) 2665478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project { 2666478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Create the statements that check for the DLT 2667478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2668478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s_load_dlt = new_stmt(BPF_LD|BPF_W|BPF_ABS); 2669478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s_load_dlt->s.k = 4; 2670478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2671478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = new_block(JMP(BPF_JEQ)); 2672478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2673478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b->stmts = s_load_dlt; 2674478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b->s.k = SWAPLONG(DLT_IEEE802_11); 2675478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 2676478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 2677478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project { 2678478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = NULL; 2679478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 2680478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2681478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 2682478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 2683478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2684511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct slist * 2685511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallgen_prism_llprefixlen(void) 2686478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 2687511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *s; 2688511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2689511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (reg_off_ll == -1) { 2690511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2691511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * We haven't yet assigned a register for the length 2692511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * of the radio header; allocate one. 2693511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2694511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall reg_off_ll = alloc_reg(); 2695511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 2696478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2697511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2698511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Load the register containing the radio length 2699511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * into the X register. 2700478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2701511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = new_stmt(BPF_LDX|BPF_MEM); 2702511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s->s.k = reg_off_ll; 2703511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return s; 2704511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall} 2705478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2706511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct slist * 2707511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallgen_avs_llprefixlen(void) 2708511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall{ 2709511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *s; 2710511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2711511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (reg_off_ll == -1) { 2712511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2713511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * We haven't yet assigned a register for the length 2714511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * of the AVS header; allocate one. 2715511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2716511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall reg_off_ll = alloc_reg(); 2717478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 2718478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2719511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2720511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Load the register containing the AVS length 2721511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * into the X register. 2722511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2723511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = new_stmt(BPF_LDX|BPF_MEM); 2724511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s->s.k = reg_off_ll; 2725511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return s; 2726511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall} 2727478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2728478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct slist * 2729478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_radiotap_llprefixlen(void) 2730478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 2731478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s; 2732478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2733511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (reg_off_ll == -1) { 2734478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2735478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * We haven't yet assigned a register for the length 2736478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of the radiotap header; allocate one. 2737478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2738511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall reg_off_ll = alloc_reg(); 2739478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 2740478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2741478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2742478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Load the register containing the radiotap length 2743478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * into the X register. 2744478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2745478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_LDX|BPF_MEM); 2746511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s->s.k = reg_off_ll; 2747478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return s; 2748478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 2749478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2750478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 2751478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * At the moment we treat PPI as normal Radiotap encoded 2752478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * packets. The difference is in the function that generates 2753478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the code at the beginning to compute the header length. 2754478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Since this code generator of PPI supports bare 802.11 2755478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * encapsulation only (i.e. the encapsulated DLT should be 2756478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * DLT_IEEE802_11) we generate code to check for this too. 2757478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2758478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct slist * 2759478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_ppi_llprefixlen(void) 2760478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 2761478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s; 2762478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2763511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (reg_off_ll == -1) { 2764478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2765478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * We haven't yet assigned a register for the length 2766478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of the radiotap header; allocate one. 2767478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2768511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall reg_off_ll = alloc_reg(); 2769478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 2770478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2771478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 2772511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Load the register containing the PPI length 2773478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * into the X register. 2774478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2775478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_LDX|BPF_MEM); 2776511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s->s.k = reg_off_ll; 2777478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return s; 2778478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 2779478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2780478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 2781478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Generate code to compute the link-layer header length, if necessary, 2782478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * putting it into the X register, and to return either a pointer to a 2783478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "struct slist" for the list of statements in that code, or NULL if 2784478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * no code is necessary. 2785478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2786478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct slist * 2787478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_llprefixlen(void) 2788478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 2789478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (linktype) { 2790478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2791511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PRISM_HEADER: 2792511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_prism_llprefixlen(); 2793511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2794511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO_AVS: 2795511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_avs_llprefixlen(); 2796478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2797478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IEEE802_11_RADIO: 2798478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_radiotap_llprefixlen(); 2799478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2800511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PPI: 2801511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_ppi_llprefixlen(); 2802511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2803478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 2804478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return NULL; 2805478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 2806478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 2807478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2808478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 2809511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Generate code to load the register containing the offset of the 2810511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * MAC-layer payload into the X register; if no register for that offset 2811511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * has been allocated, allocate it first. 2812511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2813511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct slist * 2814511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallgen_off_macpl(void) 2815511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall{ 2816511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *s; 2817511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2818511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (off_macpl_is_variable) { 2819511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (reg_off_macpl == -1) { 2820511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2821511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * We haven't yet assigned a register for the offset 2822511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * of the MAC-layer payload; allocate one. 2823511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2824511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall reg_off_macpl = alloc_reg(); 2825511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 2826511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2827511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2828511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Load the register containing the offset of the MAC-layer 2829511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * payload into the X register. 2830511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2831511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = new_stmt(BPF_LDX|BPF_MEM); 2832511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s->s.k = reg_off_macpl; 2833511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return s; 2834511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } else { 2835511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2836511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * That offset isn't variable, so we don't need to 2837511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * generate any code. 2838511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2839511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return NULL; 2840511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 2841511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall} 2842511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2843511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall/* 2844511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Map an Ethernet type to the equivalent PPP type. 2845511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2846511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic int 2847511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallethertype_to_ppptype(proto) 2848511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall int proto; 2849511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall{ 2850511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall switch (proto) { 2851511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2852511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case ETHERTYPE_IP: 2853511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall proto = PPP_IP; 2854511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2855511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2856511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case ETHERTYPE_IPV6: 2857511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall proto = PPP_IPV6; 2858511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2859511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2860511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case ETHERTYPE_DN: 2861511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall proto = PPP_DECNET; 2862511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2863511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2864511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case ETHERTYPE_ATALK: 2865511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall proto = PPP_APPLE; 2866511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2867511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2868511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case ETHERTYPE_NS: 2869511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall proto = PPP_NS; 2870511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2871511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2872511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case LLCSAP_ISONS: 2873511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall proto = PPP_OSI; 2874511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2875511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2876511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case LLCSAP_8021D: 2877511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2878511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * I'm assuming the "Bridging PDU"s that go 2879511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * over PPP are Spanning Tree Protocol 2880511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Bridging PDUs. 2881511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2882511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall proto = PPP_BRPDU; 2883511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2884511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2885511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case LLCSAP_IPX: 2886511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall proto = PPP_IPX; 2887511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2888511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 2889511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (proto); 2890511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall} 2891511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2892511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall/* 2893478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Generate code to match a particular packet type by matching the 2894478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * link-layer type field or fields in the 802.2 LLC header. 2895478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 2896478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "proto" is an Ethernet type value, if > ETHERMTU, or an LLC SAP 2897478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * value, if <= ETHERMTU. 2898478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 2899478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 2900478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_linktype(proto) 2901478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register int proto; 2902478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 2903478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1, *b2; 2904478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2905478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* are we checking MPLS-encapsulated packets? */ 2906478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (label_stack_depth > 0) { 2907478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 2908478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_IP: 2909478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case PPP_IP: 2910511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* FIXME add other L3 proto IDs */ 2911478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_mpls_linktype(Q_IP); 2912478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2913478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_IPV6: 2914478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case PPP_IPV6: 2915511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* FIXME add other L3 proto IDs */ 2916478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_mpls_linktype(Q_IPV6); 2917478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2918478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 2919478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unsupported protocol over mpls"); 2920478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 2921478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 2922478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 2923478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2924511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2925511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Are we testing PPPoE packets? 2926511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2927511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (is_pppoes) { 2928511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2929511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * The PPPoE session header is part of the 2930511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * MAC-layer payload, so all references 2931511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * should be relative to the beginning of 2932511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * that payload. 2933511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2934511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2935511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2936511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * We use Ethernet protocol types inside libpcap; 2937511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * map them to the corresponding PPP protocol types. 2938511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2939511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall proto = ethertype_to_ppptype(proto); 2940511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_cmp(OR_MACPL, off_linktype, BPF_H, (bpf_int32)proto); 2941511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 2942511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2943478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (linktype) { 2944478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2945478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_EN10MB: 2946511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER: 2947511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER_TRANSPARENT: 2948478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_ether_linktype(proto); 2949478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 2950478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 2951478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2952478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_C_HDLC: 2953478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 2954478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2955478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case LLCSAP_ISONS: 2956478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project proto = (proto << 8 | LLCSAP_ISONS); 2957478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* fall through */ 2958478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2959478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 2960478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_cmp(OR_LINK, off_linktype, BPF_H, 2961478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)proto); 2962478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 2963478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 2964478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 2965478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 2966478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 2967478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IEEE802_11: 2968511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PRISM_HEADER: 2969478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IEEE802_11_RADIO_AVS: 2970478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IEEE802_11_RADIO: 2971511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PPI: 2972511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2973511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Check that we have a data frame. 2974511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2975511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_check_802_11_data_frame(); 2976511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2977511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2978511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Now check for the specified link-layer type. 2979511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2980511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_llc_linktype(proto); 2981511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b0, b1); 2982511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return b1; 2983511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /*NOTREACHED*/ 2984511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2985511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2986511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_FDDI: 2987511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2988511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * XXX - check for asynchronous frames, as per RFC 1103. 2989511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2990511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_llc_linktype(proto); 2991511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /*NOTREACHED*/ 2992511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 2993511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 2994511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802: 2995511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 2996511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * XXX - check for LLC PDUs, as per IEEE 802.5. 2997511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 2998511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_llc_linktype(proto); 2999511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /*NOTREACHED*/ 3000511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3001511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3002478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_ATM_RFC1483: 3003478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_ATM_CLIP: 3004478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IP_OVER_FC: 3005478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_llc_linktype(proto); 3006478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 3007478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3008478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3009478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_SUNATM: 3010478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3011478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If "is_lane" is set, check for a LANE-encapsulated 3012478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * version of this protocol, otherwise check for an 3013478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * LLC-encapsulated version of this protocol. 3014478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3015478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * We assume LANE means Ethernet, not Token Ring. 3016478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3017478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (is_lane) { 3018478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3019478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Check that the packet doesn't begin with an 3020478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * LE Control marker. (We've already generated 3021478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * a test for LANE.) 3022478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3023478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, SUNATM_PKT_BEGIN_POS, BPF_H, 3024478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 0xFF00); 3025478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b0); 3026478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3027478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3028478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now generate an Ethernet test. 3029478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3030478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_ether_linktype(proto); 3031478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 3032478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 3033478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else { 3034478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3035478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Check for LLC encapsulation and then check the 3036478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * protocol. 3037478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3038478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_atmfield_code(A_PROTOTYPE, PT_LLC, BPF_JEQ, 0); 3039478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_llc_linktype(proto); 3040478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 3041478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 3042478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3043478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 3044478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3045478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3046478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_LINUX_SLL: 3047478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_linux_sll_linktype(proto); 3048478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 3049478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3050478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3051478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_SLIP: 3052478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_SLIP_BSDOS: 3053478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_RAW: 3054478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3055478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * These types don't provide any type field; packets 3056478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * are always IPv4 or IPv6. 3057478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3058478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - for IPv4, check for a version number of 4, and, 3059478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * for IPv6, check for a version number of 6? 3060478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3061478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 3062478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3063478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_IP: 3064478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Check for a version number of 4. */ 3065478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_mcmp(OR_LINK, 0, BPF_B, 0x40, 0xF0); 3066511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3067478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_IPV6: 3068478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Check for a version number of 6. */ 3069478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_mcmp(OR_LINK, 0, BPF_B, 0x60, 0xF0); 3070478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3071478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 3072478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_false(); /* always false */ 3073478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3074478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 3075478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3076478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3077511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IPV4: 3078511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 3079511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Raw IPv4, so no type field. 3080511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 3081511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (proto == ETHERTYPE_IP) 3082511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_true(); /* always true */ 3083511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3084511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* Checking for something other than IPv4; always false */ 3085511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_false(); 3086511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /*NOTREACHED*/ 3087511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3088511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3089511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IPV6: 3090511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 3091511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Raw IPv6, so no type field. 3092511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 3093511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (proto == ETHERTYPE_IPV6) 3094511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_true(); /* always true */ 3095511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3096511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* Checking for something other than IPv6; always false */ 3097511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_false(); 3098511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /*NOTREACHED*/ 3099511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3100511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3101478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PPP: 3102478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PPP_PPPD: 3103478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PPP_SERIAL: 3104478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PPP_ETHER: 3105478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3106478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * We use Ethernet protocol types inside libpcap; 3107478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * map them to the corresponding PPP protocol types. 3108478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3109511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall proto = ethertype_to_ppptype(proto); 3110511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_cmp(OR_LINK, off_linktype, BPF_H, (bpf_int32)proto); 3111511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /*NOTREACHED*/ 3112478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3113478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3114478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PPP_BSDOS: 3115478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3116478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * We use Ethernet protocol types inside libpcap; 3117478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * map them to the corresponding PPP protocol types. 3118478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3119478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 3120478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3121478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_IP: 3122511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 3123511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Also check for Van Jacobson-compressed IP. 3124511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * XXX - do this for other forms of PPP? 3125511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 3126478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, off_linktype, BPF_H, PPP_IP); 3127478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_cmp(OR_LINK, off_linktype, BPF_H, PPP_VJC); 3128478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 3129478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, off_linktype, BPF_H, PPP_VJNC); 3130478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b1, b0); 3131478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b0; 3132478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3133511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall default: 3134511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall proto = ethertype_to_ppptype(proto); 3135511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_cmp(OR_LINK, off_linktype, BPF_H, 3136511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (bpf_int32)proto); 3137478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3138511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /*NOTREACHED*/ 3139478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3140478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3141478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_NULL: 3142478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_LOOP: 3143478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_ENC: 3144478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3145478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For DLT_NULL, the link-layer header is a 32-bit 3146478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * word containing an AF_ value in *host* byte order, 3147478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * and for DLT_ENC, the link-layer header begins 3148478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * with a 32-bit work containing an AF_ value in 3149478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * host byte order. 3150478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3151478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * In addition, if we're reading a saved capture file, 3152478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the host byte order in the capture may not be the 3153478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * same as the host byte order on this machine. 3154478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3155478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For DLT_LOOP, the link-layer header is a 32-bit 3156478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * word containing an AF_ value in *network* byte order. 3157478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3158478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - AF_ values may, unfortunately, be platform- 3159478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * dependent; for example, FreeBSD's AF_INET6 is 24 3160478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * whilst NetBSD's and OpenBSD's is 26. 3161478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3162478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This means that, when reading a capture file, just 3163478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * checking for our AF_INET6 value won't work if the 3164478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * capture file came from another OS. 3165478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3166478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 3167478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3168478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_IP: 3169478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project proto = AF_INET; 3170478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3171478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3172478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef INET6 3173478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_IPV6: 3174478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project proto = AF_INET6; 3175478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3176478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 3177478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3178478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 3179478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3180478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Not a type on which we support filtering. 3181478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - support those that have AF_ values 3182478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * #defined on this platform, at least? 3183478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3184478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_false(); 3185478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3186478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3187478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (linktype == DLT_NULL || linktype == DLT_ENC) { 3188478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3189478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * The AF_ value is in host byte order, but 3190478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the BPF interpreter will convert it to 3191478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * network byte order. 3192478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3193478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If this is a save file, and it's from a 3194478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * machine with the opposite byte order to 3195478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * ours, we byte-swap the AF_ value. 3196478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3197478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Then we run it through "htonl()", and 3198478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * generate code to compare against the result. 3199478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3200511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (bpf_pcap->rfile != NULL && bpf_pcap->swapped) 3201478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project proto = SWAPLONG(proto); 3202478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project proto = htonl(proto); 3203478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3204478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (gen_cmp(OR_LINK, 0, BPF_W, (bpf_int32)proto)); 3205478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3206478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef HAVE_NET_PFVAR_H 3207478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PFLOG: 3208478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3209478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * af field is host byte order in contrast to the rest of 3210478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the packet. 3211478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3212478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto == ETHERTYPE_IP) 3213478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (gen_cmp(OR_LINK, offsetof(struct pfloghdr, af), 3214478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project BPF_B, (bpf_int32)AF_INET)); 3215478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (proto == ETHERTYPE_IPV6) 3216478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (gen_cmp(OR_LINK, offsetof(struct pfloghdr, af), 3217478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project BPF_B, (bpf_int32)AF_INET6)); 3218478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 3219478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_false(); 3220478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 3221478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3222478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif /* HAVE_NET_PFVAR_H */ 3223478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3224478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_ARCNET: 3225478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_ARCNET_LINUX: 3226478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3227478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX should we check for first fragment if the protocol 3228478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * uses PHDS? 3229478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3230478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 3231478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3232478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 3233478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_false(); 3234478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3235478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_IPV6: 3236478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (gen_cmp(OR_LINK, off_linktype, BPF_B, 3237478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)ARCTYPE_INET6)); 3238478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3239478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_IP: 3240478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, off_linktype, BPF_B, 3241478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)ARCTYPE_IP); 3242478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_cmp(OR_LINK, off_linktype, BPF_B, 3243478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)ARCTYPE_IP_OLD); 3244478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 3245478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (b1); 3246478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3247478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_ARP: 3248478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, off_linktype, BPF_B, 3249478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)ARCTYPE_ARP); 3250478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_cmp(OR_LINK, off_linktype, BPF_B, 3251478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)ARCTYPE_ARP_OLD); 3252478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 3253478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (b1); 3254478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3255478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_REVARP: 3256478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (gen_cmp(OR_LINK, off_linktype, BPF_B, 3257478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)ARCTYPE_REVARP)); 3258478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3259478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_ATALK: 3260478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (gen_cmp(OR_LINK, off_linktype, BPF_B, 3261478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)ARCTYPE_ATALK)); 3262478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3263478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 3264478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3265478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3266478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_LTALK: 3267478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 3268478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_ATALK: 3269478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_true(); 3270478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 3271478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_false(); 3272478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3273478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 3274478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3275478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3276478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_FRELAY: 3277478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3278478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - assumes a 2-byte Frame Relay header with 3279478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * DLCI and flags. What if the address is longer? 3280478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3281478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 3282478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3283478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_IP: 3284478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3285478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Check for the special NLPID for IP. 3286478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3287478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_cmp(OR_LINK, 2, BPF_H, (0x03<<8) | 0xcc); 3288478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3289478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_IPV6: 3290478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3291478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Check for the special NLPID for IPv6. 3292478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3293478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_cmp(OR_LINK, 2, BPF_H, (0x03<<8) | 0x8e); 3294478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3295478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case LLCSAP_ISONS: 3296478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3297478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Check for several OSI protocols. 3298478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3299478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Frame Relay packets typically have an OSI 3300478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * NLPID at the beginning; we check for each 3301478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of them. 3302478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3303478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * What we check for is the NLPID and a frame 3304478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * control field of UI, i.e. 0x03 followed 3305478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * by the NLPID. 3306478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3307478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, 2, BPF_H, (0x03<<8) | ISO8473_CLNP); 3308478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_cmp(OR_LINK, 2, BPF_H, (0x03<<8) | ISO9542_ESIS); 3309478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2 = gen_cmp(OR_LINK, 2, BPF_H, (0x03<<8) | ISO10589_ISIS); 3310478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b1, b2); 3311478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b2); 3312478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b2; 3313478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3314478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 3315478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_false(); 3316478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3317478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 3318478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3319478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3320511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_MFR: 3321511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("Multi-link Frame Relay link-layer type filtering not implemented"); 3322511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3323478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_MFR: 3324478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_MLFR: 3325478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_MLPPP: 3326478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_ATM1: 3327478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_ATM2: 3328478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_PPPOE: 3329478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_PPPOE_ATM: 3330478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_GGSN: 3331478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_ES: 3332478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_MONITOR: 3333478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_SERVICES: 3334478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_ETHER: 3335478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_PPP: 3336478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_FRELAY: 3337478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_CHDLC: 3338478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_VP: 3339511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_ST: 3340511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_ISM: 3341511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_VS: 3342511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_SRX_E2E: 3343511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_FIBRECHANNEL: 3344511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_ATM_CEMIC: 3345511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3346478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* just lets verify the magic number for now - 3347478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * on ATM we may have up to 6 different encapsulations on the wire 3348478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * and need a lot of heuristics to figure out that the payload 3349478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * might be; 3350478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3351478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * FIXME encapsulation specific BPF_ filters 3352478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3353478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_mcmp(OR_LINK, 0, BPF_W, 0x4d474300, 0xffffff00); /* compare the magic number */ 3354478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3355511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_BACNET_MS_TP: 3356511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_mcmp(OR_LINK, 0, BPF_W, 0x55FF0000, 0xffff0000); 3357511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3358511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IPNET: 3359511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_ipnet_linktype(proto); 3360511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3361478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_LINUX_IRDA: 3362478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("IrDA link-layer type filtering not implemented"); 3363478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3364478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_DOCSIS: 3365478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("DOCSIS link-layer type filtering not implemented"); 3366478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3367511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_MTP2: 3368511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_MTP2_WITH_PHDR: 3369511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("MTP2 link-layer type filtering not implemented"); 3370511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3371511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_ERF: 3372511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("ERF link-layer type filtering not implemented"); 3373511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3374511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PFSYNC: 3375511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("PFSYNC link-layer type filtering not implemented"); 3376511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3377478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_LINUX_LAPD: 3378478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("LAPD link-layer type filtering not implemented"); 3379511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3380511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_USB: 3381511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_USB_LINUX: 3382511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_USB_LINUX_MMAPPED: 3383511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("USB link-layer type filtering not implemented"); 3384511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3385511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_BLUETOOTH_HCI_H4: 3386511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_BLUETOOTH_HCI_H4_WITH_PHDR: 3387511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("Bluetooth link-layer type filtering not implemented"); 3388511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3389511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_CAN20B: 3390511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_CAN_SOCKETCAN: 3391511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("CAN link-layer type filtering not implemented"); 3392511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3393511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_15_4: 3394511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_15_4_LINUX: 3395511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_15_4_NONASK_PHY: 3396511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_15_4_NOFCS: 3397511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("IEEE 802.15.4 link-layer type filtering not implemented"); 3398511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3399511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_16_MAC_CPS_RADIO: 3400511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("IEEE 802.16 link-layer type filtering not implemented"); 3401511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3402511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_SITA: 3403511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("SITA link-layer type filtering not implemented"); 3404511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3405511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_RAIF1: 3406511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("RAIF1 link-layer type filtering not implemented"); 3407511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3408511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IPMB: 3409511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("IPMB link-layer type filtering not implemented"); 3410511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3411511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_AX25_KISS: 3412511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("AX.25 link-layer type filtering not implemented"); 3413478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3414478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3415478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3416478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * All the types that have no encapsulation should either be 3417478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * handled as DLT_SLIP, DLT_SLIP_BSDOS, and DLT_RAW are, if 3418478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * all packets are IP packets, or should be handled in some 3419478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * special case, if none of them are (if some are and some 3420478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * aren't, the lack of encapsulation is a problem, as we'd 3421478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * have to find some other way of determining the packet type). 3422478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3423478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Therefore, if "off_linktype" is -1, there's an error. 3424478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3425478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (off_linktype == (u_int)-1) 3426478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 3427478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3428478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3429478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Any type not handled above should always have an Ethernet 3430511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * type at an offset of "off_linktype". 3431478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3432478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_cmp(OR_LINK, off_linktype, BPF_H, (bpf_int32)proto); 3433478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 3434478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3435478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 3436478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Check for an LLC SNAP packet with a given organization code and 3437478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * protocol type; we check the entire contents of the 802.2 LLC and 3438478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * snap headers, checking for DSAP and SSAP of SNAP and a control 3439478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * field of 0x03 in the LLC header, and for the specified organization 3440478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * code and protocol type in the SNAP header. 3441478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3442478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 3443511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallgen_snap(orgcode, ptype) 3444478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 orgcode; 3445478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 ptype; 3446478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 3447478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_char snapblock[8]; 3448478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3449478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project snapblock[0] = LLCSAP_SNAP; /* DSAP = SNAP */ 3450478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project snapblock[1] = LLCSAP_SNAP; /* SSAP = SNAP */ 3451478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project snapblock[2] = 0x03; /* control = UI */ 3452478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project snapblock[3] = (orgcode >> 16); /* upper 8 bits of organization code */ 3453478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project snapblock[4] = (orgcode >> 8); /* middle 8 bits of organization code */ 3454478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project snapblock[5] = (orgcode >> 0); /* lower 8 bits of organization code */ 3455478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project snapblock[6] = (ptype >> 8); /* upper 8 bits of protocol type */ 3456478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project snapblock[7] = (ptype >> 0); /* lower 8 bits of protocol type */ 3457511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_bcmp(OR_MACPL, 0, 8, snapblock); 3458478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 3459478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3460478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 3461478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Generate code to match a particular packet type, for link-layer types 3462478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * using 802.2 LLC headers. 3463478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3464478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This is *NOT* used for Ethernet; "gen_ether_linktype()" is used 3465478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * for that - it handles the D/I/X Ethernet vs. 802.3+802.2 issues. 3466478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3467478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "proto" is an Ethernet type value, if > ETHERMTU, or an LLC SAP 3468478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * value, if <= ETHERMTU. We use that to determine whether to 3469478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * match the DSAP or both DSAP and LSAP or to check the OUI and 3470478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * protocol ID in a SNAP header. 3471478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3472478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 3473478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_llc_linktype(proto) 3474478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int proto; 3475478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 3476478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3477478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - handle token-ring variable-length header. 3478478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3479478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 3480478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3481478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case LLCSAP_IP: 3482478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case LLCSAP_ISONS: 3483478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case LLCSAP_NETBEUI: 3484478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3485478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - should we check both the DSAP and the 3486478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * SSAP, like this, or should we check just the 3487478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * DSAP, as we do for other types <= ETHERMTU 3488478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (i.e., other SAP values)? 3489478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3490511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_cmp(OR_MACPL, 0, BPF_H, (bpf_u_int32) 3491478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project ((proto << 8) | proto)); 3492478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3493478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case LLCSAP_IPX: 3494478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3495478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - are there ever SNAP frames for IPX on 3496478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * non-Ethernet 802.x networks? 3497478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3498511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_cmp(OR_MACPL, 0, BPF_B, 3499478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)LLCSAP_IPX); 3500478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3501478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case ETHERTYPE_ATALK: 3502478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3503478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 802.2-encapsulated ETHERTYPE_ATALK packets are 3504478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * SNAP packets with an organization code of 3505478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 0x080007 (Apple, for Appletalk) and a protocol 3506478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * type of ETHERTYPE_ATALK (Appletalk). 3507478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3508478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - check for an organization code of 3509478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * encapsulated Ethernet as well? 3510478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3511511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_snap(0x080007, ETHERTYPE_ATALK); 3512478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3513478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 3514478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3515478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - we don't have to check for IPX 802.3 3516478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * here, but should we check for the IPX Ethertype? 3517478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3518478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto <= ETHERMTU) { 3519478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3520478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This is an LLC SAP value, so check 3521478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the DSAP. 3522478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3523511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_cmp(OR_MACPL, 0, BPF_B, (bpf_int32)proto); 3524478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else { 3525478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3526478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This is an Ethernet type; we assume that it's 3527478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * unlikely that it'll appear in the right place 3528478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * at random, and therefore check only the 3529478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * location that would hold the Ethernet type 3530478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * in a SNAP frame with an organization code of 3531478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 0x000000 (encapsulated Ethernet). 3532478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3533478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - if we were to check for the SNAP DSAP and 3534478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * LSAP, as per XXX, and were also to check for an 3535478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * organization code of 0x000000 (encapsulated 3536478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Ethernet), we'd do 3537478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3538511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * return gen_snap(0x000000, proto); 3539478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3540478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * here; for now, we don't, as per the above. 3541478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * I don't know whether it's worth the extra CPU 3542478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * time to do the right check or not. 3543478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3544511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_cmp(OR_MACPL, 6, BPF_H, (bpf_int32)proto); 3545478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3546478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3547478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 3548478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3549478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 3550478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_hostop(addr, mask, dir, proto, src_off, dst_off) 3551478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 addr; 3552478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 mask; 3553478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir, proto; 3554478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int src_off, dst_off; 3555478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 3556478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1; 3557478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int offset; 3558478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3559478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (dir) { 3560478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3561478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SRC: 3562478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project offset = src_off; 3563478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3564478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3565478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DST: 3566478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project offset = dst_off; 3567478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3568478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3569478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AND: 3570478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_hostop(addr, mask, Q_SRC, proto, src_off, dst_off); 3571478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_hostop(addr, mask, Q_DST, proto, src_off, dst_off); 3572478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 3573478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 3574478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3575478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_OR: 3576478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 3577478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_hostop(addr, mask, Q_SRC, proto, src_off, dst_off); 3578478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_hostop(addr, mask, Q_DST, proto, src_off, dst_off); 3579478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 3580478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 3581478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3582478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 3583478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 3584478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3585478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(proto); 3586478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_mcmp(OR_NET, offset, BPF_W, (bpf_int32)addr, mask); 3587478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 3588478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 3589478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 3590478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3591478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef INET6 3592478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 3593478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_hostop6(addr, mask, dir, proto, src_off, dst_off) 3594478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct in6_addr *addr; 3595478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct in6_addr *mask; 3596478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir, proto; 3597478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int src_off, dst_off; 3598478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 3599478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1; 3600478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int offset; 3601478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int32_t *a, *m; 3602478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3603478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (dir) { 3604478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3605478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SRC: 3606478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project offset = src_off; 3607478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3608478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3609478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DST: 3610478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project offset = dst_off; 3611478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 3612478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3613478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AND: 3614478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_hostop6(addr, mask, Q_SRC, proto, src_off, dst_off); 3615478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_hostop6(addr, mask, Q_DST, proto, src_off, dst_off); 3616478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 3617478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 3618478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3619478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_OR: 3620478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 3621478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_hostop6(addr, mask, Q_SRC, proto, src_off, dst_off); 3622478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_hostop6(addr, mask, Q_DST, proto, src_off, dst_off); 3623478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 3624478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 3625478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3626478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 3627478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 3628478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3629478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* this order is important */ 3630478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project a = (u_int32_t *)addr; 3631478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project m = (u_int32_t *)mask; 3632478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_mcmp(OR_NET, offset + 12, BPF_W, ntohl(a[3]), ntohl(m[3])); 3633478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_mcmp(OR_NET, offset + 8, BPF_W, ntohl(a[2]), ntohl(m[2])); 3634478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 3635478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_mcmp(OR_NET, offset + 4, BPF_W, ntohl(a[1]), ntohl(m[1])); 3636478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 3637478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_mcmp(OR_NET, offset + 0, BPF_W, ntohl(a[0]), ntohl(m[0])); 3638478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 3639478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(proto); 3640478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 3641478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 3642478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 3643511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif 3644478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3645478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 3646478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_ehostop(eaddr, dir) 3647478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const u_char *eaddr; 3648478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register int dir; 3649478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 3650478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register struct block *b0, *b1; 3651478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3652478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (dir) { 3653478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SRC: 3654478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_bcmp(OR_LINK, off_mac + 6, 6, eaddr); 3655478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3656478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DST: 3657478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_bcmp(OR_LINK, off_mac + 0, 6, eaddr); 3658478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3659478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AND: 3660478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ehostop(eaddr, Q_SRC); 3661478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_ehostop(eaddr, Q_DST); 3662478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 3663478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 3664478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3665478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 3666478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_OR: 3667478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ehostop(eaddr, Q_SRC); 3668478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_ehostop(eaddr, Q_DST); 3669478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 3670478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 3671511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3672511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR1: 3673511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr1' is only supported on 802.11 with 802.11 headers"); 3674511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3675511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3676511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR2: 3677511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr2' is only supported on 802.11 with 802.11 headers"); 3678511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3679511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3680511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR3: 3681511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr3' is only supported on 802.11 with 802.11 headers"); 3682511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3683511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3684511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR4: 3685511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr4' is only supported on 802.11 with 802.11 headers"); 3686511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3687511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3688511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_RA: 3689511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'ra' is only supported on 802.11 with 802.11 headers"); 3690511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3691511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3692511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_TA: 3693511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'ta' is only supported on 802.11 with 802.11 headers"); 3694511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3695478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3696478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 3697478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 3698478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 3699478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3700478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 3701478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Like gen_ehostop, but for DLT_FDDI 3702478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3703478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 3704478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_fhostop(eaddr, dir) 3705478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const u_char *eaddr; 3706478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register int dir; 3707478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 3708478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1; 3709478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3710478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (dir) { 3711478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SRC: 3712478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_bcmp(OR_LINK, 6 + 1 + pcap_fddipad, 6, eaddr); 3713478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3714478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DST: 3715478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_bcmp(OR_LINK, 0 + 1 + pcap_fddipad, 6, eaddr); 3716478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3717478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AND: 3718478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_fhostop(eaddr, Q_SRC); 3719478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_fhostop(eaddr, Q_DST); 3720478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 3721478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 3722478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3723478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 3724478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_OR: 3725478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_fhostop(eaddr, Q_SRC); 3726478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_fhostop(eaddr, Q_DST); 3727478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 3728478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 3729511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3730511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR1: 3731511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr1' is only supported on 802.11"); 3732511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3733511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3734511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR2: 3735511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr2' is only supported on 802.11"); 3736511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3737511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3738511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR3: 3739511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr3' is only supported on 802.11"); 3740511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3741511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3742511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR4: 3743511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr4' is only supported on 802.11"); 3744511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3745511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3746511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_RA: 3747511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'ra' is only supported on 802.11"); 3748511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3749511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3750511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_TA: 3751511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'ta' is only supported on 802.11"); 3752511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3753478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3754478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 3755478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 3756478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 3757478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3758478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 3759478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Like gen_ehostop, but for DLT_IEEE802 (Token Ring) 3760478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3761478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 3762478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_thostop(eaddr, dir) 3763478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const u_char *eaddr; 3764478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register int dir; 3765478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 3766478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register struct block *b0, *b1; 3767478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3768478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (dir) { 3769478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SRC: 3770478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_bcmp(OR_LINK, 8, 6, eaddr); 3771478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3772478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DST: 3773478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_bcmp(OR_LINK, 2, 6, eaddr); 3774478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3775478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AND: 3776478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_thostop(eaddr, Q_SRC); 3777478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_thostop(eaddr, Q_DST); 3778478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 3779478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 3780478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3781478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 3782478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_OR: 3783478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_thostop(eaddr, Q_SRC); 3784478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_thostop(eaddr, Q_DST); 3785478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 3786478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 3787511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3788511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR1: 3789511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr1' is only supported on 802.11"); 3790511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3791511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3792511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR2: 3793511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr2' is only supported on 802.11"); 3794511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3795511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3796511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR3: 3797511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr3' is only supported on 802.11"); 3798511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3799511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3800511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR4: 3801511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr4' is only supported on 802.11"); 3802511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3803511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3804511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_RA: 3805511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'ra' is only supported on 802.11"); 3806511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3807511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3808511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_TA: 3809511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'ta' is only supported on 802.11"); 3810511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 3811478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 3812478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 3813478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 3814478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 3815478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3816478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 3817511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Like gen_ehostop, but for DLT_IEEE802_11 (802.11 wireless LAN) and 3818511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * various 802.11 + radio headers. 3819478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3820478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 3821478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_wlanhostop(eaddr, dir) 3822478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const u_char *eaddr; 3823478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register int dir; 3824478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 3825478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register struct block *b0, *b1, *b2; 3826478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register struct slist *s; 3827478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3828511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#ifdef ENABLE_WLAN_FILTERING_PATCH 3829511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 3830511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * TODO GV 20070613 3831511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * We need to disable the optimizer because the optimizer is buggy 3832511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * and wipes out some LD instructions generated by the below 3833511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * code to validate the Frame Control bits 3834511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 3835511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall no_optimize = 1; 3836511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif /* ENABLE_WLAN_FILTERING_PATCH */ 3837511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 3838478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (dir) { 3839478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SRC: 3840478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3841478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Oh, yuk. 3842478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3843478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For control frames, there is no SA. 3844478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3845478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For management frames, SA is at an 3846478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * offset of 10 from the beginning of 3847478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the packet. 3848478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3849478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For data frames, SA is at an offset 3850478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of 10 from the beginning of the packet 3851478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * if From DS is clear, at an offset of 3852478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 16 from the beginning of the packet 3853478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * if From DS is set and To DS is clear, 3854478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * and an offset of 24 from the beginning 3855478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of the packet if From DS is set and To DS 3856478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * is set. 3857478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3858478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3859478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3860478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Generate the tests to be done for data frames 3861478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * with From DS set. 3862478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3863478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * First, check for To DS set, i.e. check "link[1] & 0x01". 3864478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3865478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_load_a(OR_LINK, 1, BPF_B); 3866478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = new_block(JMP(BPF_JSET)); 3867478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->s.k = 0x01; /* To DS */ 3868478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->stmts = s; 3869478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3870478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3871478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If To DS is set, the SA is at 24. 3872478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3873478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_bcmp(OR_LINK, 24, 6, eaddr); 3874478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b1, b0); 3875478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3876478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3877478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now, check for To DS not set, i.e. check 3878478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "!(link[1] & 0x01)". 3879478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3880478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_load_a(OR_LINK, 1, BPF_B); 3881478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2 = new_block(JMP(BPF_JSET)); 3882478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2->s.k = 0x01; /* To DS */ 3883478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2->stmts = s; 3884478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b2); 3885478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3886478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3887478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If To DS is not set, the SA is at 16. 3888478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3889478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_bcmp(OR_LINK, 16, 6, eaddr); 3890478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b2, b1); 3891478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3892478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3893478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now OR together the last two checks. That gives 3894478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the complete set of checks for data frames with 3895478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * From DS set. 3896478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3897478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b1, b0); 3898478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3899478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3900478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now check for From DS being set, and AND that with 3901478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the ORed-together checks. 3902478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3903478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_load_a(OR_LINK, 1, BPF_B); 3904478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = new_block(JMP(BPF_JSET)); 3905478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->s.k = 0x02; /* From DS */ 3906478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->stmts = s; 3907478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b1, b0); 3908478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3909478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3910478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now check for data frames with From DS not set. 3911478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3912478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_load_a(OR_LINK, 1, BPF_B); 3913478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2 = new_block(JMP(BPF_JSET)); 3914478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2->s.k = 0x02; /* From DS */ 3915478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2->stmts = s; 3916478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b2); 3917478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3918478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3919478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If From DS isn't set, the SA is at 10. 3920478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3921478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_bcmp(OR_LINK, 10, 6, eaddr); 3922478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b2, b1); 3923478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3924478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3925478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now OR together the checks for data frames with 3926478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * From DS not set and for data frames with From DS 3927478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * set; that gives the checks done for data frames. 3928478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3929478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b1, b0); 3930478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3931478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3932478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now check for a data frame. 3933478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * I.e, check "link[0] & 0x08". 3934478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3935511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_a(OR_LINK, 0, BPF_B); 3936478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = new_block(JMP(BPF_JSET)); 3937478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->s.k = 0x08; 3938478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->stmts = s; 3939478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3940478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3941478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * AND that with the checks done for data frames. 3942478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3943478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b1, b0); 3944478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3945478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3946478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If the high-order bit of the type value is 0, this 3947478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * is a management frame. 3948478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * I.e, check "!(link[0] & 0x08)". 3949478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3950478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_load_a(OR_LINK, 0, BPF_B); 3951478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2 = new_block(JMP(BPF_JSET)); 3952478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2->s.k = 0x08; 3953478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2->stmts = s; 3954478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b2); 3955478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3956478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3957478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For management frames, the SA is at 10. 3958478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3959478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_bcmp(OR_LINK, 10, 6, eaddr); 3960478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b2, b1); 3961478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3962478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3963478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * OR that with the checks done for data frames. 3964478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * That gives the checks done for management and 3965478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * data frames. 3966478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3967478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b1, b0); 3968478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3969478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3970478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If the low-order bit of the type value is 1, 3971478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * this is either a control frame or a frame 3972478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * with a reserved type, and thus not a 3973478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frame with an SA. 3974478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3975478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * I.e., check "!(link[0] & 0x04)". 3976478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3977478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_load_a(OR_LINK, 0, BPF_B); 3978478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = new_block(JMP(BPF_JSET)); 3979478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->s.k = 0x04; 3980478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->stmts = s; 3981478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b1); 3982478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3983478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3984478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * AND that with the checks for data and management 3985478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frames. 3986478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 3987478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b1, b0); 3988478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b0; 3989478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 3990478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DST: 3991478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 3992478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Oh, yuk. 3993478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3994478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For control frames, there is no DA. 3995478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 3996478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For management frames, DA is at an 3997478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * offset of 4 from the beginning of 3998478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the packet. 3999478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 4000478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For data frames, DA is at an offset 4001478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of 4 from the beginning of the packet 4002478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * if To DS is clear and at an offset of 4003478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 16 from the beginning of the packet 4004478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * if To DS is set. 4005478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4006478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4007478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 4008478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Generate the tests to be done for data frames. 4009478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 4010478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * First, check for To DS set, i.e. "link[1] & 0x01". 4011478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4012478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_load_a(OR_LINK, 1, BPF_B); 4013478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = new_block(JMP(BPF_JSET)); 4014478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->s.k = 0x01; /* To DS */ 4015478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->stmts = s; 4016478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4017478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 4018478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If To DS is set, the DA is at 16. 4019478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4020478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_bcmp(OR_LINK, 16, 6, eaddr); 4021478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b1, b0); 4022478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4023478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 4024478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now, check for To DS not set, i.e. check 4025478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "!(link[1] & 0x01)". 4026478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4027478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_load_a(OR_LINK, 1, BPF_B); 4028478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2 = new_block(JMP(BPF_JSET)); 4029478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2->s.k = 0x01; /* To DS */ 4030478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2->stmts = s; 4031478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b2); 4032478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4033478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 4034478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If To DS is not set, the DA is at 4. 4035478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4036478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_bcmp(OR_LINK, 4, 6, eaddr); 4037478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b2, b1); 4038478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4039478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 4040478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now OR together the last two checks. That gives 4041478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the complete set of checks for data frames. 4042478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4043478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b1, b0); 4044478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4045478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 4046478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now check for a data frame. 4047478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * I.e, check "link[0] & 0x08". 4048478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4049478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_load_a(OR_LINK, 0, BPF_B); 4050478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = new_block(JMP(BPF_JSET)); 4051478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->s.k = 0x08; 4052478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->stmts = s; 4053478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4054478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 4055478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * AND that with the checks done for data frames. 4056478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4057478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b1, b0); 4058478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4059478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 4060478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If the high-order bit of the type value is 0, this 4061478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * is a management frame. 4062478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * I.e, check "!(link[0] & 0x08)". 4063478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4064478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_load_a(OR_LINK, 0, BPF_B); 4065478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2 = new_block(JMP(BPF_JSET)); 4066478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2->s.k = 0x08; 4067478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2->stmts = s; 4068478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b2); 4069478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4070478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 4071478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For management frames, the DA is at 4. 4072478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4073478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_bcmp(OR_LINK, 4, 6, eaddr); 4074478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b2, b1); 4075478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4076478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 4077478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * OR that with the checks done for data frames. 4078478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * That gives the checks done for management and 4079478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * data frames. 4080478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4081478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b1, b0); 4082478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4083478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 4084478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If the low-order bit of the type value is 1, 4085478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * this is either a control frame or a frame 4086478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * with a reserved type, and thus not a 4087478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frame with an SA. 4088478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 4089478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * I.e., check "!(link[0] & 0x04)". 4090478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4091478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_load_a(OR_LINK, 0, BPF_B); 4092478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = new_block(JMP(BPF_JSET)); 4093478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->s.k = 0x04; 4094478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1->stmts = s; 4095478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b1); 4096478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4097478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 4098478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * AND that with the checks for data and management 4099478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frames. 4100478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4101478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b1, b0); 4102478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b0; 4103478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4104511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_RA: 4105511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 4106511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Not present in management frames; addr1 in other 4107511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * frames. 4108511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 4109511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4110511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 4111511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If the high-order bit of the type value is 0, this 4112511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * is a management frame. 4113511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * I.e, check "(link[0] & 0x08)". 4114511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 4115511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_a(OR_LINK, 0, BPF_B); 4116511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = new_block(JMP(BPF_JSET)); 4117511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1->s.k = 0x08; 4118511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1->stmts = s; 4119511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4120511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 4121511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Check addr1. 4122511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 4123511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_bcmp(OR_LINK, 4, 6, eaddr); 4124511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4125511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 4126511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * AND that with the check of addr1. 4127511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 4128511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b1, b0); 4129511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (b0); 4130511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4131511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_TA: 4132511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 4133511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Not present in management frames; addr2, if present, 4134511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * in other frames. 4135511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 4136511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4137511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 4138511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Not present in CTS or ACK control frames. 4139511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 4140511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_mcmp(OR_LINK, 0, BPF_B, IEEE80211_FC0_TYPE_CTL, 4141511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall IEEE80211_FC0_TYPE_MASK); 4142511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_not(b0); 4143511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_mcmp(OR_LINK, 0, BPF_B, IEEE80211_FC0_SUBTYPE_CTS, 4144511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall IEEE80211_FC0_SUBTYPE_MASK); 4145511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_not(b1); 4146511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b2 = gen_mcmp(OR_LINK, 0, BPF_B, IEEE80211_FC0_SUBTYPE_ACK, 4147511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall IEEE80211_FC0_SUBTYPE_MASK); 4148511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_not(b2); 4149511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b1, b2); 4150511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_or(b0, b2); 4151511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4152511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 4153511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If the high-order bit of the type value is 0, this 4154511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * is a management frame. 4155511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * I.e, check "(link[0] & 0x08)". 4156511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 4157511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_a(OR_LINK, 0, BPF_B); 4158511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = new_block(JMP(BPF_JSET)); 4159511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1->s.k = 0x08; 4160511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1->stmts = s; 4161511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4162511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 4163511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * AND that with the check for frames other than 4164511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * CTS and ACK frames. 4165511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 4166511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b1, b2); 4167511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4168511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 4169511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Check addr2. 4170511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 4171511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_bcmp(OR_LINK, 10, 6, eaddr); 4172511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b2, b1); 4173511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return b1; 4174511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4175511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 4176511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * XXX - add BSSID keyword? 4177511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 4178511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR1: 4179511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (gen_bcmp(OR_LINK, 4, 6, eaddr)); 4180511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4181511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR2: 4182511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 4183511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Not present in CTS or ACK control frames. 4184511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 4185511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_mcmp(OR_LINK, 0, BPF_B, IEEE80211_FC0_TYPE_CTL, 4186511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall IEEE80211_FC0_TYPE_MASK); 4187511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_not(b0); 4188511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_mcmp(OR_LINK, 0, BPF_B, IEEE80211_FC0_SUBTYPE_CTS, 4189511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall IEEE80211_FC0_SUBTYPE_MASK); 4190511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_not(b1); 4191511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b2 = gen_mcmp(OR_LINK, 0, BPF_B, IEEE80211_FC0_SUBTYPE_ACK, 4192511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall IEEE80211_FC0_SUBTYPE_MASK); 4193511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_not(b2); 4194511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b1, b2); 4195511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_or(b0, b2); 4196511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_bcmp(OR_LINK, 10, 6, eaddr); 4197511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b2, b1); 4198511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return b1; 4199511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4200511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR3: 4201511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 4202511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Not present in control frames. 4203511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 4204511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_mcmp(OR_LINK, 0, BPF_B, IEEE80211_FC0_TYPE_CTL, 4205511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall IEEE80211_FC0_TYPE_MASK); 4206511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_not(b0); 4207511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_bcmp(OR_LINK, 16, 6, eaddr); 4208511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b0, b1); 4209511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return b1; 4210511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4211511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR4: 4212511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 4213511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Present only if the direction mask has both "From DS" 4214511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * and "To DS" set. Neither control frames nor management 4215511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * frames should have both of those set, so we don't 4216511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * check the frame type. 4217511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 4218511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_mcmp(OR_LINK, 1, BPF_B, 4219511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall IEEE80211_FC1_DIR_DSTODS, IEEE80211_FC1_DIR_MASK); 4220511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_bcmp(OR_LINK, 24, 6, eaddr); 4221511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b0, b1); 4222511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return b1; 4223511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4224478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AND: 4225478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_wlanhostop(eaddr, Q_SRC); 4226478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_wlanhostop(eaddr, Q_DST); 4227478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 4228478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 4229478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4230478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 4231478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_OR: 4232478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_wlanhostop(eaddr, Q_SRC); 4233478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_wlanhostop(eaddr, Q_DST); 4234478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4235478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 4236478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 4237478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 4238478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 4239478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 4240478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4241478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 4242478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Like gen_ehostop, but for RFC 2625 IP-over-Fibre-Channel. 4243478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (We assume that the addresses are IEEE 48-bit MAC addresses, 4244478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * as the RFC states.) 4245478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4246478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 4247478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_ipfchostop(eaddr, dir) 4248478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const u_char *eaddr; 4249478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register int dir; 4250478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 4251478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register struct block *b0, *b1; 4252478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4253478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (dir) { 4254478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SRC: 4255478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_bcmp(OR_LINK, 10, 6, eaddr); 4256478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4257478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DST: 4258478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_bcmp(OR_LINK, 2, 6, eaddr); 4259478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4260478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AND: 4261478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ipfchostop(eaddr, Q_SRC); 4262478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_ipfchostop(eaddr, Q_DST); 4263478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 4264478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 4265478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4266478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 4267478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_OR: 4268478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ipfchostop(eaddr, Q_SRC); 4269478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_ipfchostop(eaddr, Q_DST); 4270478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4271478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 4272511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4273511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR1: 4274511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr1' is only supported on 802.11"); 4275511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 4276511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4277511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR2: 4278511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr2' is only supported on 802.11"); 4279511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 4280511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4281511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR3: 4282511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr3' is only supported on 802.11"); 4283511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 4284511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4285511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR4: 4286511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr4' is only supported on 802.11"); 4287511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 4288511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4289511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_RA: 4290511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'ra' is only supported on 802.11"); 4291511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 4292511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4293511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_TA: 4294511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'ta' is only supported on 802.11"); 4295511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 4296478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 4297478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 4298478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 4299478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 4300478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4301478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 4302478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This is quite tricky because there may be pad bytes in front of the 4303478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * DECNET header, and then there are two possible data packet formats that 4304478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * carry both src and dst addresses, plus 5 packet types in a format that 4305478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * carries only the src node, plus 2 types that use a different format and 4306478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * also carry just the src node. 4307478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 4308478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Yuck. 4309478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 4310478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Instead of doing those all right, we just look for data packets with 4311478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 0 or 1 bytes of padding. If you want to look at other packets, that 4312478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * will require a lot more hacking. 4313478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 4314478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * To add support for filtering on DECNET "areas" (network numbers) 4315478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * one would want to add a "mask" argument to this routine. That would 4316478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * make the filter even more inefficient, although one could be clever 4317478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * and not generate masking instructions if the mask is 0xFFFF. 4318478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4319478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 4320478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_dnhostop(addr, dir) 4321478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 addr; 4322478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir; 4323478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 4324478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1, *b2, *tmp; 4325478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int offset_lh; /* offset if long header is received */ 4326478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int offset_sh; /* offset if short header is received */ 4327478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4328478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (dir) { 4329478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4330478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DST: 4331478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project offset_sh = 1; /* follows flags */ 4332478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project offset_lh = 7; /* flgs,darea,dsubarea,HIORD */ 4333478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4334478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4335478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SRC: 4336478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project offset_sh = 3; /* follows flags, dstnode */ 4337478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project offset_lh = 15; /* flgs,darea,dsubarea,did,sarea,ssub,HIORD */ 4338478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4339478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4340478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AND: 4341478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Inefficient because we do our Calvinball dance twice */ 4342478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_dnhostop(addr, Q_SRC); 4343478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_dnhostop(addr, Q_DST); 4344478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 4345478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 4346478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4347478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_OR: 4348478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 4349478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Inefficient because we do our Calvinball dance twice */ 4350478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_dnhostop(addr, Q_SRC); 4351478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_dnhostop(addr, Q_DST); 4352478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4353478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 4354478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4355478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISO: 4356478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("ISO host filtering not implemented"); 4357478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4358478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 4359478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 4360478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 4361478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(ETHERTYPE_DN); 4362478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Check for pad = 1, long header case */ 4363478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_mcmp(OR_NET, 2, BPF_H, 4364478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)ntohs(0x0681), (bpf_int32)ntohs(0x07FF)); 4365478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_cmp(OR_NET, 2 + 1 + offset_lh, 4366478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project BPF_H, (bpf_int32)ntohs((u_short)addr)); 4367478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(tmp, b1); 4368478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Check for pad = 0, long header case */ 4369478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_mcmp(OR_NET, 2, BPF_B, (bpf_int32)0x06, (bpf_int32)0x7); 4370478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2 = gen_cmp(OR_NET, 2 + offset_lh, BPF_H, (bpf_int32)ntohs((u_short)addr)); 4371478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(tmp, b2); 4372478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b2, b1); 4373478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Check for pad = 1, short header case */ 4374478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_mcmp(OR_NET, 2, BPF_H, 4375478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)ntohs(0x0281), (bpf_int32)ntohs(0x07FF)); 4376478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2 = gen_cmp(OR_NET, 2 + 1 + offset_sh, BPF_H, (bpf_int32)ntohs((u_short)addr)); 4377478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(tmp, b2); 4378478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b2, b1); 4379478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Check for pad = 0, short header case */ 4380478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_mcmp(OR_NET, 2, BPF_B, (bpf_int32)0x02, (bpf_int32)0x7); 4381478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2 = gen_cmp(OR_NET, 2 + offset_sh, BPF_H, (bpf_int32)ntohs((u_short)addr)); 4382478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(tmp, b2); 4383478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b2, b1); 4384478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4385478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Combine with test for linktype */ 4386478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 4387478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 4388478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 4389478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4390478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 4391478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Generate a check for IPv4 or IPv6 for MPLS-encapsulated packets; 4392478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * test the bottom-of-stack bit, and then check the version number 4393478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * field in the IP header. 4394478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4395478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 4396478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_mpls_linktype(proto) 4397478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int proto; 4398478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 4399478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1; 4400478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4401478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 4402478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4403478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IP: 4404478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* match the bottom-of-stack bit */ 4405478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_mcmp(OR_NET, -2, BPF_B, 0x01, 0x01); 4406478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* match the IPv4 version number */ 4407478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_mcmp(OR_NET, 0, BPF_B, 0x40, 0xf0); 4408478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 4409478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 4410478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4411478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IPV6: 4412478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* match the bottom-of-stack bit */ 4413478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_mcmp(OR_NET, -2, BPF_B, 0x01, 0x01); 4414478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* match the IPv4 version number */ 4415478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_mcmp(OR_NET, 0, BPF_B, 0x60, 0xf0); 4416478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 4417478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 4418478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4419478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 4420478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 4421478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 4422478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 4423478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4424478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 4425478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_host(addr, mask, proto, dir, type) 4426478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 addr; 4427478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 mask; 4428478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int proto; 4429478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir; 4430478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int type; 4431478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 4432478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1; 4433478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project const char *typestr; 4434478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4435478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (type == Q_NET) 4436478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project typestr = "net"; 4437478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 4438478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project typestr = "host"; 4439478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4440478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 4441478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4442478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 4443478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_host(addr, mask, Q_IP, dir, type); 4444478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 4445478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Only check for non-IPv4 addresses if we're not 4446478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * checking MPLS-encapsulated packets. 4447478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4448478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (label_stack_depth == 0) { 4449478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_host(addr, mask, Q_ARP, dir, type); 4450478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4451478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_host(addr, mask, Q_RARP, dir, type); 4452478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b1, b0); 4453478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 4454478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b0; 4455478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4456478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IP: 4457478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_hostop(addr, mask, dir, ETHERTYPE_IP, 12, 16); 4458478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4459478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_RARP: 4460478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_hostop(addr, mask, dir, ETHERTYPE_REVARP, 14, 24); 4461478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4462478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ARP: 4463478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_hostop(addr, mask, dir, ETHERTYPE_ARP, 14, 24); 4464478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4465478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_TCP: 4466478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'tcp' modifier applied to %s", typestr); 4467478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4468478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SCTP: 4469478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'sctp' modifier applied to %s", typestr); 4470478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4471478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_UDP: 4472478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'udp' modifier applied to %s", typestr); 4473478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4474478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ICMP: 4475478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'icmp' modifier applied to %s", typestr); 4476478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4477478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IGMP: 4478478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'igmp' modifier applied to %s", typestr); 4479478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4480478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IGRP: 4481478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'igrp' modifier applied to %s", typestr); 4482478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4483478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_PIM: 4484478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'pim' modifier applied to %s", typestr); 4485478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4486478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_VRRP: 4487478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'vrrp' modifier applied to %s", typestr); 4488478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4489511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_CARP: 4490511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'carp' modifier applied to %s", typestr); 4491511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4492478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ATALK: 4493478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("ATALK host filtering not implemented"); 4494478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4495478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AARP: 4496478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("AARP host filtering not implemented"); 4497478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4498478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DECNET: 4499478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_dnhostop(addr, dir); 4500478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4501478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SCA: 4502478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("SCA host filtering not implemented"); 4503478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4504478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_LAT: 4505478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("LAT host filtering not implemented"); 4506478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4507478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_MOPDL: 4508478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("MOPDL host filtering not implemented"); 4509478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4510478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_MOPRC: 4511478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("MOPRC host filtering not implemented"); 4512478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4513478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IPV6: 4514478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'ip6' modifier applied to ip host"); 4515478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4516478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ICMPV6: 4517478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'icmp6' modifier applied to %s", typestr); 4518478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4519478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AH: 4520478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'ah' modifier applied to %s", typestr); 4521478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4522478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ESP: 4523478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'esp' modifier applied to %s", typestr); 4524478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4525478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISO: 4526478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("ISO host filtering not implemented"); 4527478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4528478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ESIS: 4529478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'esis' modifier applied to %s", typestr); 4530478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4531478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISIS: 4532478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'isis' modifier applied to %s", typestr); 4533478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4534478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_CLNP: 4535478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'clnp' modifier applied to %s", typestr); 4536478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4537478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_STP: 4538478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'stp' modifier applied to %s", typestr); 4539478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4540478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IPX: 4541478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("IPX host filtering not implemented"); 4542478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4543478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_NETBEUI: 4544478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'netbeui' modifier applied to %s", typestr); 4545478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4546478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_RADIO: 4547478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'radio' modifier applied to %s", typestr); 4548478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4549478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 4550478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 4551478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 4552478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 4553478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 4554478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4555478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef INET6 4556478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 4557478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_host6(addr, mask, proto, dir, type) 4558478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct in6_addr *addr; 4559478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct in6_addr *mask; 4560478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int proto; 4561478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir; 4562478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int type; 4563478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 4564478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project const char *typestr; 4565478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4566478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (type == Q_NET) 4567478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project typestr = "net"; 4568478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 4569478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project typestr = "host"; 4570478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4571478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 4572478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4573478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 4574478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_host6(addr, mask, Q_IPV6, dir, type); 4575478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4576511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_LINK: 4577511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("link-layer modifier applied to ip6 %s", typestr); 4578511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4579478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IP: 4580478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'ip' modifier applied to ip6 %s", typestr); 4581478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4582478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_RARP: 4583478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'rarp' modifier applied to ip6 %s", typestr); 4584478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4585478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ARP: 4586478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'arp' modifier applied to ip6 %s", typestr); 4587478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4588478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SCTP: 4589478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'sctp' modifier applied to %s", typestr); 4590478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4591478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_TCP: 4592478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'tcp' modifier applied to %s", typestr); 4593478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4594478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_UDP: 4595478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'udp' modifier applied to %s", typestr); 4596478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4597478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ICMP: 4598478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'icmp' modifier applied to %s", typestr); 4599478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4600478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IGMP: 4601478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'igmp' modifier applied to %s", typestr); 4602478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4603478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IGRP: 4604478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'igrp' modifier applied to %s", typestr); 4605478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4606478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_PIM: 4607478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'pim' modifier applied to %s", typestr); 4608478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4609478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_VRRP: 4610478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'vrrp' modifier applied to %s", typestr); 4611478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4612511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_CARP: 4613511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'carp' modifier applied to %s", typestr); 4614511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4615478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ATALK: 4616478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("ATALK host filtering not implemented"); 4617478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4618478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AARP: 4619478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("AARP host filtering not implemented"); 4620478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4621478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DECNET: 4622478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'decnet' modifier applied to ip6 %s", typestr); 4623478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4624478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SCA: 4625478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("SCA host filtering not implemented"); 4626478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4627478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_LAT: 4628478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("LAT host filtering not implemented"); 4629478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4630478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_MOPDL: 4631478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("MOPDL host filtering not implemented"); 4632478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4633478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_MOPRC: 4634478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("MOPRC host filtering not implemented"); 4635478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4636478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IPV6: 4637478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_hostop6(addr, mask, dir, ETHERTYPE_IPV6, 8, 24); 4638478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4639478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ICMPV6: 4640478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'icmp6' modifier applied to %s", typestr); 4641478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4642478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AH: 4643478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'ah' modifier applied to %s", typestr); 4644478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4645478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ESP: 4646478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'esp' modifier applied to %s", typestr); 4647478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4648478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISO: 4649478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("ISO host filtering not implemented"); 4650478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4651478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ESIS: 4652478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'esis' modifier applied to %s", typestr); 4653478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4654478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISIS: 4655478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'isis' modifier applied to %s", typestr); 4656478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4657478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_CLNP: 4658478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'clnp' modifier applied to %s", typestr); 4659478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4660478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_STP: 4661478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'stp' modifier applied to %s", typestr); 4662478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4663478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IPX: 4664478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("IPX host filtering not implemented"); 4665478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4666478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_NETBEUI: 4667478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'netbeui' modifier applied to %s", typestr); 4668478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4669478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_RADIO: 4670478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'radio' modifier applied to %s", typestr); 4671478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4672478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 4673478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 4674478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 4675478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 4676478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 4677511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif 4678478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4679478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef INET6 4680478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 4681478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_gateway(eaddr, alist, proto, dir) 4682478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project const u_char *eaddr; 4683478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 **alist; 4684478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int proto; 4685478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir; 4686478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 4687478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1, *tmp; 4688478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4689478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (dir != 0) 4690478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("direction applied to 'gateway'"); 4691478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4692478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 4693478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 4694478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IP: 4695478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ARP: 4696478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_RARP: 4697511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall switch (linktype) { 4698511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_EN10MB: 4699511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER: 4700511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER_TRANSPARENT: 4701511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_ehostop(eaddr, Q_OR); 4702511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 4703511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_FDDI: 4704511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_fhostop(eaddr, Q_OR); 4705511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 4706478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IEEE802: 4707511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_thostop(eaddr, Q_OR); 4708511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 4709478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IEEE802_11: 4710511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PRISM_HEADER: 4711478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IEEE802_11_RADIO_AVS: 4712478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IEEE802_11_RADIO: 4713511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PPI: 4714511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_wlanhostop(eaddr, Q_OR); 4715511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 4716511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_SUNATM: 4717511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (!is_lane) 4718511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error( 4719511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall "'gateway' supported only on ethernet/FDDI/token ring/802.11/ATM LANE/Fibre Channel"); 4720478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 4721478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Check that the packet doesn't begin with an 4722478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * LE Control marker. (We've already generated 4723478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * a test for LANE.) 4724478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4725511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_cmp(OR_LINK, SUNATM_PKT_BEGIN_POS, 4726511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall BPF_H, 0xFF00); 4727478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b1); 4728478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4729478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 4730478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Now check the MAC address. 4731478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 4732478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ehostop(eaddr, Q_OR); 4733478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b1, b0); 4734511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 4735478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IP_OVER_FC: 4736511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_ipfchostop(eaddr, Q_OR); 4737511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 4738511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall default: 4739511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error( 4740511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall "'gateway' supported only on ethernet/FDDI/token ring/802.11/ATM LANE/Fibre Channel"); 4741511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 4742478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_host(**alist++, 0xffffffff, proto, Q_OR, Q_HOST); 4743478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project while (*alist) { 4744478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_host(**alist++, 0xffffffff, proto, Q_OR, 4745478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project Q_HOST); 4746478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b1, tmp); 4747478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = tmp; 4748478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 4749478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b1); 4750478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 4751478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 4752478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 4753478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("illegal modifier of 'gateway'"); 4754478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 4755478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 4756478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 4757478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4758478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 4759478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_proto_abbrev(proto) 4760478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int proto; 4761478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 4762478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0; 4763478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b1; 4764478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4765478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 4766478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4767478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SCTP: 4768478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(IPPROTO_SCTP, Q_IP, Q_DEFAULT); 4769478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(IPPROTO_SCTP, Q_IPV6, Q_DEFAULT); 4770478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4771478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4772478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4773478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_TCP: 4774478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(IPPROTO_TCP, Q_IP, Q_DEFAULT); 4775478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(IPPROTO_TCP, Q_IPV6, Q_DEFAULT); 4776478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4777478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4778478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4779478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_UDP: 4780478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(IPPROTO_UDP, Q_IP, Q_DEFAULT); 4781478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(IPPROTO_UDP, Q_IPV6, Q_DEFAULT); 4782478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4783478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4784478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4785478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ICMP: 4786478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(IPPROTO_ICMP, Q_IP, Q_DEFAULT); 4787478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4788478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4789478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef IPPROTO_IGMP 4790478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#define IPPROTO_IGMP 2 4791478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 4792478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4793478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IGMP: 4794478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(IPPROTO_IGMP, Q_IP, Q_DEFAULT); 4795478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4796478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4797478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef IPPROTO_IGRP 4798478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#define IPPROTO_IGRP 9 4799478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 4800478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IGRP: 4801478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(IPPROTO_IGRP, Q_IP, Q_DEFAULT); 4802478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4803478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4804478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef IPPROTO_PIM 4805478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#define IPPROTO_PIM 103 4806478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 4807478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4808478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_PIM: 4809478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(IPPROTO_PIM, Q_IP, Q_DEFAULT); 4810478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(IPPROTO_PIM, Q_IPV6, Q_DEFAULT); 4811478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4812478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4813478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4814478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef IPPROTO_VRRP 4815478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#define IPPROTO_VRRP 112 4816478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 4817478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4818478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_VRRP: 4819478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(IPPROTO_VRRP, Q_IP, Q_DEFAULT); 4820478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4821478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4822511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#ifndef IPPROTO_CARP 4823511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#define IPPROTO_CARP 112 4824511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif 4825511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4826511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_CARP: 4827511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_proto(IPPROTO_CARP, Q_IP, Q_DEFAULT); 4828511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 4829511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 4830478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IP: 4831478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_linktype(ETHERTYPE_IP); 4832478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4833478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4834478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ARP: 4835478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_linktype(ETHERTYPE_ARP); 4836478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4837478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4838478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_RARP: 4839478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_linktype(ETHERTYPE_REVARP); 4840478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4841478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4842478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_LINK: 4843478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("link layer applied in wrong context"); 4844478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4845478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ATALK: 4846478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_linktype(ETHERTYPE_ATALK); 4847478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4848478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4849478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AARP: 4850478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_linktype(ETHERTYPE_AARP); 4851478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4852478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4853478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DECNET: 4854478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_linktype(ETHERTYPE_DN); 4855478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4856478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4857478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SCA: 4858478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_linktype(ETHERTYPE_SCA); 4859478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4860478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4861478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_LAT: 4862478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_linktype(ETHERTYPE_LAT); 4863478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4864478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4865478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_MOPDL: 4866478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_linktype(ETHERTYPE_MOPDL); 4867478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4868478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4869478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_MOPRC: 4870478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_linktype(ETHERTYPE_MOPRC); 4871478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4872478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4873478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IPV6: 4874478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_linktype(ETHERTYPE_IPV6); 4875478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4876478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4877478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef IPPROTO_ICMPV6 4878478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#define IPPROTO_ICMPV6 58 4879478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 4880478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ICMPV6: 4881478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(IPPROTO_ICMPV6, Q_IPV6, Q_DEFAULT); 4882478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4883478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4884478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef IPPROTO_AH 4885478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#define IPPROTO_AH 51 4886478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 4887478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AH: 4888478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(IPPROTO_AH, Q_IP, Q_DEFAULT); 4889478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(IPPROTO_AH, Q_IPV6, Q_DEFAULT); 4890478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4891478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4892478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4893478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef IPPROTO_ESP 4894478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#define IPPROTO_ESP 50 4895478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 4896478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ESP: 4897478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(IPPROTO_ESP, Q_IP, Q_DEFAULT); 4898478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(IPPROTO_ESP, Q_IPV6, Q_DEFAULT); 4899478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4900478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4901478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4902478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISO: 4903478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_linktype(LLCSAP_ISONS); 4904478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4905478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4906478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ESIS: 4907478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(ISO9542_ESIS, Q_ISO, Q_DEFAULT); 4908478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4909478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4910478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISIS: 4911478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(ISO10589_ISIS, Q_ISO, Q_DEFAULT); 4912478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4913478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4914478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISIS_L1: /* all IS-IS Level1 PDU-Types */ 4915478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_L1_LAN_IIH, Q_ISIS, Q_DEFAULT); 4916478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(ISIS_PTP_IIH, Q_ISIS, Q_DEFAULT); /* FIXME extract the circuit-type bits */ 4917478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4918478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_L1_LSP, Q_ISIS, Q_DEFAULT); 4919478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4920478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_L1_CSNP, Q_ISIS, Q_DEFAULT); 4921478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4922478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_L1_PSNP, Q_ISIS, Q_DEFAULT); 4923478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4924478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4925478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4926478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISIS_L2: /* all IS-IS Level2 PDU-Types */ 4927478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_L2_LAN_IIH, Q_ISIS, Q_DEFAULT); 4928478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(ISIS_PTP_IIH, Q_ISIS, Q_DEFAULT); /* FIXME extract the circuit-type bits */ 4929478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4930478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_L2_LSP, Q_ISIS, Q_DEFAULT); 4931478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4932478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_L2_CSNP, Q_ISIS, Q_DEFAULT); 4933478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4934478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_L2_PSNP, Q_ISIS, Q_DEFAULT); 4935478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4936478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4937478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4938478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISIS_IIH: /* all IS-IS Hello PDU-Types */ 4939478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_L1_LAN_IIH, Q_ISIS, Q_DEFAULT); 4940478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(ISIS_L2_LAN_IIH, Q_ISIS, Q_DEFAULT); 4941478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4942478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_PTP_IIH, Q_ISIS, Q_DEFAULT); 4943478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4944478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4945478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4946478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISIS_LSP: 4947478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_L1_LSP, Q_ISIS, Q_DEFAULT); 4948478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(ISIS_L2_LSP, Q_ISIS, Q_DEFAULT); 4949478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4950478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4951478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4952478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISIS_SNP: 4953478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_L1_CSNP, Q_ISIS, Q_DEFAULT); 4954478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(ISIS_L2_CSNP, Q_ISIS, Q_DEFAULT); 4955478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4956478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_L1_PSNP, Q_ISIS, Q_DEFAULT); 4957478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4958478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_L2_PSNP, Q_ISIS, Q_DEFAULT); 4959478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4960478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4961478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4962478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISIS_CSNP: 4963478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_L1_CSNP, Q_ISIS, Q_DEFAULT); 4964478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(ISIS_L2_CSNP, Q_ISIS, Q_DEFAULT); 4965478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4966478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4967478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4968478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISIS_PSNP: 4969478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISIS_L1_PSNP, Q_ISIS, Q_DEFAULT); 4970478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(ISIS_L2_PSNP, Q_ISIS, Q_DEFAULT); 4971478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 4972478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4973478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4974478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_CLNP: 4975478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(ISO8473_CLNP, Q_ISO, Q_DEFAULT); 4976478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4977478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4978478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_STP: 4979478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_linktype(LLCSAP_8021D); 4980478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4981478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4982478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IPX: 4983478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_linktype(LLCSAP_IPX); 4984478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4985478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4986478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_NETBEUI: 4987478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_linktype(LLCSAP_NETBEUI); 4988478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 4989478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4990478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_RADIO: 4991478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'radio' is not a valid protocol type"); 4992478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4993478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 4994478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 4995478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 4996478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 4997478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 4998478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 4999478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 5000478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_ipfrag() 5001478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5002478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s; 5003478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b; 5004478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5005511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* not IPv4 frag other than the first frag */ 5006478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_load_a(OR_NET, 6, BPF_H); 5007478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = new_block(JMP(BPF_JSET)); 5008478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b->s.k = 0x1fff; 5009478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b->stmts = s; 5010478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b); 5011478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5012478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 5013478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5014478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5015478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 5016478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Generate a comparison to a port value in the transport-layer header 5017478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * at the specified offset from the beginning of that header. 5018478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 5019478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - this handles a variable-length prefix preceding the link-layer 5020478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * header, such as the radiotap or AVS radio prefix, but doesn't handle 5021478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * variable-length link-layer headers (such as Token Ring or 802.11 5022478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * headers). 5023478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 5024478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 5025478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_portatom(off, v) 5026478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int off; 5027478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 v; 5028478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5029478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_cmp(OR_TRAN_IPV4, off, BPF_H, v); 5030478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5031478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5032478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 5033478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_portatom6(off, v) 5034478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int off; 5035478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 v; 5036478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5037478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_cmp(OR_TRAN_IPV6, off, BPF_H, v); 5038478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5039478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5040478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 5041478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_portop(port, proto, dir) 5042478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int port, proto, dir; 5043478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5044478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1, *tmp; 5045478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5046511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* ip proto 'proto' and not a fragment other than the first fragment */ 5047478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_cmp(OR_NET, 9, BPF_B, (bpf_int32)proto); 5048478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ipfrag(); 5049478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(tmp, b0); 5050478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5051478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (dir) { 5052478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SRC: 5053478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portatom(0, (bpf_int32)port); 5054478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5055478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5056478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DST: 5057478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portatom(2, (bpf_int32)port); 5058478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5059478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5060478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_OR: 5061478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 5062478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portatom(0, (bpf_int32)port); 5063478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portatom(2, (bpf_int32)port); 5064478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(tmp, b1); 5065478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5066478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5067478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AND: 5068478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portatom(0, (bpf_int32)port); 5069478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portatom(2, (bpf_int32)port); 5070478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(tmp, b1); 5071478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5072478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5073478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 5074478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 5075478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5076478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 5077478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5078478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 5079478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5080478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5081478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 5082478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_port(port, ip_proto, dir) 5083478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int port; 5084478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int ip_proto; 5085478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir; 5086478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5087478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1, *tmp; 5088478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5089478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 5090478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * ether proto ip 5091478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 5092478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For FDDI, RFC 1188 says that SNAP encapsulation is used, 5093478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * not LLC encapsulation with LLCSAP_IP. 5094478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 5095478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For IEEE 802 networks - which includes 802.5 token ring 5096478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (which is what DLT_IEEE802 means) and 802.11 - RFC 1042 5097478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * says that SNAP encapsulation is used, not LLC encapsulation 5098478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * with LLCSAP_IP. 5099478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 5100478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For LLC-encapsulated ATM/"Classical IP", RFC 1483 and 5101478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * RFC 2225 say that SNAP encapsulation is used, not LLC 5102478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * encapsulation with LLCSAP_IP. 5103478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 5104478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * So we always check for ETHERTYPE_IP. 5105478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 5106478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(ETHERTYPE_IP); 5107478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5108478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (ip_proto) { 5109478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case IPPROTO_UDP: 5110478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case IPPROTO_TCP: 5111478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case IPPROTO_SCTP: 5112478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portop(port, ip_proto, dir); 5113478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5114478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5115478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case PROTO_UNDEF: 5116478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portop(port, IPPROTO_TCP, dir); 5117478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portop(port, IPPROTO_UDP, dir); 5118478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(tmp, b1); 5119478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portop(port, IPPROTO_SCTP, dir); 5120478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(tmp, b1); 5121478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5122478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5123478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 5124478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 5125478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5126478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 5127478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 5128478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5129478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5130478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 5131478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_portop6(port, proto, dir) 5132478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int port, proto, dir; 5133478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5134478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1, *tmp; 5135478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5136478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* ip6 proto 'proto' */ 5137511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* XXX - catch the first fragment of a fragmented packet? */ 5138478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_NET, 6, BPF_B, (bpf_int32)proto); 5139478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5140478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (dir) { 5141478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SRC: 5142478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portatom6(0, (bpf_int32)port); 5143478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5144478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5145478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DST: 5146478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portatom6(2, (bpf_int32)port); 5147478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5148478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5149478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_OR: 5150478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 5151478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portatom6(0, (bpf_int32)port); 5152478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portatom6(2, (bpf_int32)port); 5153478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(tmp, b1); 5154478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5155478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5156478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AND: 5157478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portatom6(0, (bpf_int32)port); 5158478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portatom6(2, (bpf_int32)port); 5159478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(tmp, b1); 5160478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5161478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5162478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 5163478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 5164478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5165478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 5166478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5167478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 5168478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5169478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5170478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 5171478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_port6(port, ip_proto, dir) 5172478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int port; 5173478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int ip_proto; 5174478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir; 5175478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5176478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1, *tmp; 5177478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5178478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* link proto ip6 */ 5179478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(ETHERTYPE_IPV6); 5180478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5181478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (ip_proto) { 5182478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case IPPROTO_UDP: 5183478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case IPPROTO_TCP: 5184478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case IPPROTO_SCTP: 5185478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portop6(port, ip_proto, dir); 5186478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5187478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5188478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case PROTO_UNDEF: 5189478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portop6(port, IPPROTO_TCP, dir); 5190478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portop6(port, IPPROTO_UDP, dir); 5191478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(tmp, b1); 5192478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portop6(port, IPPROTO_SCTP, dir); 5193478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(tmp, b1); 5194478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5195478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5196478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 5197478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 5198478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5199478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 5200478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 5201478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5202478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5203478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* gen_portrange code */ 5204478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 5205478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_portrangeatom(off, v1, v2) 5206478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int off; 5207478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 v1, v2; 5208478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5209478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b1, *b2; 5210478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5211478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (v1 > v2) { 5212478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 5213478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Reverse the order of the ports, so v1 is the lower one. 5214478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 5215478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 vtemp; 5216478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5217478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project vtemp = v1; 5218478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v1 = v2; 5219478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v2 = vtemp; 5220478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5221478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5222478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_cmp_ge(OR_TRAN_IPV4, off, BPF_H, v1); 5223478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2 = gen_cmp_le(OR_TRAN_IPV4, off, BPF_H, v2); 5224478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5225478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b1, b2); 5226478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5227478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b2; 5228478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5229478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5230478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 5231478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_portrangeop(port1, port2, proto, dir) 5232478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int port1, port2; 5233478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int proto; 5234478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir; 5235478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5236478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1, *tmp; 5237478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5238511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* ip proto 'proto' and not a fragment other than the first fragment */ 5239478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_cmp(OR_NET, 9, BPF_B, (bpf_int32)proto); 5240478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ipfrag(); 5241478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(tmp, b0); 5242478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5243478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (dir) { 5244478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SRC: 5245478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portrangeatom(0, (bpf_int32)port1, (bpf_int32)port2); 5246478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5247478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5248478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DST: 5249478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portrangeatom(2, (bpf_int32)port1, (bpf_int32)port2); 5250478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5251478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5252478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_OR: 5253478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 5254478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portrangeatom(0, (bpf_int32)port1, (bpf_int32)port2); 5255478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portrangeatom(2, (bpf_int32)port1, (bpf_int32)port2); 5256478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(tmp, b1); 5257478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5258478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5259478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AND: 5260478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portrangeatom(0, (bpf_int32)port1, (bpf_int32)port2); 5261478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portrangeatom(2, (bpf_int32)port1, (bpf_int32)port2); 5262478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(tmp, b1); 5263478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5264478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5265478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 5266478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 5267478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5268478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 5269478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5270478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 5271478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5272478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5273478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 5274478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_portrange(port1, port2, ip_proto, dir) 5275478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int port1, port2; 5276478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int ip_proto; 5277478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir; 5278478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5279478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1, *tmp; 5280478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5281478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* link proto ip */ 5282478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(ETHERTYPE_IP); 5283478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5284478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (ip_proto) { 5285478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case IPPROTO_UDP: 5286478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case IPPROTO_TCP: 5287478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case IPPROTO_SCTP: 5288478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portrangeop(port1, port2, ip_proto, dir); 5289478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5290478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5291478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case PROTO_UNDEF: 5292478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portrangeop(port1, port2, IPPROTO_TCP, dir); 5293478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portrangeop(port1, port2, IPPROTO_UDP, dir); 5294478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(tmp, b1); 5295478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portrangeop(port1, port2, IPPROTO_SCTP, dir); 5296478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(tmp, b1); 5297478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5298478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5299478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 5300478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 5301478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5302478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 5303478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 5304478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5305478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5306478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 5307478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_portrangeatom6(off, v1, v2) 5308478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int off; 5309478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 v1, v2; 5310478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5311478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b1, *b2; 5312478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5313478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (v1 > v2) { 5314478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 5315478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Reverse the order of the ports, so v1 is the lower one. 5316478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 5317478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 vtemp; 5318478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5319478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project vtemp = v1; 5320478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v1 = v2; 5321478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v2 = vtemp; 5322478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5323478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5324478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_cmp_ge(OR_TRAN_IPV6, off, BPF_H, v1); 5325478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2 = gen_cmp_le(OR_TRAN_IPV6, off, BPF_H, v2); 5326478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5327478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b1, b2); 5328478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5329478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b2; 5330478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5331478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5332478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 5333478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_portrangeop6(port1, port2, proto, dir) 5334478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int port1, port2; 5335478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int proto; 5336478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir; 5337478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5338478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1, *tmp; 5339478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5340478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* ip6 proto 'proto' */ 5341511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* XXX - catch the first fragment of a fragmented packet? */ 5342478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_NET, 6, BPF_B, (bpf_int32)proto); 5343478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5344478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (dir) { 5345478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SRC: 5346478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portrangeatom6(0, (bpf_int32)port1, (bpf_int32)port2); 5347478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5348478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5349478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DST: 5350478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portrangeatom6(2, (bpf_int32)port1, (bpf_int32)port2); 5351478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5352478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5353478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_OR: 5354478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 5355478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portrangeatom6(0, (bpf_int32)port1, (bpf_int32)port2); 5356478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portrangeatom6(2, (bpf_int32)port1, (bpf_int32)port2); 5357478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(tmp, b1); 5358478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5359478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5360478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AND: 5361478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portrangeatom6(0, (bpf_int32)port1, (bpf_int32)port2); 5362478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portrangeatom6(2, (bpf_int32)port1, (bpf_int32)port2); 5363478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(tmp, b1); 5364478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5365478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5366478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 5367478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 5368478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5369478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 5370478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5371478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 5372478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5373478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5374478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 5375478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_portrange6(port1, port2, ip_proto, dir) 5376478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int port1, port2; 5377478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int ip_proto; 5378478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir; 5379478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5380478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1, *tmp; 5381478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5382478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* link proto ip6 */ 5383478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(ETHERTYPE_IPV6); 5384478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5385478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (ip_proto) { 5386478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case IPPROTO_UDP: 5387478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case IPPROTO_TCP: 5388478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case IPPROTO_SCTP: 5389478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portrangeop6(port1, port2, ip_proto, dir); 5390478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5391478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5392478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case PROTO_UNDEF: 5393478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portrangeop6(port1, port2, IPPROTO_TCP, dir); 5394478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_portrangeop6(port1, port2, IPPROTO_UDP, dir); 5395478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(tmp, b1); 5396478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_portrangeop6(port1, port2, IPPROTO_SCTP, dir); 5397478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(tmp, b1); 5398478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5399478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5400478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 5401478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 5402478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5403478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 5404478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 5405478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5406478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5407478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic int 5408478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectlookup_proto(name, proto) 5409478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const char *name; 5410478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register int proto; 5411478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5412478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register int v; 5413478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5414478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 5415478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5416478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 5417478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IP: 5418478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IPV6: 5419478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v = pcap_nametoproto(name); 5420478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (v == PROTO_UNDEF) 5421478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unknown ip proto '%s'", name); 5422478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5423478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5424478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_LINK: 5425478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* XXX should look up h/w protocol type based on linktype */ 5426478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v = pcap_nametoeproto(name); 5427478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (v == PROTO_UNDEF) { 5428478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v = pcap_nametollc(name); 5429478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (v == PROTO_UNDEF) 5430478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unknown ether proto '%s'", name); 5431478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5432478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5433478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5434478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISO: 5435478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (strcmp(name, "esis") == 0) 5436478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v = ISO9542_ESIS; 5437478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (strcmp(name, "isis") == 0) 5438478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v = ISO10589_ISIS; 5439478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (strcmp(name, "clnp") == 0) 5440478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v = ISO8473_CLNP; 5441478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 5442478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unknown osi proto '%s'", name); 5443478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5444478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5445478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 5446478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v = PROTO_UNDEF; 5447478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5448478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5449478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return v; 5450478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5451478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5452478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#if 0 5453478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct stmt * 5454478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_joinsp(s, n) 5455478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct stmt **s; 5456478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int n; 5457478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5458478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return NULL; 5459478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5460478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 5461478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5462478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 5463478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_protochain(v, proto, dir) 5464478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int v; 5465478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int proto; 5466478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir; 5467478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5468478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef NO_PROTOCHAIN 5469478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_proto(v, proto, dir); 5470478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#else 5471478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b; 5472478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s[100]; 5473478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int fix2, fix3, fix4, fix5; 5474478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int ahcheck, again, end; 5475478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int i, max; 5476478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int reg2 = alloc_reg(); 5477478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5478478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project memset(s, 0, sizeof(s)); 5479478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project fix2 = fix3 = fix4 = fix5 = 0; 5480478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5481478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 5482478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IP: 5483478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IPV6: 5484478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5485478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 5486478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_protochain(v, Q_IP, dir); 5487478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_protochain(v, Q_IPV6, dir); 5488478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b); 5489478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 5490478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 5491478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("bad protocol applied for 'protochain'"); 5492478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 5493478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5494478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5495478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 5496511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * We don't handle variable-length prefixes before the link-layer 5497511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * header, or variable-length link-layer headers, here yet. 5498478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * We might want to add BPF instructions to do the protochain 5499478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * work, to simplify that and, on platforms that have a BPF 5500478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * interpreter with the new instructions, let the filtering 5501478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * be done in the kernel. (We already require a modified BPF 5502478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * engine to do the protochain stuff, to support backward 5503478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * branches, and backward branch support is unlikely to appear 5504478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * in kernel BPF engines.) 5505478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 5506511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall switch (linktype) { 5507478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5508511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11: 5509511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PRISM_HEADER: 5510511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO_AVS: 5511511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO: 5512511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PPI: 5513511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'protochain' not supported with 802.11"); 5514511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 5515478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5516478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project no_optimize = 1; /*this code is not compatible with optimzer yet */ 5517478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5518478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 5519478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * s[0] is a dummy entry to protect other BPF insn from damage 5520478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * by s[fix] = foo with uninitialized variable "fix". It is somewhat 5521478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * hard to find interdependency made by jump table fixup. 5522478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 5523478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i = 0; 5524478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(0); /*dummy*/ 5525478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5526478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5527478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 5528478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IP: 5529478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(ETHERTYPE_IP); 5530478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5531478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* A = ip->ip_p */ 5532478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_LD|BPF_ABS|BPF_B); 5533511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s[i]->s.k = off_macpl + off_nl + 9; 5534478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5535478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* X = ip->ip_hl << 2 */ 5536478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_LDX|BPF_MSH|BPF_B); 5537511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s[i]->s.k = off_macpl + off_nl; 5538478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5539478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5540511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 5541478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IPV6: 5542478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(ETHERTYPE_IPV6); 5543478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5544478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* A = ip6->ip_nxt */ 5545478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_LD|BPF_ABS|BPF_B); 5546511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s[i]->s.k = off_macpl + off_nl + 6; 5547478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5548478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* X = sizeof(struct ip6_hdr) */ 5549478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_LDX|BPF_IMM); 5550478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = 40; 5551478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5552478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5553511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 5554478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 5555478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unsupported proto to gen_protochain"); 5556478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 5557478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5558478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5559478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* again: if (A == v) goto end; else fall through; */ 5560478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project again = i; 5561478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_JMP|BPF_JEQ|BPF_K); 5562478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = v; 5563478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.jt = NULL; /*later*/ 5564478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.jf = NULL; /*update in next stmt*/ 5565478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project fix5 = i; 5566478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5567478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5568478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef IPPROTO_NONE 5569478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#define IPPROTO_NONE 59 5570478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 5571478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* if (A == IPPROTO_NONE) goto end */ 5572478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_JMP|BPF_JEQ|BPF_K); 5573478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.jt = NULL; /*later*/ 5574478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.jf = NULL; /*update in next stmt*/ 5575478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = IPPROTO_NONE; 5576478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[fix5]->s.jf = s[i]; 5577478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project fix2 = i; 5578478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5579478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5580478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto == Q_IPV6) { 5581478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int v6start, v6end, v6advance, j; 5582478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5583478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v6start = i; 5584478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* if (A == IPPROTO_HOPOPTS) goto v6advance */ 5585478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_JMP|BPF_JEQ|BPF_K); 5586478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.jt = NULL; /*later*/ 5587478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.jf = NULL; /*update in next stmt*/ 5588478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = IPPROTO_HOPOPTS; 5589478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[fix2]->s.jf = s[i]; 5590478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5591478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* if (A == IPPROTO_DSTOPTS) goto v6advance */ 5592478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i - 1]->s.jf = s[i] = new_stmt(BPF_JMP|BPF_JEQ|BPF_K); 5593478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.jt = NULL; /*later*/ 5594478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.jf = NULL; /*update in next stmt*/ 5595478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = IPPROTO_DSTOPTS; 5596478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5597478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* if (A == IPPROTO_ROUTING) goto v6advance */ 5598478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i - 1]->s.jf = s[i] = new_stmt(BPF_JMP|BPF_JEQ|BPF_K); 5599478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.jt = NULL; /*later*/ 5600478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.jf = NULL; /*update in next stmt*/ 5601478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = IPPROTO_ROUTING; 5602478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5603478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* if (A == IPPROTO_FRAGMENT) goto v6advance; else goto ahcheck; */ 5604478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i - 1]->s.jf = s[i] = new_stmt(BPF_JMP|BPF_JEQ|BPF_K); 5605478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.jt = NULL; /*later*/ 5606478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.jf = NULL; /*later*/ 5607478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = IPPROTO_FRAGMENT; 5608478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project fix3 = i; 5609478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v6end = i; 5610478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5611478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5612478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* v6advance: */ 5613478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v6advance = i; 5614478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5615478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 5616478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * in short, 5617511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * A = P[X + packet head]; 5618511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * X = X + (P[X + packet head + 1] + 1) * 8; 5619478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 5620478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* A = P[X + packet head] */ 5621478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_LD|BPF_IND|BPF_B); 5622511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s[i]->s.k = off_macpl + off_nl; 5623478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5624478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* MEM[reg2] = A */ 5625478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_ST); 5626478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = reg2; 5627478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5628511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* A = P[X + packet head + 1]; */ 5629478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_LD|BPF_IND|BPF_B); 5630511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s[i]->s.k = off_macpl + off_nl + 1; 5631478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5632478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* A += 1 */ 5633478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_ALU|BPF_ADD|BPF_K); 5634478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = 1; 5635478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5636478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* A *= 8 */ 5637478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_ALU|BPF_MUL|BPF_K); 5638478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = 8; 5639478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5640511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* A += X */ 5641511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s[i] = new_stmt(BPF_ALU|BPF_ADD|BPF_X); 5642511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s[i]->s.k = 0; 5643511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall i++; 5644478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* X = A; */ 5645478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_MISC|BPF_TAX); 5646478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5647478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* A = MEM[reg2] */ 5648478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_LD|BPF_MEM); 5649478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = reg2; 5650478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5651478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5652478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* goto again; (must use BPF_JA for backward jump) */ 5653478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_JMP|BPF_JA); 5654478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = again - i - 1; 5655478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i - 1]->s.jf = s[i]; 5656478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5657478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5658478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* fixup */ 5659478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project for (j = v6start; j <= v6end; j++) 5660478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[j]->s.jt = s[v6advance]; 5661511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } else { 5662478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* nop */ 5663478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_ALU|BPF_ADD|BPF_K); 5664478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = 0; 5665478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[fix2]->s.jf = s[i]; 5666478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5667478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5668478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5669478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* ahcheck: */ 5670478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project ahcheck = i; 5671478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* if (A == IPPROTO_AH) then fall through; else goto end; */ 5672478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_JMP|BPF_JEQ|BPF_K); 5673478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.jt = NULL; /*later*/ 5674478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.jf = NULL; /*later*/ 5675478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = IPPROTO_AH; 5676478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (fix3) 5677478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[fix3]->s.jf = s[ahcheck]; 5678478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project fix4 = i; 5679478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5680478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5681478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 5682478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * in short, 5683478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * A = P[X]; 5684478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * X = X + (P[X + 1] + 2) * 4; 5685478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 5686478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* A = X */ 5687478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i - 1]->s.jt = s[i] = new_stmt(BPF_MISC|BPF_TXA); 5688478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5689478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* A = P[X + packet head]; */ 5690478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_LD|BPF_IND|BPF_B); 5691511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s[i]->s.k = off_macpl + off_nl; 5692478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5693478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* MEM[reg2] = A */ 5694478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_ST); 5695478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = reg2; 5696478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5697478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* A = X */ 5698478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i - 1]->s.jt = s[i] = new_stmt(BPF_MISC|BPF_TXA); 5699478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5700478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* A += 1 */ 5701478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_ALU|BPF_ADD|BPF_K); 5702478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = 1; 5703478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5704478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* X = A */ 5705478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_MISC|BPF_TAX); 5706478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5707478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* A = P[X + packet head] */ 5708478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_LD|BPF_IND|BPF_B); 5709511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s[i]->s.k = off_macpl + off_nl; 5710478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5711478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* A += 2 */ 5712478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_ALU|BPF_ADD|BPF_K); 5713478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = 2; 5714478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5715478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* A *= 4 */ 5716478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_ALU|BPF_MUL|BPF_K); 5717478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = 4; 5718478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5719478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* X = A; */ 5720478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_MISC|BPF_TAX); 5721478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5722478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* A = MEM[reg2] */ 5723478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_LD|BPF_MEM); 5724478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = reg2; 5725478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5726478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5727478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* goto again; (must use BPF_JA for backward jump) */ 5728478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_JMP|BPF_JA); 5729478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = again - i - 1; 5730478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5731478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5732478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* end: nop */ 5733478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project end = i; 5734478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i] = new_stmt(BPF_ALU|BPF_ADD|BPF_K); 5735478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->s.k = 0; 5736478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[fix2]->s.jt = s[end]; 5737478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[fix4]->s.jf = s[end]; 5738478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[fix5]->s.jt = s[end]; 5739478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project i++; 5740478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5741478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 5742478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * make slist chain 5743478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 5744478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project max = i; 5745478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project for (i = 0; i < max - 1; i++) 5746478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[i]->next = s[i + 1]; 5747478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s[max - 1]->next = NULL; 5748478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5749478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 5750478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * emit final check 5751478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 5752478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = new_block(JMP(BPF_JEQ)); 5753478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b->stmts = s[1]; /*remember, s[0] is dummy*/ 5754478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b->s.k = v; 5755478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5756478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project free_reg(reg2); 5757478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5758478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b); 5759478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 5760478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 5761478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 5762478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5763511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic struct block * 5764511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallgen_check_802_11_data_frame() 5765511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall{ 5766511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct slist *s; 5767511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct block *b0, *b1; 5768511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 5769511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 5770511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * A data frame has the 0x08 bit (b3) in the frame control field set 5771511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * and the 0x04 bit (b2) clear. 5772511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 5773511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_a(OR_LINK, 0, BPF_B); 5774511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = new_block(JMP(BPF_JSET)); 5775511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0->s.k = 0x08; 5776511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0->stmts = s; 5777511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 5778511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_a(OR_LINK, 0, BPF_B); 5779511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = new_block(JMP(BPF_JSET)); 5780511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1->s.k = 0x04; 5781511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1->stmts = s; 5782511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_not(b1); 5783511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 5784511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b1, b0); 5785511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 5786511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return b0; 5787511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall} 5788478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5789478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 5790478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Generate code that checks whether the packet is a packet for protocol 5791478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * <proto> and whether the type field in that protocol's header has 5792478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the value <v>, e.g. if <proto> is Q_IP, it checks whether it's an 5793478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * IP packet and checks the protocol number in the IP header against <v>. 5794478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 5795478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If <proto> is Q_DEFAULT, i.e. just "proto" was specified, it checks 5796478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * against Q_IP and Q_IPV6. 5797478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 5798478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 5799478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_proto(v, proto, dir) 5800478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int v; 5801478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int proto; 5802478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir; 5803478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 5804478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1; 5805511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#ifndef CHASE_CHAIN 5806511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct block *b2; 5807511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif 5808478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5809478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (dir != Q_DEFAULT) 5810478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("direction applied to 'proto'"); 5811478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5812478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 5813478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 5814478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(v, Q_IP, dir); 5815478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_proto(v, Q_IPV6, dir); 5816478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 5817478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 5818511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 5819478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IP: 5820478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 5821478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For FDDI, RFC 1188 says that SNAP encapsulation is used, 5822478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * not LLC encapsulation with LLCSAP_IP. 5823478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 5824478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For IEEE 802 networks - which includes 802.5 token ring 5825478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (which is what DLT_IEEE802 means) and 802.11 - RFC 1042 5826478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * says that SNAP encapsulation is used, not LLC encapsulation 5827478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * with LLCSAP_IP. 5828478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 5829478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * For LLC-encapsulated ATM/"Classical IP", RFC 1483 and 5830478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * RFC 2225 say that SNAP encapsulation is used, not LLC 5831478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * encapsulation with LLCSAP_IP. 5832478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 5833478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * So we always check for ETHERTYPE_IP. 5834478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 5835478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(ETHERTYPE_IP); 5836478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef CHASE_CHAIN 5837478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_cmp(OR_NET, 9, BPF_B, (bpf_int32)v); 5838478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#else 5839478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_protochain(v, Q_IP); 5840478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 5841478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 5842478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 5843478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5844478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISO: 5845478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (linktype) { 5846478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5847478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_FRELAY: 5848478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 5849478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Frame Relay packets typically have an OSI 5850478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * NLPID at the beginning; "gen_linktype(LLCSAP_ISONS)" 5851478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * generates code to check for all the OSI 5852478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * NLPIDs, so calling it and then adding a check 5853478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * for the particular NLPID for which we're 5854478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * looking is bogus, as we can just check for 5855478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the NLPID. 5856478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 5857478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * What we check for is the NLPID and a frame 5858478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * control field value of UI, i.e. 0x03 followed 5859478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * by the NLPID. 5860478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 5861478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - assumes a 2-byte Frame Relay header with 5862478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * DLCI and flags. What if the address is longer? 5863478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 5864478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - what about SNAP-encapsulated frames? 5865478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 5866478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_cmp(OR_LINK, 2, BPF_H, (0x03<<8) | v); 5867478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 5868478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 5869478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5870478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_C_HDLC: 5871478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 5872478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Cisco uses an Ethertype lookalike - for OSI, 5873478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * it's 0xfefe. 5874478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 5875478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(LLCSAP_ISONS<<8 | LLCSAP_ISONS); 5876478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* OSI in C-HDLC is stuffed with a fudge byte */ 5877478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_cmp(OR_NET_NOSNAP, 1, BPF_B, (long)v); 5878478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 5879478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 5880478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5881478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 5882478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(LLCSAP_ISONS); 5883478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_cmp(OR_NET_NOSNAP, 0, BPF_B, (long)v); 5884478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 5885478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 5886478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 5887478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5888478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ISIS: 5889478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_proto(ISO10589_ISIS, Q_ISO, Q_DEFAULT); 5890478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 5891478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 4 is the offset of the PDU type relative to the IS-IS 5892478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * header. 5893478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 5894478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_cmp(OR_NET_NOSNAP, 4, BPF_B, (long)v); 5895478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 5896478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 5897478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5898478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ARP: 5899478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("arp does not encapsulate another protocol"); 5900478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5901478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5902478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_RARP: 5903478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("rarp does not encapsulate another protocol"); 5904478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5905478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5906478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ATALK: 5907478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("atalk encapsulation is not specifiable"); 5908478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5909478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5910478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DECNET: 5911478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("decnet encapsulation is not specifiable"); 5912478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5913478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5914478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SCA: 5915478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("sca does not encapsulate another protocol"); 5916478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5917478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5918478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_LAT: 5919478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("lat does not encapsulate another protocol"); 5920478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5921478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5922478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_MOPRC: 5923478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("moprc does not encapsulate another protocol"); 5924478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5925478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5926478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_MOPDL: 5927478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("mopdl does not encapsulate another protocol"); 5928478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5929478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5930478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_LINK: 5931478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_linktype(v); 5932478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5933478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_UDP: 5934478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'udp proto' is bogus"); 5935478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5936478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5937478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_TCP: 5938478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'tcp proto' is bogus"); 5939478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5940478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5941478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SCTP: 5942478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'sctp proto' is bogus"); 5943478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5944478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5945478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ICMP: 5946478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'icmp proto' is bogus"); 5947478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5948478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5949478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IGMP: 5950478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'igmp proto' is bogus"); 5951478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5952478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5953478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IGRP: 5954478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'igrp proto' is bogus"); 5955478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5956478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5957478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_PIM: 5958478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'pim proto' is bogus"); 5959478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5960478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5961478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_VRRP: 5962478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'vrrp proto' is bogus"); 5963478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 5964478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5965511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_CARP: 5966511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'carp proto' is bogus"); 5967511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* NOTREACHED */ 5968511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 5969478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IPV6: 5970478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(ETHERTYPE_IPV6); 5971478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef CHASE_CHAIN 5972511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 5973511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Also check for a fragment header before the final 5974511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * header. 5975511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 5976511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b2 = gen_cmp(OR_NET, 6, BPF_B, IPPROTO_FRAGMENT); 5977511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_cmp(OR_NET, 40, BPF_B, (bpf_int32)v); 5978511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b2, b1); 5979511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b2 = gen_cmp(OR_NET, 6, BPF_B, (bpf_int32)v); 5980511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_or(b2, b1); 5981478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#else 5982478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_protochain(v, Q_IPV6); 5983478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 5984478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 5985478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 5986478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5987478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ICMPV6: 5988478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'icmp6 proto' is bogus"); 5989478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5990478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AH: 5991478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'ah proto' is bogus"); 5992478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5993478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ESP: 5994478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'ah proto' is bogus"); 5995478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5996478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_STP: 5997478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'stp proto' is bogus"); 5998478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 5999478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IPX: 6000478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'ipx proto' is bogus"); 6001478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6002478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_NETBEUI: 6003478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'netbeui proto' is bogus"); 6004478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6005478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_RADIO: 6006478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'radio proto' is bogus"); 6007478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6008478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 6009478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 6010478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 6011478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6012478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 6013478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 6014478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6015478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 6016478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_scode(name, q) 6017478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const char *name; 6018478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct qual q; 6019478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 6020478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int proto = q.proto; 6021478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir = q.dir; 6022478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int tproto; 6023478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_char *eaddr; 6024478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 mask, addr; 6025478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef INET6 6026478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 **alist; 6027478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#else 6028478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int tproto6; 6029478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct sockaddr_in *sin4; 6030478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct sockaddr_in6 *sin6; 6031478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct addrinfo *res, *res0; 6032478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct in6_addr mask128; 6033478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif /*INET6*/ 6034478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b, *tmp; 6035478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int port, real_proto; 6036478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int port1, port2; 6037478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6038478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (q.addr) { 6039478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6040478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_NET: 6041478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project addr = pcap_nametonetaddr(name); 6042478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (addr == 0) 6043478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unknown network '%s'", name); 6044478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Left justify network addr and calculate its network mask */ 6045478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project mask = 0xffffffff; 6046478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project while (addr && (addr & 0xff000000) == 0) { 6047478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project addr <<= 8; 6048478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project mask <<= 8; 6049478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6050478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_host(addr, mask, proto, dir, q.addr); 6051478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6052478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 6053478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_HOST: 6054478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto == Q_LINK) { 6055478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (linktype) { 6056478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6057478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_EN10MB: 6058511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER: 6059511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER_TRANSPARENT: 6060478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project eaddr = pcap_ether_hostton(name); 6061478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (eaddr == NULL) 6062478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error( 6063478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project "unknown ether host '%s'", name); 6064478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_ehostop(eaddr, dir); 6065478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project free(eaddr); 6066478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 6067478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6068478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_FDDI: 6069478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project eaddr = pcap_ether_hostton(name); 6070478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (eaddr == NULL) 6071478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error( 6072478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project "unknown FDDI host '%s'", name); 6073478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_fhostop(eaddr, dir); 6074478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project free(eaddr); 6075478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 6076478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6077478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IEEE802: 6078478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project eaddr = pcap_ether_hostton(name); 6079478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (eaddr == NULL) 6080478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error( 6081478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project "unknown token ring host '%s'", name); 6082478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_thostop(eaddr, dir); 6083478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project free(eaddr); 6084478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 6085478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6086478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IEEE802_11: 6087511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PRISM_HEADER: 6088478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IEEE802_11_RADIO_AVS: 6089478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IEEE802_11_RADIO: 6090478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PPI: 6091478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project eaddr = pcap_ether_hostton(name); 6092478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (eaddr == NULL) 6093478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error( 6094478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project "unknown 802.11 host '%s'", name); 6095478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_wlanhostop(eaddr, dir); 6096478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project free(eaddr); 6097478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 6098478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6099478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_IP_OVER_FC: 6100478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project eaddr = pcap_ether_hostton(name); 6101478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (eaddr == NULL) 6102478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error( 6103478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project "unknown Fibre Channel host '%s'", name); 6104478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_ipfchostop(eaddr, dir); 6105478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project free(eaddr); 6106478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 6107478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6108478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_SUNATM: 6109478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_lane) 6110478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 6111478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6112478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6113478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Check that the packet doesn't begin 6114478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * with an LE Control marker. (We've 6115478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * already generated a test for LANE.) 6116478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6117478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_cmp(OR_LINK, SUNATM_PKT_BEGIN_POS, 6118478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project BPF_H, 0xFF00); 6119478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(tmp); 6120478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6121478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project eaddr = pcap_ether_hostton(name); 6122478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (eaddr == NULL) 6123478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error( 6124478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project "unknown ether host '%s'", name); 6125478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_ehostop(eaddr, dir); 6126478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(tmp, b); 6127478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project free(eaddr); 6128478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 6129478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6130478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6131478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("only ethernet/FDDI/token ring/802.11/ATM LANE/Fibre Channel supports link-level host name"); 6132478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else if (proto == Q_DECNET) { 6133478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project unsigned short dn_addr = __pcap_nametodnaddr(name); 6134478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6135478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * I don't think DECNET hosts can be multihomed, so 6136478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * there is no need to build up a list of addresses 6137478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6138478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (gen_host(dn_addr, 0, proto, dir, q.addr)); 6139478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else { 6140478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef INET6 6141478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project alist = pcap_nametoaddr(name); 6142478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (alist == NULL || *alist == NULL) 6143478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unknown host '%s'", name); 6144478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tproto = proto; 6145478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (off_linktype == (u_int)-1 && tproto == Q_DEFAULT) 6146478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tproto = Q_IP; 6147478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_host(**alist++, 0xffffffff, tproto, dir, q.addr); 6148478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project while (*alist) { 6149478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_host(**alist++, 0xffffffff, 6150478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tproto, dir, q.addr); 6151478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b, tmp); 6152478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = tmp; 6153478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6154478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 6155478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#else 6156478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project memset(&mask128, 0xff, sizeof(mask128)); 6157478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project res0 = res = pcap_nametoaddrinfo(name); 6158478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (res == NULL) 6159478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unknown host '%s'", name); 6160511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall ai = res; 6161478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = tmp = NULL; 6162478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tproto = tproto6 = proto; 6163478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (off_linktype == -1 && tproto == Q_DEFAULT) { 6164478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tproto = Q_IP; 6165478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tproto6 = Q_IPV6; 6166478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6167478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project for (res = res0; res; res = res->ai_next) { 6168478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (res->ai_family) { 6169478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case AF_INET: 6170478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (tproto == Q_IPV6) 6171478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project continue; 6172478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6173478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sin4 = (struct sockaddr_in *) 6174478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project res->ai_addr; 6175478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_host(ntohl(sin4->sin_addr.s_addr), 6176478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 0xffffffff, tproto, dir, q.addr); 6177478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 6178478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case AF_INET6: 6179478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (tproto6 == Q_IP) 6180478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project continue; 6181478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6182478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sin6 = (struct sockaddr_in6 *) 6183478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project res->ai_addr; 6184478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = gen_host6(&sin6->sin6_addr, 6185478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project &mask128, tproto6, dir, q.addr); 6186478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 6187478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 6188478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project continue; 6189478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6190478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (b) 6191478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b, tmp); 6192478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = tmp; 6193478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6194511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall ai = NULL; 6195478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project freeaddrinfo(res0); 6196478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (b == NULL) { 6197478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unknown host '%s'%s", name, 6198478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (proto == Q_DEFAULT) 6199478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project ? "" 6200478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project : " for specified address family"); 6201478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6202478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 6203478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif /*INET6*/ 6204478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6205478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6206478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_PORT: 6207478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto != Q_DEFAULT && 6208478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project proto != Q_UDP && proto != Q_TCP && proto != Q_SCTP) 6209478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("illegal qualifier of 'port'"); 6210478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (pcap_nametoport(name, &port, &real_proto) == 0) 6211478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unknown port '%s'", name); 6212478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto == Q_UDP) { 6213478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (real_proto == IPPROTO_TCP) 6214478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("port '%s' is tcp", name); 6215478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (real_proto == IPPROTO_SCTP) 6216478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("port '%s' is sctp", name); 6217478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 6218478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* override PROTO_UNDEF */ 6219478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project real_proto = IPPROTO_UDP; 6220478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6221478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto == Q_TCP) { 6222478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (real_proto == IPPROTO_UDP) 6223478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("port '%s' is udp", name); 6224478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6225478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (real_proto == IPPROTO_SCTP) 6226478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("port '%s' is sctp", name); 6227478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 6228478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* override PROTO_UNDEF */ 6229478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project real_proto = IPPROTO_TCP; 6230478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6231478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto == Q_SCTP) { 6232478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (real_proto == IPPROTO_UDP) 6233478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("port '%s' is udp", name); 6234478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6235478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (real_proto == IPPROTO_TCP) 6236478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("port '%s' is tcp", name); 6237478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 6238478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* override PROTO_UNDEF */ 6239478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project real_proto = IPPROTO_SCTP; 6240478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6241511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (port < 0) 6242511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("illegal port number %d < 0", port); 6243511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (port > 65535) 6244511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("illegal port number %d > 65535", port); 6245478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_port(port, real_proto, dir); 6246478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(gen_port6(port, real_proto, dir), b); 6247478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 6248478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6249478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_PORTRANGE: 6250478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto != Q_DEFAULT && 6251478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project proto != Q_UDP && proto != Q_TCP && proto != Q_SCTP) 6252478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("illegal qualifier of 'portrange'"); 6253478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (pcap_nametoportrange(name, &port1, &port2, &real_proto) == 0) 6254478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unknown port in range '%s'", name); 6255478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto == Q_UDP) { 6256478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (real_proto == IPPROTO_TCP) 6257478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("port in range '%s' is tcp", name); 6258478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (real_proto == IPPROTO_SCTP) 6259478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("port in range '%s' is sctp", name); 6260478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 6261478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* override PROTO_UNDEF */ 6262478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project real_proto = IPPROTO_UDP; 6263478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6264478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto == Q_TCP) { 6265478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (real_proto == IPPROTO_UDP) 6266478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("port in range '%s' is udp", name); 6267478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (real_proto == IPPROTO_SCTP) 6268478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("port in range '%s' is sctp", name); 6269478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 6270478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* override PROTO_UNDEF */ 6271478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project real_proto = IPPROTO_TCP; 6272478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6273478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto == Q_SCTP) { 6274478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (real_proto == IPPROTO_UDP) 6275478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("port in range '%s' is udp", name); 6276478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (real_proto == IPPROTO_TCP) 6277478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("port in range '%s' is tcp", name); 6278478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 6279478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* override PROTO_UNDEF */ 6280478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project real_proto = IPPROTO_SCTP; 6281478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6282511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (port1 < 0) 6283511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("illegal port number %d < 0", port1); 6284511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (port1 > 65535) 6285511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("illegal port number %d > 65535", port1); 6286511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (port2 < 0) 6287511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("illegal port number %d < 0", port2); 6288511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (port2 > 65535) 6289511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("illegal port number %d > 65535", port2); 6290511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 6291478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_portrange(port1, port2, real_proto, dir); 6292478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(gen_portrange6(port1, port2, real_proto, dir), b); 6293478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 6294478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6295478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_GATEWAY: 6296478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifndef INET6 6297478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project eaddr = pcap_ether_hostton(name); 6298478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (eaddr == NULL) 6299478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unknown ether host: %s", name); 6300478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6301478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project alist = pcap_nametoaddr(name); 6302478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (alist == NULL || *alist == NULL) 6303478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unknown host '%s'", name); 6304478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_gateway(eaddr, alist, proto, dir); 6305478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project free(eaddr); 6306478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 6307478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#else 6308478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'gateway' not supported in this configuration"); 6309478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif /*INET6*/ 6310478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6311478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_PROTO: 6312478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project real_proto = lookup_proto(name, proto); 6313478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (real_proto >= 0) 6314478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_proto(real_proto, proto, dir); 6315478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 6316478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unknown protocol: %s", name); 6317478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6318478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_PROTOCHAIN: 6319478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project real_proto = lookup_proto(name, proto); 6320478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (real_proto >= 0) 6321478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_protochain(real_proto, proto, dir); 6322478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 6323478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unknown protocol: %s", name); 6324478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6325478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_UNDEF: 6326478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project syntax(); 6327478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 6328478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6329478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 6330478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 6331478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 6332478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6333478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 6334478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_mcode(s1, s2, masklen, q) 6335478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const char *s1, *s2; 6336478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register int masklen; 6337478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct qual q; 6338478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 6339478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register int nlen, mlen; 6340478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 n, m; 6341478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6342478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project nlen = __pcap_atoin(s1, &n); 6343478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Promote short ipaddr */ 6344478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project n <<= 32 - nlen; 6345478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6346478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (s2 != NULL) { 6347478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project mlen = __pcap_atoin(s2, &m); 6348478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Promote short ipaddr */ 6349478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project m <<= 32 - mlen; 6350478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if ((n & ~m) != 0) 6351478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("non-network bits set in \"%s mask %s\"", 6352478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s1, s2); 6353478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else { 6354478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Convert mask len to mask */ 6355478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (masklen > 32) 6356478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("mask length must be <= 32"); 6357478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (masklen == 0) { 6358478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6359478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * X << 32 is not guaranteed by C to be 0; it's 6360478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * undefined. 6361478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6362478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project m = 0; 6363478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else 6364478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project m = 0xffffffff << (32 - masklen); 6365478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if ((n & ~m) != 0) 6366478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("non-network bits set in \"%s/%d\"", 6367478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s1, masklen); 6368478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6369478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6370478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (q.addr) { 6371478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6372478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_NET: 6373478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_host(n, m, q.proto, q.dir, q.addr); 6374478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6375478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 6376478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("Mask syntax for networks only"); 6377478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 6378478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6379478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 6380478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return NULL; 6381478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 6382478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6383478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 6384478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_ncode(s, v, q) 6385478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const char *s; 6386478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 v; 6387478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct qual q; 6388478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 6389478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 mask; 6390478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int proto = q.proto; 6391478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir = q.dir; 6392478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register int vlen; 6393478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6394478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (s == NULL) 6395478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project vlen = 32; 6396478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (q.proto == Q_DECNET) 6397478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project vlen = __pcap_atodn(s, &v); 6398478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 6399478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project vlen = __pcap_atoin(s, &v); 6400478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6401478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (q.addr) { 6402478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6403478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 6404478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_HOST: 6405478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_NET: 6406478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto == Q_DECNET) 6407478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_host(v, 0, proto, dir, q.addr); 6408478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (proto == Q_LINK) { 6409478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("illegal link layer address"); 6410478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else { 6411478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project mask = 0xffffffff; 6412478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (s == NULL && q.addr == Q_NET) { 6413478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Promote short net number */ 6414478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project while (v && (v & 0xff000000) == 0) { 6415478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v <<= 8; 6416478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project mask <<= 8; 6417478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6418478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else { 6419478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Promote short ipaddr */ 6420478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project v <<= 32 - vlen; 6421478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project mask <<= 32 - vlen; 6422478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6423478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_host(v, mask, proto, dir, q.addr); 6424478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6425478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6426478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_PORT: 6427478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto == Q_UDP) 6428478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project proto = IPPROTO_UDP; 6429478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (proto == Q_TCP) 6430478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project proto = IPPROTO_TCP; 6431478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (proto == Q_SCTP) 6432478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project proto = IPPROTO_SCTP; 6433478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (proto == Q_DEFAULT) 6434478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project proto = PROTO_UNDEF; 6435478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 6436478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("illegal qualifier of 'port'"); 6437478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6438511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (v > 65535) 6439511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("illegal port number %u > 65535", v); 6440511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 6441478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project { 6442478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b; 6443478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_port((int)v, proto, dir); 6444478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(gen_port6((int)v, proto, dir), b); 6445478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 6446478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6447478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6448478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_PORTRANGE: 6449478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (proto == Q_UDP) 6450478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project proto = IPPROTO_UDP; 6451478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (proto == Q_TCP) 6452478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project proto = IPPROTO_TCP; 6453478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (proto == Q_SCTP) 6454478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project proto = IPPROTO_SCTP; 6455478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else if (proto == Q_DEFAULT) 6456478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project proto = PROTO_UNDEF; 6457478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 6458478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("illegal qualifier of 'portrange'"); 6459478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6460511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (v > 65535) 6461511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("illegal port number %u > 65535", v); 6462511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 6463478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project { 6464478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b; 6465478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_portrange((int)v, (int)v, proto, dir); 6466478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(gen_portrange6((int)v, (int)v, proto, dir), b); 6467478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 6468478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6469478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6470478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_GATEWAY: 6471478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'gateway' requires a name"); 6472478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 6473478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6474478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_PROTO: 6475478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_proto((int)v, proto, dir); 6476478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6477478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_PROTOCHAIN: 6478478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_protochain((int)v, proto, dir); 6479478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6480478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_UNDEF: 6481478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project syntax(); 6482478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 6483478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6484478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 6485478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 6486478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 6487478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6488478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 6489478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 6490478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6491478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef INET6 6492478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 6493478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_mcode6(s1, s2, masklen, q) 6494478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const char *s1, *s2; 6495478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register int masklen; 6496478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct qual q; 6497478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 6498478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct addrinfo *res; 6499478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct in6_addr *addr; 6500478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct in6_addr mask; 6501478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b; 6502478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int32_t *a, *m; 6503478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6504478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (s2) 6505478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("no mask %s supported", s2); 6506478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6507478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project res = pcap_nametoaddrinfo(s1); 6508478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!res) 6509478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("invalid ip6 address %s", s1); 6510511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall ai = res; 6511478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (res->ai_next) 6512478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("%s resolved to multiple address", s1); 6513478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project addr = &((struct sockaddr_in6 *)res->ai_addr)->sin6_addr; 6514478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6515478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (sizeof(mask) * 8 < masklen) 6516478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("mask length must be <= %u", (unsigned int)(sizeof(mask) * 8)); 6517478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project memset(&mask, 0, sizeof(mask)); 6518478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project memset(&mask, 0xff, masklen / 8); 6519478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (masklen % 8) { 6520478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project mask.s6_addr[masklen / 8] = 6521478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (0xff << (8 - masklen % 8)) & 0xff; 6522478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6523478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6524478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project a = (u_int32_t *)addr; 6525478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project m = (u_int32_t *)&mask; 6526478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if ((a[0] & ~m[0]) || (a[1] & ~m[1]) 6527478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project || (a[2] & ~m[2]) || (a[3] & ~m[3])) { 6528478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("non-network bits set in \"%s/%d\"", s1, masklen); 6529478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6530478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6531478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (q.addr) { 6532478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6533478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 6534478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_HOST: 6535478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (masklen != 128) 6536478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("Mask syntax for networks only"); 6537478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* FALLTHROUGH */ 6538478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6539478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_NET: 6540478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_host6(addr, &mask, q.proto, q.dir, q.addr); 6541511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall ai = NULL; 6542478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project freeaddrinfo(res); 6543478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 6544478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6545478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 6546478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("invalid qualifier against IPv6 address"); 6547478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 6548478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6549478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return NULL; 6550478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 6551478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif /*INET6*/ 6552478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6553478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 6554478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_ecode(eaddr, q) 6555478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const u_char *eaddr; 6556478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct qual q; 6557478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 6558478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b, *tmp; 6559478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6560478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if ((q.addr == Q_HOST || q.addr == Q_DEFAULT) && q.proto == Q_LINK) { 6561511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall switch (linktype) { 6562511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_EN10MB: 6563511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER: 6564511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER_TRANSPARENT: 6565511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_ehostop(eaddr, (int)q.dir); 6566511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_FDDI: 6567511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_fhostop(eaddr, (int)q.dir); 6568511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802: 6569511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_thostop(eaddr, (int)q.dir); 6570511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11: 6571511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PRISM_HEADER: 6572511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO_AVS: 6573511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO: 6574511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PPI: 6575511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_wlanhostop(eaddr, (int)q.dir); 6576511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_SUNATM: 6577511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (is_lane) { 6578511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 6579511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Check that the packet doesn't begin with an 6580511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * LE Control marker. (We've already generated 6581511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * a test for LANE.) 6582511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 6583511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall tmp = gen_cmp(OR_LINK, SUNATM_PKT_BEGIN_POS, BPF_H, 6584511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 0xFF00); 6585511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_not(tmp); 6586511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 6587511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 6588511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Now check the MAC address. 6589511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 6590511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b = gen_ehostop(eaddr, (int)q.dir); 6591511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(tmp, b); 6592511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return b; 6593511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 6594511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 6595511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IP_OVER_FC: 6596511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_ipfchostop(eaddr, (int)q.dir); 6597511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall default: 6598511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("ethernet addresses supported only on ethernet/FDDI/token ring/802.11/ATM LANE/Fibre Channel"); 6599511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 6600511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 6601478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6602478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("ethernet address used in non-ether expression"); 6603478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 6604478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return NULL; 6605478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 6606478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6607478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectvoid 6608478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectsappend(s0, s1) 6609478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s0, *s1; 6610478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 6611478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6612478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This is definitely not the best way to do this, but the 6613478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * lists will rarely get long. 6614478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6615478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project while (s0->next) 6616478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s0 = s0->next; 6617478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s0->next = s1; 6618478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 6619478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6620478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct slist * 6621478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectxfer_to_x(a) 6622478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct arth *a; 6623478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 6624478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s; 6625478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6626478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_LDX|BPF_MEM); 6627478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s->s.k = a->regno; 6628478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return s; 6629478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 6630478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6631478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct slist * 6632478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectxfer_to_a(a) 6633478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct arth *a; 6634478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 6635478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s; 6636478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6637478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_LD|BPF_MEM); 6638478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s->s.k = a->regno; 6639478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return s; 6640478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 6641478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6642478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 6643478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Modify "index" to use the value stored into its register as an 6644478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * offset relative to the beginning of the header for the protocol 6645478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "proto", and allocate a register and put an item "size" bytes long 6646478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (1, 2, or 4) at that offset into that register, making it the register 6647478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * for "index". 6648478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6649478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct arth * 6650478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_load(proto, inst, size) 6651478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int proto; 6652478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct arth *inst; 6653478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int size; 6654478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 6655478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s, *tmp; 6656478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b; 6657478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int regno = alloc_reg(); 6658478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6659478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project free_reg(inst->regno); 6660478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (size) { 6661478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6662478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 6663478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("data size must be 1, 2, or 4"); 6664478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6665478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case 1: 6666478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project size = BPF_B; 6667478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 6668478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6669478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case 2: 6670478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project size = BPF_H; 6671478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 6672478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6673478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case 4: 6674478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project size = BPF_W; 6675478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 6676478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6677478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 6678478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 6679478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("unsupported index operation"); 6680478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6681478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_RADIO: 6682478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6683478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * The offset is relative to the beginning of the packet 6684478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * data, if we have a radio header. (If we don't, this 6685478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * is an error.) 6686478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6687478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (linktype != DLT_IEEE802_11_RADIO_AVS && 6688478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project linktype != DLT_IEEE802_11_RADIO && 6689478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project linktype != DLT_PRISM_HEADER) 6690478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("radio information not present in capture"); 6691478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6692478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6693478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Load into the X register the offset computed into the 6694511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * register specified by "index". 6695478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6696478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = xfer_to_x(inst); 6697478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6698478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6699478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Load the item at that offset. 6700478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6701478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = new_stmt(BPF_LD|BPF_IND|size); 6702478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, tmp); 6703478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(inst->s, s); 6704478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 6705478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6706478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_LINK: 6707478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6708478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * The offset is relative to the beginning of 6709478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the link-layer header. 6710478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 6711478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - what about ATM LANE? Should the index be 6712478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * relative to the beginning of the AAL5 frame, so 6713478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * that 0 refers to the beginning of the LE Control 6714478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * field, or relative to the beginning of the LAN 6715478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * frame, so that 0 refers, for Ethernet LANE, to 6716478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the beginning of the destination address? 6717478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6718478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_llprefixlen(); 6719478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6720478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6721478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If "s" is non-null, it has code to arrange that the 6722478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * X register contains the length of the prefix preceding 6723478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the link-layer header. Add to it the offset computed 6724478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * into the register specified by "index", and move that 6725478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * into the X register. Otherwise, just load into the X 6726511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * register the offset computed into the register specified 6727478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * by "index". 6728478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6729478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (s != NULL) { 6730478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, xfer_to_a(inst)); 6731478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, new_stmt(BPF_ALU|BPF_ADD|BPF_X)); 6732478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, new_stmt(BPF_MISC|BPF_TAX)); 6733478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else 6734478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = xfer_to_x(inst); 6735478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6736478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6737478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Load the item at the sum of the offset we've put in the 6738478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * X register and the offset of the start of the link 6739478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * layer header (which is 0 if the radio header is 6740478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * variable-length; that header length is what we put 6741478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * into the X register and then added to the index). 6742478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6743478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = new_stmt(BPF_LD|BPF_IND|size); 6744478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp->s.k = off_ll; 6745478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, tmp); 6746478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(inst->s, s); 6747478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 6748478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6749478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IP: 6750478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ARP: 6751478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_RARP: 6752478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ATALK: 6753478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DECNET: 6754478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SCA: 6755478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_LAT: 6756478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_MOPRC: 6757478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_MOPDL: 6758478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IPV6: 6759478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6760478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * The offset is relative to the beginning of 6761478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the network-layer header. 6762478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - are there any cases where we want 6763478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * off_nl_nosnap? 6764478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6765511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_off_macpl(); 6766478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6767478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6768478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If "s" is non-null, it has code to arrange that the 6769511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * X register contains the offset of the MAC-layer 6770511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * payload. Add to it the offset computed into the 6771511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * register specified by "index", and move that into 6772511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the X register. Otherwise, just load into the X 6773511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * register the offset computed into the register specified 6774478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * by "index". 6775478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6776478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (s != NULL) { 6777478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, xfer_to_a(inst)); 6778478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, new_stmt(BPF_ALU|BPF_ADD|BPF_X)); 6779478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, new_stmt(BPF_MISC|BPF_TAX)); 6780478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else 6781478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = xfer_to_x(inst); 6782478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6783478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6784478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Load the item at the sum of the offset we've put in the 6785478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * X register, the offset of the start of the network 6786511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * layer header from the beginning of the MAC-layer 6787511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * payload, and the purported offset of the start of the 6788511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * MAC-layer payload (which might be 0 if there's a 6789511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * variable-length prefix before the link-layer header 6790511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * or the link-layer header itself is variable-length; 6791511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the variable-length offset of the start of the 6792511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * MAC-layer payload is what we put into the X register 6793511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * and then added to the index). 6794478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6795478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = new_stmt(BPF_LD|BPF_IND|size); 6796511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall tmp->s.k = off_macpl + off_nl; 6797478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, tmp); 6798478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(inst->s, s); 6799478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6800478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6801478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Do the computation only if the packet contains 6802478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the protocol in question. 6803478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6804478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_proto_abbrev(proto); 6805478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (inst->b) 6806478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(inst->b, b); 6807478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project inst->b = b; 6808478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 6809478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6810478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SCTP: 6811478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_TCP: 6812478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_UDP: 6813478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ICMP: 6814478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IGMP: 6815478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IGRP: 6816478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_PIM: 6817478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_VRRP: 6818511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_CARP: 6819478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6820478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * The offset is relative to the beginning of 6821478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the transport-layer header. 6822478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 6823478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Load the X register with the length of the IPv4 header 6824478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (plus the offset of the link-layer header, if it's 6825478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * a variable-length header), in bytes. 6826478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 6827478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - are there any cases where we want 6828478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * off_nl_nosnap? 6829478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - we should, if we're built with 6830478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * IPv6 support, generate code to load either 6831478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * IPv4, IPv6, or both, as appropriate. 6832478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6833478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_loadx_iphdrlen(); 6834478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6835478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6836478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * The X register now contains the sum of the length 6837478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of any variable-length header preceding the link-layer 6838511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * header, any variable-length link-layer header, and the 6839511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * length of the network-layer header. 6840511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 6841478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Load into the A register the offset relative to 6842478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the beginning of the transport layer header, 6843478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * add the X register to that, move that to the 6844478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * X register, and load with an offset from the 6845478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * X register equal to the offset of the network 6846478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * layer header relative to the beginning of 6847511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the MAC-layer payload plus the fixed-length 6848511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * portion of the offset of the MAC-layer payload 6849511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * from the beginning of the raw packet data. 6850478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6851478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, xfer_to_a(inst)); 6852478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, new_stmt(BPF_ALU|BPF_ADD|BPF_X)); 6853478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, new_stmt(BPF_MISC|BPF_TAX)); 6854478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s, tmp = new_stmt(BPF_LD|BPF_IND|size)); 6855511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall tmp->s.k = off_macpl + off_nl; 6856478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(inst->s, s); 6857478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6858478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 6859478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Do the computation only if the packet contains 6860478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the protocol in question - which is true only 6861478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * if this is an IP datagram and is the first or 6862478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * only fragment of that datagram. 6863478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 6864478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(gen_proto_abbrev(proto), b = gen_ipfrag()); 6865478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (inst->b) 6866478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(inst->b, b); 6867478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(gen_proto_abbrev(Q_IP), b); 6868478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project inst->b = b; 6869478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 6870478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_ICMPV6: 6871478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("IPv6 upper-layer protocol is not supported by proto[x]"); 6872478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 6873478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6874478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project inst->regno = regno; 6875478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_ST); 6876478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s->s.k = regno; 6877478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(inst->s, s); 6878478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6879478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return inst; 6880478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 6881478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6882478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 6883478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_relation(code, a0, a1, reversed) 6884478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int code; 6885478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct arth *a0, *a1; 6886478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int reversed; 6887478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 6888478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s0, *s1, *s2; 6889478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b, *tmp; 6890478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6891478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s0 = xfer_to_x(a1); 6892478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s1 = xfer_to_a(a0); 6893478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (code == BPF_JEQ) { 6894478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_ALU|BPF_SUB|BPF_X); 6895478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = new_block(JMP(code)); 6896478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s1, s2); 6897478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6898478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 6899478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = new_block(BPF_JMP|code|BPF_X); 6900478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (reversed) 6901478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b); 6902478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6903478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s0, s1); 6904478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(a1->s, s0); 6905478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(a0->s, a1->s); 6906478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6907478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b->stmts = a0->s; 6908478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6909478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project free_reg(a0->regno); 6910478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project free_reg(a1->regno); 6911478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6912478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 'and' together protocol checks */ 6913478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (a0->b) { 6914478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (a1->b) { 6915478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(a0->b, tmp = a1->b); 6916478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 6917478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else 6918478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = a0->b; 6919478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else 6920478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project tmp = a1->b; 6921478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6922478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (tmp) 6923478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(tmp, b); 6924478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6925478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 6926478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 6927478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6928478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct arth * 6929478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_loadlen() 6930478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 6931478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int regno = alloc_reg(); 6932478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct arth *a = (struct arth *)newchunk(sizeof(*a)); 6933478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s; 6934478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6935478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_LD|BPF_LEN); 6936478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s->next = new_stmt(BPF_ST); 6937478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s->next->s.k = regno; 6938478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project a->s = s; 6939478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project a->regno = regno; 6940478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6941478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return a; 6942478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 6943478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6944478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct arth * 6945478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_loadi(val) 6946478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int val; 6947478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 6948478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct arth *a; 6949478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s; 6950478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int reg; 6951478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6952478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project a = (struct arth *)newchunk(sizeof(*a)); 6953478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6954478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project reg = alloc_reg(); 6955478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6956478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_LD|BPF_IMM); 6957478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s->s.k = val; 6958478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s->next = new_stmt(BPF_ST); 6959478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s->next->s.k = reg; 6960478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project a->s = s; 6961478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project a->regno = reg; 6962478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6963478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return a; 6964478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 6965478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6966478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct arth * 6967478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_neg(a) 6968478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct arth *a; 6969478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 6970478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s; 6971478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6972478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = xfer_to_a(a); 6973478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(a->s, s); 6974478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_ALU|BPF_NEG); 6975478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s->s.k = 0; 6976478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(a->s, s); 6977478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_ST); 6978478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s->s.k = a->regno; 6979478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(a->s, s); 6980478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6981478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return a; 6982478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 6983478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6984478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct arth * 6985478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_arth(code, a0, a1) 6986478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int code; 6987478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct arth *a0, *a1; 6988478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 6989478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s0, *s1, *s2; 6990478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6991478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s0 = xfer_to_x(a1); 6992478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s1 = xfer_to_a(a0); 6993478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s2 = new_stmt(BPF_ALU|BPF_X|code); 6994478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 6995478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s1, s2); 6996478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(s0, s1); 6997478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(a1->s, s0); 6998478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(a0->s, a1->s); 6999478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7000478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project free_reg(a0->regno); 7001478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project free_reg(a1->regno); 7002478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7003478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s0 = new_stmt(BPF_ST); 7004478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project a0->regno = s0->s.k = alloc_reg(); 7005478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project sappend(a0->s, s0); 7006478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7007478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return a0; 7008478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7009478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7010478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 7011478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Here we handle simple allocation of the scratch registers. 7012478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * If too many registers are alloc'd, the allocator punts. 7013478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 7014478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic int regused[BPF_MEMWORDS]; 7015478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic int curreg; 7016478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7017478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 7018511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Initialize the table of used registers and the current register. 7019511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7020511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstatic void 7021511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallinit_regs() 7022511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall{ 7023511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall curreg = 0; 7024511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall memset(regused, 0, sizeof regused); 7025511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall} 7026511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7027511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall/* 7028478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Return the next free register. 7029478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 7030478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic int 7031478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectalloc_reg() 7032478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7033478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int n = BPF_MEMWORDS; 7034478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7035478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project while (--n >= 0) { 7036478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (regused[curreg]) 7037478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project curreg = (curreg + 1) % BPF_MEMWORDS; 7038478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project else { 7039478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project regused[curreg] = 1; 7040478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return curreg; 7041478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7042478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7043478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("too many registers needed to evaluate expression"); 7044478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7045478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return 0; 7046478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7047478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7048478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 7049478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Return a register to the table so it can 7050478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * be used later. 7051478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 7052478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic void 7053478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectfree_reg(n) 7054478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int n; 7055478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7056478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project regused[n] = 0; 7057478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7058478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7059478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 7060478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_len(jmp, n) 7061478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int jmp, n; 7062478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7063478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s; 7064478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b; 7065478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7066478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_LD|BPF_LEN); 7067478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = new_block(JMP(jmp)); 7068478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b->stmts = s; 7069478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b->s.k = n; 7070478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7071478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 7072478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7073478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7074478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7075478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_greater(n) 7076478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int n; 7077478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7078478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_len(BPF_JGE, n); 7079478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7080478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7081478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 7082478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Actually, this is less than or equal. 7083478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 7084478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7085478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_less(n) 7086478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int n; 7087478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7088478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b; 7089478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7090478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_len(BPF_JGT, n); 7091478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b); 7092478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7093478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 7094478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7095478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7096478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 7097478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This is for "byte {idx} {op} {val}"; "idx" is treated as relative to 7098478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the beginning of the link-layer header. 7099478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - that means you can't test values in the radiotap header, but 7100478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * as that header is difficult if not impossible to parse generally 7101478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * without a loop, that might not be a severe problem. A new keyword 7102478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "radio" could be added for that, although what you'd really want 7103478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * would be a way of testing particular radio header values, which 7104478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * would generate code appropriate to the radio header in question. 7105478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 7106478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7107478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_byteop(op, idx, val) 7108478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int op, idx, val; 7109478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7110478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b; 7111478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct slist *s; 7112478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7113478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (op) { 7114478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 7115478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 7116478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7117478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case '=': 7118478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_cmp(OR_LINK, (u_int)idx, BPF_B, (bpf_int32)val); 7119478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7120478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case '<': 7121478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_cmp_lt(OR_LINK, (u_int)idx, BPF_B, (bpf_int32)val); 7122478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 7123478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7124478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case '>': 7125478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = gen_cmp_gt(OR_LINK, (u_int)idx, BPF_B, (bpf_int32)val); 7126478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 7127478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7128478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case '|': 7129478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_ALU|BPF_OR|BPF_K); 7130478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 7131478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7132478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case '&': 7133478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = new_stmt(BPF_ALU|BPF_AND|BPF_K); 7134478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 7135478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7136478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s->s.k = val; 7137478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b = new_block(JMP(BPF_JEQ)); 7138478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b->stmts = s; 7139478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b); 7140478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7141478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b; 7142478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7143478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7144478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic u_char abroadcast[] = { 0x0 }; 7145478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7146478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7147478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_broadcast(proto) 7148478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int proto; 7149478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7150478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 hostmask; 7151478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1, *b2; 7152478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project static u_char ebroadcast[] = { 0xff, 0xff, 0xff, 0xff, 0xff, 0xff }; 7153478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7154478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 7155478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7156478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 7157478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_LINK: 7158511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall switch (linktype) { 7159511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_ARCNET: 7160511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_ARCNET_LINUX: 7161511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_ahostop(abroadcast, Q_DST); 7162511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_EN10MB: 7163511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER: 7164511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER_TRANSPARENT: 7165511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_ehostop(ebroadcast, Q_DST); 7166511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_FDDI: 7167511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_fhostop(ebroadcast, Q_DST); 7168511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802: 7169511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_thostop(ebroadcast, Q_DST); 7170511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11: 7171511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PRISM_HEADER: 7172511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO_AVS: 7173511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO: 7174511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PPI: 7175511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_wlanhostop(ebroadcast, Q_DST); 7176511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IP_OVER_FC: 7177511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_ipfchostop(ebroadcast, Q_DST); 7178511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_SUNATM: 7179511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (is_lane) { 7180511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7181511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Check that the packet doesn't begin with an 7182511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * LE Control marker. (We've already generated 7183511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * a test for LANE.) 7184511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7185511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_cmp(OR_LINK, SUNATM_PKT_BEGIN_POS, 7186511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall BPF_H, 0xFF00); 7187511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_not(b1); 7188478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7189511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7190511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Now check the MAC address. 7191511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7192511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_ehostop(ebroadcast, Q_DST); 7193511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b1, b0); 7194511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return b0; 7195511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 7196511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 7197511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall default: 7198511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("not a broadcast link"); 7199511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 7200478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 7201478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7202478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IP: 7203511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7204511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * We treat a netmask of PCAP_NETMASK_UNKNOWN (0xffffffff) 7205511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * as an indication that we don't know the netmask, and fail 7206511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * in that case. 7207511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7208511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (netmask == PCAP_NETMASK_UNKNOWN) 7209511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("netmask not known, so 'ip broadcast' not supported"); 7210478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(ETHERTYPE_IP); 7211478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project hostmask = ~netmask; 7212478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_mcmp(OR_NET, 16, BPF_W, (bpf_int32)0, hostmask); 7213478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b2 = gen_mcmp(OR_NET, 16, BPF_W, 7214478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)(~0 & hostmask), hostmask); 7215478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b1, b2); 7216478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b2); 7217478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b2; 7218478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7219478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("only link-layer/IP broadcast filters supported"); 7220478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7221478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return NULL; 7222478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7223478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7224478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 7225478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Generate code to test the low-order bit of a MAC address (that's 7226478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the bottom bit of the *first* byte). 7227478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 7228478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 7229478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_mac_multicast(offset) 7230478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int offset; 7231478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7232478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register struct block *b0; 7233478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register struct slist *s; 7234478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7235478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* link[offset] & 1 != 0 */ 7236478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project s = gen_load_a(OR_LINK, offset, BPF_B); 7237478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = new_block(JMP(BPF_JSET)); 7238478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0->s.k = 1; 7239478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0->stmts = s; 7240478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b0; 7241478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7242478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7243478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7244478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_multicast(proto) 7245478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int proto; 7246478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7247478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register struct block *b0, *b1, *b2; 7248478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register struct slist *s; 7249478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7250478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (proto) { 7251478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7252478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 7253478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_LINK: 7254511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall switch (linktype) { 7255511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_ARCNET: 7256511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_ARCNET_LINUX: 7257511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* all ARCnet multicasts use the same address */ 7258511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_ahostop(abroadcast, Q_DST); 7259511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_EN10MB: 7260511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER: 7261511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER_TRANSPARENT: 7262511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* ether[0] & 1 != 0 */ 7263511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_mac_multicast(0); 7264511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_FDDI: 7265478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 7266511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * XXX TEST THIS: MIGHT NOT PORT PROPERLY XXX 7267511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 7268511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * XXX - was that referring to bit-order issues? 7269478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 7270511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* fddi[1] & 1 != 0 */ 7271511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_mac_multicast(1); 7272511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802: 7273511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* tr[2] & 1 != 0 */ 7274511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return gen_mac_multicast(2); 7275511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11: 7276511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PRISM_HEADER: 7277511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO_AVS: 7278511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO: 7279511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PPI: 7280511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7281511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Oh, yuk. 7282511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 7283511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * For control frames, there is no DA. 7284511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 7285511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * For management frames, DA is at an 7286511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * offset of 4 from the beginning of 7287511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the packet. 7288511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 7289511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * For data frames, DA is at an offset 7290511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * of 4 from the beginning of the packet 7291511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * if To DS is clear and at an offset of 7292511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 16 from the beginning of the packet 7293511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * if To DS is set. 7294511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7295511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7296511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7297511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Generate the tests to be done for data frames. 7298511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 7299511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * First, check for To DS set, i.e. "link[1] & 0x01". 7300511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7301511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_a(OR_LINK, 1, BPF_B); 7302511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = new_block(JMP(BPF_JSET)); 7303511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1->s.k = 0x01; /* To DS */ 7304511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1->stmts = s; 7305511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7306511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7307511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If To DS is set, the DA is at 16. 7308511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7309511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_mac_multicast(16); 7310511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b1, b0); 7311511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7312511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7313511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Now, check for To DS not set, i.e. check 7314511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * "!(link[1] & 0x01)". 7315511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7316511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_a(OR_LINK, 1, BPF_B); 7317511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b2 = new_block(JMP(BPF_JSET)); 7318511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b2->s.k = 0x01; /* To DS */ 7319511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b2->stmts = s; 7320511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_not(b2); 7321511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7322511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7323511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If To DS is not set, the DA is at 4. 7324511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7325511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_mac_multicast(4); 7326511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b2, b1); 7327511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7328511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7329511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Now OR together the last two checks. That gives 7330511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the complete set of checks for data frames. 7331511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7332511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_or(b1, b0); 7333511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7334511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7335511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Now check for a data frame. 7336511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * I.e, check "link[0] & 0x08". 7337511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7338511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_a(OR_LINK, 0, BPF_B); 7339511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = new_block(JMP(BPF_JSET)); 7340511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1->s.k = 0x08; 7341511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1->stmts = s; 7342511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7343511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7344511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * AND that with the checks done for data frames. 7345511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7346511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b1, b0); 7347511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7348511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7349511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If the high-order bit of the type value is 0, this 7350511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * is a management frame. 7351511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * I.e, check "!(link[0] & 0x08)". 7352511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7353511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_a(OR_LINK, 0, BPF_B); 7354511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b2 = new_block(JMP(BPF_JSET)); 7355511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b2->s.k = 0x08; 7356511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b2->stmts = s; 7357511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_not(b2); 7358511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7359511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7360511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * For management frames, the DA is at 4. 7361511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7362511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_mac_multicast(4); 7363511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b2, b1); 7364511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7365511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7366511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * OR that with the checks done for data frames. 7367511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * That gives the checks done for management and 7368511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * data frames. 7369511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7370511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_or(b1, b0); 7371511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7372511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7373511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If the low-order bit of the type value is 1, 7374511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * this is either a control frame or a frame 7375511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * with a reserved type, and thus not a 7376511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * frame with an SA. 7377511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 7378511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * I.e., check "!(link[0] & 0x04)". 7379511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7380511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall s = gen_load_a(OR_LINK, 0, BPF_B); 7381511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = new_block(JMP(BPF_JSET)); 7382511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1->s.k = 0x04; 7383511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1->stmts = s; 7384478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_not(b1); 7385478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7386511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7387511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * AND that with the checks for data and management 7388511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * frames. 7389511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7390478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b1, b0); 7391478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b0; 7392511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IP_OVER_FC: 7393511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_mac_multicast(2); 7394511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return b0; 7395511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_SUNATM: 7396511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (is_lane) { 7397511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7398511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Check that the packet doesn't begin with an 7399511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * LE Control marker. (We've already generated 7400511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * a test for LANE.) 7401511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7402511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_cmp(OR_LINK, SUNATM_PKT_BEGIN_POS, 7403511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall BPF_H, 0xFF00); 7404511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_not(b1); 7405511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7406511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* ether[off_mac] & 1 != 0 */ 7407511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_mac_multicast(off_mac); 7408511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b1, b0); 7409511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return b0; 7410511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 7411511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 7412511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall default: 7413511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 7414511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 7415511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* Link not known to support multicasts */ 7416511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 7417478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7418478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IP: 7419478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(ETHERTYPE_IP); 7420478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_cmp_ge(OR_NET, 16, BPF_B, (bpf_int32)224); 7421478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 7422478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 7423478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7424478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_IPV6: 7425478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(ETHERTYPE_IPV6); 7426478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_cmp(OR_NET, 24, BPF_B, (bpf_int32)255); 7427478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 7428478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 7429478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7430478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("link-layer multicast filters supported only on ethernet/FDDI/token ring/ARCNET/802.11/ATM LANE/Fibre Channel"); 7431478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7432478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return NULL; 7433478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7434478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7435478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 7436511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Filter on inbound (dir == 0) or outbound (dir == 1) traffic. 7437511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Outbound traffic is sent by this machine, while inbound traffic is 7438511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * sent by a remote machine (and may include packets destined for a 7439511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * unicast or multicast link-layer address we are not subscribing to). 7440511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * These are the same definitions implemented by pcap_setdirection(). 7441511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Capturing only unicast traffic destined for this host is probably 7442511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * better accomplished using a higher-layer filter. 7443478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 7444478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7445478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_inbound(dir) 7446478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int dir; 7447478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7448478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register struct block *b0; 7449478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7450478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 7451478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Only some data link types support inbound/outbound qualifiers. 7452478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 7453478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (linktype) { 7454478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_SLIP: 7455478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_relation(BPF_JEQ, 7456478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_load(Q_LINK, gen_loadi(0), 1), 7457478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_loadi(0), 7458478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project dir); 7459478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 7460478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7461511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IPNET: 7462478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (dir) { 7463511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* match outgoing packets */ 7464511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_cmp(OR_LINK, 2, BPF_H, IPNET_OUTBOUND); 7465478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else { 7466511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* match incoming packets */ 7467511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_cmp(OR_LINK, 2, BPF_H, IPNET_INBOUND); 7468511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 7469511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 7470511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7471511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_LINUX_SLL: 7472511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* match outgoing packets */ 7473511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_cmp(OR_LINK, 0, BPF_H, LINUX_SLL_OUTGOING); 7474511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (!dir) { 7475511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* to filter on inbound traffic, invert the match */ 7476511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_not(b0); 7477478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7478478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 7479478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7480478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef HAVE_NET_PFVAR_H 7481478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PFLOG: 7482478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, offsetof(struct pfloghdr, dir), BPF_B, 7483478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)((dir == 0) ? PF_IN : PF_OUT)); 7484478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 7485478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif 7486478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7487478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PPP_PPPD: 7488478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (dir) { 7489478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* match outgoing packets */ 7490478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, 0, BPF_B, PPP_PPPD_OUT); 7491478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else { 7492478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* match incoming packets */ 7493478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, 0, BPF_B, PPP_PPPD_IN); 7494478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7495478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 7496478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7497478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_MFR: 7498478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_MLFR: 7499478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_MLPPP: 7500478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_ATM1: 7501478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_ATM2: 7502478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_PPPOE: 7503478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_PPPOE_ATM: 7504478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_GGSN: 7505478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_ES: 7506478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_MONITOR: 7507478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_SERVICES: 7508478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_ETHER: 7509478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_PPP: 7510478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_FRELAY: 7511478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_CHDLC: 7512478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_JUNIPER_VP: 7513511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_ST: 7514511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_ISM: 7515511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_VS: 7516511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_SRX_E2E: 7517511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_FIBRECHANNEL: 7518511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_JUNIPER_ATM_CEMIC: 7519511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7520478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* juniper flags (including direction) are stored 7521478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the byte after the 3-byte magic number */ 7522478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (dir) { 7523478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* match outgoing packets */ 7524478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_mcmp(OR_LINK, 3, BPF_B, 0, 0x01); 7525478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else { 7526478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* match incoming packets */ 7527478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_mcmp(OR_LINK, 3, BPF_B, 1, 0x01); 7528478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7529511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 7530478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7531478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 7532511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7533511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If we have packet meta-data indicating a direction, 7534511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * check it, otherwise give up as this link-layer type 7535511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * has nothing in the packet data. 7536511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7537511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#if defined(linux) && defined(PF_PACKET) && defined(SO_ATTACH_FILTER) 7538511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* 7539511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * This is Linux with PF_PACKET support. 7540511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * If this is a *live* capture, we can look at 7541511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * special meta-data in the filter expression; 7542511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * if it's a savefile, we can't. 7543511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall */ 7544511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (bpf_pcap->rfile != NULL) { 7545511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* We have a FILE *, so this is a savefile */ 7546511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("inbound/outbound not supported on linktype %d when reading savefiles", 7547511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall linktype); 7548511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = NULL; 7549511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* NOTREACHED */ 7550511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 7551511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* match outgoing packets */ 7552511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_cmp(OR_LINK, SKF_AD_OFF + SKF_AD_PKTTYPE, BPF_H, 7553511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall PACKET_OUTGOING); 7554511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (!dir) { 7555511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* to filter on inbound traffic, invert the match */ 7556511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_not(b0); 7557511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 7558511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#else /* defined(linux) && defined(PF_PACKET) && defined(SO_ATTACH_FILTER) */ 7559478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("inbound/outbound not supported on linktype %d", 7560478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project linktype); 7561478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = NULL; 7562478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7563511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif /* defined(linux) && defined(PF_PACKET) && defined(SO_ATTACH_FILTER) */ 7564478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7565478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (b0); 7566478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7567478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7568478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#ifdef HAVE_NET_PFVAR_H 7569478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* PF firewall log matched interface */ 7570478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7571478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_pf_ifname(const char *ifname) 7572478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7573478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0; 7574478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project u_int len, off; 7575478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7576511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (linktype != DLT_PFLOG) { 7577511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("ifname supported only on PF linktype"); 7578478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7579478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7580511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall len = sizeof(((struct pfloghdr *)0)->ifname); 7581511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off = offsetof(struct pfloghdr, ifname); 7582478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (strlen(ifname) >= len) { 7583478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("ifname interface names can only be %d characters", 7584478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project len-1); 7585478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7586478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7587478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_bcmp(OR_LINK, off, strlen(ifname), (const u_char *)ifname); 7588478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (b0); 7589478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7590478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7591478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* PF firewall log ruleset name */ 7592478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7593478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_pf_ruleset(char *ruleset) 7594478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7595478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0; 7596478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7597478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (linktype != DLT_PFLOG) { 7598511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("ruleset supported only on PF linktype"); 7599478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7600478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7601511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7602478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (strlen(ruleset) >= sizeof(((struct pfloghdr *)0)->ruleset)) { 7603478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("ruleset names can only be %ld characters", 7604478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (long)(sizeof(((struct pfloghdr *)0)->ruleset) - 1)); 7605478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7606478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7607511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7608478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_bcmp(OR_LINK, offsetof(struct pfloghdr, ruleset), 7609478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project strlen(ruleset), (const u_char *)ruleset); 7610478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (b0); 7611478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7612478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7613478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* PF firewall log rule number */ 7614478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7615478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_pf_rnr(int rnr) 7616478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7617478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0; 7618478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7619511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (linktype != DLT_PFLOG) { 7620511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("rnr supported only on PF linktype"); 7621478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7622478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7623478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7624511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_cmp(OR_LINK, offsetof(struct pfloghdr, rulenr), BPF_W, 7625511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (bpf_int32)rnr); 7626478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (b0); 7627478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7628478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7629478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* PF firewall log sub-rule number */ 7630478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7631478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_pf_srnr(int srnr) 7632478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7633478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0; 7634478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7635478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (linktype != DLT_PFLOG) { 7636511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("srnr supported only on PF linktype"); 7637478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7638478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7639478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7640478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_cmp(OR_LINK, offsetof(struct pfloghdr, subrulenr), BPF_W, 7641478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (bpf_int32)srnr); 7642478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (b0); 7643478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7644478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7645478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* PF firewall log reason code */ 7646478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7647478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_pf_reason(int reason) 7648478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7649478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0; 7650478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7651511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (linktype != DLT_PFLOG) { 7652511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("reason supported only on PF linktype"); 7653478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7654478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7655478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7656511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_cmp(OR_LINK, offsetof(struct pfloghdr, reason), BPF_B, 7657511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (bpf_int32)reason); 7658478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (b0); 7659478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7660478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7661478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* PF firewall log action */ 7662478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7663478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_pf_action(int action) 7664478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7665478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0; 7666478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7667511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (linktype != DLT_PFLOG) { 7668511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("action supported only on PF linktype"); 7669478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7670478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7671478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7672511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_cmp(OR_LINK, offsetof(struct pfloghdr, action), BPF_B, 7673511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (bpf_int32)action); 7674478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (b0); 7675478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7676478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#else /* !HAVE_NET_PFVAR_H */ 7677478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7678478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_pf_ifname(const char *ifname) 7679478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7680478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("libpcap was compiled without pf support"); 7681478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7682478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (NULL); 7683478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7684478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7685478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7686478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_pf_ruleset(char *ruleset) 7687478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7688478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("libpcap was compiled on a machine without pf support"); 7689478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7690478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (NULL); 7691478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7692478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7693478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7694478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_pf_rnr(int rnr) 7695478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7696478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("libpcap was compiled on a machine without pf support"); 7697478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7698478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (NULL); 7699478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7700478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7701478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7702478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_pf_srnr(int srnr) 7703478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7704478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("libpcap was compiled on a machine without pf support"); 7705478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7706478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (NULL); 7707478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7708478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7709478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7710478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_pf_reason(int reason) 7711478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7712478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("libpcap was compiled on a machine without pf support"); 7713478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7714478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (NULL); 7715478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7716478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7717478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7718478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_pf_action(int action) 7719478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7720478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("libpcap was compiled on a machine without pf support"); 7721478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7722478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (NULL); 7723478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7724478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project#endif /* HAVE_NET_PFVAR_H */ 7725478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7726511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall/* IEEE 802.11 wireless header */ 7727511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstruct block * 7728511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallgen_p80211_type(int type, int mask) 7729511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall{ 7730511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct block *b0; 7731511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7732511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall switch (linktype) { 7733511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7734511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11: 7735511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PRISM_HEADER: 7736511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO_AVS: 7737511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO: 7738511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_mcmp(OR_LINK, 0, BPF_B, (bpf_int32)type, 7739511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (bpf_int32)mask); 7740511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 7741511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7742511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall default: 7743511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("802.11 link-layer types supported only on 802.11"); 7744511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* NOTREACHED */ 7745511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 7746511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7747511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (b0); 7748511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall} 7749511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7750511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallstruct block * 7751511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallgen_p80211_fcdir(int fcdir) 7752511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall{ 7753511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct block *b0; 7754511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7755511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall switch (linktype) { 7756511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7757511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11: 7758511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_PRISM_HEADER: 7759511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO_AVS: 7760511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_IEEE802_11_RADIO: 7761511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 7762511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7763511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall default: 7764511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("frame direction supported only with 802.11 headers"); 7765511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* NOTREACHED */ 7766511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 7767511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7768511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_mcmp(OR_LINK, 1, BPF_B, (bpf_int32)fcdir, 7769511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (bpf_u_int32)IEEE80211_FC1_DIR_MASK); 7770511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7771511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (b0); 7772511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall} 7773511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7774478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7775478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_acode(eaddr, q) 7776478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const u_char *eaddr; 7777478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct qual q; 7778478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7779511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall switch (linktype) { 7780511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7781511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_ARCNET: 7782511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_ARCNET_LINUX: 7783511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if ((q.addr == Q_HOST || q.addr == Q_DEFAULT) && 7784511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall q.proto == Q_LINK) 7785511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall return (gen_ahostop(eaddr, (int)q.dir)); 7786511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall else { 7787511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("ARCnet address used in non-arc expression"); 7788511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* NOTREACHED */ 7789511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 7790511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 7791511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7792511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall default: 7793511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("aid supported only on ARCnet"); 7794511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* NOTREACHED */ 7795478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7796478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("ARCnet address used in non-arc expression"); 7797478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7798478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return NULL; 7799478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7800478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7801478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 7802478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_ahostop(eaddr, dir) 7803478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register const u_char *eaddr; 7804478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register int dir; 7805478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7806478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project register struct block *b0, *b1; 7807478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7808478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (dir) { 7809478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* src comes first, different from Ethernet */ 7810478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_SRC: 7811478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_bcmp(OR_LINK, 0, 1, eaddr); 7812478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7813478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DST: 7814478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_bcmp(OR_LINK, 1, 1, eaddr); 7815478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7816478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_AND: 7817478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ahostop(eaddr, Q_SRC); 7818478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_ahostop(eaddr, Q_DST); 7819478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 7820478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 7821478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7822478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_DEFAULT: 7823478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case Q_OR: 7824478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ahostop(eaddr, Q_SRC); 7825478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_ahostop(eaddr, Q_DST); 7826478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 7827478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 7828511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7829511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR1: 7830511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr1' is only supported on 802.11"); 7831511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 7832511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7833511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR2: 7834511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr2' is only supported on 802.11"); 7835511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 7836511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7837511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR3: 7838511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr3' is only supported on 802.11"); 7839511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 7840511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7841511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_ADDR4: 7842511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'addr4' is only supported on 802.11"); 7843511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 7844511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7845511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_RA: 7846511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'ra' is only supported on 802.11"); 7847511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 7848511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7849511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case Q_TA: 7850511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'ta' is only supported on 802.11"); 7851511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 7852478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7853478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 7854478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* NOTREACHED */ 7855478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7856478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7857478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 7858478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * support IEEE 802.1Q VLAN trunk over ethernet 7859478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 7860478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7861478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_vlan(vlan_num) 7862478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int vlan_num; 7863478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7864478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1; 7865478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7866478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* can't check for VLAN-encapsulated packets inside MPLS */ 7867478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (label_stack_depth > 0) 7868478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("no VLAN match after MPLS"); 7869478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7870478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 7871511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * Check for a VLAN packet, and then change the offsets to point 7872511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * to the type and data fields within the VLAN packet. Just 7873511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * increment the offsets, so that we can support a hierarchy, e.g. 7874511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * "vlan 300 && vlan 200" to capture VLAN 200 encapsulated within 7875511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * VLAN 100. 7876478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 7877478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - this is a bit of a kludge. If we were to split the 7878478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * compiler into a parser that parses an expression and 7879478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * generates an expression tree, and a code generator that 7880478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * takes an expression tree (which could come from our 7881478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * parser or from some other parser) and generates BPF code, 7882478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * we could perhaps make the offsets parameters of routines 7883478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * and, in the handler for an "AND" node, pass to subnodes 7884478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * other than the VLAN node the adjusted offsets. 7885478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 7886478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This would mean that "vlan" would, instead of changing the 7887478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * behavior of *all* tests after it, change only the behavior 7888478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of tests ANDed with it. That would change the documented 7889478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * semantics of "vlan", which might break some expressions. 7890478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * However, it would mean that "(vlan and ip) or ip" would check 7891478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * both for VLAN-encapsulated IP and IP-over-Ethernet, rather than 7892478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * checking only for VLAN-encapsulated IP, so that could still 7893478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * be considered worth doing; it wouldn't break expressions 7894478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * that are of the form "vlan and ..." or "vlan N and ...", 7895478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * which I suspect are the most common expressions involving 7896478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "vlan". "vlan or ..." doesn't necessarily do what the user 7897478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * would really want, now, as all the "or ..." tests would 7898478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * be done assuming a VLAN, even though the "or" could be viewed 7899478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * as meaning "or, if this isn't a VLAN packet...". 7900478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 7901478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project orig_nl = off_nl; 7902478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7903478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (linktype) { 7904478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7905478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_EN10MB: 7906511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER: 7907511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER_TRANSPARENT: 7908511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* check for VLAN, including QinQ */ 7909511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_cmp(OR_LINK, off_linktype, BPF_H, 7910511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (bpf_int32)ETHERTYPE_8021Q); 7911511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_cmp(OR_LINK, off_linktype, BPF_H, 7912511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (bpf_int32)ETHERTYPE_8021QINQ); 7913511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_or(b0,b1); 7914511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = b1; 7915511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7916511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* If a specific VLAN is requested, check VLAN id */ 7917511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (vlan_num >= 0) { 7918511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_mcmp(OR_MACPL, 0, BPF_H, 7919511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (bpf_int32)vlan_num, 0x0fff); 7920511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b0, b1); 7921511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = b1; 7922511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 7923511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 7924511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl += 4; 7925478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype += 4; 7926511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#if 0 7927478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap += 4; 7928478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl += 4; 7929511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall#endif 7930478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 7931478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7932478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 7933478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("no VLAN support for data link type %d", 7934478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project linktype); 7935478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 7936478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7937478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7938478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (b0); 7939478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 7940478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7941478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 7942478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * support for MPLS 7943478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 7944478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 7945478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_mpls(label_num) 7946478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int label_num; 7947478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 7948478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0,*b1; 7949478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7950478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 7951478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Change the offsets to point to the type and data fields within 7952478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the MPLS packet. Just increment the offsets, so that we 7953478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * can support a hierarchy, e.g. "mpls 100000 && mpls 1024" to 7954478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * capture packets with an outer label of 100000 and an inner 7955478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * label of 1024. 7956478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 7957478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - this is a bit of a kludge. See comments in gen_vlan(). 7958478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 7959478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project orig_nl = off_nl; 7960478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7961478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (label_stack_depth > 0) { 7962478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* just match the bottom-of-stack bit clear */ 7963511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_mcmp(OR_MACPL, orig_nl-2, BPF_B, 0, 0x01); 7964478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } else { 7965478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 7966478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Indicate that we're checking MPLS-encapsulated headers, 7967478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * to make sure higher level code generators don't try to 7968478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * match against IP-related protocols such as Q_ARP, Q_RARP 7969478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * etc. 7970478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 7971478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (linktype) { 7972478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7973478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_C_HDLC: /* fall through */ 7974478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_EN10MB: 7975511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER: 7976511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case DLT_NETANALYZER_TRANSPARENT: 7977478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(ETHERTYPE_MPLS); 7978478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 7979478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7980478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case DLT_PPP: 7981478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype(PPP_MPLS_UCAST); 7982478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 7983478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7984478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* FIXME add other DLT_s ... 7985478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * for Frame-Relay/and ATM this may get messy due to SNAP headers 7986478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * leave it for now */ 7987478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7988478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 7989478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("no MPLS support for data link type %d", 7990478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project linktype); 7991478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = NULL; 7992478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /*NOTREACHED*/ 7993478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 7994478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7995478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 7996478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 7997478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* If a specific MPLS label is requested, check it */ 7998478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (label_num >= 0) { 7999478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project label_num = label_num << 12; /* label is shifted 12 bits on the wire */ 8000511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_mcmp(OR_MACPL, orig_nl, BPF_W, (bpf_int32)label_num, 8001478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 0xfffff000); /* only compare the first 20 bits */ 8002478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 8003478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = b1; 8004478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 8005478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8006478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl_nosnap += 4; 8007478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_nl += 4; 8008478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project label_stack_depth++; 8009478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return (b0); 8010478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 8011478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8012478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 8013478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Support PPPOE discovery and session. 8014478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 8015478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 8016478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_pppoed() 8017478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 8018478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* check for PPPoE discovery */ 8019478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return gen_linktype((bpf_int32)ETHERTYPE_PPPOED); 8020478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 8021478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8022478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 8023511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrallgen_pppoes(sess_num) 8024511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall int sess_num; 8025478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 8026511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall struct block *b0, *b1; 8027478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8028478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 8029478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Test against the PPPoE session link-layer type. 8030478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 8031478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_linktype((bpf_int32)ETHERTYPE_PPPOES); 8032478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8033478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 8034478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Change the offsets to point to the type and data fields within 8035511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * the PPP packet, and note that this is PPPoE rather than 8036511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * raw PPP. 8037478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 8038478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * XXX - this is a bit of a kludge. If we were to split the 8039478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * compiler into a parser that parses an expression and 8040478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * generates an expression tree, and a code generator that 8041478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * takes an expression tree (which could come from our 8042478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * parser or from some other parser) and generates BPF code, 8043478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * we could perhaps make the offsets parameters of routines 8044478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * and, in the handler for an "AND" node, pass to subnodes 8045478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * other than the PPPoE node the adjusted offsets. 8046478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 8047478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * This would mean that "pppoes" would, instead of changing the 8048478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * behavior of *all* tests after it, change only the behavior 8049478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * of tests ANDed with it. That would change the documented 8050478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * semantics of "pppoes", which might break some expressions. 8051478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * However, it would mean that "(pppoes and ip) or ip" would check 8052478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * both for VLAN-encapsulated IP and IP-over-Ethernet, rather than 8053478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * checking only for VLAN-encapsulated IP, so that could still 8054478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * be considered worth doing; it wouldn't break expressions 8055478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * that are of the form "pppoes and ..." which I suspect are the 8056478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * most common expressions involving "pppoes". "pppoes or ..." 8057478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * doesn't necessarily do what the user would really want, now, 8058478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * as all the "or ..." tests would be done assuming PPPoE, even 8059478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * though the "or" could be viewed as meaning "or, if this isn't 8060478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * a PPPoE packet...". 8061478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 8062478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project orig_linktype = off_linktype; /* save original values */ 8063478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project orig_nl = off_nl; 8064511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall is_pppoes = 1; 8065511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 8066511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* If a specific session is requested, check PPPoE session id */ 8067511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if (sess_num >= 0) { 8068511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_mcmp(OR_MACPL, orig_nl, BPF_W, 8069511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (bpf_int32)sess_num, 0x0000ffff); 8070511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b0, b1); 8071511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = b1; 8072511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall } 8073478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8074478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 8075478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * The "network-layer" protocol is PPPoE, which has a 6-byte 8076511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * PPPoE header, followed by a PPP packet. 8077511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * 8078511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * There is no HDLC encapsulation for the PPP packet (it's 8079511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * encapsulated in PPPoES instead), so the link-layer type 8080511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * starts at the first byte of the PPP packet. For PPPoE, 8081511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * that offset is relative to the beginning of the total 8082511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * link-layer payload, including any 802.2 LLC header, so 8083511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * it's 6 bytes past off_nl. 8084478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 8085511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_linktype = off_nl + 6; 8086478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8087478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 8088511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * The network-layer offsets are relative to the beginning 8089511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * of the MAC-layer payload; that's past the 6-byte 8090511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * PPPoE header and the 2-byte PPP header. 8091478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 8092511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 6+2; 8093511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 6+2; 8094478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8095478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b0; 8096478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 8097478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8098478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 8099478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_atmfield_code(atmfield, jvalue, jtype, reverse) 8100478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int atmfield; 8101478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_int32 jvalue; 8102478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 jtype; 8103478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int reverse; 8104478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 8105478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0; 8106478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8107478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (atmfield) { 8108478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8109478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_VPI: 8110478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_atm) 8111478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'vpi' supported only on raw ATM"); 8112478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (off_vpi == (u_int)-1) 8113478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 8114478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ncmp(OR_LINK, off_vpi, BPF_B, 0xffffffff, jtype, 8115478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project reverse, jvalue); 8116478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8117478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8118478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_VCI: 8119478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_atm) 8120478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'vci' supported only on raw ATM"); 8121478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (off_vci == (u_int)-1) 8122478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 8123478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ncmp(OR_LINK, off_vci, BPF_H, 0xffffffff, jtype, 8124478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project reverse, jvalue); 8125478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8126478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8127478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_PROTOTYPE: 8128478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (off_proto == (u_int)-1) 8129478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); /* XXX - this isn't on FreeBSD */ 8130478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ncmp(OR_LINK, off_proto, BPF_B, 0x0f, jtype, 8131478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project reverse, jvalue); 8132478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8133478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8134478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_MSGTYPE: 8135478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (off_payload == (u_int)-1) 8136478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 8137478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ncmp(OR_LINK, off_payload + MSG_TYPE_POS, BPF_B, 8138478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 0xffffffff, jtype, reverse, jvalue); 8139478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8140478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8141478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_CALLREFTYPE: 8142478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_atm) 8143478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'callref' supported only on raw ATM"); 8144478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (off_proto == (u_int)-1) 8145478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 8146478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ncmp(OR_LINK, off_proto, BPF_B, 0xffffffff, 8147478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project jtype, reverse, jvalue); 8148478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8149478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8150478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 8151478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 8152478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 8153478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b0; 8154478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 8155478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8156478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 8157478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_atmtype_abbrev(type) 8158478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int type; 8159478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 8160478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1; 8161478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8162478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (type) { 8163478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8164478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_METAC: 8165478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Get all packets in Meta signalling Circuit */ 8166478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_atm) 8167478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'metac' supported only on raw ATM"); 8168478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_atmfield_code(A_VPI, 0, BPF_JEQ, 0); 8169478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmfield_code(A_VCI, 1, BPF_JEQ, 0); 8170478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 8171478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8172478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8173478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_BCC: 8174478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Get all packets in Broadcast Circuit*/ 8175478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_atm) 8176478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'bcc' supported only on raw ATM"); 8177478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_atmfield_code(A_VPI, 0, BPF_JEQ, 0); 8178478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmfield_code(A_VCI, 2, BPF_JEQ, 0); 8179478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 8180478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8181478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8182478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_OAMF4SC: 8183478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Get all cells in Segment OAM F4 circuit*/ 8184478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_atm) 8185478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'oam4sc' supported only on raw ATM"); 8186478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_atmfield_code(A_VPI, 0, BPF_JEQ, 0); 8187478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmfield_code(A_VCI, 3, BPF_JEQ, 0); 8188478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 8189478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8190478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8191478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_OAMF4EC: 8192478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Get all cells in End-to-End OAM F4 Circuit*/ 8193478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_atm) 8194478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'oam4ec' supported only on raw ATM"); 8195478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_atmfield_code(A_VPI, 0, BPF_JEQ, 0); 8196478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmfield_code(A_VCI, 4, BPF_JEQ, 0); 8197478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 8198478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8199478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8200478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_SC: 8201478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Get all packets in connection Signalling Circuit */ 8202478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_atm) 8203478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'sc' supported only on raw ATM"); 8204478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_atmfield_code(A_VPI, 0, BPF_JEQ, 0); 8205478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmfield_code(A_VCI, 5, BPF_JEQ, 0); 8206478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 8207478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8208478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8209478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_ILMIC: 8210478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Get all packets in ILMI Circuit */ 8211478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_atm) 8212478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'ilmic' supported only on raw ATM"); 8213478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_atmfield_code(A_VPI, 0, BPF_JEQ, 0); 8214478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmfield_code(A_VCI, 16, BPF_JEQ, 0); 8215478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 8216478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8217478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8218478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_LANE: 8219478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Get all LANE packets */ 8220478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_atm) 8221478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'lane' supported only on raw ATM"); 8222478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmfield_code(A_PROTOTYPE, PT_LANE, BPF_JEQ, 0); 8223478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8224478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 8225478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Arrange that all subsequent tests assume LANE 8226478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * rather than LLC-encapsulated packets, and set 8227478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * the offsets appropriately for LANE-encapsulated 8228478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Ethernet. 8229478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * 8230478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * "off_mac" is the offset of the Ethernet header, 8231478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * which is 2 bytes past the ATM pseudo-header 8232478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * (skipping the pseudo-header and 2-byte LE Client 8233478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * field). The other offsets are Ethernet offsets 8234478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * relative to "off_mac". 8235478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 8236478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project is_lane = 1; 8237478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_mac = off_payload + 2; /* MAC header */ 8238478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project off_linktype = off_mac + 12; 8239511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_macpl = off_mac + 14; /* Ethernet */ 8240511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl = 0; /* Ethernet II */ 8241511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall off_nl_nosnap = 3; /* 802.3+802.2 */ 8242478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8243478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8244478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_LLC: 8245478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* Get all LLC-encapsulated packets */ 8246478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_atm) 8247478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'llc' supported only on raw ATM"); 8248478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmfield_code(A_PROTOTYPE, PT_LLC, BPF_JEQ, 0); 8249478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project is_lane = 0; 8250478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8251478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8252478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 8253478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 8254478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 8255478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 8256478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 8257478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8258478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project/* 8259478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Filtering for MTP2 messages based on li value 8260478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * FISU, length is null 8261478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * LSSU, length is 1 or 2 8262478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * MSU, length is 3 or more 8263511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall * For MTP2_HSL, sequences are on 2 bytes, and length on 9 bits 8264478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 8265478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 8266478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_mtp2type_abbrev(type) 8267478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int type; 8268478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 8269478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1; 8270478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8271478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (type) { 8272478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8273478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case M_FISU: 8274478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if ( (linktype != DLT_MTP2) && 8275511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (linktype != DLT_ERF) && 8276478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (linktype != DLT_MTP2_WITH_PHDR) ) 8277478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'fisu' supported only on MTP2"); 8278478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* gen_ncmp(offrel, offset, size, mask, jtype, reverse, value) */ 8279478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ncmp(OR_PACKET, off_li, BPF_B, 0x3f, BPF_JEQ, 0, 0); 8280478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8281478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8282478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case M_LSSU: 8283478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if ( (linktype != DLT_MTP2) && 8284511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (linktype != DLT_ERF) && 8285478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (linktype != DLT_MTP2_WITH_PHDR) ) 8286478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'lssu' supported only on MTP2"); 8287478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ncmp(OR_PACKET, off_li, BPF_B, 0x3f, BPF_JGT, 1, 2); 8288478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_ncmp(OR_PACKET, off_li, BPF_B, 0x3f, BPF_JGT, 0, 0); 8289478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b1, b0); 8290478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8291478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8292478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case M_MSU: 8293478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if ( (linktype != DLT_MTP2) && 8294511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (linktype != DLT_ERF) && 8295478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (linktype != DLT_MTP2_WITH_PHDR) ) 8296478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'msu' supported only on MTP2"); 8297478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_ncmp(OR_PACKET, off_li, BPF_B, 0x3f, BPF_JGT, 0, 2); 8298478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8299478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8300511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case MH_FISU: 8301511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if ( (linktype != DLT_MTP2) && 8302511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (linktype != DLT_ERF) && 8303511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (linktype != DLT_MTP2_WITH_PHDR) ) 8304511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'hfisu' supported only on MTP2_HSL"); 8305511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* gen_ncmp(offrel, offset, size, mask, jtype, reverse, value) */ 8306511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_ncmp(OR_PACKET, off_li_hsl, BPF_H, 0xff80, BPF_JEQ, 0, 0); 8307511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 8308511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 8309511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case MH_LSSU: 8310511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if ( (linktype != DLT_MTP2) && 8311511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (linktype != DLT_ERF) && 8312511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (linktype != DLT_MTP2_WITH_PHDR) ) 8313511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'hlssu' supported only on MTP2_HSL"); 8314511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_ncmp(OR_PACKET, off_li_hsl, BPF_H, 0xff80, BPF_JGT, 1, 0x0100); 8315511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b1 = gen_ncmp(OR_PACKET, off_li_hsl, BPF_H, 0xff80, BPF_JGT, 0, 0); 8316511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall gen_and(b1, b0); 8317511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 8318511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 8319511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case MH_MSU: 8320511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall if ( (linktype != DLT_MTP2) && 8321511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (linktype != DLT_ERF) && 8322511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall (linktype != DLT_MTP2_WITH_PHDR) ) 8323511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall bpf_error("'hmsu' supported only on MTP2_HSL"); 8324511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_ncmp(OR_PACKET, off_li_hsl, BPF_H, 0xff80, BPF_JGT, 0, 0x0100); 8325511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall break; 8326511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 8327478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 8328478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 8329478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 8330478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b0; 8331478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 8332478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8333478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 8334478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_mtp3field_code(mtp3field, jvalue, jtype, reverse) 8335478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int mtp3field; 8336478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 jvalue; 8337478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 jtype; 8338478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int reverse; 8339478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 8340478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0; 8341478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_u_int32 val1 , val2 , val3; 8342511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall u_int newoff_sio=off_sio; 8343511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall u_int newoff_opc=off_opc; 8344511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall u_int newoff_dpc=off_dpc; 8345511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall u_int newoff_sls=off_sls; 8346478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8347478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (mtp3field) { 8348478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8349511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case MH_SIO: 8350511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall newoff_sio += 3; /* offset for MTP2_HSL */ 8351511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* FALLTHROUGH */ 8352511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 8353478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case M_SIO: 8354478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (off_sio == (u_int)-1) 8355478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'sio' supported only on SS7"); 8356478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* sio coded on 1 byte so max value 255 */ 8357478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if(jvalue > 255) 8358478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("sio value %u too big; max value = 255", 8359478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project jvalue); 8360511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_ncmp(OR_PACKET, newoff_sio, BPF_B, 0xffffffff, 8361478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (u_int)jtype, reverse, (u_int)jvalue); 8362478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8363478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8364511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case MH_OPC: 8365511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall newoff_opc+=3; 8366478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case M_OPC: 8367478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (off_opc == (u_int)-1) 8368478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'opc' supported only on SS7"); 8369478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* opc coded on 14 bits so max value 16383 */ 8370478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (jvalue > 16383) 8371478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("opc value %u too big; max value = 16383", 8372478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project jvalue); 8373478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* the following instructions are made to convert jvalue 8374478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * to the form used to write opc in an ss7 message*/ 8375478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project val1 = jvalue & 0x00003c00; 8376478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project val1 = val1 >>10; 8377478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project val2 = jvalue & 0x000003fc; 8378478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project val2 = val2 <<6; 8379478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project val3 = jvalue & 0x00000003; 8380478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project val3 = val3 <<22; 8381478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project jvalue = val1 + val2 + val3; 8382511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_ncmp(OR_PACKET, newoff_opc, BPF_W, 0x00c0ff0f, 8383478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (u_int)jtype, reverse, (u_int)jvalue); 8384478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8385478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8386511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case MH_DPC: 8387511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall newoff_dpc += 3; 8388511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall /* FALLTHROUGH */ 8389511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall 8390478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case M_DPC: 8391478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (off_dpc == (u_int)-1) 8392478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'dpc' supported only on SS7"); 8393478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* dpc coded on 14 bits so max value 16383 */ 8394478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (jvalue > 16383) 8395478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("dpc value %u too big; max value = 16383", 8396478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project jvalue); 8397478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* the following instructions are made to convert jvalue 8398478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * to the forme used to write dpc in an ss7 message*/ 8399478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project val1 = jvalue & 0x000000ff; 8400478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project val1 = val1 << 24; 8401478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project val2 = jvalue & 0x00003f00; 8402478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project val2 = val2 << 8; 8403478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project jvalue = val1 + val2; 8404511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_ncmp(OR_PACKET, newoff_dpc, BPF_W, 0xff3f0000, 8405478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (u_int)jtype, reverse, (u_int)jvalue); 8406478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8407478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8408511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall case MH_SLS: 8409511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall newoff_sls+=3; 8410478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case M_SLS: 8411478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (off_sls == (u_int)-1) 8412478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'sls' supported only on SS7"); 8413478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* sls coded on 4 bits so max value 15 */ 8414478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (jvalue > 15) 8415478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("sls value %u too big; max value = 15", 8416478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project jvalue); 8417478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* the following instruction is made to convert jvalue 8418478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * to the forme used to write sls in an ss7 message*/ 8419478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project jvalue = jvalue << 4; 8420511eca30a483e912c274e1d8ba3a0f8f081e2227JP Abgrall b0 = gen_ncmp(OR_PACKET, newoff_sls, BPF_B, 0xf0, 8421478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project (u_int)jtype,reverse, (u_int)jvalue); 8422478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8423478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8424478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 8425478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 8426478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 8427478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b0; 8428478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 8429478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8430478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstatic struct block * 8431478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_msg_abbrev(type) 8432478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int type; 8433478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 8434478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b1; 8435478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8436478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 8437478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Q.2931 signalling protocol messages for handling virtual circuits 8438478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * establishment and teardown 8439478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 8440478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (type) { 8441478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8442478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_SETUP: 8443478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmfield_code(A_MSGTYPE, SETUP, BPF_JEQ, 0); 8444478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8445478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8446478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_CALLPROCEED: 8447478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmfield_code(A_MSGTYPE, CALL_PROCEED, BPF_JEQ, 0); 8448478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8449478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8450478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_CONNECT: 8451478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmfield_code(A_MSGTYPE, CONNECT, BPF_JEQ, 0); 8452478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8453478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8454478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_CONNECTACK: 8455478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmfield_code(A_MSGTYPE, CONNECT_ACK, BPF_JEQ, 0); 8456478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8457478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8458478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_RELEASE: 8459478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmfield_code(A_MSGTYPE, RELEASE, BPF_JEQ, 0); 8460478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8461478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8462478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_RELEASE_DONE: 8463478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmfield_code(A_MSGTYPE, RELEASE_DONE, BPF_JEQ, 0); 8464478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8465478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8466478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 8467478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 8468478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 8469478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 8470478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 8471478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8472478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectstruct block * 8473478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Projectgen_atmmulti_abbrev(type) 8474478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project int type; 8475478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project{ 8476478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project struct block *b0, *b1; 8477478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8478478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project switch (type) { 8479478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8480478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_OAM: 8481478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_atm) 8482478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'oam' supported only on raw ATM"); 8483478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmmulti_abbrev(A_OAMF4); 8484478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8485478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8486478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_OAMF4: 8487478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_atm) 8488478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'oamf4' supported only on raw ATM"); 8489478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* OAM F4 type */ 8490478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_atmfield_code(A_VCI, 3, BPF_JEQ, 0); 8491478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_atmfield_code(A_VCI, 4, BPF_JEQ, 0); 8492478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 8493478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_atmfield_code(A_VPI, 0, BPF_JEQ, 0); 8494478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 8495478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8496478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8497478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_CONNECTMSG: 8498478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project /* 8499478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * Get Q.2931 signalling messages for switched 8500478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project * virtual connection 8501478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project */ 8502478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_atm) 8503478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'connectmsg' supported only on raw ATM"); 8504478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_msg_abbrev(A_SETUP); 8505478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_msg_abbrev(A_CALLPROCEED); 8506478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 8507478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_msg_abbrev(A_CONNECT); 8508478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 8509478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_msg_abbrev(A_CONNECTACK); 8510478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 8511478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_msg_abbrev(A_RELEASE); 8512478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 8513478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_msg_abbrev(A_RELEASE_DONE); 8514478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 8515478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_atmtype_abbrev(A_SC); 8516478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 8517478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8518478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8519478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project case A_METACONNECT: 8520478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project if (!is_atm) 8521478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project bpf_error("'metaconnect' supported only on raw ATM"); 8522478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_msg_abbrev(A_SETUP); 8523478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b1 = gen_msg_abbrev(A_CALLPROCEED); 8524478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 8525478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_msg_abbrev(A_CONNECT); 8526478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 8527478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_msg_abbrev(A_RELEASE); 8528478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 8529478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_msg_abbrev(A_RELEASE_DONE); 8530478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_or(b0, b1); 8531478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project b0 = gen_atmtype_abbrev(A_METAC); 8532478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project gen_and(b0, b1); 8533478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project break; 8534478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project 8535478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project default: 8536478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project abort(); 8537478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project } 8538478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project return b1; 8539478ab6c8b5bc982589be32eae1e5736efe721b58The Android Open Source Project} 8540