]> The Tcpdump Group git mirrors - libpcap/blobdiff - gencode.c
Tony Li's changes, from FreeBSD, to support filtering for OSI packets
[libpcap] / gencode.c
index 615a2586f624ea719e0781570d256ae66fde86fe..ea844903b1a8b74c85109358f532d1565ef29abb 100644 (file)
--- a/gencode.c
+++ b/gencode.c
@@ -21,7 +21,7 @@
  */
 #ifndef lint
 static const char rcsid[] =
-    "@(#) $Header: /tcpdump/master/libpcap/gencode.c,v 1.127 2000-10-28 08:19:29 guy Exp $ (LBL)";
+    "@(#) $Header: /tcpdump/master/libpcap/gencode.c,v 1.129 2000-10-28 09:30:21 guy Exp $ (LBL)";
 #endif
 
 #ifdef HAVE_CONFIG_H
@@ -50,6 +50,7 @@ struct rtentry;
 #include "pcap-int.h"
 
 #include "ethertype.h"
+#include "nlpid.h"
 #include "gencode.h"
 #include "ppp.h"
 #include <pcap-namedb.h>
@@ -58,6 +59,10 @@ struct rtentry;
 #include <sys/socket.h>
 #endif /*INET6*/
 
+#define LLC_ISO_LSAP   0xfe
+
+#define ETHERMTU       1500
+
 #ifdef HAVE_OS_PROTO_H
 #include "os-proto.h"
 #endif
@@ -730,6 +735,17 @@ gen_linktype(proto)
                 */
                switch (proto) {
 
+               case LLC_ISO_LSAP:
+                       /*
+                        * OSI protocols always use 802.2 encapsulation.
+                        */
+                       b0 = gen_cmp_gt(off_linktype, BPF_H, ETHERMTU);
+                       gen_not(b0);
+                       b1 = gen_cmp(off_linktype + 2, BPF_H, (long)
+                                    ((LLC_ISO_LSAP << 8) | LLC_ISO_LSAP));
+                       gen_and(b0, b1);
+                       return b1;
+
                case ETHERTYPE_ATALK:
                case ETHERTYPE_AARP:
                        /*
@@ -742,7 +758,7 @@ gen_linktype(proto)
                         * we check for an Ethernet type field less than
                         * 1500, which means it's an 802.3 length field.
                         */
-                       b0 = gen_cmp_gt(off_linktype, BPF_H, 1500);
+                       b0 = gen_cmp_gt(off_linktype, BPF_H, ETHERMTU);
                        gen_not(b0);
 
                        /*
@@ -779,15 +795,41 @@ gen_linktype(proto)
 
        case DLT_PPP:
        case DLT_PPP_SERIAL:
-               if (proto == ETHERTYPE_IP)
+               /*
+                * We use Ethernet protocol types inside libpcap;
+                * map them to the corresponding PPP protocol types.
+                */
+               switch (proto) {
+
+               case ETHERTYPE_IP:
                        proto = PPP_IP;                 /* XXX was 0x21 */
+                       break;
+
 #ifdef INET6
-               else if (proto == ETHERTYPE_IPV6)
+               case ETHERTYPE_IPV6:
                        proto = PPP_IPV6;
+                       break;
 #endif
+
+               case ETHERTYPE_DN:
+                       proto = PPP_DECNET;
+                       break;
+
+               case ETHERTYPE_ATALK:
+                       proto = PPP_APPLE;
+                       break;
+
+               case ETHERTYPE_NS:
+                       proto = PPP_NS;
+                       break;
+               }
                break;
 
        case DLT_PPP_BSDOS:
+               /*
+                * We use Ethernet protocol types inside libpcap;
+                * map them to the corresponding PPP protocol types.
+                */
                switch (proto) {
 
                case ETHERTYPE_IP:
@@ -1117,6 +1159,9 @@ gen_dnhostop(addr, dir, base_off)
                gen_or(b0, b1);
                return b1;
 
+       case Q_ISO:
+               bpf_error("ISO host filtering not implemented");
+               
        default:
                abort();
        }
@@ -1502,6 +1547,18 @@ gen_proto_abbrev(proto)
 #endif
                break;
 
+       case Q_ISO:
+               b1 = gen_linktype(LLC_ISO_LSAP);
+               break;
+
+       case Q_ESIS:
+               b1 = gen_proto(ISO9542_ESIS, Q_ISO, Q_DEFAULT);
+               break;
+
+       case Q_ISIS:
+               b1 = gen_proto(ISO10589_ISIS, Q_ISO, Q_DEFAULT);
+               break;
+
        default:
                abort();
        }
@@ -2073,6 +2130,12 @@ gen_proto(v, proto, dir)
                gen_and(b0, b1);
                return b1;
 
+       case Q_ISO:
+               b0 = gen_linktype(LLC_ISO_LSAP);
+               b1 = gen_cmp(off_nl + 3, BPF_B, (long)v);
+               gen_and(b0, b1);
+               return b1;
+
        case Q_ARP:
                bpf_error("arp does not encapsulate another protocol");
                /* NOTREACHED */
@@ -2888,6 +2951,9 @@ gen_greater(n)
        return gen_len(BPF_JGE, n);
 }
 
+/*
+ * Actually, this is less than or equal.
+ */
 struct block *
 gen_less(n)
        int n;