summaryrefslogtreecommitdiffstats
path: root/contrib
diff options
context:
space:
mode:
authorfenner <fenner@FreeBSD.org>2002-06-21 01:36:27 +0000
committerfenner <fenner@FreeBSD.org>2002-06-21 01:36:27 +0000
commitb8f074bf7dfede04fc792ddf5b8025dd111ed4f9 (patch)
tree440f1a28651463cca1d4b0dd9fedca2620595212 /contrib
parent71820ddb169f081273a4e230c5a500cd3a8c5fc2 (diff)
parent1e8ea467791f99f6068888787c27fd8b6b923d2c (diff)
downloadFreeBSD-src-b8f074bf7dfede04fc792ddf5b8025dd111ed4f9.zip
FreeBSD-src-b8f074bf7dfede04fc792ddf5b8025dd111ed4f9.tar.gz
This commit was generated by cvs2svn to compensate for changes in r98530,
which included commits to RCS files with non-trunk default branches.
Diffstat (limited to 'contrib')
-rw-r--r--contrib/libpcap/.cvsignore2
-rw-r--r--contrib/libpcap/CHANGES9
-rw-r--r--contrib/libpcap/CREDITS19
-rw-r--r--contrib/libpcap/FILES5
-rw-r--r--contrib/libpcap/INSTALL.txt342
-rw-r--r--contrib/libpcap/Makefile.in2
-rw-r--r--contrib/libpcap/README12
-rw-r--r--contrib/libpcap/README.aix68
-rw-r--r--contrib/libpcap/README.linux18
-rw-r--r--contrib/libpcap/README.tru6449
-rw-r--r--contrib/libpcap/TODO16
-rw-r--r--contrib/libpcap/VERSION2
-rw-r--r--contrib/libpcap/acconfig.h7
-rw-r--r--contrib/libpcap/arcnet.h52
-rwxr-xr-xcontrib/libpcap/config.guess471
-rw-r--r--contrib/libpcap/config.h.in29
-rwxr-xr-xcontrib/libpcap/config.sub98
-rwxr-xr-xcontrib/libpcap/configure297
-rwxr-xr-xcontrib/libpcap/configure.in37
-rw-r--r--contrib/libpcap/ethertype.h11
-rw-r--r--contrib/libpcap/inet.c949
-rw-r--r--contrib/libpcap/llc.h11
-rw-r--r--contrib/libpcap/optimize.c29
-rw-r--r--contrib/libpcap/pcap-bpf.c78
-rw-r--r--contrib/libpcap/pcap-dlpi.c463
-rw-r--r--contrib/libpcap/pcap-linux.c735
-rw-r--r--contrib/libpcap/pcap-nit.c18
-rw-r--r--contrib/libpcap/pcap-pf.c92
-rw-r--r--contrib/libpcap/pcap-snit.c19
-rw-r--r--contrib/libpcap/pcap-snoop.c21
-rw-r--r--contrib/libpcap/pcap.c63
-rw-r--r--contrib/libpcap/savefile.c40
32 files changed, 3224 insertions, 840 deletions
diff --git a/contrib/libpcap/.cvsignore b/contrib/libpcap/.cvsignore
index 12a60dd..a1cfe23 100644
--- a/contrib/libpcap/.cvsignore
+++ b/contrib/libpcap/.cvsignore
@@ -3,6 +3,8 @@ config.cache
config.status
config.h
.devel
+stamp-h
+stamp-h.in
Makefile
scanner.c
grammar.c
diff --git a/contrib/libpcap/CHANGES b/contrib/libpcap/CHANGES
index 5793de0..87c2784 100644
--- a/contrib/libpcap/CHANGES
+++ b/contrib/libpcap/CHANGES
@@ -1,4 +1,11 @@
-@(#) $Header: /tcpdump/master/libpcap/CHANGES,v 1.55 2001/01/10 04:10:33 guy Exp $ (LBL)
+@(#) $Header: /tcpdump/master/libpcap/CHANGES,v 1.56 2001/10/23 04:37:31 mcr Exp $ (LBL)
+
+Monday October 23, 2001. mcr@sandelman.ottawa.on.ca. Summary for 0.7 release
+
+ Added pcap_findalldevs() call to get list of interfaces in a MI way.
+
+ pcap_stats() has been documented as to what its counters mean on
+ each platform.
Tuesday January 9, 2001. guy@alum.mit.edu. Summary for 0.6 release
diff --git a/contrib/libpcap/CREDITS b/contrib/libpcap/CREDITS
index 5797237..77127dc 100644
--- a/contrib/libpcap/CREDITS
+++ b/contrib/libpcap/CREDITS
@@ -13,22 +13,41 @@ The current maintainers:
Additional people who have contributed patches:
Arkadiusz Miskiewicz <misiek@pld.org.pl>
+ Armando L. Caro Jr. <acaro@mail.eecis.udel.edu>
Fulvio Risso <risso@polito.it>
Charles M. Hannum <mycroft@netbsd.org>
Chris G. Demetriou <cgd@netbsd.org>
+ Chris Pepper <pepper@mail.reppep.com>
Darren Reed <darrenr@reed.wattle.id.au>
+ Franz Schaefer <schaefer@mond.at>
Greg Troxel <gdt@ir.bbn.com>
+ Hyung Sik Yoon <hsyn@kr.ibm.com>
+ Igor Khristophorov <igor@atdot.org>
+ Jason R. Thorpe <thorpej@zembu.com>
+ Javier Achirica <achirica@ttd.net>
Jefferson Ogata <jogata@nodc.noaa.gov>
Juergen Schoenwaelder <schoenw@ibr.cs.tu-bs.de>
+ Klaus Klein <kleink@netbsd.org>
Lorenzo Cavallaro <sullivan@sikurezza.org>
Love Hörnquist-Åstrand <lha@stacken.kth.se>
+ Maciej W. Rozycki <macro@ds2.pg.gda.pl>
+ Marcus Felipe Pereira <marcus@task.com.br>
+ Martin Husemann <martin@netbsd.org>
Monroe Williams <monroe@pobox.com>
Olaf Kirch <okir@caldera.de>
+ Onno van der Linden <onno@simplex.nl>
+ Pavel Kankovsky <kan@dcit.cz>
Peter Jeremy <peter.jeremy@alcatel.com.au>
+ Phil Wood <cpw@lanl.gov>
Rafal Maszkowski <rzm@icm.edu.pl>
Rick Jones <raj@cup.hp.com>
+ Scott Barron <sb125499@ohiou.edu>
+ Scott Gifford <sgifford@tir.com>
+ Stefan Hudson <hudson@mbay.net>
Tony Li <tli@jnx.com>
+ Uns Lider <unslider@miranda.org>
Uwe Girlich <Uwe.Girlich@philosys.de>
+ Xianjie Zhang <xzhang@cup.hp.com>
The original LBL crew:
Steve McCanne
diff --git a/contrib/libpcap/FILES b/contrib/libpcap/FILES
index 36141ca..bf18f7e 100644
--- a/contrib/libpcap/FILES
+++ b/contrib/libpcap/FILES
@@ -1,17 +1,19 @@
CHANGES
CREDITS
FILES
-INSTALL
+INSTALL.txt
LICENSE
Makefile.in
README
README.aix
README.linux
+README.tru64
SUNOS4/nit_if.o.sparc
SUNOS4/nit_if.o.sun3
SUNOS4/nit_if.o.sun4c.4.0.3c
VERSION
aclocal.m4
+arcnet.h
bpf/net/bpf.h
bpf/net/bpf_filter.c
bpf_dump.c
@@ -32,6 +34,7 @@ lbl/os-osf4.h
lbl/os-solaris2.h
lbl/os-sunos4.h
lbl/os-ultrix4.h
+llc.h
mkdep
nametoaddr.c
nlpid.h
diff --git a/contrib/libpcap/INSTALL.txt b/contrib/libpcap/INSTALL.txt
new file mode 100644
index 0000000..1325f80
--- /dev/null
+++ b/contrib/libpcap/INSTALL.txt
@@ -0,0 +1,342 @@
+@(#) $Header: /tcpdump/master/libpcap/INSTALL.txt,v 1.2 2001/06/05 03:45:53 guy Exp $ (LBL)
+
+To build libpcap, run "./configure" (a shell script). The configure
+script will determine your system attributes and generate an
+appropriate Makefile from Makefile.in. Next run "make". If everything
+goes well you can su to root and run "make install". However, you need
+not install libpcap if you just want to build tcpdump; just make sure
+the tcpdump and libpcap directory trees have the same parent
+directory.
+
+If configure says:
+
+ configure: warning: cannot determine packet capture interface
+ configure: warning: (see INSTALL for more info)
+
+then your system either does not support packet capture or your system
+does support packet capture but libpcap does not support that
+particular type. (If you have HP-UX, see below.) If your system uses a
+packet capture not supported by libpcap, please send us patches; don't
+forget to include an autoconf fragment suitable for use in
+configure.in.
+
+It is possible to override the default packet capture type, although
+the circumstance where this works are limited. For example if you have
+installed bpf under SunOS 4 and wish to build a snit libpcap:
+
+ ./configure --with-pcap=snit
+
+Another example is to force a supported packet capture type in the case
+where the configure scripts fails to detect it.
+
+You will need an ANSI C compiler to build libpcap. The configure script
+will abort if your compiler is not ANSI compliant. If this happens, use
+the GNU C compiler, available via anonymous ftp:
+
+ ftp://ftp.gnu.org/pub/gnu/gcc/
+
+If you use flex, you must use version 2.4.6 or higher. The configure
+script automatically detects the version of flex and will not use it
+unless it is new enough. You can use "flex -V" to see what version you
+have (unless it's really old). The current version of flex is available
+via anonymous ftp:
+
+ ftp://ftp.ee.lbl.gov/flex-*.tar.Z
+
+As of this writing, the current version is 2.5.4.
+
+If you use bison, you must use flex (and visa versa). The configure
+script automatically falls back to lex and yacc if both flex and bison
+are not found.
+
+Sometimes the stock C compiler does not interact well with flex and
+bison. The list of problems includes undefined references for alloca.
+You can get around this by installing gcc or manually disabling flex
+and bison with:
+
+ ./configure --without-flex --without-bison
+
+If your system only has AT&T lex, this is okay unless your libpcap
+program uses other lex/yacc generated code. (Although it's possible to
+map the yy* identifiers with a script, we use flex and bison so we
+don't feel this is necessary.)
+
+Some systems support the Berkeley Packet Filter natively; for example
+out of the box OSF and BSD/OS have bpf. If your system does not support
+bpf, you will need to pick up:
+
+ ftp://ftp.ee.lbl.gov/bpf-*.tar.Z
+
+Note well: you MUST have kernel source for your operating system in
+order to install bpf. An exception is SunOS 4; the bpf distribution
+includes replacement kernel objects for some of the standard SunOS 4
+network device drivers. See the bpf INSTALL document for more
+information.
+
+If you use Solaris, there is a bug with bufmod(7) that is fixed in
+Solaris 2.3.2 (aka SunOS 5.3.2). Setting a snapshot length with the
+broken bufmod(7) results in data be truncated from the FRONT of the
+packet instead of the end. The work around is to not set a snapshot
+length but this results in performance problems since the entire packet
+is copied to user space. If you must run an older version of Solaris,
+there is a patch available from Sun; ask for bugid 1149065. After
+installing the patch, use "setenv BUFMOD_FIXED" to enable use of
+bufmod(7). However, we recommend you run a more current release of
+Solaris.
+
+If you use the SPARCompiler, you must be careful to not use the
+/usr/ucb/cc interface. If you do, you will get bogus warnings and
+perhaps errors. Either make sure your path has /opt/SUNWspro/bin
+before /usr/ucb or else:
+
+ setenv CC /opt/SUNWspro/bin/cc
+
+before running configure. (You might have to do a "make distclean"
+if you already ran configure once).
+
+Also note that "make depend" won't work; while all of the known
+universe uses -M, the SPARCompiler uses -xM to generate makefile
+dependencies.
+
+If you are trying to do packet capture with a FORE ATM card, you may or
+may not be able to. They usually only release their driver in object
+code so unless their driver supports packet capture, there's not much
+libpcap can do.
+
+If you get an error like:
+
+ tcpdump: recv_ack: bind error 0x???
+
+when using DLPI, look for the DL_ERROR_ACK error return values, usually
+in /usr/include/sys/dlpi.h, and find the corresponding value.
+
+Under {DEC OSF/1, Digital UNIX, Tru64 UNIX}, packet capture must be
+enabled before it can be used. For instructions on how to enable packet
+filter support, see:
+
+ ftp://ftp.digital.com/pub/Digital/dec-faq/Digital-UNIX
+
+Look for the "How do I configure the Berkeley Packet Filter and capture
+tcpdump traces?" item.
+
+Once you enable packet filter support, your OSF system will support bpf
+natively.
+
+Under Ultrix, packet capture must be enabled before it can be used. For
+instructions on how to enable packet filter support, see:
+
+ ftp://ftp.digital.com/pub/Digital/dec-faq/ultrix
+
+If you use HP-UX, you must have at least version 9 and either the
+version of cc that supports ANSI C (cc -Aa) or else use the GNU C
+compiler. You must also buy the optional streams package. If you don't
+have:
+
+ /usr/include/sys/dlpi.h
+ /usr/include/sys/dlpi_ext.h
+
+then you don't have the streams package. In addition, we believe you
+need to install the "9.X LAN and DLPI drivers cumulative" patch
+(PHNE_6855) to make the version 9 DLPI work with libpcap.
+
+The DLPI streams package is standard starting with HP-UX 10.
+
+The HP implementation of DLPI is a little bit eccentric. Unlike
+Solaris, you must attach /dev/dlpi instead of the specific /dev/*
+network pseudo device entry in order to capture packets. The PPA is
+based on the ifnet "index" number. Under HP-UX 9, it is necessary to
+read /dev/kmem and the kernel symbol file (/hp-ux). Under HP-UX 10,
+DLPI can provide information for determining the PPA. It does not seem
+to be possible to trace the loopback interface. Unlike other DLPI
+implementations, PHYS implies MULTI and SAP and you get an error if you
+try to enable more than one promiscuous mode at a time.
+
+It is impossible to capture outbound packets on HP-UX 9. To do so on
+HP-UX 10, you will, apparently, need a late "LAN products cumulative
+patch" (at one point, it was claimed that this would be PHNE_18173 for
+s700/10.20; at another point, it was claimed that the required patches
+were PHNE_20892, PHNE_20725 and PHCO_10947, or newer patches), and to do
+so on HP-UX 11 you will, apparently, need the latest lancommon/DLPI
+patches and the latest driver patch for the interface(s) in use on HP-UX
+11 (at one point, it was claimed that patches PHNE_19766, PHNE_19826,
+PHNE_20008, and PHNE_20735 did the trick).
+
+Furthermore, on HP-UX 10, you will need to turn on a kernel switch by
+doing
+
+ echo 'lanc_outbound_promisc_flag/W 1' | adb -w /stand/vmunix /dev/mem
+
+You would have to arrange that this happen on reboots; the right way to
+do that would probably be to put it into an executable script file
+"/sbin/init.d/outbound_promisc" and making
+"/sbin/rc2.d/S350outbound_promisc" a symbolic link to that script.
+
+Finally, testing shows that there can't be more than one simultaneous
+DLPI user per network interface.
+
+If you use Linux, this version of libpcap is known to compile and run
+under Red Hat 4.0 with the 2.0.25 kernel. It may work with earlier 2.X
+versions but is guaranteed not to work with 1.X kernels. Running more
+than one libpcap program at a time, on a system with a 2.0.X kernel, can
+cause problems since promiscuous mode is implemented by twiddling the
+interface flags from the libpcap application; the packet capture
+mechanism in the 2.2 and later kernels doesn't have this problem. Also,
+packet timestamps aren't very good. This appears to be due to haphazard
+handling of the timestamp in the kernel.
+
+Note well: there is rumoured to be a version of tcpdump floating around
+called 3.0.3 that includes libpcap and is supposed to support Linux.
+You should be advised that neither the Network Research Group at LBNL
+nor the Tcpdump Group ever generated a release with this version number.
+The LBNL Network Research Group notes with interest that a standard
+cracker trick to get people to install trojans is to distribute bogus
+packages that have a version number higher than the current release.
+They also noted with annoyance that 90% of the Linux related bug reports
+they got are due to changes made to unofficial versions of their page.
+If you are having trouble but aren't using a version that came from
+tcpdump.org, please try that before submitting a bug report!
+
+On Linux, libpcap will not work if the kernel does not have the packet
+socket option enabled; see the README.linux file for information about
+this.
+
+If you use AIX, you may not be able to build libpcap from this release.
+We do not have an AIX system in house so it's impossible for us to test
+AIX patches submitted to us. We are told that you must link against
+/lib/pse.exp, that you must use AIX cc or a GNU C compiler newer than
+2.7.2, and that you may need to run strload before running a libpcap
+application.
+
+Read the README.aix file for information on installing libpcap and
+configuring your system to be able to support libpcap.
+
+If you use NeXTSTEP, you will not be able to build libpcap from this
+release. We hope to support this operating system in some future
+release of libpcap.
+
+If you use SINIX, you should be able to build libpcap from this
+release. It is known to compile and run on SINIX-Y/N 5.42 with the C-DS
+V1.0 or V1.1 compiler. But note that in some releases of SINIX, yacc
+emits incorrect code; if grammar.y fails to compile, change every
+occurence of:
+
+ #ifdef YYDEBUG
+
+to:
+ #if YYDEBUG
+
+Another workaround is to use flex and bison.
+
+If you use SCO, you might have trouble building libpcap from this
+release. We do not have a machine running SCO and have not had reports
+of anyone successfully building on it. Since SCO apparently supports
+DLPI, it's possible the current version works. Meanwhile, SCO provides
+a tcpdump binary as part of their "Network/Security Tools" package:
+
+ http://www.sco.com/technology/internet/goodies/#SECURITY
+
+There is also a README that explains how to enable packet capture.
+
+If you use UnixWare, you will not be able to build libpcap from this
+release. We hope to support this operating system in some future
+release of libpcap. Meanwhile, there appears to be an UnixWare port of
+libpcap 0.0 (and tcpdump 3.0) in:
+
+ ftp://ftp1.freebird.org/pub/mirror/freebird/internet/systools/
+
+UnixWare appears to use a hacked version of DLPI.
+
+If linking tcpdump fails with "Undefined: _alloca" when using bison on
+a Sun4, your version of bison is broken. In any case version 1.16 or
+higher is recommended (1.14 is known to cause problems 1.16 is known to
+work). Either pick up a current version from:
+
+ ftp://ftp.gnu.org/pub/gnu/bison
+
+or hack around it by inserting the lines:
+
+ #ifdef __GNUC__
+ #define alloca __builtin_alloca
+ #else
+ #ifdef sparc
+ #include <alloca.h>
+ #else
+ char *alloca ();
+ #endif
+ #endif
+
+right after the (100 line!) GNU license comment in bison.simple, remove
+grammar.[co] and fire up make again.
+
+If you use SunOS 4, your kernel must support streams NIT. If you run a
+libpcap program and it dies with:
+
+ /dev/nit: No such device
+
+You must add streams NIT support to your kernel configuration, run
+config and boot the new kernel.
+
+If you are running a version of SunOS earlier than 4.1, you will need
+to replace the Sun supplied /sys/sun{3,4,4c}/OBJ/nit_if.o with the
+appropriate version from this distribution's SUNOS4 subdirectory and
+build a new kernel:
+
+ nit_if.o.sun3-sunos4 (any flavor of sun3)
+ nit_if.o.sun4c-sunos4.0.3c (SS1, SS1+, IPC, SLC, etc.)
+ nit_if.o.sun4-sunos4 (Sun4's not covered by
+ nit_if.o.sun4c-sunos4.0.3c)
+
+These nit replacements fix a bug that makes nit essentially unusable in
+pre-SunOS 4.1. In addition, our sun4c-sunos4.0.3c nit gives you
+timestamps to the resolution of the SS-1 clock (1 us) rather than the
+lousy 20ms timestamps Sun gives you (tcpdump will print out the full
+timestamp resolution if it finds it's running on a SS-1).
+
+FILES
+-----
+CHANGES - description of differences between releases
+FILES - list of files exported as part of the distribution
+INSTALL - this file
+Makefile.in - compilation rules (input to the configure script)
+README - description of distribution
+SUNOS4 - pre-SunOS 4.1 replacement kernel nit modules
+VERSION - version of this release
+aclocal.m4 - autoconf macros
+bpf/net - copies of bpf_filter.c and bpf.h
+bpf_filter.c - symlink to bpf/net/bpf_filter.c
+bpf_image.c - bpf disassembly routine
+config.guess - autoconf support
+config.sub - autoconf support
+configure - configure script (run this first)
+configure.in - configure script source
+etherent.c - /etc/ethers support routines
+ethertype.h - ethernet protocol types and names definitions
+gencode.c - bpf code generation routines
+gencode.h - bpf code generation definitions
+grammar.y - filter string grammar
+inet.c - network routines
+install-sh - BSD style install script
+lbl/gnuc.h - gcc macros and defines
+lbl/os-*.h - os dependent defines and prototypes
+mkdep - construct Makefile dependency list
+nametoaddr.c - hostname to address routines
+net - symlink to bpf/net
+optimize.c - bpf optimization routines
+pcap-bpf.c - BSD Packet Filter support
+pcap-dlpi.c - Data Link Provider Interface support
+pcap-enet.c - enet support
+pcap-int.h - internal libpcap definitions
+pcap-namedb.h - public libpcap name database definitions
+pcap-nit.c - Network Interface Tap support
+pcap-nit.h - Network Interface Tap definitions
+pcap-null.c - dummy monitor support (allows offline use of libpcap)
+pcap-pf.c - Packet Filter support
+pcap-pf.h - Packet Filter definitions
+pcap-snit.c - Streams based Network Interface Tap support
+pcap-snoop.c - Snoop network monitoring support
+pcap.3 - manual entry
+pcap.c - pcap utility routines
+pcap.h - public libpcap definitions
+ppp.h - Point to Point Protocol definitions
+savefile.c - offline support
+scanner.l - filter string scanner
diff --git a/contrib/libpcap/Makefile.in b/contrib/libpcap/Makefile.in
index 600087a..9b0ae79 100644
--- a/contrib/libpcap/Makefile.in
+++ b/contrib/libpcap/Makefile.in
@@ -17,7 +17,7 @@
# WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
# MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
#
-# @(#) $Header: /tcpdump/master/libpcap/Makefile.in,v 1.87.2.1 2001/01/18 04:06:24 guy Exp $ (LBL)
+# @(#) $Header: /tcpdump/master/libpcap/Makefile.in,v 1.88 2001/01/18 04:05:12 guy Exp $ (LBL)
#
# Various configurable paths (remember to edit Makefile.in, not Makefile)
diff --git a/contrib/libpcap/README b/contrib/libpcap/README
index c4161cd..ca6347c 100644
--- a/contrib/libpcap/README
+++ b/contrib/libpcap/README
@@ -1,18 +1,18 @@
-@(#) $Header: /tcpdump/master/libpcap/README,v 1.22 2000/07/13 06:24:14 guy Exp $ (LBL)
+@(#) $Header: /tcpdump/master/libpcap/README,v 1.24 2001/06/05 03:45:55 guy Exp $ (LBL)
-LIBPCAP 0.5
+LIBPCAP 0.6.2
Now maintained by "The Tcpdump Group"
See www.tcpdump.org
Please send inquiries/comments/reports to tcpdump-workers@tcpdump.org
Anonymous CVS is available via:
- cvs -d cvs.tcpdump.org:/tcpdump/master login
+ cvs -d :pserver:tcpdump@cvs.tcpdump.org:/tcpdump/master login
(password "anoncvs")
- cvs -d cvs.tcpdump.org:/tcpdump/master checkout libpcap
+ cvs -d :pserver:tcpdump@cvs.tcpdump.org:/tcpdump/master checkout libpcap
-Version 0.5 of LIBPCAP can be retrived with the CVS tag "libpcap_0_5":
- cvs -d cvs.tcpdump.org:/tcpdump/master checkout -r libpcap_0_5 libpcap
+Version 0.6.2 of LIBPCAP can be retrieved with the CVS tag "libpcap_0_6rel2":
+ cvs -d :pserver:tcpdump@cvs.tcpdump.org:/tcpdump/master checkout -r libpcap_0_6rel2 libpcap
Please send patches against the master copy to patches@tcpdump.org.
diff --git a/contrib/libpcap/README.aix b/contrib/libpcap/README.aix
index c78a40b..ad2ce45 100644
--- a/contrib/libpcap/README.aix
+++ b/contrib/libpcap/README.aix
@@ -1,6 +1,20 @@
-(1) To configure libpcap under AIX 4.x, you should use DLPI instead
- of BPF, since IBM's version of BPF includes some undocumented
- and unsupported changes to the original BPF.
+(1) AIX 4.x's version of BPF is undocumented and somewhat unstandard; the
+ current BPF support code includes changes that should work around
+ that, but, lacking an AIX machine on which to compile it, we don't
+ know whether the BPF support for AIX will compile.
+
+ If it doesn't, or if the workarounds fail to make it work correctly,
+ you should send to tcpdump-workers@tcpdump.org a detailed bug report
+ (if the compile fails, send us the compile error messages; if it
+ compiles but fails to work correctly, send us as detailed as
+ possible a description of the symptoms, including indications of the
+ network link-layer type being wrong or time stamps being wrong).
+
+ If you fix the problems yourself, please send to patches@tcpdump.org
+ a patch, so we can incorporate them into the next release.
+
+ If you don't fix the problems yourself, you can, as a workaround,
+ make libpcap use DLPI instead of BPF.
This can be done by specifying the flag:
@@ -8,39 +22,39 @@
to the "configure" script for libpcap.
-(2) Also, it is a good idea to have the latest version of the DLPI
- driver on your system, since certain versions may be buggy and
- cause your AIX system to crash. DLPI is included in the
- fileset bos.rte.tty. I found that the DLPI driver that came with
- AIX 4.3.2 was buggy, and had to upgrade to bos.rte.tty 4.3.2.4:
+(2) Also, it is a good idea to have the latest version of the DLPI
+ driver on your system, since certain versions may be buggy and
+ cause your AIX system to crash. DLPI is included in the
+ fileset bos.rte.tty. I found that the DLPI driver that came with
+ AIX 4.3.2 was buggy, and had to upgrade to bos.rte.tty 4.3.2.4:
- lslpp -l bos.rte.tty
+ lslpp -l bos.rte.tty
- bos.rte.tty 4.3.2.4 COMMITTED Base TTY Support and Commands
+ bos.rte.tty 4.3.2.4 COMMITTED Base TTY Support and Commands
- Updates for AIX filesets can be obtained from:
- ftp://service.software.ibm.com/aix/fixes/
+ Updates for AIX filesets can be obtained from:
+ ftp://service.software.ibm.com/aix/fixes/
- These updates can be installed with the smit program.
+ These updates can be installed with the smit program.
-(3) After compiling libpcap, you need to make sure that the DLPI driver
- is loaded. Type:
+(3) After compiling libpcap, you need to make sure that the DLPI driver
+ is loaded. Type:
- strload -q -d dlpi
+ strload -q -d dlpi
- If the result is:
- dlpi: yes
+ If the result is:
+ dlpi: yes
- then the DLPI driver is loaded correctly.
+ then the DLPI driver is loaded correctly.
- If it is:
- dlpi: no
+ If it is:
+ dlpi: no
- Then you need to type:
- strload -f /etc/dlpi.conf
+ Then you need to type:
+ strload -f /etc/dlpi.conf
- Check again with strload -q -d dlpi that the dlpi driver is loaded.
+ Check again with strload -q -d dlpi that the dlpi driver is loaded.
- Alternatively, you can uncomment the lines for DLPI in
- /etc/pse.conf and reboot the machine; this way DLPI will always
- be loaded when you boot your system.
+ Alternatively, you can uncomment the lines for DLPI in
+ /etc/pse.conf and reboot the machine; this way DLPI will always
+ be loaded when you boot your system.
diff --git a/contrib/libpcap/README.linux b/contrib/libpcap/README.linux
index ecd00e8..dd95913 100644
--- a/contrib/libpcap/README.linux
+++ b/contrib/libpcap/README.linux
@@ -68,3 +68,21 @@ file says:
Filtering works on all socket types except TCP for now. See the text
file linux/Documentation/networking/filter.txt for more information.
If unsure, say N.
+
+
+Statistics:
+Statistics reported by pcap are platform specific. The statistics
+reported by pcap_stats on Linux are as follows:
+
+2.2.x
+=====
+ps_recv Number of packets that were accepted by the pcap filter
+ps_drops Always 0, this statistic is not gatherd on this platform
+
+2.4.x
+=====
+ps_rec Number of packets that were accepted by the pcap filter
+ps_drops Number of packets that had passed filtering but were not
+ passed on to pcap due to things like buffer shortage, etc.
+ This is useful because these are packets you are interested in
+ but won't be reported by, for example, tcpdump output.
diff --git a/contrib/libpcap/README.tru64 b/contrib/libpcap/README.tru64
new file mode 100644
index 0000000..7fe1ef0
--- /dev/null
+++ b/contrib/libpcap/README.tru64
@@ -0,0 +1,49 @@
+The following instructions are applicable to Tru64 UNIX
+(formerly Digital UNIX (formerly DEC OSF/1)) version 4.0, and
+probably to later versions as well; at least some options apply to
+Digital UNIX 3.2 - perhaps all do.
+
+In order to use kernel packet filtering on this system, you have
+to configure it in such a way:
+
+Kernel configuration
+--------------------
+
+The packet filtering kernel option must be enabled at kernel
+installation. If it was not the case, you can rebuild the kernel with
+"doconfig -c" after adding the following line in the kernel
+configuration file (/sys/conf/<HOSTNAME>):
+
+ option PACKETFILTER
+
+or use "doconfig" without any arguments to add the packet filter driver
+option via the kernel option menu (see the system administration
+documentation for information on how to do this).
+
+Device configuration
+--------------------
+
+Devices used for packet filtering must be created thanks to
+the following command (executed in the /dev directory):
+
+ ./MAKEDEV pfilt
+
+Interface configuration
+-----------------------
+
+In order to capture all packets on a network, you may want to allow
+applications to put the interface on that network into "local copy"
+mode, so that tcpdump can see packets sent by the host on which it's
+running as well as packets received by that host, and to put the
+interface into "promiscuous" mode, so that tcpdump can see packets on
+the network segment not sent to the host on which it's running, by using
+the pfconfig(1) command:
+
+ pfconfig +c +p <network_device>
+
+or allow application to put any interface into "local copy" or
+"promiscuous" mode by using the command:
+
+ pfconfig +c +p -a
+
+Note: all instructions given require root privileges.
diff --git a/contrib/libpcap/TODO b/contrib/libpcap/TODO
index e90b9d8..633a776 100644
--- a/contrib/libpcap/TODO
+++ b/contrib/libpcap/TODO
@@ -11,14 +11,14 @@ General
should stick to the standard.
- The source files should be better documented. There is no official
- design guideline what is done where. There should be a common coding
- style (okay, you can guess that bye looking at the code) and a guideline
+ design guideline for what is done where. There should be a common coding
+ style (okay, you can guess that by looking at the code) and a guide for
what needs to be documented.
Linux kernel interface
- Currently there is a race condition in that a socket is activated at the
- same time when it is opened - before applying a filter. This has to
+ same time it is opened - before applying a filter. This has to
be corrected so that capture starts when pcap_read is called for the
first time.
@@ -28,9 +28,13 @@ Less urgent items
- Better documentation and cleanup of the interface. I am seeing a few
problems at the first glance which needs fixing:
+ pcap_lookupnet makes little to no sense with protocols != IPv4
- + not very suited for interactive programs (think ethereal). There should
- be a way for the application to get a file descriptor which it has to
- monitor and a callback in pcap which has to be called on activity
+ + not very well suited for interactive programs (think ethereal). There
+ should be a way for the application to get a file descriptor which it
+ has to monitor and a callback in pcap which has to be called on
+ activity (XXX - "pcap_fileno()" handles the first part, although
+ "select()" and "poll()" don't work on BPF devices on most BSDs, and
+ you can call "pcap_dispatch()" as the dispatch routine after putting
+ the descriptor into non-blocking mode)
+ too many functions. There are a lot of functions for everything which
violates the KISS principle. Why do we need pcap_strerror, pcap_perror
and pcap_geterr?
diff --git a/contrib/libpcap/VERSION b/contrib/libpcap/VERSION
index 5a2a580..eb49d7c 100644
--- a/contrib/libpcap/VERSION
+++ b/contrib/libpcap/VERSION
@@ -1 +1 @@
-0.6
+0.7
diff --git a/contrib/libpcap/acconfig.h b/contrib/libpcap/acconfig.h
new file mode 100644
index 0000000..a23f320
--- /dev/null
+++ b/contrib/libpcap/acconfig.h
@@ -0,0 +1,7 @@
+/* Long story short: aclocal.m4 depends on autoconf 2.13
+ * implementation details wrt "const"; newer versions
+ * have different implementation details so for now we
+ * put "const" here. This may cause duplicate definitions
+ * in config.h but that should be OK since they're the same.
+ */
+#undef const
diff --git a/contrib/libpcap/arcnet.h b/contrib/libpcap/arcnet.h
new file mode 100644
index 0000000..dce7335
--- /dev/null
+++ b/contrib/libpcap/arcnet.h
@@ -0,0 +1,52 @@
+/*
+ * Copyright (c) 1982, 1986, 1993
+ * The Regents of the University of California. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ * notice, this list of conditions and the following disclaimer in the
+ * documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ * must display the following acknowledgement:
+ * This product includes software developed by the University of
+ * California, Berkeley and its contributors.
+ * 4. Neither the name of the University nor the names of its contributors
+ * may be used to endorse or promote products derived from this software
+ * without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
+ *
+ * @(#) $Id: arcnet.h,v 1.2 2001/04/24 02:17:52 guy Exp $ (LBL)
+ *
+ * from: NetBSD: if_arc.h,v 1.13 1999/11/19 20:41:19 thorpej Exp
+ */
+
+/* RFC 1051 */
+#define ARCTYPE_IP_OLD 240 /* IP protocol */
+#define ARCTYPE_ARP_OLD 241 /* address resolution protocol */
+
+/* RFC 1201 */
+#define ARCTYPE_IP 212 /* IP protocol */
+#define ARCTYPE_ARP 213 /* address resolution protocol */
+#define ARCTYPE_REVARP 214 /* reverse addr resolution protocol */
+
+#define ARCTYPE_ATALK 221 /* Appletalk */
+#define ARCTYPE_BANIAN 247 /* Banyan Vines */
+#define ARCTYPE_IPX 250 /* Novell IPX */
+
+#define ARCTYPE_INET6 0xc4 /* IPng */
+#define ARCTYPE_DIAGNOSE 0x80 /* as per ANSI/ATA 878.1 */
diff --git a/contrib/libpcap/config.guess b/contrib/libpcap/config.guess
index 980ea5b..ba66165 100755
--- a/contrib/libpcap/config.guess
+++ b/contrib/libpcap/config.guess
@@ -1,9 +1,9 @@
#! /bin/sh
# Attempt to guess a canonical system name.
-# Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000
+# Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001
# Free Software Foundation, Inc.
-timestamp='2000-12-15'
+timestamp='2001-04-20'
# This file is free software; you can redistribute it and/or modify it
# under the terms of the GNU General Public License as published by
@@ -33,10 +33,6 @@ timestamp='2000-12-15'
#
# The plan is that this can be called by configure scripts if you
# don't specify an explicit build system type.
-#
-# Only a few systems have been added to this list; please add others
-# (but try to keep the structure clean).
-#
me=`echo "$0" | sed -e 's,.*/,,'`
@@ -93,7 +89,7 @@ fi
dummy=dummy-$$
-trap 'rm -f $dummy.c $dummy.o $dummy; exit 1' 1 2 15
+trap 'rm -f $dummy.c $dummy.o $dummy.rel $dummy; exit 1' 1 2 15
# CC_FOR_BUILD -- compiler used by this script.
# Historically, `CC_FOR_BUILD' used to be named `HOST_CC'. We still
@@ -107,7 +103,7 @@ case $CC_FOR_BUILD,$HOST_CC,$CC in
CC_FOR_BUILD="$c"; break
fi
done
- rm -f $dummy.c $dummy.o
+ rm -f $dummy.c $dummy.o $dummy.rel
if test x"$CC_FOR_BUILD" = x ; then
CC_FOR_BUILD=no_compiler_found
fi
@@ -276,7 +272,7 @@ EOF
arm:RISC*:1.[012]*:*|arm:riscix:1.[012]*:*)
echo arm-acorn-riscix${UNAME_RELEASE}
exit 0;;
- SR2?01:HI-UX/MPP:*:*)
+ SR2?01:HI-UX/MPP:*:* | SR8000:HI-UX/MPP:*:*)
echo hppa1.1-hitachi-hiuxmpp
exit 0;;
Pyramid*:OSx*:*:* | MIS*:OSx*:*:* | MIS*:SMP_DC-OSx*:*:*)
@@ -412,10 +408,13 @@ EOF
EOF
$CC_FOR_BUILD $dummy.c -o $dummy \
&& ./$dummy `echo "${UNAME_RELEASE}" | sed -n 's/\([0-9]*\).*/\1/p'` \
- && rm $dummy.c $dummy && exit 0
+ && rm -f $dummy.c $dummy && exit 0
rm -f $dummy.c $dummy
echo mips-mips-riscos${UNAME_RELEASE}
exit 0 ;;
+ Motorola:PowerMAX_OS:*:*)
+ echo powerpc-motorola-powermax
+ exit 0 ;;
Night_Hawk:Power_UNIX:*:*)
echo powerpc-harris-powerunix
exit 0 ;;
@@ -463,9 +462,17 @@ EOF
????????:AIX?:[12].1:2) # AIX 2.2.1 or AIX 2.1.1 is RT/PC AIX.
echo romp-ibm-aix # uname -m gives an 8 hex-code CPU id
exit 0 ;; # Note that: echo "'`uname -s`'" gives 'AIX '
- i?86:AIX:*:*)
+ i*86:AIX:*:*)
echo i386-ibm-aix
exit 0 ;;
+ ia64:AIX:*:*)
+ if [ -x /usr/bin/oslevel ] ; then
+ IBM_REV=`/usr/bin/oslevel`
+ else
+ IBM_REV=${UNAME_VERSION}.${UNAME_RELEASE}
+ fi
+ echo ${UNAME_MACHINE}-ibm-aix${IBM_REV}
+ exit 0 ;;
*:AIX:2:3)
if grep bos325 /usr/include/stdio.h >/dev/null 2>&1; then
sed 's/^ //' << EOF >$dummy.c
@@ -479,7 +486,7 @@ EOF
exit(0);
}
EOF
- $CC_FOR_BUILD $dummy.c -o $dummy && ./$dummy && rm $dummy.c $dummy && exit 0
+ $CC_FOR_BUILD $dummy.c -o $dummy && ./$dummy && rm -f $dummy.c $dummy && exit 0
rm -f $dummy.c $dummy
echo rs6000-ibm-aix3.2.5
elif grep bos324 /usr/include/stdio.h >/dev/null 2>&1; then
@@ -488,9 +495,9 @@ EOF
echo rs6000-ibm-aix3.2
fi
exit 0 ;;
- *:AIX:*:4)
+ *:AIX:*:[45])
IBM_CPU_ID=`/usr/sbin/lsdev -C -c processor -S available | head -1 | awk '{ print $1 }'`
- if /usr/sbin/lsattr -EHl ${IBM_CPU_ID} | grep POWER >/dev/null 2>&1; then
+ if /usr/sbin/lsattr -El ${IBM_CPU_ID} | grep ' POWER' >/dev/null 2>&1; then
IBM_ARCH=rs6000
else
IBM_ARCH=powerpc
@@ -498,23 +505,10 @@ EOF
if [ -x /usr/bin/oslevel ] ; then
IBM_REV=`/usr/bin/oslevel`
else
- IBM_REV=4.${UNAME_RELEASE}
+ IBM_REV=${UNAME_VERSION}.${UNAME_RELEASE}
fi
echo ${IBM_ARCH}-ibm-aix${IBM_REV}
exit 0 ;;
- *:AIX:*:5)
- case "`lsattr -El proc0 -a type -F value`" in
- PowerPC*) IBM_ARCH=powerpc
- IBM_MANUF=ibm ;;
- Itanium) IBM_ARCH=ia64
- IBM_MANUF=unknown ;;
- POWER*) IBM_ARCH=power
- IBM_MANUF=ibm ;;
- *) IBM_ARCH=powerpc
- IBM_MANUF=ibm ;;
- esac
- echo ${IBM_ARCH}-${IBM_MANUF}-aix${UNAME_VERSION}.${UNAME_RELEASE}
- exit 0 ;;
*:AIX:*:*)
echo rs6000-ibm-aix
exit 0 ;;
@@ -599,6 +593,10 @@ EOF
esac
echo ${HP_ARCH}-hp-hpux${HPUX_REV}
exit 0 ;;
+ ia64:HP-UX:*:*)
+ HPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'`
+ echo ia64-hp-hpux${HPUX_REV}
+ exit 0 ;;
3050*:HI-UX:*:*)
sed 's/^ //' << EOF >$dummy.c
#include <unistd.h>
@@ -625,7 +623,7 @@ EOF
exit (0);
}
EOF
- $CC_FOR_BUILD $dummy.c -o $dummy && ./$dummy && rm $dummy.c $dummy && exit 0
+ $CC_FOR_BUILD $dummy.c -o $dummy && ./$dummy && rm -f $dummy.c $dummy && exit 0
rm -f $dummy.c $dummy
echo unknown-hitachi-hiuxwe2
exit 0 ;;
@@ -644,7 +642,7 @@ EOF
hp8??:OSF1:*:*)
echo hppa1.0-hp-osf
exit 0 ;;
- i?86:OSF1:*:*)
+ i*86:OSF1:*:*)
if [ -x /usr/sbin/sysversion ] ; then
echo ${UNAME_MACHINE}-unknown-osf1mk
else
@@ -701,18 +699,16 @@ EOF
CRAY-2:*:*:*)
echo cray2-cray-unicos
exit 0 ;;
- F300:UNIX_System_V:*:*)
+ F30[01]:UNIX_System_V:*:* | F700:UNIX_System_V:*:*)
+ FUJITSU_PROC=`uname -m | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'`
FUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\///'`
FUJITSU_REL=`echo ${UNAME_RELEASE} | sed -e 's/ /_/'`
- echo "f300-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}"
+ echo "${FUJITSU_PROC}-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}"
exit 0 ;;
- F301:UNIX_System_V:*:*)
- echo f301-fujitsu-uxpv`echo $UNAME_RELEASE | sed 's/ .*//'`
- exit 0 ;;
hp300:OpenBSD:*:*)
echo m68k-unknown-openbsd${UNAME_RELEASE}
exit 0 ;;
- i?86:BSD/386:*:* | i?86:BSD/OS:*:* | *:Ascend\ Embedded/OS:*:*)
+ i*86:BSD/386:*:* | i*86:BSD/OS:*:* | *:Ascend\ Embedded/OS:*:*)
echo ${UNAME_MACHINE}-pc-bsdi${UNAME_RELEASE}
exit 0 ;;
sparc*:BSD/OS:*:*)
@@ -757,60 +753,38 @@ EOF
i*86:Minix:*:*)
echo ${UNAME_MACHINE}-pc-minix
exit 0 ;;
- *:Linux:*:*)
-
- # The BFD linker knows what the default object file format is, so
- # first see if it will tell us. cd to the root directory to prevent
- # problems with other programs or directories called `ld' in the path.
- ld_supported_emulations=`cd /; ld --help 2>&1 \
- | sed -ne '/supported emulations:/!d
- s/[ ][ ]*/ /g
- s/.*supported emulations: *//
- s/ .*//
- p'`
- case "$ld_supported_emulations" in
- *ia64)
- echo "${UNAME_MACHINE}-unknown-linux"
- exit 0
- ;;
- i?86linux)
- echo "${UNAME_MACHINE}-pc-linux-gnuaout"
- exit 0
- ;;
- elf_i?86)
- TENTATIVE="${UNAME_MACHINE}-pc-linux-gnu"
- ;;
- i?86coff)
- echo "${UNAME_MACHINE}-pc-linux-gnucoff"
- exit 0
- ;;
- sparclinux)
- echo "${UNAME_MACHINE}-unknown-linux-gnuaout"
- exit 0
- ;;
- elf32_sparc)
- echo "${UNAME_MACHINE}-unknown-linux-gnu"
- exit 0
- ;;
- armlinux)
- echo "${UNAME_MACHINE}-unknown-linux-gnuaout"
- exit 0
- ;;
- elf32arm*)
- echo "${UNAME_MACHINE}-unknown-linux-gnuoldld"
- exit 0
- ;;
- armelf_linux*)
- echo "${UNAME_MACHINE}-unknown-linux-gnu"
- exit 0
- ;;
- m68klinux)
- echo "${UNAME_MACHINE}-unknown-linux-gnuaout"
- exit 0
- ;;
- elf32ppc | elf32ppclinux)
- # Determine Lib Version
- cat >$dummy.c <<EOF
+ arm*:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-gnu
+ exit 0 ;;
+ ia64:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux
+ exit 0 ;;
+ m68*:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-gnu
+ exit 0 ;;
+ mips:Linux:*:*)
+ cat >$dummy.c <<EOF
+#ifdef __cplusplus
+#include <stdio.h> /* for printf() prototype */
+int main (int argc, char *argv[]) {
+#else
+int main (argc, argv) int argc; char *argv[]; {
+#endif
+#ifdef __MIPSEB__
+ printf ("%s-unknown-linux-gnu\n", argv[1]);
+#endif
+#ifdef __MIPSEL__
+ printf ("%sel-unknown-linux-gnu\n", argv[1]);
+#endif
+ return 0;
+}
+EOF
+ $CC_FOR_BUILD $dummy.c -o $dummy 2>/dev/null && ./$dummy "${UNAME_MACHINE}" && rm -f $dummy.c $dummy && exit 0
+ rm -f $dummy.c $dummy
+ ;;
+ ppc:Linux:*:*)
+ # Determine Lib Version
+ cat >$dummy.c <<EOF
#include <features.h>
#if defined(__GLIBC__)
extern char __libc_version[];
@@ -823,143 +797,127 @@ main(argc, argv)
#if defined(__GLIBC__)
printf("%s %s\n", __libc_version, __libc_release);
#else
- printf("unkown\n");
+ printf("unknown\n");
#endif
return 0;
}
EOF
- LIBC=""
- $CC_FOR_BUILD $dummy.c -o $dummy 2>/dev/null
+ LIBC=""
+ $CC_FOR_BUILD $dummy.c -o $dummy 2>/dev/null
+ if test "$?" = 0 ; then
+ ./$dummy | grep 1\.99 > /dev/null
+ if test "$?" = 0 ; then LIBC="libc1" ; fi
+ fi
+ rm -f $dummy.c $dummy
+ echo powerpc-unknown-linux-gnu${LIBC}
+ exit 0 ;;
+ alpha:Linux:*:*)
+ cat <<EOF >$dummy.s
+ .data
+ \$Lformat:
+ .byte 37,100,45,37,120,10,0 # "%d-%x\n"
+ .text
+ .globl main
+ .align 4
+ .ent main
+ main:
+ .frame \$30,16,\$26,0
+ ldgp \$29,0(\$27)
+ .prologue 1
+ .long 0x47e03d80 # implver \$0
+ lda \$2,-1
+ .long 0x47e20c21 # amask \$2,\$1
+ lda \$16,\$Lformat
+ mov \$0,\$17
+ not \$1,\$18
+ jsr \$26,printf
+ ldgp \$29,0(\$26)
+ mov 0,\$16
+ jsr \$26,exit
+ .end main
+EOF
+ LIBC=""
+ $CC_FOR_BUILD $dummy.s -o $dummy 2>/dev/null
+ if test "$?" = 0 ; then
+ case `./$dummy` in
+ 0-0) UNAME_MACHINE="alpha" ;;
+ 1-0) UNAME_MACHINE="alphaev5" ;;
+ 1-1) UNAME_MACHINE="alphaev56" ;;
+ 1-101) UNAME_MACHINE="alphapca56" ;;
+ 2-303) UNAME_MACHINE="alphaev6" ;;
+ 2-307) UNAME_MACHINE="alphaev67" ;;
+ esac
+ objdump --private-headers $dummy | \
+ grep ld.so.1 > /dev/null
if test "$?" = 0 ; then
- ./$dummy | grep 1\.99 > /dev/null
- if test "$?" = 0 ; then
- LIBC="libc1"
- fi
+ LIBC="libc1"
fi
- rm -f $dummy.c $dummy
- echo powerpc-unknown-linux-gnu${LIBC}
+ fi
+ rm -f $dummy.s $dummy
+ echo ${UNAME_MACHINE}-unknown-linux-gnu${LIBC}
+ exit 0 ;;
+ parisc:Linux:*:* | hppa:Linux:*:*)
+ # Look for CPU level
+ case `grep '^cpu[^a-z]*:' /proc/cpuinfo 2>/dev/null | cut -d' ' -f2` in
+ PA7*) echo hppa1.1-unknown-linux-gnu ;;
+ PA8*) echo hppa2.0-unknown-linux-gnu ;;
+ *) echo hppa-unknown-linux-gnu ;;
+ esac
+ exit 0 ;;
+ parisc64:Linux:*:* | hppa64:Linux:*:*)
+ echo hppa64-unknown-linux-gnu
+ exit 0 ;;
+ s390:Linux:*:* | s390x:Linux:*:*)
+ echo ${UNAME_MACHINE}-ibm-linux
+ exit 0 ;;
+ sh*:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-gnu
+ exit 0 ;;
+ sparc:Linux:*:* | sparc64:Linux:*:*)
+ echo ${UNAME_MACHINE}-unknown-linux-gnu
+ exit 0 ;;
+ x86_64:Linux:*:*)
+ echo x86_64-unknown-linux-gnu
+ exit 0 ;;
+ i*86:Linux:*:*)
+ # The BFD linker knows what the default object file format is, so
+ # first see if it will tell us. cd to the root directory to prevent
+ # problems with other programs or directories called `ld' in the path.
+ ld_supported_emulations=`cd /; ld --help 2>&1 \
+ | sed -ne '/supported emulations:/!d
+ s/[ ][ ]*/ /g
+ s/.*supported emulations: *//
+ s/ .*//
+ p'`
+ case "$ld_supported_emulations" in
+ i*86linux)
+ echo "${UNAME_MACHINE}-pc-linux-gnuaout"
exit 0
;;
- shelf_linux)
- echo "${UNAME_MACHINE}-unknown-linux-gnu"
+ elf_i*86)
+ TENTATIVE="${UNAME_MACHINE}-pc-linux-gnu"
+ ;;
+ i*86coff)
+ echo "${UNAME_MACHINE}-pc-linux-gnucoff"
exit 0
;;
esac
-
- if test "${UNAME_MACHINE}" = "alpha" ; then
- cat <<EOF >$dummy.s
- .data
- \$Lformat:
- .byte 37,100,45,37,120,10,0 # "%d-%x\n"
-
- .text
- .globl main
- .align 4
- .ent main
- main:
- .frame \$30,16,\$26,0
- ldgp \$29,0(\$27)
- .prologue 1
- .long 0x47e03d80 # implver \$0
- lda \$2,-1
- .long 0x47e20c21 # amask \$2,\$1
- lda \$16,\$Lformat
- mov \$0,\$17
- not \$1,\$18
- jsr \$26,printf
- ldgp \$29,0(\$26)
- mov 0,\$16
- jsr \$26,exit
- .end main
-EOF
- LIBC=""
- $CC_FOR_BUILD $dummy.s -o $dummy 2>/dev/null
- if test "$?" = 0 ; then
- case `./$dummy` in
- 0-0)
- UNAME_MACHINE="alpha"
- ;;
- 1-0)
- UNAME_MACHINE="alphaev5"
- ;;
- 1-1)
- UNAME_MACHINE="alphaev56"
- ;;
- 1-101)
- UNAME_MACHINE="alphapca56"
- ;;
- 2-303)
- UNAME_MACHINE="alphaev6"
- ;;
- 2-307)
- UNAME_MACHINE="alphaev67"
- ;;
- esac
-
- objdump --private-headers $dummy | \
- grep ld.so.1 > /dev/null
- if test "$?" = 0 ; then
- LIBC="libc1"
- fi
- fi
- rm -f $dummy.s $dummy
- echo ${UNAME_MACHINE}-unknown-linux-gnu${LIBC} ; exit 0
- elif test "${UNAME_MACHINE}" = "mips" ; then
- cat >$dummy.c <<EOF
-#ifdef __cplusplus
-#include <stdio.h> /* for printf() prototype */
- int main (int argc, char *argv[]) {
-#else
- int main (argc, argv) int argc; char *argv[]; {
-#endif
-#ifdef __MIPSEB__
- printf ("%s-unknown-linux-gnu\n", argv[1]);
-#endif
-#ifdef __MIPSEL__
- printf ("%sel-unknown-linux-gnu\n", argv[1]);
-#endif
- return 0;
-}
-EOF
- $CC_FOR_BUILD $dummy.c -o $dummy 2>/dev/null && ./$dummy "${UNAME_MACHINE}" && rm $dummy.c $dummy && exit 0
- rm -f $dummy.c $dummy
- elif test "${UNAME_MACHINE}" = "s390"; then
- echo s390-ibm-linux && exit 0
- elif test "${UNAME_MACHINE}" = "x86_64"; then
- echo x86_64-unknown-linux-gnu && exit 0
- elif test "${UNAME_MACHINE}" = "parisc" -o "${UNAME_MACHINE}" = "hppa"; then
- # Look for CPU level
- case `grep '^cpu[^a-z]*:' /proc/cpuinfo 2>/dev/null | cut -d' ' -f2` in
- PA7*)
- echo hppa1.1-unknown-linux-gnu
- ;;
- PA8*)
- echo hppa2.0-unknown-linux-gnu
- ;;
- *)
- echo hppa-unknown-linux-gnu
- ;;
- esac
- exit 0
- else
- # Either a pre-BFD a.out linker (linux-gnuoldld)
- # or one that does not give us useful --help.
- # GCC wants to distinguish between linux-gnuoldld and linux-gnuaout.
- # If ld does not provide *any* "supported emulations:"
- # that means it is gnuoldld.
- test -z "$ld_supported_emulations" \
- && echo "${UNAME_MACHINE}-pc-linux-gnuoldld" && exit 0
-
- case "${UNAME_MACHINE}" in
- i?86)
- VENDOR=pc;
- ;;
- *)
- VENDOR=unknown;
- ;;
- esac
- # Determine whether the default compiler is a.out or elf
- cat >$dummy.c <<EOF
+ # Either a pre-BFD a.out linker (linux-gnuoldld)
+ # or one that does not give us useful --help.
+ # GCC wants to distinguish between linux-gnuoldld and linux-gnuaout.
+ # If ld does not provide *any* "supported emulations:"
+ # that means it is gnuoldld.
+ test -z "$ld_supported_emulations" && echo "${UNAME_MACHINE}-pc-linux-gnuoldld" && exit 0
+ case "${UNAME_MACHINE}" in
+ i*86)
+ VENDOR=pc;
+ ;;
+ *)
+ VENDOR=unknown;
+ ;;
+ esac
+ # Determine whether the default compiler is a.out or elf
+ cat >$dummy.c <<EOF
#include <features.h>
#ifdef __cplusplus
#include <stdio.h> /* for printf() prototype */
@@ -983,16 +941,16 @@ EOF
return 0;
}
EOF
- $CC_FOR_BUILD $dummy.c -o $dummy 2>/dev/null && ./$dummy "${UNAME_MACHINE}" && rm $dummy.c $dummy && exit 0
- rm -f $dummy.c $dummy
- test x"${TENTATIVE}" != x && echo "${TENTATIVE}" && exit 0
- fi ;;
+ $CC_FOR_BUILD $dummy.c -o $dummy 2>/dev/null && ./$dummy "${UNAME_MACHINE}" && rm -f $dummy.c $dummy && exit 0
+ rm -f $dummy.c $dummy
+ test x"${TENTATIVE}" != x && echo "${TENTATIVE}" && exit 0
+ ;;
# ptx 4.0 does uname -s correctly, with DYNIX/ptx in there. earlier versions
# are messed up and put the nodename in both sysname and nodename.
- i?86:DYNIX/ptx:4*:*)
+ i*86:DYNIX/ptx:4*:*)
echo i386-sequent-sysv4
exit 0 ;;
- i?86:UNIX_SV:4.2MP:2.*)
+ i*86:UNIX_SV:4.2MP:2.*)
# Unixware is an offshoot of SVR4, but it has its own version
# number series starting with 2...
# I am not positive that other SVR4 systems won't match this,
@@ -1000,7 +958,7 @@ EOF
# Use sysv4.2uw... so that sysv4* matches it.
echo ${UNAME_MACHINE}-pc-sysv4.2uw${UNAME_VERSION}
exit 0 ;;
- i?86:*:4.*:* | i?86:SYSTEM_V:4.*:*)
+ i*86:*:4.*:* | i*86:SYSTEM_V:4.*:*)
UNAME_REL=`echo ${UNAME_RELEASE} | sed 's/\/MP$//'`
if grep Novell /usr/include/link.h >/dev/null 2>/dev/null; then
echo ${UNAME_MACHINE}-univel-sysv${UNAME_REL}
@@ -1008,7 +966,7 @@ EOF
echo ${UNAME_MACHINE}-pc-sysv${UNAME_REL}
fi
exit 0 ;;
- i?86:*:5:7*)
+ i*86:*:5:7*)
# Fixed at (any) Pentium or better
UNAME_MACHINE=i586
if [ ${UNAME_SYSTEM} = "UnixWare" ] ; then
@@ -1017,7 +975,7 @@ EOF
echo ${UNAME_MACHINE}-pc-sysv${UNAME_RELEASE}
fi
exit 0 ;;
- i?86:*:3.2:*)
+ i*86:*:3.2:*)
if test -f /usr/options/cb.name; then
UNAME_REL=`sed -n 's/.*Version //p' </usr/options/cb.name`
echo ${UNAME_MACHINE}-pc-isc$UNAME_REL
@@ -1035,7 +993,7 @@ EOF
echo ${UNAME_MACHINE}-pc-sysv32
fi
exit 0 ;;
- i?86:*DOS:*:*)
+ i*86:*DOS:*:*)
echo ${UNAME_MACHINE}-pc-msdosdjgpp
exit 0 ;;
pc:*:*:*)
@@ -1074,21 +1032,24 @@ EOF
3[34]??:*:4.0:* | 3[34]??,*:*:4.0:*)
/bin/uname -p 2>/dev/null | grep 86 >/dev/null \
&& echo i486-ncr-sysv4 && exit 0 ;;
- m68*:LynxOS:2.*:*)
+ m68*:LynxOS:2.*:* | m68*:LynxOS:3.0*:*)
echo m68k-unknown-lynxos${UNAME_RELEASE}
exit 0 ;;
mc68030:UNIX_System_V:4.*:*)
echo m68k-atari-sysv4
exit 0 ;;
- i?86:LynxOS:2.*:* | i?86:LynxOS:3.[01]*:*)
+ i*86:LynxOS:2.*:* | i*86:LynxOS:3.[01]*:* | i*86:LynxOS:4.0*:*)
echo i386-unknown-lynxos${UNAME_RELEASE}
exit 0 ;;
TSUNAMI:LynxOS:2.*:*)
echo sparc-unknown-lynxos${UNAME_RELEASE}
exit 0 ;;
- rs6000:LynxOS:2.*:* | PowerPC:LynxOS:2.*:*)
+ rs6000:LynxOS:2.*:*)
echo rs6000-unknown-lynxos${UNAME_RELEASE}
exit 0 ;;
+ PowerPC:LynxOS:2.*:* | PowerPC:LynxOS:3.[01]*:* | PowerPC:LynxOS:4.0*:*)
+ echo powerpc-unknown-lynxos${UNAME_RELEASE}
+ exit 0 ;;
SM[BE]S:UNIX_SV:*:*)
echo mips-dde-sysv${UNAME_RELEASE}
exit 0 ;;
@@ -1188,11 +1149,29 @@ EOF
fi
echo ${UNAME_MACHINE}-unknown-plan9
exit 0 ;;
- i?86:OS/2:*:*)
+ i*86:OS/2:*:*)
# If we were able to find `uname', then EMX Unix compatibility
# is probably installed.
echo ${UNAME_MACHINE}-pc-os2-emx
exit 0 ;;
+ *:TOPS-10:*:*)
+ echo pdp10-unknown-tops10
+ exit 0 ;;
+ *:TENEX:*:*)
+ echo pdp10-unknown-tenex
+ exit 0 ;;
+ KS10:TOPS-20:*:* | KL10:TOPS-20:*:* | TYPE4:TOPS-20:*:*)
+ echo pdp10-dec-tops20
+ exit 0 ;;
+ XKL-1:TOPS-20:*:* | TYPE5:TOPS-20:*:*)
+ echo pdp10-xkl-tops20
+ exit 0 ;;
+ *:TOPS-20:*:*)
+ echo pdp10-unknown-tops20
+ exit 0 ;;
+ *:ITS:*:*)
+ echo pdp10-unknown-its
+ exit 0 ;;
esac
#echo '(No uname command or uname output not recognized.)' 1>&2
@@ -1284,11 +1263,24 @@ main ()
#endif
#if defined (vax)
-#if !defined (ultrix)
- printf ("vax-dec-bsd\n"); exit (0);
-#else
- printf ("vax-dec-ultrix\n"); exit (0);
-#endif
+# if !defined (ultrix)
+# include <sys/param.h>
+# if defined (BSD)
+# if BSD == 43
+ printf ("vax-dec-bsd4.3\n"); exit (0);
+# else
+# if BSD == 199006
+ printf ("vax-dec-bsd4.3reno\n"); exit (0);
+# else
+ printf ("vax-dec-bsd\n"); exit (0);
+# endif
+# endif
+# else
+ printf ("vax-dec-bsd\n"); exit (0);
+# endif
+# else
+ printf ("vax-dec-ultrix\n"); exit (0);
+# endif
#endif
#if defined (alliant) && defined (i860)
@@ -1299,7 +1291,7 @@ main ()
}
EOF
-$CC_FOR_BUILD $dummy.c -o $dummy 2>/dev/null && ./$dummy && rm $dummy.c $dummy && exit 0
+$CC_FOR_BUILD $dummy.c -o $dummy 2>/dev/null && ./$dummy && rm -f $dummy.c $dummy && exit 0
rm -f $dummy.c $dummy
# Apollos put the system type in the environment.
@@ -1335,8 +1327,9 @@ fi
cat >&2 <<EOF
$0: unable to guess system type
-The $version version of this script cannot recognize your system type.
-Please download the most up to date version of the config scripts:
+This script, last modified $timestamp, has failed to recognize
+the operating system you are using. It is advised that you
+download the most up to date version of the config scripts from
ftp://ftp.gnu.org/pub/gnu/config/
@@ -1345,7 +1338,7 @@ send the following data and any information you think might be
pertinent to <config-patches@gnu.org> in order to provide the needed
information to handle your system.
-config.guess version = $version
+config.guess timestamp = $timestamp
uname -m = `(uname -m) 2>/dev/null || echo unknown`
uname -r = `(uname -r) 2>/dev/null || echo unknown`
diff --git a/contrib/libpcap/config.h.in b/contrib/libpcap/config.h.in
index f012a9d..dfa7b36 100644
--- a/contrib/libpcap/config.h.in
+++ b/contrib/libpcap/config.h.in
@@ -6,12 +6,17 @@
/* Define as __inline if that's what the C compiler calls it. */
#undef inline
+/* Long story short: aclocal.m4 depends on autoconf 2.13
+ * implementation details wrt "const"; newer versions
+ * have different implementation details so for now we
+ * put "const" here. This may cause duplicate definitions
+ * in config.h but that should be OK since they're the same.
+ */
+#undef const
+
/* Define if you have the ether_hostton function. */
#undef HAVE_ETHER_HOSTTON
-/* Define if you have the freeifaddrs function. */
-#undef HAVE_FREEIFADDRS
-
/* Define if you have the strerror function. */
#undef HAVE_STRERROR
@@ -21,12 +26,12 @@
/* Define if you have the <ifaddrs.h> header file. */
#undef HAVE_IFADDRS_H
+/* Define if you have the <limits.h> header file. */
+#undef HAVE_LIMITS_H
+
/* Define if you have the <netinet/if_ether.h> header file. */
#undef HAVE_NETINET_IF_ETHER_H
-/* Define if you have the <netpacket/packet.h> header file. */
-#undef HAVE_NETPACKET_PACKET_H
-
/* Define if you have the <sys/bufmod.h> header file. */
#undef HAVE_SYS_BUFMOD_H
@@ -60,12 +65,24 @@
/* IPv6 */
#undef INET6
+/* Enable optimizer debugging */
+#undef BDEBUG
+
+/* Enable parser debugging */
+#undef YYDEBUG
+
/* define if you have a /dev/dlpi */
#undef HAVE_DEV_DLPI
/* /dev/dlpi directory */
#undef PCAP_DEV_PREFIX
+/* if if_packet.h has tpacket_stats defined */
+#undef HAVE_TPACKET_STATS
+
+/* define if you have a /proc/net/dev */
+#undef HAVE_PROC_NET_DEV
+
/* define on AIX to get certain functions */
#undef _SUN
diff --git a/contrib/libpcap/config.sub b/contrib/libpcap/config.sub
index 4849dfd..a06a480 100755
--- a/contrib/libpcap/config.sub
+++ b/contrib/libpcap/config.sub
@@ -1,9 +1,9 @@
#! /bin/sh
# Configuration validation subroutine script.
-# Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000
+# Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001
# Free Software Foundation, Inc.
-timestamp='2000-12-15'
+timestamp='2001-04-20'
# This file is (in principle) common to ALL GNU software.
# The presence of a machine in this file suggests that SOME GNU software
@@ -69,7 +69,7 @@ Report bugs and patches to <config-patches@gnu.org>."
version="\
GNU config.sub ($timestamp)
-Copyright (C) 1992, 93, 94, 95, 96, 97, 98, 99, 2000
+Copyright (C) 1992, 1993, 1994, 1995, 1996, 1997, 1998, 1999, 2000, 2001
Free Software Foundation, Inc.
This is free software; see the source for copying conditions. There is NO
@@ -117,7 +117,7 @@ esac
# Here we must recognize all the valid KERNEL-OS combinations.
maybe_os=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\2/'`
case $maybe_os in
- nto-qnx* | linux-gnu* | storm-chaos*)
+ nto-qnx* | linux-gnu* | storm-chaos* | os2-emx*)
os=-$maybe_os
basic_machine=`echo $1 | sed 's/^\(.*\)-\([^-]*-[^-]*\)$/\1/'`
;;
@@ -226,12 +226,15 @@ case $basic_machine in
| alphaev6[78] \
| we32k | ns16k | clipper | i370 | sh | sh[34] \
| powerpc | powerpcle \
- | 1750a | dsp16xx | pdp11 | mips16 | mips64 | mipsel | mips64el \
+ | 1750a | dsp16xx | pdp10 | pdp11 \
+ | mips16 | mips64 | mipsel | mips64el \
| mips64orion | mips64orionel | mipstx39 | mipstx39el \
| mips64vr4300 | mips64vr4300el | mips64vr4100 | mips64vr4100el \
- | mips64vr5000 | miprs64vr5000el | mcore \
- | sparc | sparclet | sparclite | sparc64 | sparcv9 | v850 | c4x \
- | thumb | d10v | d30v | fr30 | avr)
+ | mips64vr5000 | miprs64vr5000el | mcore | s390 | s390x \
+ | sparc | sparclet | sparclite | sparc64 | sparcv9 | sparcv9b \
+ | v850 | c4x \
+ | thumb | d10v | d30v | fr30 | avr | openrisc | tic80 \
+ | pj | pjl | h8500)
basic_machine=$basic_machine-unknown
;;
m6811 | m68hc11 | m6812 | m68hc12)
@@ -239,13 +242,13 @@ case $basic_machine in
basic_machine=$basic_machine-unknown
os=-none
;;
- m88110 | m680[12346]0 | m683?2 | m68360 | m5200 | z8k | v70 | h8500 | w65 | pj | pjl)
+ m88110 | m680[12346]0 | m683?2 | m68360 | m5200 | z8k | v70 | w65)
;;
# We use `pc' rather than `unknown'
# because (1) that's what they normally are, and
# (2) the word "unknown" tends to confuse beginning users.
- i[234567]86 | x86_64)
+ i*86 | x86_64)
basic_machine=$basic_machine-pc
;;
# Object if more than one company name word.
@@ -255,7 +258,7 @@ case $basic_machine in
;;
# Recognize the basic CPU types with company name.
# FIXME: clean up the formatting here.
- vax-* | tahoe-* | i[234567]86-* | i860-* | ia64-* | m32r-* | m68k-* | m68000-* \
+ vax-* | tahoe-* | i*86-* | i860-* | ia64-* | m32r-* | m68k-* | m68000-* \
| m88k-* | sparc-* | ns32k-* | fx80-* | arc-* | c[123]* \
| arm-* | armbe-* | armle-* | armv*-* | strongarm-* | xscale-* \
| mips-* | pyramid-* | tron-* | a29k-* | romp-* | rs6000-* \
@@ -268,15 +271,17 @@ case $basic_machine in
| alphaev6[78]-* \
| we32k-* | cydra-* | ns16k-* | pn-* | np1-* | xps100-* \
| clipper-* | orion-* \
- | sparclite-* | pdp11-* | sh-* | powerpc-* | powerpcle-* \
- | sparc64-* | sparcv9-* | sparc86x-* | mips16-* | mips64-* | mipsel-* \
+ | sparclite-* | pdp10-* | pdp11-* | sh-* | powerpc-* | powerpcle-* \
+ | sparc64-* | sparcv9-* | sparcv9b-* | sparc86x-* \
+ | mips16-* | mips64-* | mipsel-* \
| mips64el-* | mips64orion-* | mips64orionel-* \
| mips64vr4100-* | mips64vr4100el-* | mips64vr4300-* | mips64vr4300el-* \
| mipstx39-* | mipstx39el-* | mcore-* \
- | f30[01]-* | s390-* | sv1-* | t3e-* \
+ | f30[01]-* | f700-* | s390-* | s390x-* | sv1-* | t3e-* \
+ | [cjt]90-* \
| m88110-* | m680[01234]0-* | m683?2-* | m68360-* | z8k-* | d10v-* \
- | thumb-* | v850-* | d30v-* | tic30-* | c30-* | fr30-* \
- | bs2000-* | tic54x-* | c54x-* | x86_64-*)
+ | thumb-* | v850-* | d30v-* | tic30-* | tic80-* | c30-* | fr30-* \
+ | bs2000-* | tic54x-* | c54x-* | x86_64-* | pj-* | pjl-*)
;;
# Recognize the various machine names and aliases which stand
# for a CPU type and a company and sometimes even an OS.
@@ -367,8 +372,8 @@ case $basic_machine in
basic_machine=cray2-cray
os=-unicos
;;
- [ctj]90-cray)
- basic_machine=c90-cray
+ [cjt]90)
+ basic_machine=${basic_machine}-cray
os=-unicos
;;
crds | unos)
@@ -424,6 +429,10 @@ case $basic_machine in
basic_machine=tron-gmicro
os=-sysv
;;
+ go32)
+ basic_machine=i386-pc
+ os=-go32
+ ;;
h3050r* | hiux*)
basic_machine=hppa1.1-hitachi
os=-hiuxwe2
@@ -499,19 +508,19 @@ case $basic_machine in
basic_machine=i370-ibm
;;
# I'm not sure what "Sysv32" means. Should this be sysv3.2?
- i[34567]86v32)
+ i*86v32)
basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
os=-sysv32
;;
- i[34567]86v4*)
+ i*86v4*)
basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
os=-sysv4
;;
- i[34567]86v)
+ i*86v)
basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
os=-sysv
;;
- i[34567]86sol2)
+ i*86sol2)
basic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`
os=-solaris2
;;
@@ -523,18 +532,6 @@ case $basic_machine in
basic_machine=i386-unknown
os=-vsta
;;
- i386-go32 | go32)
- basic_machine=i386-unknown
- os=-go32
- ;;
- i386-mingw32 | mingw32)
- basic_machine=i386-unknown
- os=-mingw32
- ;;
- i[34567]86-pw32 | pw32)
- basic_machine=i586-unknown
- os=-pw32
- ;;
iris | iris4d)
basic_machine=mips-sgi
case $os in
@@ -560,6 +557,10 @@ case $basic_machine in
basic_machine=ns32k-utek
os=-sysv
;;
+ mingw32)
+ basic_machine=i386-pc
+ os=-mingw32
+ ;;
miniframe)
basic_machine=m68000-convergent
;;
@@ -590,7 +591,7 @@ case $basic_machine in
os=-coff
;;
msdos)
- basic_machine=i386-unknown
+ basic_machine=i386-pc
os=-msdos
;;
mvs)
@@ -729,6 +730,10 @@ case $basic_machine in
ps2)
basic_machine=i386-ibm
;;
+ pw32)
+ basic_machine=i586-unknown
+ os=-pw32
+ ;;
rom68k)
basic_machine=m68k-rom68k
os=-coff
@@ -919,6 +924,10 @@ case $basic_machine in
vax)
basic_machine=vax-dec
;;
+ pdp10)
+ # there are many clones, so DEC is not a safe bet
+ basic_machine=pdp10-unknown
+ ;;
pdp11)
basic_machine=pdp11-dec
;;
@@ -928,7 +937,7 @@ case $basic_machine in
sh3 | sh4)
basic_machine=sh-unknown
;;
- sparc | sparcv9)
+ sparc | sparcv9 | sparcv9b)
basic_machine=sparc-sun
;;
cydra)
@@ -950,6 +959,9 @@ case $basic_machine in
basic_machine=c4x-none
os=-coff
;;
+ *-unknown)
+ # Make sure to match an already-canonicalized machine name.
+ ;;
*)
echo Invalid configuration \`$1\': machine \`$basic_machine\' not recognized 1>&2
exit 1
@@ -1009,12 +1021,13 @@ case $os in
| -cygwin* | -pe* | -psos* | -moss* | -proelf* | -rtems* \
| -mingw32* | -linux-gnu* | -uxpv* | -beos* | -mpeix* | -udk* \
| -interix* | -uwin* | -rhapsody* | -darwin* | -opened* \
- | -openstep* | -oskit* | -conix* | -pw32* | -nonstopux* | -storm-chaos*)
+ | -openstep* | -oskit* | -conix* | -pw32* | -nonstopux* \
+ | -storm-chaos* | -tops10* | -tenex* | -tops20* | -its* | -os2*)
# Remember, each alternative MUST END IN *, to match a version number.
;;
-qnx*)
case $basic_machine in
- x86-* | i[34567]86-*)
+ x86-* | i*86-*)
;;
*)
os=-nto$os
@@ -1107,7 +1120,7 @@ case $os in
-xenix)
os=-xenix
;;
- -*mint | -*MiNT)
+ -*mint | -mint[0-9]* | -*MiNT | -MiNT[0-9]*)
os=-mint
;;
-none)
@@ -1141,6 +1154,9 @@ case $basic_machine in
arm*-semi)
os=-aout
;;
+ pdp10-*)
+ os=-tops20
+ ;;
pdp11-*)
os=-none
;;
@@ -1249,7 +1265,7 @@ case $basic_machine in
*-masscomp)
os=-rtu
;;
- f30[01]-fujitsu)
+ f30[01]-fujitsu | f700-fujitsu)
os=-uxpv
;;
*-rom68k)
@@ -1327,7 +1343,7 @@ case $basic_machine in
-mpw* | -macos*)
vendor=apple
;;
- -*mint | -*MiNT)
+ -*mint | -mint[0-9]* | -*MiNT | -MiNT[0-9]*)
vendor=atari
;;
esac
diff --git a/contrib/libpcap/configure b/contrib/libpcap/configure
index dea3a59..65d6393 100755
--- a/contrib/libpcap/configure
+++ b/contrib/libpcap/configure
@@ -1,6 +1,7 @@
#! /bin/sh
-# From configure.in Revision: 1.87.2.1
+# From configure.in Revision: 1.94
+
@@ -55,6 +56,10 @@ ac_help="$ac_help
ac_help="$ac_help
--enable-ipv6 build IPv6-capable version"
ac_help="$ac_help
+ --enable-optimizer-dbg build optimizer debugging code"
+ac_help="$ac_help
+ --enable-yydebug build parser debugging code"
+ac_help="$ac_help
--without-flex don't use flex"
ac_help="$ac_help
--without-bison don't use bison"
@@ -616,7 +621,7 @@ else { echo "configure: error: can not run $ac_config_sub" 1>&2; exit 1; }
fi
echo $ac_n "checking host system type""... $ac_c" 1>&6
-echo "configure:620: checking host system type" >&5
+echo "configure:625: checking host system type" >&5
host_alias=$host
case "$host_alias" in
@@ -637,7 +642,7 @@ host_os=`echo $host | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\3/'`
echo "$ac_t""$host" 1>&6
echo $ac_n "checking target system type""... $ac_c" 1>&6
-echo "configure:641: checking target system type" >&5
+echo "configure:646: checking target system type" >&5
target_alias=$target
case "$target_alias" in
@@ -655,7 +660,7 @@ target_os=`echo $target | sed 's/^\([^-]*\)-\([^-]*\)-\(.*\)$/\3/'`
echo "$ac_t""$target" 1>&6
echo $ac_n "checking build system type""... $ac_c" 1>&6
-echo "configure:659: checking build system type" >&5
+echo "configure:664: checking build system type" >&5
build_alias=$build
case "$build_alias" in
@@ -703,7 +708,7 @@ fi
# Extract the first word of "shlicc2", so it can be a program name with args.
set dummy shlicc2; ac_word=$2
echo $ac_n "checking for $ac_word""... $ac_c" 1>&6
-echo "configure:707: checking for $ac_word" >&5
+echo "configure:712: checking for $ac_word" >&5
if eval "test \"`echo '$''{'ac_cv_prog_SHLICC2'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
@@ -744,7 +749,7 @@ fi
# Extract the first word of "gcc", so it can be a program name with args.
set dummy gcc; ac_word=$2
echo $ac_n "checking for $ac_word""... $ac_c" 1>&6
-echo "configure:748: checking for $ac_word" >&5
+echo "configure:753: checking for $ac_word" >&5
if eval "test \"`echo '$''{'ac_cv_prog_CC'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
@@ -774,7 +779,7 @@ if test -z "$CC"; then
# Extract the first word of "cc", so it can be a program name with args.
set dummy cc; ac_word=$2
echo $ac_n "checking for $ac_word""... $ac_c" 1>&6
-echo "configure:778: checking for $ac_word" >&5
+echo "configure:783: checking for $ac_word" >&5
if eval "test \"`echo '$''{'ac_cv_prog_CC'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
@@ -825,7 +830,7 @@ fi
# Extract the first word of "cl", so it can be a program name with args.
set dummy cl; ac_word=$2
echo $ac_n "checking for $ac_word""... $ac_c" 1>&6
-echo "configure:829: checking for $ac_word" >&5
+echo "configure:834: checking for $ac_word" >&5
if eval "test \"`echo '$''{'ac_cv_prog_CC'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
@@ -857,7 +862,7 @@ fi
fi
echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works""... $ac_c" 1>&6
-echo "configure:861: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works" >&5
+echo "configure:866: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) works" >&5
ac_ext=c
# CFLAGS is not in ac_cpp because -g, -O, etc. are not valid cpp options.
@@ -868,12 +873,12 @@ cross_compiling=$ac_cv_prog_cc_cross
cat > conftest.$ac_ext << EOF
-#line 872 "configure"
+#line 877 "configure"
#include "confdefs.h"
main(){return(0);}
EOF
-if { (eval echo configure:877: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then
+if { (eval echo configure:882: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then
ac_cv_prog_cc_works=yes
# If we can't run a trivial program, we are probably using a cross compiler.
if (./conftest; exit) 2>/dev/null; then
@@ -899,12 +904,12 @@ if test $ac_cv_prog_cc_works = no; then
{ echo "configure: error: installation or configuration problem: C compiler cannot create executables." 1>&2; exit 1; }
fi
echo $ac_n "checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler""... $ac_c" 1>&6
-echo "configure:903: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler" >&5
+echo "configure:908: checking whether the C compiler ($CC $CFLAGS $LDFLAGS) is a cross-compiler" >&5
echo "$ac_t""$ac_cv_prog_cc_cross" 1>&6
cross_compiling=$ac_cv_prog_cc_cross
echo $ac_n "checking whether we are using GNU C""... $ac_c" 1>&6
-echo "configure:908: checking whether we are using GNU C" >&5
+echo "configure:913: checking whether we are using GNU C" >&5
if eval "test \"`echo '$''{'ac_cv_prog_gcc'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
@@ -913,7 +918,7 @@ else
yes;
#endif
EOF
-if { ac_try='${CC-cc} -E conftest.c'; { (eval echo configure:917: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }; } | egrep yes >/dev/null 2>&1; then
+if { ac_try='${CC-cc} -E conftest.c'; { (eval echo configure:922: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }; } | egrep yes >/dev/null 2>&1; then
ac_cv_prog_gcc=yes
else
ac_cv_prog_gcc=no
@@ -932,7 +937,7 @@ ac_test_CFLAGS="${CFLAGS+set}"
ac_save_CFLAGS="$CFLAGS"
CFLAGS=
echo $ac_n "checking whether ${CC-cc} accepts -g""... $ac_c" 1>&6
-echo "configure:936: checking whether ${CC-cc} accepts -g" >&5
+echo "configure:941: checking whether ${CC-cc} accepts -g" >&5
if eval "test \"`echo '$''{'ac_cv_prog_cc_g'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
@@ -969,7 +974,7 @@ fi
V_CCOPT="-O2"
else
echo $ac_n "checking gcc version""... $ac_c" 1>&6
-echo "configure:973: checking gcc version" >&5
+echo "configure:978: checking gcc version" >&5
if eval "test \"`echo '$''{'ac_cv_lbl_gcc_vers'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
@@ -987,19 +992,19 @@ fi
fi
else
echo $ac_n "checking that $CC handles ansi prototypes""... $ac_c" 1>&6
-echo "configure:991: checking that $CC handles ansi prototypes" >&5
+echo "configure:996: checking that $CC handles ansi prototypes" >&5
if eval "test \"`echo '$''{'ac_cv_lbl_cc_ansi_prototypes'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
cat > conftest.$ac_ext <<EOF
-#line 996 "configure"
+#line 1001 "configure"
#include "confdefs.h"
#include <sys/types.h>
int main() {
int frob(int, char *)
; return 0; }
EOF
-if { (eval echo configure:1003: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
+if { (eval echo configure:1008: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
rm -rf conftest*
ac_cv_lbl_cc_ansi_prototypes=yes
else
@@ -1017,21 +1022,21 @@ fi
hpux*)
echo $ac_n "checking for HP-UX ansi compiler ($CC -Aa -D_HPUX_SOURCE)""... $ac_c" 1>&6
-echo "configure:1021: checking for HP-UX ansi compiler ($CC -Aa -D_HPUX_SOURCE)" >&5
+echo "configure:1026: checking for HP-UX ansi compiler ($CC -Aa -D_HPUX_SOURCE)" >&5
savedcflags="$CFLAGS"
CFLAGS="-Aa -D_HPUX_SOURCE $CFLAGS"
if eval "test \"`echo '$''{'ac_cv_lbl_cc_hpux_cc_aa'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
cat > conftest.$ac_ext <<EOF
-#line 1028 "configure"
+#line 1033 "configure"
#include "confdefs.h"
#include <sys/types.h>
int main() {
int frob(int, char *)
; return 0; }
EOF
-if { (eval echo configure:1035: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
+if { (eval echo configure:1040: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
rm -rf conftest*
ac_cv_lbl_cc_hpux_cc_aa=yes
else
@@ -1075,12 +1080,12 @@ EOF
ultrix*)
echo $ac_n "checking that Ultrix $CC hacks const in prototypes""... $ac_c" 1>&6
-echo "configure:1079: checking that Ultrix $CC hacks const in prototypes" >&5
+echo "configure:1084: checking that Ultrix $CC hacks const in prototypes" >&5
if eval "test \"`echo '$''{'ac_cv_lbl_cc_const_proto'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
cat > conftest.$ac_ext <<EOF
-#line 1084 "configure"
+#line 1089 "configure"
#include "confdefs.h"
#include <sys/types.h>
int main() {
@@ -1088,7 +1093,7 @@ struct a { int b; };
void c(const struct a *)
; return 0; }
EOF
-if { (eval echo configure:1092: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
+if { (eval echo configure:1097: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
rm -rf conftest*
ac_cv_lbl_cc_const_proto=yes
else
@@ -1112,21 +1117,21 @@ EOF
fi
echo $ac_n "checking for inline""... $ac_c" 1>&6
-echo "configure:1116: checking for inline" >&5
+echo "configure:1121: checking for inline" >&5
if eval "test \"`echo '$''{'ac_cv_c_inline'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
ac_cv_c_inline=no
for ac_kw in inline __inline__ __inline; do
cat > conftest.$ac_ext <<EOF
-#line 1123 "configure"
+#line 1128 "configure"
#include "confdefs.h"
int main() {
} $ac_kw foo() {
; return 0; }
EOF
-if { (eval echo configure:1130: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
+if { (eval echo configure:1135: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
rm -rf conftest*
ac_cv_c_inline=$ac_kw; break
else
@@ -1153,13 +1158,13 @@ esac
echo $ac_n "checking for __attribute__""... $ac_c" 1>&6
-echo "configure:1157: checking for __attribute__" >&5
+echo "configure:1162: checking for __attribute__" >&5
if eval "test \"`echo '$''{'ac_cv___attribute__'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
cat > conftest.$ac_ext <<EOF
-#line 1163 "configure"
+#line 1168 "configure"
#include "confdefs.h"
#include <stdlib.h>
@@ -1176,7 +1181,7 @@ foo(void)
; return 0; }
EOF
-if { (eval echo configure:1180: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
+if { (eval echo configure:1185: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
rm -rf conftest*
ac_cv___attribute__=yes
else
@@ -1198,12 +1203,12 @@ echo "$ac_t""$ac_cv___attribute__" 1>&6
echo $ac_n "checking for u_int8_t using $CC""... $ac_c" 1>&6
-echo "configure:1202: checking for u_int8_t using $CC" >&5
+echo "configure:1207: checking for u_int8_t using $CC" >&5
if eval "test \"`echo '$''{'ac_cv_lbl_have_u_int8_t'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
cat > conftest.$ac_ext <<EOF
-#line 1207 "configure"
+#line 1212 "configure"
#include "confdefs.h"
# include "confdefs.h"
@@ -1216,7 +1221,7 @@ int main() {
u_int8_t i
; return 0; }
EOF
-if { (eval echo configure:1220: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
+if { (eval echo configure:1225: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
rm -rf conftest*
ac_cv_lbl_have_u_int8_t=yes
else
@@ -1236,12 +1241,12 @@ EOF
fi
echo $ac_n "checking for u_int16_t using $CC""... $ac_c" 1>&6
-echo "configure:1240: checking for u_int16_t using $CC" >&5
+echo "configure:1245: checking for u_int16_t using $CC" >&5
if eval "test \"`echo '$''{'ac_cv_lbl_have_u_int16_t'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
cat > conftest.$ac_ext <<EOF
-#line 1245 "configure"
+#line 1250 "configure"
#include "confdefs.h"
# include "confdefs.h"
@@ -1254,7 +1259,7 @@ int main() {
u_int16_t i
; return 0; }
EOF
-if { (eval echo configure:1258: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
+if { (eval echo configure:1263: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
rm -rf conftest*
ac_cv_lbl_have_u_int16_t=yes
else
@@ -1274,12 +1279,12 @@ EOF
fi
echo $ac_n "checking for u_int32_t using $CC""... $ac_c" 1>&6
-echo "configure:1278: checking for u_int32_t using $CC" >&5
+echo "configure:1283: checking for u_int32_t using $CC" >&5
if eval "test \"`echo '$''{'ac_cv_lbl_have_u_int32_t'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
cat > conftest.$ac_ext <<EOF
-#line 1283 "configure"
+#line 1288 "configure"
#include "confdefs.h"
# include "confdefs.h"
@@ -1292,7 +1297,7 @@ int main() {
u_int32_t i
; return 0; }
EOF
-if { (eval echo configure:1296: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
+if { (eval echo configure:1301: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
rm -rf conftest*
ac_cv_lbl_have_u_int32_t=yes
else
@@ -1313,7 +1318,7 @@ EOF
fi
echo $ac_n "checking how to run the C preprocessor""... $ac_c" 1>&6
-echo "configure:1317: checking how to run the C preprocessor" >&5
+echo "configure:1322: checking how to run the C preprocessor" >&5
# On Suns, sometimes $CPP names a directory.
if test -n "$CPP" && test -d "$CPP"; then
CPP=
@@ -1328,13 +1333,13 @@ else
# On the NeXT, cc -E runs the code through the compiler's parser,
# not just through cpp.
cat > conftest.$ac_ext <<EOF
-#line 1332 "configure"
+#line 1337 "configure"
#include "confdefs.h"
#include <assert.h>
Syntax Error
EOF
ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out"
-{ (eval echo configure:1338: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }
+{ (eval echo configure:1343: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }
ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"`
if test -z "$ac_err"; then
:
@@ -1345,13 +1350,13 @@ else
rm -rf conftest*
CPP="${CC-cc} -E -traditional-cpp"
cat > conftest.$ac_ext <<EOF
-#line 1349 "configure"
+#line 1354 "configure"
#include "confdefs.h"
#include <assert.h>
Syntax Error
EOF
ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out"
-{ (eval echo configure:1355: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }
+{ (eval echo configure:1360: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }
ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"`
if test -z "$ac_err"; then
:
@@ -1362,13 +1367,13 @@ else
rm -rf conftest*
CPP="${CC-cc} -nologo -E"
cat > conftest.$ac_ext <<EOF
-#line 1366 "configure"
+#line 1371 "configure"
#include "confdefs.h"
#include <assert.h>
Syntax Error
EOF
ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out"
-{ (eval echo configure:1372: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }
+{ (eval echo configure:1377: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }
ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"`
if test -z "$ac_err"; then
:
@@ -1392,21 +1397,21 @@ else
fi
echo "$ac_t""$CPP" 1>&6
-for ac_hdr in sys/ioccom.h sys/sockio.h ifaddrs.h netinet/if_ether.h
+for ac_hdr in sys/ioccom.h sys/sockio.h ifaddrs.h limits.h netinet/if_ether.h
do
ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'`
echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6
-echo "configure:1400: checking for $ac_hdr" >&5
+echo "configure:1405: checking for $ac_hdr" >&5
if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
cat > conftest.$ac_ext <<EOF
-#line 1405 "configure"
+#line 1410 "configure"
#include "confdefs.h"
#include <$ac_hdr>
EOF
ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out"
-{ (eval echo configure:1410: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }
+{ (eval echo configure:1415: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }
ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"`
if test -z "$ac_err"; then
rm -rf conftest*
@@ -1435,12 +1440,12 @@ done
if test "$GCC" = yes ; then
echo $ac_n "checking for ANSI ioctl definitions""... $ac_c" 1>&6
-echo "configure:1439: checking for ANSI ioctl definitions" >&5
+echo "configure:1444: checking for ANSI ioctl definitions" >&5
if eval "test \"`echo '$''{'ac_cv_lbl_gcc_fixincludes'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
cat > conftest.$ac_ext <<EOF
-#line 1444 "configure"
+#line 1449 "configure"
#include "confdefs.h"
/*
* This generates a "duplicate case value" when fixincludes
@@ -1459,7 +1464,7 @@ switch (0) {
}
; return 0; }
EOF
-if { (eval echo configure:1463: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
+if { (eval echo configure:1468: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
rm -rf conftest*
ac_cv_lbl_gcc_fixincludes=yes
else
@@ -1479,15 +1484,15 @@ fi
fi
fi
-for ac_func in ether_hostton strerror freeifaddrs strlcpy
+for ac_func in ether_hostton strerror strlcpy
do
echo $ac_n "checking for $ac_func""... $ac_c" 1>&6
-echo "configure:1486: checking for $ac_func" >&5
+echo "configure:1491: checking for $ac_func" >&5
if eval "test \"`echo '$''{'ac_cv_func_$ac_func'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
cat > conftest.$ac_ext <<EOF
-#line 1491 "configure"
+#line 1496 "configure"
#include "confdefs.h"
/* System header to define __stub macros and hopefully few prototypes,
which can conflict with char $ac_func(); below. */
@@ -1510,7 +1515,7 @@ $ac_func();
; return 0; }
EOF
-if { (eval echo configure:1514: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then
+if { (eval echo configure:1519: \"$ac_link\") 1>&5; (eval $ac_link) 2>&5; } && test -s conftest${ac_exeext}; then
rm -rf conftest*
eval "ac_cv_func_$ac_func=yes"
else
@@ -1536,7 +1541,7 @@ done
echo $ac_n "checking if --disable-protochain option is specified""... $ac_c" 1>&6
-echo "configure:1540: checking if --disable-protochain option is specified" >&5
+echo "configure:1545: checking if --disable-protochain option is specified" >&5
# Check whether --enable-protochain or --disable-protochain was given.
if test "${enable_protochain+set}" = set; then
enableval="$enable_protochain"
@@ -1567,7 +1572,7 @@ if test "${with_pcap+set}" = set; then
fi
echo $ac_n "checking packet capture type""... $ac_c" 1>&6
-echo "configure:1571: checking packet capture type" >&5
+echo "configure:1576: checking packet capture type" >&5
if test ! -z "$with_pcap" ; then
V_PCAP="$withval"
elif test -r /dev/bpf0 ; then
@@ -1598,7 +1603,7 @@ fi
echo "$ac_t""$V_PCAP" 1>&6
echo $ac_n "checking if --enable-ipv6 option is specified""... $ac_c" 1>&6
-echo "configure:1602: checking if --enable-ipv6 option is specified" >&5
+echo "configure:1607: checking if --enable-ipv6 option is specified" >&5
# Check whether --enable-ipv6 or --disable-ipv6 was given.
if test "${enable_ipv6+set}" = set; then
enableval="$enable_ipv6"
@@ -1613,6 +1618,38 @@ EOF
fi
echo "$ac_t""${enable_ipv6-no}" 1>&6
+echo $ac_n "checking whether to build optimizer debugging code""... $ac_c" 1>&6
+echo "configure:1623: checking whether to build optimizer debugging code" >&5
+# Check whether --enable-optimizer-dbg or --disable-optimizer-dbg was given.
+if test "${enable_optimizer_dbg+set}" = set; then
+ enableval="$enable_optimizer_dbg"
+ :
+fi
+
+if test "$enable_optimizer_dbg" = "yes"; then
+ cat >> confdefs.h <<\EOF
+#define BDEBUG 1
+EOF
+
+fi
+echo "$ac_t""${enable_optimizer_dbg-no}" 1>&6
+
+echo $ac_n "checking whether to build parser debugging code""... $ac_c" 1>&6
+echo "configure:1639: checking whether to build parser debugging code" >&5
+# Check whether --enable-yydebug or --disable-yydebug was given.
+if test "${enable_yydebug+set}" = set; then
+ enableval="$enable_yydebug"
+ :
+fi
+
+if test "$enable_yydebug" = "yes"; then
+ cat >> confdefs.h <<\EOF
+#define YYDEBUG 1
+EOF
+
+fi
+echo "$ac_t""${enable_yydebug-no}" 1>&6
+
case "$V_PCAP" in
dlpi)
@@ -1620,17 +1657,17 @@ dlpi)
do
ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'`
echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6
-echo "configure:1624: checking for $ac_hdr" >&5
+echo "configure:1661: checking for $ac_hdr" >&5
if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
cat > conftest.$ac_ext <<EOF
-#line 1629 "configure"
+#line 1666 "configure"
#include "confdefs.h"
#include <$ac_hdr>
EOF
ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out"
-{ (eval echo configure:1634: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }
+{ (eval echo configure:1671: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }
ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"`
if test -z "$ac_err"; then
rm -rf conftest*
@@ -1657,7 +1694,7 @@ fi
done
echo $ac_n "checking for /dev/dlpi device""... $ac_c" 1>&6
-echo "configure:1661: checking for /dev/dlpi device" >&5
+echo "configure:1698: checking for /dev/dlpi device" >&5
if test -c /dev/dlpi ; then
echo "$ac_t""yes" 1>&6
cat >> confdefs.h <<\EOF
@@ -1668,7 +1705,7 @@ EOF
echo "$ac_t""no" 1>&6
dir="/dev/dlpi"
echo $ac_n "checking for $dir directory""... $ac_c" 1>&6
-echo "configure:1672: checking for $dir directory" >&5
+echo "configure:1709: checking for $dir directory" >&5
if test -d $dir ; then
echo "$ac_t""yes" 1>&6
cat >> confdefs.h <<EOF
@@ -1682,48 +1719,8 @@ EOF
;;
linux)
- for ac_hdr in netpacket/packet.h
-do
-ac_safe=`echo "$ac_hdr" | sed 'y%./+-%__p_%'`
-echo $ac_n "checking for $ac_hdr""... $ac_c" 1>&6
-echo "configure:1690: checking for $ac_hdr" >&5
-if eval "test \"`echo '$''{'ac_cv_header_$ac_safe'+set}'`\" = set"; then
- echo $ac_n "(cached) $ac_c" 1>&6
-else
- cat > conftest.$ac_ext <<EOF
-#line 1695 "configure"
-#include "confdefs.h"
-#include <$ac_hdr>
-EOF
-ac_try="$ac_cpp conftest.$ac_ext >/dev/null 2>conftest.out"
-{ (eval echo configure:1700: \"$ac_try\") 1>&5; (eval $ac_try) 2>&5; }
-ac_err=`grep -v '^ *+' conftest.out | grep -v "^conftest.${ac_ext}\$"`
-if test -z "$ac_err"; then
- rm -rf conftest*
- eval "ac_cv_header_$ac_safe=yes"
-else
- echo "$ac_err" >&5
- echo "configure: failed program was:" >&5
- cat conftest.$ac_ext >&5
- rm -rf conftest*
- eval "ac_cv_header_$ac_safe=no"
-fi
-rm -f conftest*
-fi
-if eval "test \"`echo '$ac_cv_header_'$ac_safe`\" = yes"; then
- echo "$ac_t""yes" 1>&6
- ac_tr_hdr=HAVE_`echo $ac_hdr | sed 'y%abcdefghijklmnopqrstuvwxyz./-%ABCDEFGHIJKLMNOPQRSTUVWXYZ___%'`
- cat >> confdefs.h <<EOF
-#define $ac_tr_hdr 1
-EOF
-
-else
- echo "$ac_t""no" 1>&6
-fi
-done
-
echo $ac_n "checking Linux kernel version""... $ac_c" 1>&6
-echo "configure:1727: checking Linux kernel version" >&5
+echo "configure:1724: checking Linux kernel version" >&5
if test "$cross_compiling" = yes; then
if eval "test \"`echo '$''{'ac_cv_linux_vers'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
@@ -1747,6 +1744,39 @@ fi
if test $ac_cv_linux_vers -lt 2 ; then
{ echo "configure: error: version 2 or higher required; see the INSTALL doc for more info" 1>&2; exit 1; }
fi
+ echo $ac_n "checking if if_packet.h has tpacket_stats defined""... $ac_c" 1>&6
+echo "configure:1749: checking if if_packet.h has tpacket_stats defined" >&5
+ if eval "test \"`echo '$''{'ac_cv_lbl_tpacket_stats'+set}'`\" = set"; then
+ echo $ac_n "(cached) $ac_c" 1>&6
+else
+ cat > conftest.$ac_ext <<EOF
+#line 1754 "configure"
+#include "confdefs.h"
+
+# include <linux/if_packet.h>
+int main() {
+struct tpacket_stats stats
+; return 0; }
+EOF
+if { (eval echo configure:1762: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
+ rm -rf conftest*
+ ac_cv_lbl_tpacket_stats=yes
+else
+ echo "configure: failed program was:" >&5
+ cat conftest.$ac_ext >&5
+ rm -rf conftest*
+ ac_cv_lbl_tpacket_stats=no
+fi
+rm -f conftest*
+fi
+
+ echo "$ac_t""$ac_cv_lbl_tpacket_stats" 1>&6
+ if test $ac_cv_lbl_tpacket_stats = yes; then
+ cat >> confdefs.h <<\EOF
+#define HAVE_TPACKET_STATS 1
+EOF
+
+ fi
;;
null)
@@ -1756,6 +1786,21 @@ null)
esac
+echo $ac_n "checking whether we have /proc/net/dev""... $ac_c" 1>&6
+echo "configure:1791: checking whether we have /proc/net/dev" >&5
+if test -r /proc/net/dev ; then
+ ac_cv_lbl_proc_net_dev=yes
+else
+ ac_cv_lbl_proc_net_dev=no
+fi
+if test $ac_cv_lbl_proc_net_dev = yes; then
+ cat >> confdefs.h <<\EOF
+#define HAVE_PROC_NET_DEV 1
+EOF
+
+fi
+echo "$ac_t""$ac_cv_lbl_proc_net_dev" 1>&6
+
# Check whether --with-flex or --without-flex was given.
if test "${with_flex+set}" = set; then
withval="$with_flex"
@@ -1776,7 +1821,7 @@ do
# Extract the first word of "$ac_prog", so it can be a program name with args.
set dummy $ac_prog; ac_word=$2
echo $ac_n "checking for $ac_word""... $ac_c" 1>&6
-echo "configure:1780: checking for $ac_word" >&5
+echo "configure:1825: checking for $ac_word" >&5
if eval "test \"`echo '$''{'ac_cv_prog_V_LEX'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
@@ -1810,7 +1855,7 @@ test -n "$V_LEX" || V_LEX="lex"
if test "$V_LEX" = flex ; then
# The -V flag was added in 2.4
echo $ac_n "checking for flex 2.4 or higher""... $ac_c" 1>&6
-echo "configure:1814: checking for flex 2.4 or higher" >&5
+echo "configure:1859: checking for flex 2.4 or higher" >&5
if eval "test \"`echo '$''{'ac_cv_lbl_flex_v24'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
@@ -1836,7 +1881,7 @@ do
# Extract the first word of "$ac_prog", so it can be a program name with args.
set dummy $ac_prog; ac_word=$2
echo $ac_n "checking for $ac_word""... $ac_c" 1>&6
-echo "configure:1840: checking for $ac_word" >&5
+echo "configure:1885: checking for $ac_word" >&5
if eval "test \"`echo '$''{'ac_cv_prog_V_YACC'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
@@ -1883,7 +1928,7 @@ if test "$V_LEX" = lex ; then
# Some versions of lex can't handle the definitions section of scanner.l .
# Try lexing it and complain if it can't deal.
echo $ac_n "checking for capable lex""... $ac_c" 1>&6
-echo "configure:1887: checking for capable lex" >&5
+echo "configure:1932: checking for capable lex" >&5
if eval "test \"`echo '$''{'tcpdump_cv_capable_lex'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
@@ -1903,7 +1948,7 @@ echo "$ac_t""$tcpdump_cv_capable_lex" 1>&6
fi
fi
-case "$target_os" in
+case "$host_os" in
aix*)
cat >> confdefs.h <<\EOF
@@ -1934,19 +1979,19 @@ EOF
sinix*)
echo $ac_n "checking if SINIX compiler defines sinix""... $ac_c" 1>&6
-echo "configure:1938: checking if SINIX compiler defines sinix" >&5
+echo "configure:1983: checking if SINIX compiler defines sinix" >&5
if eval "test \"`echo '$''{'ac_cv_cc_sinix_defined'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
cat > conftest.$ac_ext <<EOF
-#line 1943 "configure"
+#line 1988 "configure"
#include "confdefs.h"
int main() {
int i = sinix;
; return 0; }
EOF
-if { (eval echo configure:1950: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
+if { (eval echo configure:1995: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
rm -rf conftest*
ac_cv_cc_sinix_defined=yes
else
@@ -1978,7 +2023,7 @@ esac
# Extract the first word of "ranlib", so it can be a program name with args.
set dummy ranlib; ac_word=$2
echo $ac_n "checking for $ac_word""... $ac_c" 1>&6
-echo "configure:1982: checking for $ac_word" >&5
+echo "configure:2027: checking for $ac_word" >&5
if eval "test \"`echo '$''{'ac_cv_prog_RANLIB'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
@@ -2046,12 +2091,12 @@ EOF
fi
echo $ac_n "checking if sockaddr struct has sa_len member""... $ac_c" 1>&6
-echo "configure:2050: checking if sockaddr struct has sa_len member" >&5
+echo "configure:2095: checking if sockaddr struct has sa_len member" >&5
if eval "test \"`echo '$''{'ac_cv_lbl_sockaddr_has_sa_len'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
cat > conftest.$ac_ext <<EOF
-#line 2055 "configure"
+#line 2100 "configure"
#include "confdefs.h"
# include <sys/types.h>
@@ -2060,7 +2105,7 @@ int main() {
u_int i = sizeof(((struct sockaddr *)0)->sa_len)
; return 0; }
EOF
-if { (eval echo configure:2064: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
+if { (eval echo configure:2109: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
rm -rf conftest*
ac_cv_lbl_sockaddr_has_sa_len=yes
else
@@ -2081,12 +2126,12 @@ EOF
fi
echo $ac_n "checking if dl_hp_ppa_info_t struct has dl_module_id_1 member""... $ac_c" 1>&6
-echo "configure:2085: checking if dl_hp_ppa_info_t struct has dl_module_id_1 member" >&5
+echo "configure:2130: checking if dl_hp_ppa_info_t struct has dl_module_id_1 member" >&5
if eval "test \"`echo '$''{'ac_cv_lbl_dl_hp_ppa_info_t_has_dl_module_id_1'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
cat > conftest.$ac_ext <<EOF
-#line 2090 "configure"
+#line 2135 "configure"
#include "confdefs.h"
# include <sys/types.h>
@@ -2096,7 +2141,7 @@ int main() {
u_int i = sizeof(((dl_hp_ppa_info_t *)0)->dl_module_id_1)
; return 0; }
EOF
-if { (eval echo configure:2100: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
+if { (eval echo configure:2145: \"$ac_compile\") 1>&5; (eval $ac_compile) 2>&5; }; then
rm -rf conftest*
ac_cv_lbl_dl_hp_ppa_info_t_has_dl_module_id_1=yes
else
@@ -2117,14 +2162,14 @@ EOF
fi
echo $ac_n "checking if unaligned accesses fail""... $ac_c" 1>&6
-echo "configure:2121: checking if unaligned accesses fail" >&5
+echo "configure:2166: checking if unaligned accesses fail" >&5
if eval "test \"`echo '$''{'ac_cv_lbl_unaligned_fail'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
else
- case "$target_cpu" in
+ case "$host_cpu" in
# XXX: should also check that they don't do weird things (like on arm)
- alpha*|arm*|hp*|mips|sparc)
+ alpha*|arm*|hp*|mips*|sparc*|ia64)
ac_cv_lbl_unaligned_fail=yes
;;
@@ -2202,7 +2247,7 @@ ln -s ${srcdir}/bpf/net net
# SVR4 /usr/ucb/install, which tries to use the nonexistent group "staff"
# ./install, which can be erroneously created by make from ./install.sh.
echo $ac_n "checking for a BSD compatible install""... $ac_c" 1>&6
-echo "configure:2206: checking for a BSD compatible install" >&5
+echo "configure:2251: checking for a BSD compatible install" >&5
if test -z "$INSTALL"; then
if eval "test \"`echo '$''{'ac_cv_path_install'+set}'`\" = set"; then
echo $ac_n "(cached) $ac_c" 1>&6
diff --git a/contrib/libpcap/configure.in b/contrib/libpcap/configure.in
index c2dfc99..08c42f0 100755
--- a/contrib/libpcap/configure.in
+++ b/contrib/libpcap/configure.in
@@ -1,4 +1,4 @@
-dnl @(#) $Header: /tcpdump/master/libpcap/configure.in,v 1.87.2.1 2001/01/17 18:21:54 guy Exp $ (LBL)
+dnl @(#) $Header: /tcpdump/master/libpcap/configure.in,v 1.94 2001/12/10 08:33:42 guy Exp $ (LBL)
dnl
dnl Copyright (c) 1994, 1995, 1996, 1997
dnl The Regents of the University of California. All rights reserved.
@@ -6,7 +6,7 @@ dnl
dnl Process this file with autoconf to produce a configure script.
dnl
-AC_REVISION($Revision: 1.87.2.1 $)
+AC_REVISION($Revision: 1.94 $)
AC_INIT(pcap.c)
AC_CANONICAL_SYSTEM
@@ -25,11 +25,11 @@ dnl in "AC_LBL_FIXINCLUDES" in "aclocal.m4" uses it, so we have to
dnl test for it and set "HAVE_SYS_IOCCOM_H" if we have it, otherwise
dnl "AC_LBL_FIXINCLUDES" won't work on some platforms such as Solaris.
dnl
-AC_CHECK_HEADERS(sys/ioccom.h sys/sockio.h ifaddrs.h netinet/if_ether.h)
+AC_CHECK_HEADERS(sys/ioccom.h sys/sockio.h ifaddrs.h limits.h netinet/if_ether.h)
AC_LBL_FIXINCLUDES
-AC_CHECK_FUNCS(ether_hostton strerror freeifaddrs strlcpy)
+AC_CHECK_FUNCS(ether_hostton strerror strlcpy)
dnl to pacify those who hate protochain insn
AC_MSG_CHECKING(if --disable-protochain option is specified)
@@ -94,6 +94,20 @@ if test "$enable_ipv6" = "yes"; then
fi
AC_MSG_RESULT(${enable_ipv6-no})
+AC_MSG_CHECKING(whether to build optimizer debugging code)
+AC_ARG_ENABLE(optimizer-dbg, [ --enable-optimizer-dbg build optimizer debugging code])
+if test "$enable_optimizer_dbg" = "yes"; then
+ AC_DEFINE(BDEBUG,1,[Enable optimizer debugging])
+fi
+AC_MSG_RESULT(${enable_optimizer_dbg-no})
+
+AC_MSG_CHECKING(whether to build parser debugging code)
+AC_ARG_ENABLE(yydebug, [ --enable-yydebug build parser debugging code])
+if test "$enable_yydebug" = "yes"; then
+ AC_DEFINE(YYDEBUG,1,[Enable parser debugging])
+fi
+AC_MSG_RESULT(${enable_yydebug-no})
+
case "$V_PCAP" in
dlpi)
@@ -116,7 +130,6 @@ dlpi)
;;
linux)
- AC_CHECK_HEADERS(netpacket/packet.h)
AC_MSG_CHECKING(Linux kernel version)
if test "$cross_compiling" = yes; then
AC_CACHE_VAL(ac_cv_linux_vers,
@@ -133,6 +146,7 @@ linux)
if test $ac_cv_linux_vers -lt 2 ; then
AC_MSG_ERROR(version 2 or higher required; see the INSTALL doc for more info)
fi
+ AC_LBL_TPACKET_STATS
;;
null)
@@ -142,6 +156,17 @@ null)
esac
+AC_MSG_CHECKING(whether we have /proc/net/dev)
+if test -r /proc/net/dev ; then
+ ac_cv_lbl_proc_net_dev=yes
+else
+ ac_cv_lbl_proc_net_dev=no
+fi
+if test $ac_cv_lbl_proc_net_dev = yes; then
+ AC_DEFINE(HAVE_PROC_NET_DEV, 1, [define if you have a /proc/net/dev])
+fi
+AC_MSG_RESULT($ac_cv_lbl_proc_net_dev)
+
AC_LBL_LEX_AND_YACC(V_LEX, V_YACC, pcap_)
if test "$V_LEX" = lex ; then
# Some versions of lex can't handle the definitions section of scanner.l .
@@ -160,7 +185,7 @@ if test "$V_LEX" = lex ; then
fi
fi
-case "$target_os" in
+case "$host_os" in
aix*)
dnl Workaround to enable certain features
diff --git a/contrib/libpcap/ethertype.h b/contrib/libpcap/ethertype.h
index 42afe9b..3af5576 100644
--- a/contrib/libpcap/ethertype.h
+++ b/contrib/libpcap/ethertype.h
@@ -18,7 +18,7 @@
* WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * @(#) $Header: /tcpdump/master/libpcap/ethertype.h,v 1.11 2000/10/22 04:15:55 guy Exp $ (LBL)
+ * @(#) $Header: /tcpdump/master/libpcap/ethertype.h,v 1.12 2001/01/14 21:26:52 guy Exp $ (LBL)
*/
/*
@@ -93,12 +93,15 @@
#ifndef ETHERTYPE_AARP
#define ETHERTYPE_AARP 0x80f3
#endif
-#ifndef ETHERTYPE_IPV6
-#define ETHERTYPE_IPV6 0x86dd
-#endif
#ifndef ETHERTYPE_8021Q
#define ETHERTYPE_8021Q 0x8100
#endif
+#ifndef ETHERTYPE_IPX
+#define ETHERTYPE_IPX 0x8137
+#endif
+#ifndef ETHERTYPE_IPV6
+#define ETHERTYPE_IPV6 0x86dd
+#endif
#ifndef ETHERTYPE_LOOPBACK
#define ETHERTYPE_LOOPBACK 0x9000
#endif
diff --git a/contrib/libpcap/inet.c b/contrib/libpcap/inet.c
index 0b5b696..fa97aaf 100644
--- a/contrib/libpcap/inet.c
+++ b/contrib/libpcap/inet.c
@@ -1,3 +1,4 @@
+/* -*- Mode: c; tab-width: 8; indent-tabs-mode: 1; c-basic-offset: 8; -*- */
/*
* Copyright (c) 1994, 1995, 1996, 1997, 1998
* The Regents of the University of California. All rights reserved.
@@ -33,7 +34,7 @@
#ifndef lint
static const char rcsid[] =
- "@(#) $Header: /tcpdump/master/libpcap/inet.c,v 1.36 2000/09/20 15:10:29 torsten Exp $ (LBL)";
+ "@(#) $Header: /tcpdump/master/libpcap/inet.c,v 1.45 2001/10/28 20:40:43 guy Exp $ (LBL)";
#endif
#ifdef HAVE_CONFIG_H
@@ -61,6 +62,11 @@ struct rtentry;
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
+#ifdef HAVE_LIMITS_H
+#include <limits.h>
+#else
+#define INT_MAX 2147483647
+#endif
#ifdef HAVE_IFADDRS_H
#include <ifaddrs.h>
#endif
@@ -73,189 +79,918 @@ struct rtentry;
/* Not all systems have IFF_LOOPBACK */
#ifdef IFF_LOOPBACK
-#define ISLOOPBACK(p) ((p)->ifr_flags & IFF_LOOPBACK)
-#define ISLOOPBACK_IFA(p) ((p)->ifa_flags & IFF_LOOPBACK)
+#define ISLOOPBACK(name, flags) ((flags) & IFF_LOOPBACK)
#else
-#define ISLOOPBACK(p) ((p)->ifr_name[0] == 'l' && (p)->ifr_name[1] == 'o' && \
- (isdigit((p)->ifr_name[2]) || (p)->ifr_name[2] == '\0'))
-#define ISLOOPBACK_IFA(p) ((p)->ifa_name[0] == 'l' && (p)->ifa_name[1] == 'o' && \
- (isdigit((p)->ifa_name[2]) || (p)->ifa_name[2] == '\0'))
+#define ISLOOPBACK(name, flags) ((name)[0] == 'l' && (name)[1] == 'o' && \
+ (isdigit((unsigned char)((name)[2])) || (name)[2] == '\0'))
#endif
/*
- * Return the name of a network interface attached to the system, or NULL
- * if none can be found. The interface must be configured up; the
- * lowest unit number is preferred; loopback is ignored.
+ * This is fun.
+ *
+ * In older BSD systems, socket addresses were fixed-length, and
+ * "sizeof (struct sockaddr)" gave the size of the structure.
+ * All addresses fit within a "struct sockaddr".
+ *
+ * In newer BSD systems, the socket address is variable-length, and
+ * there's an "sa_len" field giving the length of the structure;
+ * this allows socket addresses to be longer than 2 bytes of family
+ * and 14 bytes of data.
+ *
+ * Some commercial UNIXes use the old BSD scheme, and some might use
+ * the new BSD scheme.
+ *
+ * GNU libc uses neither scheme, but has an "SA_LEN()" macro that
+ * determines the size based on the address family.
*/
-char *
-pcap_lookupdev(errbuf)
- register char *errbuf;
+#ifndef SA_LEN
+#ifdef HAVE_SOCKADDR_SA_LEN
+#define SA_LEN(addr) ((addr)->sa_len)
+#else /* HAVE_SOCKADDR_SA_LEN */
+#define SA_LEN(addr) (sizeof (struct sockaddr))
+#endif /* HAVE_SOCKADDR_SA_LEN */
+#endif /* SA_LEN */
+
+/*
+ * Description string for the "any" device.
+ */
+static const char any_descr[] = "Pseudo-device that captures on all interfaces";
+
+static struct sockaddr *
+dup_sockaddr(struct sockaddr *sa)
+{
+ struct sockaddr *newsa;
+ unsigned int size;
+
+ size = SA_LEN(sa);
+ if ((newsa = malloc(size)) == NULL)
+ return (NULL);
+ return (memcpy(newsa, sa, size));
+}
+
+static int
+get_instance(char *name)
+{
+ char *cp, *endcp;
+ int n;
+
+ if (strcmp(name, "any") == 0) {
+ /*
+ * Give the "any" device an artificially high instance
+ * number, so it shows up after all other non-loopback
+ * interfaces.
+ */
+ return INT_MAX;
+ }
+
+ endcp = name + strlen(name);
+ for (cp = name; cp < endcp && !isdigit((unsigned char)*cp); ++cp)
+ continue;
+
+ if (isdigit((unsigned char)*cp))
+ n = atoi(cp);
+ else
+ n = 0;
+ return (n);
+}
+
+static int
+add_or_find_if(pcap_if_t **curdev_ret, pcap_if_t **alldevs, char *name,
+ u_int flags, const char *description, char *errbuf)
+{
+ pcap_t *p;
+ pcap_if_t *curdev, *prevdev, *nextdev;
+ int this_instance;
+
+ /*
+ * Can we open this interface for live capture?
+ */
+ p = pcap_open_live(name, 68, 0, 0, errbuf);
+ if (p == NULL) {
+ /*
+ * No. Don't bother including it.
+ * Don't treat this as an error, though.
+ */
+ *curdev_ret = NULL;
+ return (0);
+ }
+ pcap_close(p);
+
+ /*
+ * Is there already an entry in the list for this interface?
+ */
+ for (curdev = *alldevs; curdev != NULL; curdev = curdev->next) {
+ if (strcmp(name, curdev->name) == 0)
+ break; /* yes, we found it */
+ }
+ if (curdev == NULL) {
+ /*
+ * No, we didn't find it.
+ * Allocate a new entry.
+ */
+ curdev = malloc(sizeof(pcap_if_t));
+ if (curdev == NULL) {
+ (void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
+ "malloc: %s", pcap_strerror(errno));
+ return (-1);
+ }
+
+ /*
+ * Fill in the entry.
+ */
+ curdev->next = NULL;
+ curdev->name = malloc(strlen(name) + 1);
+ strcpy(curdev->name, name);
+ if (description != NULL) {
+ /*
+ * We have a description for this interface.
+ */
+ curdev->description = malloc(strlen(description) + 1);
+ strcpy(curdev->description, description);
+ } else {
+ /*
+ * We don't.
+ */
+ curdev->description = NULL;
+ }
+ curdev->addresses = NULL; /* list starts out as empty */
+ curdev->flags = 0;
+ if (ISLOOPBACK(name, flags))
+ curdev->flags |= PCAP_IF_LOOPBACK;
+
+ /*
+ * Add it to the list, in the appropriate location.
+ * First, get the instance number of this interface.
+ */
+ this_instance = get_instance(name);
+
+ /*
+ * Now look for the last interface with an instance number
+ * less than or equal to the new interface's instance
+ * number - except that non-loopback interfaces are
+ * arbitrarily treated as having interface numbers less
+ * than those of loopback interfaces, so the loopback
+ * interfaces are put at the end of the list.
+ *
+ * We start with "prevdev" being NULL, meaning we're before
+ * the first element in the list.
+ */
+ prevdev = NULL;
+ for (;;) {
+ /*
+ * Get the interface after this one.
+ */
+ if (prevdev == NULL) {
+ /*
+ * The next element is the first element.
+ */
+ nextdev = *alldevs;
+ } else
+ nextdev = prevdev->next;
+
+ /*
+ * Are we at the end of the list?
+ */
+ if (nextdev == NULL) {
+ /*
+ * Yes - we have to put the new entry
+ * after "prevdev".
+ */
+ break;
+ }
+
+ /*
+ * Is the new interface a non-loopback interface
+ * and the next interface a loopback interface?
+ */
+ if (!(curdev->flags & PCAP_IF_LOOPBACK) &&
+ (nextdev->flags & PCAP_IF_LOOPBACK)) {
+ /*
+ * Yes, we should put the new entry
+ * before "nextdev", i.e. after "prevdev".
+ */
+ break;
+ }
+
+ /*
+ * Is the new interface's instance number less
+ * than the next interface's instance number,
+ * and is it the case that the new interface is a
+ * non-loopback interface or the next interface is
+ * a loopback interface?
+ *
+ * (The goal of both loopback tests is to make
+ * sure that we never put a loopback interface
+ * before any non-loopback interface and that we
+ * always put a non-loopback interface before all
+ * loopback interfaces.)
+ */
+ if (this_instance < get_instance(nextdev->name) &&
+ (!(curdev->flags & PCAP_IF_LOOPBACK) ||
+ (nextdev->flags & PCAP_IF_LOOPBACK))) {
+ /*
+ * Yes - we should put the new entry
+ * before "nextdev", i.e. after "prevdev".
+ */
+ break;
+ }
+
+ prevdev = nextdev;
+ }
+
+ /*
+ * Insert before "nextdev".
+ */
+ curdev->next = nextdev;
+
+ /*
+ * Insert after "prevdev" - unless "prevdev" is null,
+ * in which case this is the first interface.
+ */
+ if (prevdev == NULL) {
+ /*
+ * This is the first interface. Pass back a
+ * pointer to it, and put "curdev" before
+ * "nextdev".
+ */
+ *alldevs = curdev;
+ } else
+ prevdev->next = curdev;
+ }
+
+ *curdev_ret = curdev;
+ return (0);
+}
+
+static int
+add_addr_to_iflist(pcap_if_t **alldevs, char *name, u_int flags,
+ struct sockaddr *addr, struct sockaddr *netmask,
+ struct sockaddr *broadaddr, struct sockaddr *dstaddr, char *errbuf)
{
+ pcap_if_t *curdev;
+ pcap_addr_t *curaddr, *prevaddr, *nextaddr;
+
+ if (add_or_find_if(&curdev, alldevs, name, flags, NULL, errbuf) == -1) {
+ /*
+ * Error - give up.
+ */
+ return (-1);
+ }
+ if (curdev == NULL) {
+ /*
+ * Device wasn't added because it can't be opened.
+ * Not a fatal error.
+ */
+ return (0);
+ }
+
+ /*
+ * "curdev" is an entry for this interface; add an entry for this
+ * address to its list of addresses.
+ *
+ * Allocate the new entry and fill it in.
+ */
+ curaddr = malloc(sizeof(pcap_addr_t));
+ if (curaddr == NULL) {
+ (void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
+ "malloc: %s", pcap_strerror(errno));
+ return (-1);
+ }
+
+ curaddr->next = NULL;
+ if (addr != NULL) {
+ curaddr->addr = dup_sockaddr(addr);
+ if (curaddr->addr == NULL) {
+ (void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
+ "malloc: %s", pcap_strerror(errno));
+ free(curaddr);
+ return (-1);
+ }
+ } else
+ curaddr->addr = NULL;
+
+ if (netmask != NULL) {
+ curaddr->netmask = dup_sockaddr(netmask);
+ if (curaddr->netmask == NULL) {
+ (void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
+ "malloc: %s", pcap_strerror(errno));
+ free(curaddr);
+ return (-1);
+ }
+ } else
+ curaddr->netmask = NULL;
+
+ if (broadaddr != NULL) {
+ curaddr->broadaddr = dup_sockaddr(broadaddr);
+ if (curaddr->broadaddr == NULL) {
+ (void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
+ "malloc: %s", pcap_strerror(errno));
+ free(curaddr);
+ return (-1);
+ }
+ } else
+ curaddr->broadaddr = NULL;
+
+ if (dstaddr != NULL) {
+ curaddr->dstaddr = dup_sockaddr(dstaddr);
+ if (curaddr->dstaddr == NULL) {
+ (void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
+ "malloc: %s", pcap_strerror(errno));
+ free(curaddr);
+ return (-1);
+ }
+ } else
+ curaddr->dstaddr = NULL;
+
+ /*
+ * Find the end of the list of addresses.
+ */
+ for (prevaddr = curdev->addresses; prevaddr != NULL; prevaddr = nextaddr) {
+ nextaddr = prevaddr->next;
+ if (nextaddr == NULL) {
+ /*
+ * This is the end of the list.
+ */
+ break;
+ }
+ }
+
+ if (prevaddr == NULL) {
+ /*
+ * The list was empty; this is the first member.
+ */
+ curdev->addresses = curaddr;
+ } else {
+ /*
+ * "prevaddr" is the last member of the list; append
+ * this member to it.
+ */
+ prevaddr->next = curaddr;
+ }
+
+ return (0);
+}
+
+static int
+pcap_add_if(pcap_if_t **devlist, char *name, u_int flags,
+ const char *description, char *errbuf)
+{
+ pcap_if_t *curdev;
+
+ return (add_or_find_if(&curdev, devlist, name, flags, description,
+ errbuf));
+}
+
+/*
+ * Get a list of all interfaces that are up and that we can open.
+ * Returns -1 on error, 0 otherwise.
+ * The list, as returned through "alldevsp", may be null if no interfaces
+ * were up and could be opened.
+ */
#ifdef HAVE_IFADDRS_H
- struct ifaddrs *ifap, *ifa, *mp;
- int n, minunit;
- char *cp;
- static char device[IF_NAMESIZE + 1];
+int
+pcap_findalldevs(pcap_if_t **alldevsp, char *errbuf)
+{
+ pcap_if_t *devlist = NULL;
+ struct ifaddrs *ifap, *ifa;
+ struct sockaddr *broadaddr, *dstaddr;
+ int ret = 0;
+ /*
+ * Get the list of interface addresses.
+ *
+ * Note: this won't return information about interfaces
+ * with no addresses; are there any such interfaces
+ * that would be capable of receiving packets?
+ * (Interfaces incapable of receiving packets aren't
+ * very interesting from libpcap's point of view.)
+ *
+ * LAN interfaces will probably have link-layer
+ * addresses; I don't know whether all implementations
+ * of "getifaddrs()" now, or in the future, will return
+ * those.
+ */
if (getifaddrs(&ifap) != 0) {
(void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
"getifaddrs: %s", pcap_strerror(errno));
- return NULL;
+ return (-1);
+ }
+ for (ifa = ifap; ifa != NULL; ifa = ifa->ifa_next) {
+ /*
+ * Is this interface up?
+ */
+ if (!(ifa->ifa_flags & IFF_UP)) {
+ /*
+ * No, so don't add it to the list.
+ */
+ continue;
+ }
+
+ /*
+ * "ifa_broadaddr" may be non-null even on
+ * non-broadcast interfaces; "ifa_dstaddr"
+ * was, on at least one FreeBSD 4.1 system,
+ * non-null on a non-point-to-point
+ * interface.
+ */
+ if (ifa->ifa_flags & IFF_BROADCAST)
+ broadaddr = ifa->ifa_broadaddr;
+ else
+ broadaddr = NULL;
+ if (ifa->ifa_flags & IFF_POINTOPOINT)
+ dstaddr = ifa->ifa_dstaddr;
+ else
+ dstaddr = NULL;
+
+ /*
+ * Add information for this address to the list.
+ */
+ if (add_addr_to_iflist(&devlist, ifa->ifa_name,
+ ifa->ifa_flags, ifa->ifa_addr, ifa->ifa_netmask,
+ broadaddr, dstaddr, errbuf) < 0) {
+ ret = -1;
+ break;
+ }
}
- mp = NULL;
- minunit = 666;
- for (ifa = ifap; ifa; ifa = ifa->ifa_next) {
- const char *endcp;
+ freeifaddrs(ifap);
- if ((ifa->ifa_flags & IFF_UP) == 0 || ISLOOPBACK_IFA(ifa))
- continue;
+ if (ret != -1) {
+ /*
+ * We haven't had any errors yet; add the "any" device,
+ * if we can open it.
+ */
+ if (pcap_add_if(&devlist, "any", 0, any_descr, errbuf) < 0)
+ ret = -1;
+ }
+
+ if (ret == -1) {
+ /*
+ * We had an error; free the list we've been constructing.
+ */
+ if (devlist != NULL) {
+ pcap_freealldevs(devlist);
+ devlist = NULL;
+ }
+ }
+
+ *alldevsp = devlist;
+ return (ret);
+}
+#else /* HAVE_IFADDRS_H */
+#ifdef HAVE_PROC_NET_DEV
+/*
+ * Get from "/proc/net/dev" all interfaces listed there; if they're
+ * already in the list of interfaces we have, that won't add another
+ * instance, but if they're not, that'll add them.
+ *
+ * We don't bother getting any addresses for them; it appears you can't
+ * use SIOCGIFADDR on Linux to get IPv6 addresses for interfaces, and,
+ * although some other types of addresses can be fetched with SIOCGIFADDR,
+ * we don't bother with them for now.
+ *
+ * We also don't fail if we couldn't open "/proc/net/dev"; we just leave
+ * the list of interfaces as is.
+ */
+static int
+scan_proc_net_dev(pcap_if_t **devlistp, int fd, char *errbuf)
+{
+ FILE *proc_net_f;
+ char linebuf[512];
+ int linenum;
+ unsigned char *p;
+ char name[512]; /* XXX - pick a size */
+ char *q, *saveq;
+ struct ifreq ifrflags;
+ int ret = 0;
- endcp = ifa->ifa_name + strlen(ifa->ifa_name);
- for (cp = ifa->ifa_name; cp < endcp && !isdigit(*cp); ++cp)
+ proc_net_f = fopen("/proc/net/dev", "r");
+ if (proc_net_f == NULL)
+ return (0);
+
+ for (linenum = 1;
+ fgets(linebuf, sizeof linebuf, proc_net_f) != NULL; linenum++) {
+ /*
+ * Skip the first two lines - they're headers.
+ */
+ if (linenum <= 2)
continue;
- if (isdigit (*cp)) {
- n = atoi(cp);
- } else {
- n = 0;
+ p = &linebuf[0];
+
+ /*
+ * Skip leading white space.
+ */
+ while (*p != '\0' && isspace(*p))
+ p++;
+ if (*p == '\0' || *p == '\n')
+ continue; /* blank line */
+
+ /*
+ * Get the interface name.
+ */
+ q = &name[0];
+ while (*p != '\0' && !isspace(*p)) {
+ if (*p == ':') {
+ /*
+ * This could be the separator between a
+ * name and an alias number, or it could be
+ * the separator between a name with no
+ * alias number and the next field.
+ *
+ * If there's a colon after digits, it
+ * separates the name and the alias number,
+ * otherwise it separates the name and the
+ * next field.
+ */
+ saveq = q;
+ while (isdigit(*p))
+ *q++ = *p++;
+ if (*p != ':') {
+ /*
+ * That was the next field,
+ * not the alias number.
+ */
+ q = saveq;
+ }
+ break;
+ } else
+ *q++ = *p++;
+ }
+ *q = '\0';
+
+ /*
+ * Get the flags for this interface, and skip it if
+ * it's not up.
+ */
+ strncpy(ifrflags.ifr_name, name, sizeof(ifrflags.ifr_name));
+ if (ioctl(fd, SIOCGIFFLAGS, (char *)&ifrflags) < 0) {
+ if (errno == ENXIO)
+ continue;
+ (void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
+ "SIOCGIFFLAGS: %.*s: %s",
+ (int)sizeof(ifrflags.ifr_name),
+ ifrflags.ifr_name,
+ pcap_strerror(errno));
+ ret = -1;
+ break;
}
- if (n < minunit) {
- minunit = n;
- mp = ifa;
+ if (!(ifrflags.ifr_flags & IFF_UP))
+ continue;
+
+ /*
+ * Add an entry for this interface, with no addresses.
+ */
+ if (pcap_add_if(devlistp, name, ifrflags.ifr_flags, NULL,
+ errbuf) == -1) {
+ /*
+ * Failure.
+ */
+ ret = -1;
+ break;
}
}
- if (mp == NULL) {
- (void)strlcpy(errbuf, "no suitable device found",
- PCAP_ERRBUF_SIZE);
-#ifdef HAVE_FREEIFADDRS
- freeifaddrs(ifap);
-#else
- free(ifap);
-#endif
- return (NULL);
+ if (ret != -1) {
+ /*
+ * Well, we didn't fail for any other reason; did we
+ * fail due to an error reading the file?
+ */
+ if (ferror(proc_net_f)) {
+ (void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
+ "Error reading /proc/net/dev: %s",
+ pcap_strerror(errno));
+ ret = -1;
+ }
}
- (void)strlcpy(device, mp->ifa_name, sizeof(device));
-#ifdef HAVE_FREEIFADDRS
- freeifaddrs(ifap);
-#else
- free(ifap);
-#endif
- return (device);
-#else
- register int fd, minunit, n;
- register char *cp;
- register struct ifreq *ifrp, *ifend, *ifnext, *mp;
+ (void)fclose(proc_net_f);
+ return (ret);
+}
+#endif /* HAVE_PROC_NET_DEV */
+
+int
+pcap_findalldevs(pcap_if_t **alldevsp, char *errbuf)
+{
+ pcap_if_t *devlist = NULL;
+ register int fd;
+ register struct ifreq *ifrp, *ifend, *ifnext;
+ int n;
struct ifconf ifc;
- char *buf;
- struct ifreq ifr;
- static char device[sizeof(ifrp->ifr_name) + 1];
+ char *buf = NULL;
unsigned buf_size;
+ struct ifreq ifrflags, ifrnetmask, ifrbroadaddr, ifrdstaddr;
+ struct sockaddr *netmask, *broadaddr, *dstaddr;
+ int ret = 0;
+ /*
+ * Create a socket from which to fetch the list of interfaces.
+ */
fd = socket(AF_INET, SOCK_DGRAM, 0);
if (fd < 0) {
(void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
"socket: %s", pcap_strerror(errno));
- return (NULL);
+ return (-1);
}
+ /*
+ * Start with an 8K buffer, and keep growing the buffer until
+ * we get the entire interface list or fail to get it for some
+ * reason other than EINVAL (which is presumed here to mean
+ * "buffer is too small").
+ */
buf_size = 8192;
-
for (;;) {
- buf = malloc (buf_size);
+ buf = malloc(buf_size);
if (buf == NULL) {
- close (fd);
(void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
- "out of memory");
- return (NULL);
+ "malloc: %s", pcap_strerror(errno));
+ (void)close(fd);
+ return (-1);
}
ifc.ifc_len = buf_size;
ifc.ifc_buf = buf;
- memset (buf, 0, buf_size);
+ memset(buf, 0, buf_size);
if (ioctl(fd, SIOCGIFCONF, (char *)&ifc) < 0
&& errno != EINVAL) {
- free (buf);
(void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
"SIOCGIFCONF: %s", pcap_strerror(errno));
(void)close(fd);
- return (NULL);
+ free(buf);
+ return (-1);
}
if (ifc.ifc_len < buf_size)
break;
- free (buf);
+ free(buf);
buf_size *= 2;
}
ifrp = (struct ifreq *)buf;
ifend = (struct ifreq *)(buf + ifc.ifc_len);
- mp = NULL;
- minunit = 666;
for (; ifrp < ifend; ifrp = ifnext) {
- const char *endcp;
-
-#ifdef HAVE_SOCKADDR_SA_LEN
- n = ifrp->ifr_addr.sa_len + sizeof(ifrp->ifr_name);
+ n = SA_LEN(&ifrp->ifr_addr) + sizeof(ifrp->ifr_name);
if (n < sizeof(*ifrp))
ifnext = ifrp + 1;
else
ifnext = (struct ifreq *)((char *)ifrp + n);
- if (ifrp->ifr_addr.sa_family != AF_INET)
- continue;
-#else
- ifnext = ifrp + 1;
-#endif
+
/*
- * Need a template to preserve address info that is
- * used below to locate the next entry. (Otherwise,
- * SIOCGIFFLAGS stomps over it because the requests
- * are returned in a union.)
+ * Get the flags for this interface, and skip it if it's
+ * not up.
*/
- strncpy(ifr.ifr_name, ifrp->ifr_name, sizeof(ifr.ifr_name));
- if (ioctl(fd, SIOCGIFFLAGS, (char *)&ifr) < 0) {
+ strncpy(ifrflags.ifr_name, ifrp->ifr_name,
+ sizeof(ifrflags.ifr_name));
+ if (ioctl(fd, SIOCGIFFLAGS, (char *)&ifrflags) < 0) {
if (errno == ENXIO)
continue;
(void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
"SIOCGIFFLAGS: %.*s: %s",
- (int)sizeof(ifr.ifr_name), ifr.ifr_name,
+ (int)sizeof(ifrflags.ifr_name),
+ ifrflags.ifr_name,
pcap_strerror(errno));
- (void)close(fd);
- free (buf);
- return (NULL);
+ ret = -1;
+ break;
}
-
- /* Must be up and not the loopback */
- if ((ifr.ifr_flags & IFF_UP) == 0 || ISLOOPBACK(&ifr))
+ if (!(ifrflags.ifr_flags & IFF_UP))
continue;
- endcp = ifrp->ifr_name + strlen(ifrp->ifr_name);
- for (cp = ifrp->ifr_name; cp < endcp && !isdigit(*cp); ++cp)
- continue;
-
- if (isdigit (*cp)) {
- n = atoi(cp);
+ /*
+ * Get the netmask for this address on this interface.
+ */
+ strncpy(ifrnetmask.ifr_name, ifrp->ifr_name,
+ sizeof(ifrnetmask.ifr_name));
+ memcpy(&ifrnetmask.ifr_addr, &ifrp->ifr_addr,
+ sizeof(ifrnetmask.ifr_addr));
+ if (ioctl(fd, SIOCGIFNETMASK, (char *)&ifrnetmask) < 0) {
+ if (errno == EADDRNOTAVAIL) {
+ /*
+ * Not available.
+ */
+ netmask = NULL;
+ } else {
+ (void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
+ "SIOCGIFNETMASK: %.*s: %s",
+ (int)sizeof(ifrnetmask.ifr_name),
+ ifrnetmask.ifr_name,
+ pcap_strerror(errno));
+ ret = -1;
+ break;
+ }
+ } else
+ netmask = &ifrnetmask.ifr_addr;
+
+ /*
+ * Get the broadcast address for this address on this
+ * interface (if any).
+ */
+ if (ifrflags.ifr_flags & IFF_BROADCAST) {
+ strncpy(ifrbroadaddr.ifr_name, ifrp->ifr_name,
+ sizeof(ifrbroadaddr.ifr_name));
+ memcpy(&ifrbroadaddr.ifr_addr, &ifrp->ifr_addr,
+ sizeof(ifrbroadaddr.ifr_addr));
+ if (ioctl(fd, SIOCGIFBRDADDR,
+ (char *)&ifrbroadaddr) < 0) {
+ if (errno == EADDRNOTAVAIL) {
+ /*
+ * Not available.
+ */
+ broadaddr = NULL;
+ } else {
+ (void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
+ "SIOCGIFBRDADDR: %.*s: %s",
+ (int)sizeof(ifrbroadaddr.ifr_name),
+ ifrbroadaddr.ifr_name,
+ pcap_strerror(errno));
+ ret = -1;
+ break;
+ }
+ } else
+ broadaddr = &ifrbroadaddr.ifr_broadaddr;
} else {
- n = 0;
+ /*
+ * Not a broadcast interface, so no broadcast
+ * address.
+ */
+ broadaddr = NULL;
}
- if (n < minunit) {
- minunit = n;
- mp = ifrp;
+
+ /*
+ * Get the destination address for this address on this
+ * interface (if any).
+ */
+ if (ifrflags.ifr_flags & IFF_POINTOPOINT) {
+ strncpy(ifrdstaddr.ifr_name, ifrp->ifr_name,
+ sizeof(ifrdstaddr.ifr_name));
+ memcpy(&ifrdstaddr.ifr_addr, &ifrp->ifr_addr,
+ sizeof(ifrdstaddr.ifr_addr));
+ if (ioctl(fd, SIOCGIFDSTADDR,
+ (char *)&ifrdstaddr) < 0) {
+ if (errno == EADDRNOTAVAIL) {
+ /*
+ * Not available.
+ */
+ dstaddr = NULL;
+ } else {
+ (void)snprintf(errbuf, PCAP_ERRBUF_SIZE,
+ "SIOCGIFDSTADDR: %.*s: %s",
+ (int)sizeof(ifrdstaddr.ifr_name),
+ ifrdstaddr.ifr_name,
+ pcap_strerror(errno));
+ ret = -1;
+ break;
+ }
+ } else
+ dstaddr = &ifrdstaddr.ifr_dstaddr;
+ } else
+ dstaddr = NULL;
+
+ /*
+ * Add information for this address to the list.
+ */
+ if (add_addr_to_iflist(&devlist, ifrp->ifr_name,
+ ifrflags.ifr_flags, &ifrp->ifr_addr,
+ netmask, broadaddr, dstaddr, errbuf) < 0) {
+ ret = -1;
+ break;
}
}
+ free(buf);
+
+#ifdef HAVE_PROC_NET_DEV
+ if (ret != -1) {
+ /*
+ * We haven't had any errors yet; now read "/proc/net/dev",
+ * and add to the list of interfaces all interfaces listed
+ * there that we don't already have, because, on Linux,
+ * SIOCGIFCONF reports only interfaces with IPv4 addresses,
+ * so you need to read "/proc/net/dev" to get the names of
+ * the rest of the interfaces.
+ */
+ ret = scan_proc_net_dev(&devlist, fd, errbuf);
+ }
+#endif
(void)close(fd);
- if (mp == NULL) {
+
+ if (ret != -1) {
+ /*
+ * We haven't had any errors yet; add the "any" device,
+ * if we can open it.
+ */
+ if (pcap_add_if(&devlist, "any", 0, any_descr, errbuf) < 0) {
+ /*
+ * Oops, we had a fatal error.
+ */
+ ret = -1;
+ }
+ }
+
+ if (ret == -1) {
+ /*
+ * We had an error; free the list we've been constructing.
+ */
+ if (devlist != NULL) {
+ pcap_freealldevs(devlist);
+ devlist = NULL;
+ }
+ }
+
+ *alldevsp = devlist;
+ return (ret);
+}
+#endif /* HAVE_IFADDRS_H */
+
+/*
+ * Free a list of interfaces.
+ */
+void
+pcap_freealldevs(pcap_if_t *alldevs)
+{
+ pcap_if_t *curdev, *nextdev;
+ pcap_addr_t *curaddr, *nextaddr;
+
+ for (curdev = alldevs; curdev != NULL; curdev = nextdev) {
+ nextdev = curdev->next;
+
+ /*
+ * Free all addresses.
+ */
+ for (curaddr = curdev->addresses; curaddr != NULL; curaddr = nextaddr) {
+ nextaddr = curaddr->next;
+ if (curaddr->addr)
+ free(curaddr->addr);
+ if (curaddr->netmask)
+ free(curaddr->netmask);
+ if (curaddr->broadaddr)
+ free(curaddr->broadaddr);
+ if (curaddr->dstaddr)
+ free(curaddr->dstaddr);
+ free(curaddr);
+ }
+
+ /*
+ * Free the name string.
+ */
+ free(curdev->name);
+
+ /*
+ * Free the description string, if any.
+ */
+ if (curdev->description != NULL)
+ free(curdev->description);
+
+ /*
+ * Free the interface.
+ */
+ free(curdev);
+ }
+}
+
+/*
+ * Return the name of a network interface attached to the system, or NULL
+ * if none can be found. The interface must be configured up; the
+ * lowest unit number is preferred; loopback is ignored.
+ */
+char *
+pcap_lookupdev(errbuf)
+ register char *errbuf;
+{
+ pcap_if_t *alldevs;
+/* for old BSD systems, including bsdi3 */
+#ifndef IF_NAMESIZE
+#define IF_NAMESIZE IFNAMSIZ
+#endif
+ static char device[IF_NAMESIZE + 1];
+ char *ret;
+
+ if (pcap_findalldevs(&alldevs, errbuf) == -1)
+ return (NULL);
+
+ if (alldevs == NULL || (alldevs->flags & PCAP_IF_LOOPBACK)) {
+ /*
+ * There are no devices on the list, or the first device
+ * on the list is a loopback device, which means there
+ * are no non-loopback devices on the list. This means
+ * we can't return any device.
+ *
+ * XXX - why not return a loopback device? If we can't
+ * capture on it, it won't be on the list, and if it's
+ * on the list, there aren't any non-loopback devices,
+ * so why not just supply it as the default device?
+ */
(void)strlcpy(errbuf, "no suitable device found",
PCAP_ERRBUF_SIZE);
- free(buf);
- return (NULL);
+ ret = NULL;
+ } else {
+ /*
+ * Return the name of the first device on the list.
+ */
+ (void)strlcpy(device, alldevs->name, sizeof(device));
+ ret = device;
}
- (void)strlcpy(device, mp->ifr_name, sizeof(device));
- free(buf);
- return (device);
-#endif
+ pcap_freealldevs(alldevs);
+ return (ret);
}
int
diff --git a/contrib/libpcap/llc.h b/contrib/libpcap/llc.h
index 2800315..ffd3a60 100644
--- a/contrib/libpcap/llc.h
+++ b/contrib/libpcap/llc.h
@@ -18,7 +18,7 @@
* WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
- * @(#) $Header: /tcpdump/master/libpcap/llc.h,v 1.1 2001/01/14 21:26:53 guy Exp $ (LBL)
+ * @(#) $Header: /tcpdump/master/libpcap/llc.h,v 1.2 2001/01/28 09:44:50 guy Exp $ (LBL)
*/
/*
@@ -58,9 +58,12 @@
#ifndef LLCSAP_SNAP
#define LLCSAP_SNAP 0xaa
#endif
-#ifndef LLCSAP_ISONS
-#define LLCSAP_ISONS 0xfe
-#endif
#ifndef LLCSAP_IPX
#define LLCSAP_IPX 0xe0
#endif
+#ifndef LLCSAP_NETBEUI
+#define LLCSAP_NETBEUI 0xf0
+#endif
+#ifndef LLCSAP_ISONS
+#define LLCSAP_ISONS 0xfe
+#endif
diff --git a/contrib/libpcap/optimize.c b/contrib/libpcap/optimize.c
index bb3b6c9..a3ef13e 100644
--- a/contrib/libpcap/optimize.c
+++ b/contrib/libpcap/optimize.c
@@ -22,7 +22,7 @@
*/
#ifndef lint
static const char rcsid[] =
- "@(#) $Header: /tcpdump/master/libpcap/optimize.c,v 1.67 2000/11/19 13:37:20 itojun Exp $ (LBL)";
+ "@(#) $Header: /tcpdump/master/libpcap/optimize.c,v 1.69 2001/11/12 21:57:06 fenner Exp $ (LBL)";
#endif
#ifdef HAVE_CONFIG_H
@@ -940,7 +940,10 @@ opt_stmt(s, val, alter)
op = BPF_OP(s->code);
if (alter) {
if (s->k == 0) {
- if (op == BPF_ADD || op == BPF_SUB ||
+ /* don't optimize away "sub #0"
+ * as it may be needed later to
+ * fixup the generated math code */
+ if (op == BPF_ADD ||
op == BPF_LSH || op == BPF_RSH ||
op == BPF_OR) {
s->code = NOP;
@@ -1578,8 +1581,10 @@ opt_loop(root, do_stmts)
{
#ifdef BDEBUG
- if (dflag > 1)
+ if (dflag > 1) {
+ printf("opt_loop(root, %d) begin\n", do_stmts);
opt_dump(root);
+ }
#endif
do {
done = 1;
@@ -1590,8 +1595,10 @@ opt_loop(root, do_stmts)
find_edom(root);
opt_blks(root, do_stmts);
#ifdef BDEBUG
- if (dflag > 1)
+ if (dflag > 1) {
+ printf("opt_loop(root, %d) bottom, done=%d\n", do_stmts, done);
opt_dump(root);
+ }
#endif
} while (!done);
}
@@ -1611,7 +1618,19 @@ bpf_optimize(rootp)
opt_loop(root, 0);
opt_loop(root, 1);
intern_blocks(root);
+#ifdef BDEBUG
+ if (dflag > 1) {
+ printf("after intern_blocks()\n");
+ opt_dump(root);
+ }
+#endif
opt_root(rootp);
+#ifdef BDEBUG
+ if (dflag > 1) {
+ printf("after opt_root()\n");
+ opt_dump(root);
+ }
+#endif
opt_cleanup();
}
@@ -2075,7 +2094,7 @@ icode_to_fcode(root, lenp)
struct bpf_insn *fp;
/*
- * Loop doing convert_codr_r() until no branches remain
+ * Loop doing convert_code_r() until no branches remain
* with too-large offsets.
*/
while (1) {
diff --git a/contrib/libpcap/pcap-bpf.c b/contrib/libpcap/pcap-bpf.c
index fc56365..0d97d41 100644
--- a/contrib/libpcap/pcap-bpf.c
+++ b/contrib/libpcap/pcap-bpf.c
@@ -20,7 +20,7 @@
*/
#ifndef lint
static const char rcsid[] =
- "@(#) $Header: /tcpdump/master/libpcap/pcap-bpf.c,v 1.44 2000/10/28 00:01:28 guy Exp $ (LBL)";
+ "@(#) $Header: /tcpdump/master/libpcap/pcap-bpf.c,v 1.48 2001/12/10 07:14:14 guy Exp $ (LBL)";
#endif
#ifdef HAVE_CONFIG_H
@@ -35,6 +35,16 @@ static const char rcsid[] =
#include <sys/ioctl.h>
#include <net/if.h>
+#ifdef _AIX
+/*
+ * XXX - I'm guessing here AIX defines IFT_ values in <net/if_types.h>,
+ * as BSD does. If not, this code won't compile, but, if not, you
+ * want to send us a bug report and fall back on using DLPI.
+ * It's not as if BPF used to work right on AIX before this change;
+ * this change attempts to fix the fact that it didn't....
+ */
+#include <net/if_types.h> /* for IFT_ values */
+#endif
#include <ctype.h>
#include <errno.h>
@@ -57,6 +67,19 @@ pcap_stats(pcap_t *p, struct pcap_stat *ps)
{
struct bpf_stat s;
+ /*
+ * "ps_recv" counts packets handed to the filter, not packets
+ * that passed the filter. This includes packets later dropped
+ * because we ran out of buffer space.
+ *
+ * "ps_drop" counts packets dropped inside the BPF device
+ * because we ran out of buffer space. It doesn't count
+ * packets dropped by the interface driver. It counts
+ * only packets that passed the filter.
+ *
+ * Both statistics include packets not yet read from the kernel
+ * by libpcap, and thus not yet seen by the application.
+ */
if (ioctl(p->fd, BIOCGSTATS, (caddr_t)&s) < 0) {
snprintf(p->errbuf, PCAP_ERRBUF_SIZE, "BIOCGSTATS: %s",
pcap_strerror(errno));
@@ -123,6 +146,20 @@ pcap_read(pcap_t *p, int cnt, pcap_handler callback, u_char *user)
/*
* XXX A bpf_hdr matches a pcap_pkthdr.
*/
+#ifdef _AIX
+ /*
+ * AIX's BPF returns seconds/nanoseconds time stamps, not
+ * seconds/microseconds time stamps.
+ *
+ * XXX - I'm guessing here that it's a "struct timestamp";
+ * if not, this code won't compile, but, if not, you
+ * want to send us a bug report and fall back on using
+ * DLPI. It's not as if BPF used to work right on
+ * AIX before this change; this change attempts to fix
+ * the fact that it didn't....
+ */
+ bhp->bh_tstamp.tv_usec = bhp->bh_tstamp.tv_usec/1000;
+#endif
(*callback)(user, (struct pcap_pkthdr*)bp, bp + hdrlen);
bp += BPF_WORDALIGN(caplen + hdrlen);
if (++n >= cnt && cnt > 0) {
@@ -235,17 +272,32 @@ pcap_open_live(char *device, int snaplen, int promisc, int to_ms, char *ebuf)
pcap_strerror(errno));
goto bad;
}
-#ifdef __OpenBSD__
+#ifdef _AIX
+ /*
+ * AIX's BPF returns IFF_ types, not DLT_ types, in BIOCGDLT.
+ */
switch (v) {
- case DLT_LOOP:
+
+ case IFT_ETHER:
+ case IFT_ISO88023:
+ v = DLT_EN10MB;
+ break;
+
+ case IFT_FDDI:
+ v = DLT_FDDI;
+ break;
+
+ case IFT_ISO88025:
+ v = DLT_IEEE802;
+ break;
+
+ default:
/*
- * XXX - DLT_LOOP has a network-byte-order, rather than
- * a host-byte-order, AF_ value as the link-layer
- * header; will the BPF code generator handle that
- * correctly on little-endian machines?
+ * We don't know what to map this to yet.
*/
- v = DLT_NULL;
- break;
+ snprintf(ebuf, PCAP_ERRBUF_SIZE, "unknown interface type %lu",
+ v);
+ goto bad;
}
#endif
#if _BSDI_VERSION - 0 >= 199510
@@ -340,9 +392,13 @@ pcap_open_live(char *device, int snaplen, int promisc, int to_ms, char *ebuf)
#endif /* BIOCIMMEDIATE */
#endif /* _AIX */
- if (promisc)
+ if (promisc) {
/* set promiscuous mode, okay if it fails */
- (void)ioctl(p->fd, BIOCPROMISC, NULL);
+ if (ioctl(p->fd, BIOCPROMISC, NULL) < 0) {
+ snprintf(ebuf, PCAP_ERRBUF_SIZE, "BIOCPROMISC: %s",
+ pcap_strerror(errno));
+ }
+ }
if (ioctl(fd, BIOCGBLEN, (caddr_t)&v) < 0) {
snprintf(ebuf, PCAP_ERRBUF_SIZE, "BIOCGBLEN: %s",
diff --git a/contrib/libpcap/pcap-dlpi.c b/contrib/libpcap/pcap-dlpi.c
index 1a152bc..16a36c5 100644
--- a/contrib/libpcap/pcap-dlpi.c
+++ b/contrib/libpcap/pcap-dlpi.c
@@ -38,7 +38,7 @@
#ifndef lint
static const char rcsid[] =
- "@(#) $Header: /tcpdump/master/libpcap/pcap-dlpi.c,v 1.63 2000/11/22 05:32:55 guy Exp $ (LBL)";
+ "@(#) $Header: /tcpdump/master/libpcap/pcap-dlpi.c,v 1.74 2001/12/10 07:14:15 guy Exp $ (LBL)";
#endif
#ifdef HAVE_CONFIG_H
@@ -89,12 +89,17 @@ static const char rcsid[] =
#endif
#ifndef PCAP_DEV_PREFIX
+#ifdef _AIX
+#define PCAP_DEV_PREFIX "/dev/dlpi"
+#else
#define PCAP_DEV_PREFIX "/dev"
#endif
+#endif
#define MAXDLBUF 8192
/* Forwards */
+static char *split_dname(char *, int *, char *);
static int dlattachreq(int, bpf_u_int32, char *);
static int dlbindack(int, char *, char *);
static int dlbindreq(int, bpf_u_int32, char *);
@@ -102,6 +107,8 @@ static int dlinfoack(int, char *, char *);
static int dlinforeq(int, char *);
static int dlokack(int, const char *, char *, char *);
static int recv_ack(int, int, const char *, char *, char *);
+static char *dlstrerror(bpf_u_int32);
+static char *dlprim(bpf_u_int32);
static int dlpromisconreq(int, bpf_u_int32, char *);
#if defined(HAVE_SOLARIS) && defined(HAVE_SYS_BUFMOD_H)
static char *get_release(bpf_u_int32 *, bpf_u_int32 *, bpf_u_int32 *);
@@ -121,6 +128,23 @@ int
pcap_stats(pcap_t *p, struct pcap_stat *ps)
{
+ /*
+ * "ps_recv" counts packets handed to the filter, not packets
+ * that passed the filter. As filtering is done in userland,
+ * this does not include packets dropped because we ran out
+ * of buffer space.
+ *
+ * "ps_drop" counts packets dropped inside the DLPI service
+ * provider device device because of flow control requirements
+ * or resource exhaustion; it doesn't count packets dropped by
+ * the interface driver, or packets dropped upstream. As
+ * filtering is done in userland, it counts packets regardless
+ * of whether they would've passed the filter.
+ *
+ * These statistics don't include packets not yet read from
+ * the kernel by libpcap, but they may include packets not
+ * yet read from libpcap by the application.
+ */
*ps = p->md.stat;
return (0);
}
@@ -226,9 +250,8 @@ pcap_t *
pcap_open_live(char *device, int snaplen, int promisc, int to_ms, char *ebuf)
{
register char *cp;
- char *eos;
register pcap_t *p;
- register int ppa;
+ int ppa;
register dl_info_ack_t *infop;
#ifdef HAVE_SYS_BUFMOD_H
bpf_u_int32 ss, flag;
@@ -249,6 +272,7 @@ pcap_open_live(char *device, int snaplen, int promisc, int to_ms, char *ebuf)
return (NULL);
}
memset(p, 0, sizeof(*p));
+ p->fd = -1; /* indicate that it hasn't been opened yet */
#ifdef HAVE_DEV_DLPI
/*
@@ -262,20 +286,12 @@ pcap_open_live(char *device, int snaplen, int promisc, int to_ms, char *ebuf)
strlcpy(dname, cp, sizeof(dname));
/*
- * Split the name into a device type and a unit number.
+ * Split the device name into a device type name and a unit number;
+ * chop off the unit number, so "dname" is just a device type name.
*/
- cp = strpbrk(dname, "0123456789");
- if (cp == NULL) {
- snprintf(ebuf, PCAP_ERRBUF_SIZE,
- "%s missing unit number", device);
- goto bad;
- }
- ppa = strtol(cp, &eos, 10);
- if (*eos != '\0') {
- snprintf(ebuf, PCAP_ERRBUF_SIZE,
- "%s bad unit number", device);
+ cp = split_dname(dname, &ppa, ebuf);
+ if (cp == NULL)
goto bad;
- }
*cp = '\0';
/*
@@ -305,30 +321,33 @@ pcap_open_live(char *device, int snaplen, int promisc, int to_ms, char *ebuf)
goto bad;
#else
/*
- ** Determine device and ppa
- */
- cp = strpbrk(device, "0123456789");
- if (cp == NULL) {
- snprintf(ebuf, PCAP_ERRBUF_SIZE, "%s missing unit number",
- device);
- goto bad;
- }
- ppa = strtol(cp, &eos, 10);
- if (*eos != '\0') {
- snprintf(ebuf, PCAP_ERRBUF_SIZE, "%s bad unit number", device);
+ * Get the unit number, and a pointer to the end of the device
+ * type name.
+ */
+ cp = split_dname(device, &ppa, ebuf);
+ if (cp == NULL)
goto bad;
- }
+ /*
+ * If the device name begins with "/", assume it begins with
+ * the pathname of the directory containing the device to open;
+ * otherwise, concatenate the device directory name and the
+ * device name.
+ */
if (*device == '/')
strlcpy(dname, device, sizeof(dname));
else
snprintf(dname, sizeof(dname), "%s/%s", PCAP_DEV_PREFIX,
device);
+ /*
+ * Make a copy of the device pathname, and then remove the unit
+ * number from the device pathname.
+ */
+ strlcpy(dname2, dname, sizeof(dname));
+ *(dname + strlen(dname) - strlen(cp)) = '\0';
+
/* Try device without unit number */
- strlcpy(dname2, dname, sizeof(dname2));
- cp = strchr(dname, *cp);
- *cp = '\0';
if ((p->fd = open(dname, O_RDWR)) < 0) {
if (errno != ENOENT) {
snprintf(ebuf, PCAP_ERRBUF_SIZE, "%s: %s", dname,
@@ -366,10 +385,24 @@ pcap_open_live(char *device, int snaplen, int promisc, int to_ms, char *ebuf)
*/
#if !defined(HAVE_HPUX9) && !defined(HAVE_HPUX10_20) && !defined(sinix)
#ifdef _AIX
- /* According to IBM's AIX Support Line, the dl_sap value
- ** should not be less than 0x600 (1536) for standard ethernet
- */
- if (dlbindreq(p->fd, 1537, ebuf) < 0 ||
+ /* According to IBM's AIX Support Line, the dl_sap value
+ ** should not be less than 0x600 (1536) for standard Ethernet.
+ ** However, we seem to get DL_BADADDR - "DLSAP addr in improper
+ ** format or invalid" - errors if we use 1537 on the "tr0"
+ ** device, which, given that its name starts with "tr" and that
+ ** it's IBM, probably means a Token Ring device. (Perhaps we
+ ** need to use 1537 on "/dev/dlpi/en" because that device is for
+ ** D/I/X Ethernet, the "SAP" is actually an Ethernet type, and
+ ** it rejects invalid Ethernet types.)
+ **
+ ** So if 1537 fails, we try 2, as Hyung Sik Yoon of IBM Korea
+ ** says that works on Token Ring (he says that 0 does *not*
+ ** work; perhaps that's considered an invalid LLC SAP value - I
+ ** assume the SAP value in a DLPI bind is an LLC SAP for network
+ ** types that use 802.2 LLC).
+ */
+ if ((dlbindreq(p->fd, 1537, ebuf) < 0 &&
+ dlbindreq(p->fd, 2, ebuf) < 0) ||
#else
if (dlbindreq(p->fd, 0, ebuf) < 0 ||
#endif
@@ -448,6 +481,11 @@ pcap_open_live(char *device, int snaplen, int promisc, int to_ms, char *ebuf)
p->offset = 3;
break;
+ case DL_TPR:
+ p->linktype = DLT_IEEE802;
+ p->offset = 2;
+ break;
+
default:
snprintf(ebuf, PCAP_ERRBUF_SIZE, "unknown mac type %lu",
infop->dl_mac_type);
@@ -547,10 +585,50 @@ pcap_open_live(char *device, int snaplen, int promisc, int to_ms, char *ebuf)
return (p);
bad:
+ if (p->fd >= 0)
+ close(p->fd);
free(p);
return (NULL);
}
+/*
+ * Split a device name into a device type name and a unit number;
+ * return the a pointer to the beginning of the unit number, which
+ * is the end of the device type name, and set "*unitp" to the unit
+ * number.
+ *
+ * Returns NULL on error, and fills "ebuf" with an error message.
+ */
+static char *
+split_dname(char *device, int *unitp, char *ebuf)
+{
+ char *cp;
+ char *eos;
+ int unit;
+
+ /*
+ * Look for a number at the end of the device name string.
+ */
+ cp = device + strlen(device) - 1;
+ if (*cp < '0' || *cp > '9') {
+ snprintf(ebuf, PCAP_ERRBUF_SIZE, "%s missing unit number",
+ device);
+ return (NULL);
+ }
+
+ /* Digits at end of string are unit number */
+ while (cp-1 >= device && *(cp-1) >= '0' && *(cp-1) <= '9')
+ cp--;
+
+ unit = strtol(cp, &eos, 10);
+ if (*eos != '\0') {
+ snprintf(ebuf, PCAP_ERRBUF_SIZE, "%s bad unit number", device);
+ return (NULL);
+ }
+ *unitp = unit;
+ return (cp);
+}
+
int
pcap_setfilter(pcap_t *p, struct bpf_program *fp)
{
@@ -607,54 +685,245 @@ recv_ack(int fd, int size, const char *what, char *bufp, char *ebuf)
#ifdef DL_HP_PPA_ACK
case DL_HP_PPA_ACK:
#endif
-
/* These are OK */
break;
case DL_ERROR_ACK:
switch (dlp->error_ack.dl_errno) {
- case DL_BADPPA:
- snprintf(ebuf, PCAP_ERRBUF_SIZE,
- "recv_ack: %s bad ppa (device unit)", what);
- break;
-
-
case DL_SYSERR:
- snprintf(ebuf, PCAP_ERRBUF_SIZE, "recv_ack: %s: %s",
- what, pcap_strerror(dlp->error_ack.dl_unix_errno));
- break;
-
- case DL_UNSUPPORTED:
snprintf(ebuf, PCAP_ERRBUF_SIZE,
- "recv_ack: %s: Service not supplied by provider",
- what);
+ "recv_ack: %s: UNIX error - %s",
+ what, pcap_strerror(dlp->error_ack.dl_unix_errno));
break;
default:
- snprintf(ebuf, PCAP_ERRBUF_SIZE,
- "recv_ack: %s error 0x%x",
- what, (bpf_u_int32)dlp->error_ack.dl_errno);
+ snprintf(ebuf, PCAP_ERRBUF_SIZE, "recv_ack: %s: %s",
+ what, dlstrerror(dlp->error_ack.dl_errno));
break;
}
return (-1);
default:
snprintf(ebuf, PCAP_ERRBUF_SIZE,
- "recv_ack: %s unexpected primitive ack 0x%x ",
- what, (bpf_u_int32)dlp->dl_primitive);
+ "recv_ack: %s: Unexpected primitive ack %s",
+ what, dlprim(dlp->dl_primitive));
return (-1);
}
if (ctl.len < size) {
snprintf(ebuf, PCAP_ERRBUF_SIZE,
- "recv_ack: %s ack too small (%d < %d)",
+ "recv_ack: %s: Ack too small (%d < %d)",
what, ctl.len, size);
return (-1);
}
return (ctl.len);
}
+static char *
+dlstrerror(bpf_u_int32 dl_errno)
+{
+ static char errstring[6+2+8+1];
+
+ switch (dl_errno) {
+
+ case DL_ACCESS:
+ return ("Improper permissions for request");
+
+ case DL_BADADDR:
+ return ("DLSAP addr in improper format or invalid");
+
+ case DL_BADCORR:
+ return ("Seq number not from outstand DL_CONN_IND");
+
+ case DL_BADDATA:
+ return ("User data exceeded provider limit");
+
+ case DL_BADPPA:
+#ifdef HAVE_DEV_DLPI
+ /*
+ * With a single "/dev/dlpi" device used for all
+ * DLPI providers, PPAs have nothing to do with
+ * unit numbers.
+ */
+ return ("Specified PPA was invalid");
+#else
+ /*
+ * We have separate devices for separate devices;
+ * the PPA is just the unit number.
+ */
+ return ("Specified PPA (device unit) was invalid");
+#endif
+
+ case DL_BADPRIM:
+ return ("Primitive received not known by provider");
+
+ case DL_BADQOSPARAM:
+ return ("QOS parameters contained invalid values");
+
+ case DL_BADQOSTYPE:
+ return ("QOS structure type is unknown/unsupported");
+
+ case DL_BADSAP:
+ return ("Bad LSAP selector");
+
+ case DL_BADTOKEN:
+ return ("Token used not an active stream");
+
+ case DL_BOUND:
+ return ("Attempted second bind with dl_max_conind");
+
+ case DL_INITFAILED:
+ return ("Physical link initialization failed");
+
+ case DL_NOADDR:
+ return ("Provider couldn't allocate alternate address");
+
+ case DL_NOTINIT:
+ return ("Physical link not initialized");
+
+ case DL_OUTSTATE:
+ return ("Primitive issued in improper state");
+
+ case DL_SYSERR:
+ return ("UNIX system error occurred");
+
+ case DL_UNSUPPORTED:
+ return ("Requested service not supplied by provider");
+
+ case DL_UNDELIVERABLE:
+ return ("Previous data unit could not be delivered");
+
+ case DL_NOTSUPPORTED:
+ return ("Primitive is known but not supported");
+
+ case DL_TOOMANY:
+ return ("Limit exceeded");
+
+ case DL_NOTENAB:
+ return ("Promiscuous mode not enabled");
+
+ case DL_BUSY:
+ return ("Other streams for PPA in post-attached");
+
+ case DL_NOAUTO:
+ return ("Automatic handling XID&TEST not supported");
+
+ case DL_NOXIDAUTO:
+ return ("Automatic handling of XID not supported");
+
+ case DL_NOTESTAUTO:
+ return ("Automatic handling of TEST not supported");
+
+ case DL_XIDAUTO:
+ return ("Automatic handling of XID response");
+
+ case DL_TESTAUTO:
+ return ("Automatic handling of TEST response");
+
+ case DL_PENDING:
+ return ("Pending outstanding connect indications");
+
+ default:
+ sprintf(errstring, "Error %02x", dl_errno);
+ return (errstring);
+ }
+}
+
+static char *
+dlprim(bpf_u_int32 prim)
+{
+ static char primbuf[80];
+
+ switch (prim) {
+
+ case DL_INFO_REQ:
+ return ("DL_INFO_REQ");
+
+ case DL_INFO_ACK:
+ return ("DL_INFO_ACK");
+
+ case DL_ATTACH_REQ:
+ return ("DL_ATTACH_REQ");
+
+ case DL_DETACH_REQ:
+ return ("DL_DETACH_REQ");
+
+ case DL_BIND_REQ:
+ return ("DL_BIND_REQ");
+
+ case DL_BIND_ACK:
+ return ("DL_BIND_ACK");
+
+ case DL_UNBIND_REQ:
+ return ("DL_UNBIND_REQ");
+
+ case DL_OK_ACK:
+ return ("DL_OK_ACK");
+
+ case DL_ERROR_ACK:
+ return ("DL_ERROR_ACK");
+
+ case DL_SUBS_BIND_REQ:
+ return ("DL_SUBS_BIND_REQ");
+
+ case DL_SUBS_BIND_ACK:
+ return ("DL_SUBS_BIND_ACK");
+
+ case DL_UNITDATA_REQ:
+ return ("DL_UNITDATA_REQ");
+
+ case DL_UNITDATA_IND:
+ return ("DL_UNITDATA_IND");
+
+ case DL_UDERROR_IND:
+ return ("DL_UDERROR_IND");
+
+ case DL_UDQOS_REQ:
+ return ("DL_UDQOS_REQ");
+
+ case DL_CONNECT_REQ:
+ return ("DL_CONNECT_REQ");
+
+ case DL_CONNECT_IND:
+ return ("DL_CONNECT_IND");
+
+ case DL_CONNECT_RES:
+ return ("DL_CONNECT_RES");
+
+ case DL_CONNECT_CON:
+ return ("DL_CONNECT_CON");
+
+ case DL_TOKEN_REQ:
+ return ("DL_TOKEN_REQ");
+
+ case DL_TOKEN_ACK:
+ return ("DL_TOKEN_ACK");
+
+ case DL_DISCONNECT_REQ:
+ return ("DL_DISCONNECT_REQ");
+
+ case DL_DISCONNECT_IND:
+ return ("DL_DISCONNECT_IND");
+
+ case DL_RESET_REQ:
+ return ("DL_RESET_REQ");
+
+ case DL_RESET_IND:
+ return ("DL_RESET_IND");
+
+ case DL_RESET_RES:
+ return ("DL_RESET_RES");
+
+ case DL_RESET_CON:
+ return ("DL_RESET_CON");
+
+ default:
+ (void) sprintf(primbuf, "unknown primitive 0x%x", prim);
+ return (primbuf);
+ }
+}
+
static int
dlattachreq(int fd, bpf_u_int32 ppa, char *ebuf)
{
@@ -765,7 +1034,7 @@ get_release(bpf_u_int32 *majorp, bpf_u_int32 *minorp, bpf_u_int32 *microp)
if (sysinfo(SI_RELEASE, buf, sizeof(buf)) < 0)
return ("?");
cp = buf;
- if (!isdigit(*cp))
+ if (!isdigit((unsigned char)*cp))
return (buf);
*majorp = strtol(cp, &cp, 10);
if (*cp++ != '.')
@@ -829,18 +1098,85 @@ get_dlpi_ppa(register int fd, register const char *device, register int unit,
register u_long majdev;
struct stat statbuf;
dl_hp_ppa_req_t req;
- bpf_u_int32 buf[MAXDLBUF];
+ char buf[MAXDLBUF];
+ char *ppa_data_buf;
+ dl_hp_ppa_ack_t *dlp;
+ struct strbuf ctl;
+ int flags;
+ int ppa;
memset((char *)&req, 0, sizeof(req));
req.dl_primitive = DL_HP_PPA_REQ;
memset((char *)buf, 0, sizeof(buf));
- if (send_request(fd, (char *)&req, sizeof(req), "hpppa", ebuf) < 0 ||
- recv_ack(fd, DL_HP_PPA_ACK_SIZE, "hpppa", (char *)buf, ebuf) < 0)
+ if (send_request(fd, (char *)&req, sizeof(req), "hpppa", ebuf) < 0)
return (-1);
+ ctl.maxlen = DL_HP_PPA_ACK_SIZE;
+ ctl.len = 0;
+ ctl.buf = (char *)buf;
+
+ flags = 0;
+ /*
+ * DLPI may return a big chunk of data for a DL_HP_PPA_REQ. The normal
+ * recv_ack will fail because it set the maxlen to MAXDLBUF (8192)
+ * which is NOT big enough for a DL_HP_PPA_REQ.
+ *
+ * This causes libpcap applications to fail on a system with HP-APA
+ * installed.
+ *
+ * To figure out how big the returned data is, we first call getmsg
+ * to get the small head and peek at the head to get the actual data
+ * length, and then issue another getmsg to get the actual PPA data.
+ */
+ /* get the head first */
+ if (getmsg(fd, &ctl, (struct strbuf *)NULL, &flags) < 0) {
+ snprintf(ebuf, PCAP_ERRBUF_SIZE,
+ "get_dlpi_ppa: hpppa getmsg: %s", pcap_strerror(errno));
+ return (-1);
+ }
+
+ dlp = (dl_hp_ppa_ack_t *)ctl.buf;
+ if (dlp->dl_primitive != DL_HP_PPA_ACK) {
+ snprintf(ebuf, PCAP_ERRBUF_SIZE,
+ "get_dlpi_ppa: hpppa unexpected primitive ack 0x%x",
+ (bpf_u_int32)dlp->dl_primitive);
+ return (-1);
+ }
+
+ if (ctl.len < DL_HP_PPA_ACK_SIZE) {
+ snprintf(ebuf, PCAP_ERRBUF_SIZE,
+ "get_dlpi_ppa: hpppa ack too small (%d < %d)",
+ ctl.len, DL_HP_PPA_ACK_SIZE);
+ return (-1);
+ }
+
+ /* allocate buffer */
+ if ((ppa_data_buf = (char *)malloc(dlp->dl_length)) == NULL) {
+ snprintf(ebuf, PCAP_ERRBUF_SIZE,
+ "get_dlpi_ppa: hpppa malloc: %s", pcap_strerror(errno));
+ return (-1);
+ }
+ ctl.maxlen = dlp->dl_length;
+ ctl.len = 0;
+ ctl.buf = (char *)ppa_data_buf;
+ /* get the data */
+ if (getmsg(fd, &ctl, (struct strbuf *)NULL, &flags) < 0) {
+ snprintf(ebuf, PCAP_ERRBUF_SIZE,
+ "get_dlpi_ppa: hpppa getmsg: %s", pcap_strerror(errno));
+ free(ppa_data_buf);
+ return (-1);
+ }
+ if (ctl.len < dlp->dl_length) {
+ snprintf(ebuf, PCAP_ERRBUF_SIZE,
+ "get_dlpi_ppa: hpppa ack too small (%d < %d)",
+ ctl.len, dlp->dl_length);
+ free(ppa_data_buf);
+ return (-1);
+ }
+
ap = (dl_hp_ppa_ack_t *)buf;
- ipstart = (dl_hp_ppa_info_t *)((u_char *)ap + ap->dl_offset);
+ ipstart = (dl_hp_ppa_info_t *)ppa_data_buf;
ip = ipstart;
#ifdef HAVE_HP_PPA_INFO_T_DL_MODULE_ID_1
@@ -858,8 +1194,8 @@ get_dlpi_ppa(register int fd, register const char *device, register int unit,
* instance number.
*/
for (i = 0; i < ap->dl_count; i++) {
- if ((strcmp(ip->dl_module_id_1, device) == 0 ||
- strcmp(ip->dl_module_id_2, device) == 0) &&
+ if ((strcmp((const char *)ip->dl_module_id_1, device) == 0 ||
+ strcmp((const char *)ip->dl_module_id_2, device) == 0) &&
ip->dl_instance_num == unit)
break;
@@ -915,9 +1251,12 @@ get_dlpi_ppa(register int fd, register const char *device, register int unit,
if (ip->dl_hdw_state == HDW_DEAD) {
snprintf(ebuf, PCAP_ERRBUF_SIZE,
"%s%d: hardware state: DOWN\n", device, unit);
+ free(ppa_data_buf);
return (-1);
}
- return ((int)ip->dl_ppa);
+ ppa = ip->dl_ppa;
+ free(ppa_data_buf);
+ return (ppa);
}
#endif
diff --git a/contrib/libpcap/pcap-linux.c b/contrib/libpcap/pcap-linux.c
index 1199f8f..179cbc0 100644
--- a/contrib/libpcap/pcap-linux.c
+++ b/contrib/libpcap/pcap-linux.c
@@ -26,7 +26,7 @@
*/
#ifndef lint
static const char rcsid[] =
- "@(#) $Header: /tcpdump/master/libpcap/pcap-linux.c,v 1.51.2.3 2001/01/18 03:59:56 guy Exp $ (LBL)";
+ "@(#) $Header: /tcpdump/master/libpcap/pcap-linux.c,v 1.73 2001/12/10 07:14:16 guy Exp $ (LBL)";
#endif
/*
@@ -51,6 +51,24 @@ static const char rcsid[] =
* do, if another socket also requested promiscuous mode between
* the time when we opened the socket and the time when we close
* the socket.
+ *
+ * - MSG_TRUNC isn't supported, so you can't specify that "recvfrom()"
+ * return the amount of data that you could have read, rather than
+ * the amount that was returned, so we can't just allocate a buffer
+ * whose size is the snapshot length and pass the snapshot length
+ * as the byte count, and also pass MSG_TRUNC, so that the return
+ * value tells us how long the packet was on the wire.
+ *
+ * This means that, if we want to get the actual size of the packet,
+ * so we can return it in the "len" field of the packet header,
+ * we have to read the entire packet, not just the part that fits
+ * within the snapshot length, and thus waste CPU time copying data
+ * from the kernel that our caller won't see.
+ *
+ * We have to get the actual size, and supply it in "len", because
+ * otherwise, the IP dissector in tcpdump, for example, will complain
+ * about "truncated-ip", as the packet will appear to have been
+ * shorter, on the wire, than the IP header said it should have been.
*/
@@ -74,37 +92,38 @@ static const char rcsid[] =
#include <linux/if_ether.h>
#include <net/if_arp.h>
-#ifdef HAVE_NETPACKET_PACKET_H
-# include <netpacket/packet.h>
-
- /*
- * We assume this means we really do have PF_PACKET sockets.
- */
-# define HAVE_PF_PACKET_SOCKETS
-#else
- /*
- * Oh, joy. Some Linux distributions have 2.2 or later kernels and
- * libc5. On at least one of those systems (Slackware 4.0), it
- * appears that "/usr/include/sys/socket.h" includes <linux/socket.h>,
- * which means it picks up all the AF_, PF_, and SO_ definitions
- * appropriate for the current kernel; however, it also appears that
- * they did not see fit to provide a "/usr/include/netpacket/packet.h"
- * file.
- *
- * However, you should be able to get the right definitions by including
- * <linux/if_packet.h>.
- *
- * So if this system has PF_PACKET defined but doesn't have the
- * <netpacket/packet.h> header file, we include <linux/if_packet.h>
- * instead.
- */
-# ifdef PF_PACKET
-# include <linux/if_packet.h>
+/*
+ * If PF_PACKET is defined, we can use {SOCK_RAW,SOCK_DGRAM}/PF_PACKET
+ * sockets rather than SOCK_PACKET sockets.
+ *
+ * To use them, we include <linux/if_packet.h> rather than
+ * <netpacket/packet.h>; we do so because
+ *
+ * some Linux distributions (e.g., Slackware 4.0) have 2.2 or
+ * later kernels and libc5, and don't provide a <netpacket/packet.h>
+ * file;
+ *
+ * not all versions of glibc2 have a <netpacket/packet.h> file
+ * that defines stuff needed for some of the 2.4-or-later-kernel
+ * features, so if the system has a 2.4 or later kernel, we
+ * still can't use those features.
+ *
+ * We're already including a number of other <linux/XXX.h> headers, and
+ * this code is Linux-specific (no other OS has PF_PACKET sockets as
+ * a raw packet capture mechanism), so it's not as if you gain any
+ * useful portability by using <netpacket/packet.h>
+ *
+ * XXX - should we just include <linux/if_packet.h> even if PF_PACKET
+ * isn't defined? It only defines one data structure in 2.0.x, so
+ * it shouldn't cause any problems.
+ */
+#ifdef PF_PACKET
+# include <linux/if_packet.h>
/*
- * However, on at least some Linux distributions (for example, Red Hat
- * 5.2), there's no <netpacket/packet.h> file, but PF_PACKET is defined
- * if you include <sys/socket.h>, but <linux/if_packet.h> doesn't define
+ * On at least some Linux distributions (for example, Red Hat 5.2),
+ * there's no <netpacket/packet.h> file, but PF_PACKET is defined if
+ * you include <sys/socket.h>, but <linux/if_packet.h> doesn't define
* any of the PF_PACKET stuff such as "struct sockaddr_ll" or any of
* the PACKET_xxx stuff.
*
@@ -114,8 +133,7 @@ static const char rcsid[] =
# ifdef PACKET_HOST
# define HAVE_PF_PACKET_SOCKETS
# endif /* PACKET_HOST */
-# endif /* PF_PACKET */
-#endif /* HAVE_NETPACKET_PACKET_H */
+#endif /* PF_PACKET */
#ifdef SO_ATTACH_FILTER
#include <linux/types.h>
@@ -127,7 +145,15 @@ typedef int socklen_t;
#endif
#ifndef MSG_TRUNC
-#define MSG_TRUNC 0
+/*
+ * This is being compiled on a system that lacks MSG_TRUNC; define it
+ * with the value it has in the 2.2 and later kernels, so that, on
+ * those kernels, when we pass it in the flags argument to "recvfrom()"
+ * we're passing the right value and thus get the MSG_TRUNC behavior
+ * we want. (We don't get that behavior on 2.0[.x] kernels, because
+ * they didn't support MSG_TRUNC.)
+ */
+#define MSG_TRUNC 0x20
#endif
#define MAX_LINKHEADER_SIZE 256
@@ -142,7 +168,7 @@ typedef int socklen_t;
/*
* Prototypes for internal functions
*/
-static int map_arphrd_to_dlt(int arptype );
+static void map_arphrd_to_dlt(pcap_t *, int);
static int live_open_old(pcap_t *, char *, int, int, char *);
static int live_open_new(pcap_t *, char *, int, int, char *);
static int pcap_read_packet(pcap_t *, pcap_handler, u_char *);
@@ -163,6 +189,13 @@ static int iface_bind_old(int fd, const char *device, char *ebuf);
#ifdef SO_ATTACH_FILTER
static int fix_program(pcap_t *handle, struct sock_fprog *fcode);
static int fix_offset(struct bpf_insn *p);
+static int set_kernel_filter(pcap_t *handle, struct sock_fprog *fcode);
+static int reset_kernel_filter(pcap_t *handle);
+
+static struct sock_filter total_insn
+ = BPF_STMT(BPF_RET | BPF_K, 0);
+static struct sock_fprog total_fcode
+ = { 1, &total_insn };
#endif
/*
@@ -178,9 +211,13 @@ static int fix_offset(struct bpf_insn *p);
pcap_t *
pcap_open_live(char *device, int snaplen, int promisc, int to_ms, char *ebuf)
{
+ pcap_t *handle;
+ int mtu;
+ struct utsname utsname;
+
/* Allocate a handle for this session. */
- pcap_t *handle = malloc(sizeof(*handle));
+ handle = malloc(sizeof(*handle));
if (handle == NULL) {
snprintf(ebuf, PCAP_ERRBUF_SIZE, "malloc: %s",
pcap_strerror(errno));
@@ -200,6 +237,13 @@ pcap_open_live(char *device, int snaplen, int promisc, int to_ms, char *ebuf)
if (!device || strcmp(device, "any") == 0) {
device = NULL;
handle->md.device = strdup("any");
+ if (promisc) {
+ promisc = 0;
+ /* Just a warning. */
+ snprintf(ebuf, PCAP_ERRBUF_SIZE,
+ "Promiscuous mode not supported on the \"any\" device");
+ }
+
} else
handle->md.device = strdup(device);
@@ -234,6 +278,93 @@ pcap_open_live(char *device, int snaplen, int promisc, int to_ms, char *ebuf)
return NULL;
}
+ /*
+ * Compute the buffer size.
+ *
+ * If we're using SOCK_PACKET, this might be a 2.0[.x] kernel,
+ * and might require special handling - check.
+ */
+ if (handle->md.sock_packet && (uname(&utsname) < 0 ||
+ strncmp(utsname.release, "2.0", 3) == 0)) {
+ /*
+ * We're using a SOCK_PACKET structure, and either
+ * we couldn't find out what kernel release this is,
+ * or it's a 2.0[.x] kernel.
+ *
+ * In the 2.0[.x] kernel, a "recvfrom()" on
+ * a SOCK_PACKET socket, with MSG_TRUNC set, will
+ * return the number of bytes read, so if we pass
+ * a length based on the snapshot length, it'll
+ * return the number of bytes from the packet
+ * copied to userland, not the actual length
+ * of the packet.
+ *
+ * This means that, for example, the IP dissector
+ * in tcpdump will get handed a packet length less
+ * than the length in the IP header, and will
+ * complain about "truncated-ip".
+ *
+ * So we don't bother trying to copy from the
+ * kernel only the bytes in which we're interested,
+ * but instead copy them all, just as the older
+ * versions of libpcap for Linux did.
+ *
+ * The buffer therefore needs to be big enough to
+ * hold the largest packet we can get from this
+ * device. Unfortunately, we can't get the MRU
+ * of the network; we can only get the MTU. The
+ * MTU may be too small, in which case a packet larger
+ * than the buffer size will be truncated *and* we
+ * won't get the actual packet size.
+ *
+ * However, if the snapshot length is larger than
+ * the buffer size based on the MTU, we use the
+ * snapshot length as the buffer size, instead;
+ * this means that with a sufficiently large snapshot
+ * length we won't artificially truncate packets
+ * to the MTU-based size.
+ *
+ * This mess just one of many problems with packet
+ * capture on 2.0[.x] kernels; you really want a
+ * 2.2[.x] or later kernel if you want packet capture
+ * to work well.
+ */
+ mtu = iface_get_mtu(handle->fd, device, ebuf);
+ if (mtu == -1) {
+ close(handle->fd);
+ free(handle->md.device);
+ free(handle);
+ return NULL;
+ }
+ handle->bufsize = MAX_LINKHEADER_SIZE + mtu;
+ if (handle->bufsize < handle->snapshot)
+ handle->bufsize = handle->snapshot;
+ } else {
+ /*
+ * This is a 2.2[.x] or later kernel (we know that
+ * either because we're not using a SOCK_PACKET
+ * socket - PF_PACKET is supported only in 2.2
+ * and later kernels - or because we checked the
+ * kernel version).
+ *
+ * We can safely pass "recvfrom()" a byte count
+ * based on the snapshot length.
+ */
+ handle->bufsize = handle->snapshot;
+ }
+
+ /* Allocate the buffer */
+
+ handle->buffer = malloc(handle->bufsize + handle->offset);
+ if (!handle->buffer) {
+ snprintf(ebuf, PCAP_ERRBUF_SIZE,
+ "malloc: %s", pcap_strerror(errno));
+ close(handle->fd);
+ free(handle->md.device);
+ free(handle);
+ return NULL;
+ }
+
return handle;
}
@@ -260,6 +391,7 @@ pcap_read(pcap_t *handle, int max_packets, pcap_handler callback, u_char *user)
static int
pcap_read_packet(pcap_t *handle, pcap_handler callback, u_char *userdata)
{
+ u_char *bp;
int offset;
#ifdef HAVE_PF_PACKET_SOCKETS
struct sockaddr_ll from;
@@ -290,11 +422,12 @@ pcap_read_packet(pcap_t *handle, pcap_handler callback, u_char *userdata)
/* Receive a single packet from the kernel */
+ bp = handle->buffer + handle->offset;
do {
fromlen = sizeof(from);
packet_len = recvfrom(
- handle->fd, handle->buffer + offset + handle->offset,
- handle->md.readlen - offset, MSG_TRUNC,
+ handle->fd, bp + offset,
+ handle->bufsize - offset, MSG_TRUNC,
(struct sockaddr *) &from, &fromlen);
} while (packet_len == -1 && errno == EINTR);
@@ -337,7 +470,7 @@ pcap_read_packet(pcap_t *handle, pcap_handler callback, u_char *userdata)
*/
packet_len += SLL_HDR_LEN;
- hdrp = (struct sll_header *)handle->buffer;
+ hdrp = (struct sll_header *)bp;
/*
* Map the PACKET_ value to a LINUX_SLL_ value; we
@@ -422,7 +555,7 @@ pcap_read_packet(pcap_t *handle, pcap_handler callback, u_char *userdata)
/* Run the packet filter if not using kernel filter */
if (!handle->md.use_bpf && handle->fcode.bf_insns) {
- if (bpf_filter(handle->fcode.bf_insns, handle->buffer,
+ if (bpf_filter(handle->fcode.bf_insns, bp,
packet_len, caplen) == 0)
{
/* rejected by filter */
@@ -440,20 +573,139 @@ pcap_read_packet(pcap_t *handle, pcap_handler callback, u_char *userdata)
pcap_header.caplen = caplen;
pcap_header.len = packet_len;
- /* Call the user supplied callback function */
+ /*
+ * Count the packet.
+ *
+ * Arguably, we should count them before we check the filter,
+ * as on many other platforms "ps_recv" counts packets
+ * handed to the filter rather than packets that passed
+ * the filter, but if filtering is done in the kernel, we
+ * can't get a count of packets that passed the filter,
+ * and that would mean the meaning of "ps_recv" wouldn't
+ * be the same on all Linux systems.
+ *
+ * XXX - it's not the same on all systems in any case;
+ * ideally, we should have a "get the statistics" call
+ * that supplies more counts and indicates which of them
+ * it supplies, so that we supply a count of packets
+ * handed to the filter only on platforms where that
+ * information is available.
+ *
+ * We count them here even if we can get the packet count
+ * from the kernel, as we can only determine at run time
+ * whether we'll be able to get it from the kernel (if
+ * HAVE_TPACKET_STATS isn't defined, we can't get it from
+ * the kernel, but if it is defined, the library might
+ * have been built with a 2.4 or later kernel, but we
+ * might be running on a 2.2[.x] kernel without Alexey
+ * Kuznetzov's turbopacket patches, and thus the kernel
+ * might not be able to supply those statistics). We
+ * could, I guess, try, when opening the socket, to get
+ * the statistics, and if we can not increment the count
+ * here, but it's not clear that always incrementing
+ * the count is more expensive than always testing a flag
+ * in memory.
+ */
handle->md.stat.ps_recv++;
- callback(userdata, &pcap_header, handle->buffer + handle->offset);
+
+ /* Call the user supplied callback function */
+ callback(userdata, &pcap_header, bp);
return 1;
}
/*
* Get the statistics for the given packet capture handle.
- * FIXME: Currently does not report the number of dropped packets.
+ * Reports the number of dropped packets iff the kernel supports
+ * the PACKET_STATISTICS "getsockopt()" argument (2.4 and later
+ * kernels, and 2.2[.x] kernels with Alexey Kuznetzov's turbopacket
+ * patches); otherwise, that information isn't available, and we lie
+ * and report 0 as the count of dropped packets.
*/
int
pcap_stats(pcap_t *handle, struct pcap_stat *stats)
{
+#ifdef HAVE_TPACKET_STATS
+ struct tpacket_stats kstats;
+ socklen_t len = sizeof (struct tpacket_stats);
+
+ /*
+ * Try to get the packet counts from the kernel.
+ */
+ if (getsockopt(handle->fd, SOL_PACKET, PACKET_STATISTICS,
+ &kstats, &len) > -1) {
+ /*
+ * In "linux/net/packet/af_packet.c", at least in the
+ * 2.4.9 kernel, "tp_packets" is incremented for every
+ * packet that passes the packet filter *and* is
+ * successfully queued on the socket; "tp_drops" is
+ * incremented for every packet dropped because there's
+ * not enough free space in the socket buffer.
+ *
+ * When the statistics are returned for a PACKET_STATISTICS
+ * "getsockopt()" call, "tp_drops" is added to "tp_packets",
+ * so that "tp_packets" counts all packets handed to
+ * the PF_PACKET socket, including packets dropped because
+ * there wasn't room on the socket buffer - but not
+ * including packets that didn't pass the filter.
+ *
+ * In the BSD BPF, the count of received packets is
+ * incremented for every packet handed to BPF, regardless
+ * of whether it passed the filter.
+ *
+ * We can't make "pcap_stats()" work the same on both
+ * platforms, but the best approximation is to return
+ * "tp_packets" as the count of packets and "tp_drops"
+ * as the count of drops.
+ */
+ handle->md.stat.ps_recv = kstats.tp_packets;
+ handle->md.stat.ps_drop = kstats.tp_drops;
+ }
+ else
+ {
+ /*
+ * If the error was EOPNOTSUPP, fall through, so that
+ * if you build the library on a system with
+ * "struct tpacket_stats" and run it on a system
+ * that doesn't, it works as it does if the library
+ * is built on a system without "struct tpacket_stats".
+ */
+ if (errno != EOPNOTSUPP) {
+ snprintf(handle->errbuf, PCAP_ERRBUF_SIZE,
+ "pcap_stats: %s", pcap_strerror(errno));
+ return -1;
+ }
+ }
+#endif
+ /*
+ * On systems where the PACKET_STATISTICS "getsockopt()" argument
+ * is supported on PF_PACKET sockets:
+ *
+ * "ps_recv" counts only packets that *passed* the filter,
+ * not packets that didn't pass the filter. This includes
+ * packets later dropped because we ran out of buffer space.
+ *
+ * "ps_drop" counts packets dropped because we ran out of
+ * buffer space. It doesn't count packets dropped by the
+ * interface driver. It counts only packets that passed
+ * the filter.
+ *
+ * Both statistics include packets not yet read from the
+ * kernel by libpcap, and thus not yet seen by the application.
+ *
+ * On systems where the PACKET_STATISTICS "getsockopt()" argument
+ * is not supported on PF_PACKET sockets:
+ *
+ * "ps_recv" counts only packets that *passed* the filter,
+ * not packets that didn't pass the filter. It does not
+ * count packets dropped because we ran out of buffer
+ * space.
+ *
+ * "ps_drop" is not supported.
+ *
+ * "ps_recv" doesn't include packets not yet read from
+ * the kernel by libpcap.
+ */
*stats = handle->md.stat;
return 0;
}
@@ -557,8 +809,7 @@ pcap_setfilter(pcap_t *handle, struct bpf_program *filter)
}
if (can_filter_in_kernel) {
- if (setsockopt(handle->fd, SOL_SOCKET, SO_ATTACH_FILTER,
- &fcode, sizeof(fcode)) == 0)
+ if (set_kernel_filter(handle, &fcode) == 0)
{
/* Installation succeded - using kernel filter. */
handle->md.use_bpf = 1;
@@ -579,6 +830,17 @@ pcap_setfilter(pcap_t *handle, struct bpf_program *filter)
}
/*
+ * If we're not using the kernel filter, get rid of any kernel
+ * filter that might've been there before, e.g. because the
+ * previous filter could work in the kernel, or because some other
+ * code attached a filter to the socket by some means other than
+ * calling "pcap_setfilter()". Otherwise, the kernel filter may
+ * filter out packets that would pass the new userland filter.
+ */
+ if (!handle->md.use_bpf)
+ reset_kernel_filter(handle);
+
+ /*
* Free up the copy of the filter that was made by "fix_program()".
*/
if (fcode.filter != NULL)
@@ -591,37 +853,133 @@ pcap_setfilter(pcap_t *handle, struct bpf_program *filter)
/*
* Linux uses the ARP hardware type to identify the type of an
* interface. pcap uses the DLT_xxx constants for this. This
- * function maps the ARPHRD_xxx constant to an appropriate
- * DLT_xxx constant.
+ * function takes a pointer to a "pcap_t", and an ARPHRD_xxx
+ * constant, as arguments, and sets "handle->linktype" to the
+ * appropriate DLT_XXX constant and sets "handle->offset" to
+ * the appropriate value (to make "handle->offset" plus link-layer
+ * header length be a multiple of 4, so that the link-layer payload
+ * will be aligned on a 4-byte boundary when capturing packets).
+ * (If the offset isn't set here, it'll be 0; add code as appropriate
+ * for cases where it shouldn't be 0.)
*
- * Returns -1 if unable to map the type; we print a message and,
- * if we're using PF_PACKET/SOCK_RAW rather than PF_INET/SOCK_PACKET,
- * we fall back on using PF_PACKET/SOCK_DGRAM.
+ * Sets the link type to -1 if unable to map the type.
*/
-static int map_arphrd_to_dlt(int arptype)
+static void map_arphrd_to_dlt(pcap_t *handle, int arptype)
{
switch (arptype) {
+
case ARPHRD_ETHER:
case ARPHRD_METRICOM:
- case ARPHRD_LOOPBACK: return DLT_EN10MB;
- case ARPHRD_EETHER: return DLT_EN3MB;
- case ARPHRD_AX25: return DLT_AX25;
- case ARPHRD_PRONET: return DLT_PRONET;
- case ARPHRD_CHAOS: return DLT_CHAOS;
+ case ARPHRD_LOOPBACK:
+ handle->linktype = DLT_EN10MB;
+ handle->offset = 2;
+ break;
+
+ case ARPHRD_EETHER:
+ handle->linktype = DLT_EN3MB;
+ break;
+
+ case ARPHRD_AX25:
+ handle->linktype = DLT_AX25;
+ break;
+
+ case ARPHRD_PRONET:
+ handle->linktype = DLT_PRONET;
+ break;
+
+ case ARPHRD_CHAOS:
+ handle->linktype = DLT_CHAOS;
+ break;
+
#ifndef ARPHRD_IEEE802_TR
#define ARPHRD_IEEE802_TR 800 /* From Linux 2.4 */
#endif
case ARPHRD_IEEE802_TR:
- case ARPHRD_IEEE802: return DLT_IEEE802;
- case ARPHRD_ARCNET: return DLT_ARCNET;
- case ARPHRD_FDDI: return DLT_FDDI;
+ case ARPHRD_IEEE802:
+ handle->linktype = DLT_IEEE802;
+ handle->offset = 2;
+ break;
+
+ case ARPHRD_ARCNET:
+ handle->linktype = DLT_ARCNET;
+ break;
+
+ case ARPHRD_FDDI:
+ handle->linktype = DLT_FDDI;
+ handle->offset = 3;
+ break;
#ifndef ARPHRD_ATM /* FIXME: How to #include this? */
#define ARPHRD_ATM 19
#endif
- case ARPHRD_ATM: return DLT_ATM_CLIP;
+ case ARPHRD_ATM:
+ /*
+ * The Classical IP implementation in ATM for Linux
+ * supports both what RFC 1483 calls "LLC Encapsulation",
+ * in which each packet has an LLC header, possibly
+ * with a SNAP header as well, prepended to it, and
+ * what RFC 1483 calls "VC Based Multiplexing", in which
+ * different virtual circuits carry different network
+ * layer protocols, and no header is prepended to packets.
+ *
+ * They both have an ARPHRD_ type of ARPHRD_ATM, so
+ * you can't use the ARPHRD_ type to find out whether
+ * captured packets will have an LLC header, and,
+ * while there's a socket ioctl to *set* the encapsulation
+ * type, there's no ioctl to *get* the encapsulation type.
+ *
+ * This means that
+ *
+ * programs that dissect Linux Classical IP frames
+ * would have to check for an LLC header and,
+ * depending on whether they see one or not, dissect
+ * the frame as LLC-encapsulated or as raw IP (I
+ * don't know whether there's any traffic other than
+ * IP that would show up on the socket, or whether
+ * there's any support for IPv6 in the Linux
+ * Classical IP code);
+ *
+ * filter expressions would have to compile into
+ * code that checks for an LLC header and does
+ * the right thing.
+ *
+ * Both of those are a nuisance - and, at least on systems
+ * that support PF_PACKET sockets, we don't have to put
+ * up with those nuisances; instead, we can just capture
+ * in cooked mode. That's what we'll do.
+ */
+ handle->linktype = DLT_LINUX_SLL;
+ break;
+
+#ifndef ARPHRD_IEEE80211 /* From Linux 2.4.6 */
+#define ARPHRD_IEEE80211 801
+#endif
+ case ARPHRD_IEEE80211:
+ handle->linktype = DLT_IEEE802_11;
+ break;
case ARPHRD_PPP:
+ /*
+ * Some PPP code in the kernel supplies no link-layer
+ * header whatsoever to PF_PACKET sockets; other PPP
+ * code supplies PPP link-layer headers ("syncppp.c");
+ * some PPP code might supply random link-layer
+ * headers (PPP over ISDN - there's code in Ethereal,
+ * for example, to cope with PPP-over-ISDN captures
+ * with which the Ethereal developers have had to cope,
+ * heuristically trying to determine which of the
+ * oddball link-layer headers particular packets have).
+ *
+ * As such, we just punt, and run all PPP interfaces
+ * in cooked mode.
+ */
+ handle->linktype = DLT_LINUX_SLL;
+ break;
+
+ case ARPHRD_HDLC:
+ handle->linktype = DLT_C_HDLC;
+ break;
+
/* Not sure if this is correct for all tunnels, but it
* works for CIPE */
case ARPHRD_TUNNEL:
@@ -632,10 +990,23 @@ static int map_arphrd_to_dlt(int arptype)
case ARPHRD_CSLIP:
case ARPHRD_SLIP6:
case ARPHRD_CSLIP6:
- case ARPHRD_SLIP: return DLT_RAW;
- }
+ case ARPHRD_ADAPT:
+ case ARPHRD_SLIP:
+ /*
+ * XXX - should some of those be mapped to DLT_LINUX_SLL
+ * instead? Should we just map all of them to DLT_LINUX_SLL?
+ */
+ handle->linktype = DLT_RAW;
+ break;
- return -1;
+ case ARPHRD_LOCALTLK:
+ handle->linktype = DLT_LTALK;
+ break;
+
+ default:
+ handle->linktype = -1;
+ break;
+ }
}
/* ===== Functions to interface to the newer kernels ================== */
@@ -650,7 +1021,7 @@ live_open_new(pcap_t *handle, char *device, int promisc,
int to_ms, char *ebuf)
{
#ifdef HAVE_PF_PACKET_SOCKETS
- int sock_fd = -1, device_id, mtu, arptype;
+ int sock_fd = -1, device_id, arptype;
struct packet_mreq mr;
/* One shot loop used for error handling - bail out with break */
@@ -688,6 +1059,12 @@ live_open_new(pcap_t *handle, char *device, int promisc,
handle->md.lo_ifindex = iface_get_id(sock_fd, "lo", ebuf);
/*
+ * Default value for offset to align link-layer payload
+ * on a 4-byte boundary.
+ */
+ handle->offset = 0;
+
+ /*
* What kind of frames do we have to deal with? Fall back
* to cooked mode if we have an unknown interface type.
*/
@@ -699,21 +1076,20 @@ live_open_new(pcap_t *handle, char *device, int promisc,
arptype = iface_get_arptype(sock_fd, device, ebuf);
if (arptype == -1)
break;
- handle->linktype = map_arphrd_to_dlt(arptype);
+ map_arphrd_to_dlt(handle, arptype);
if (handle->linktype == -1 ||
+ handle->linktype == DLT_LINUX_SLL ||
(handle->linktype == DLT_EN10MB &&
(strncmp("isdn", device, 4) == 0 ||
- strncmp("isdY", device, 4) == 0)) ||
- (handle->linktype == DLT_RAW &&
- (strncmp("ippp", device, 4) == 0))) {
+ strncmp("isdY", device, 4) == 0))) {
/*
- * Unknown interface type (-1), or an ISDN
- * device (whose link-layer type we
- * can only determine by using APIs
- * that may be different on different
+ * Unknown interface type (-1), or a
+ * device we explicitly chose to run
+ * in cooked mode (e.g., PPP devices),
+ * or an ISDN device (whose link-layer
+ * type we can only determine by using
+ * APIs that may be different on different
* kernels) - reopen in cooked mode.
- *
- * XXX - do that with DLT_RAW as well?
*/
if (close(sock_fd) == -1) {
snprintf(ebuf, PCAP_ERRBUF_SIZE,
@@ -736,11 +1112,11 @@ live_open_new(pcap_t *handle, char *device, int promisc,
* update "map_arphrd_to_dlt()"
* to handle the new type.
*/
- fprintf(stderr,
- "Warning: arptype %d not "
+ snprintf(ebuf, PCAP_ERRBUF_SIZE,
+ "arptype %d not "
"supported by libpcap - "
"falling back to cooked "
- "socket\n",
+ "socket",
arptype);
}
handle->linktype = DLT_LINUX_SLL;
@@ -793,34 +1169,10 @@ live_open_new(pcap_t *handle, char *device, int promisc,
}
#endif
- /* Compute the buffersize */
-
- mtu = iface_get_mtu(sock_fd, device, ebuf);
- if (mtu == -1)
- break;
- handle->bufsize = MAX_LINKHEADER_SIZE + mtu;
-
- /* Fill in the pcap structure */
+ /* Save the socket FD in the pcap structure */
handle->fd = sock_fd;
- handle->offset = 0;
-
- handle->buffer = malloc(handle->bufsize);
- if (!handle->buffer) {
- snprintf(ebuf, PCAP_ERRBUF_SIZE,
- "malloc: %s", pcap_strerror(errno));
- break;
- }
- /*
- * This is a 2.2 or later kernel, as it has PF_PACKET;
- * "recvfrom()", when passed the MSG_TRUNC flag, will
- * return the actual length of the packet, not the
- * number of bytes from the packet copied to userland,
- * so we can safely pass it a byte count based on the
- * snapshot length.
- */
- handle->md.readlen = handle->snapshot;
return 1;
} while(0);
@@ -995,8 +1347,7 @@ static int
live_open_old(pcap_t *handle, char *device, int promisc,
int to_ms, char *ebuf)
{
- int sock_fd = -1, mtu, arptype;
- struct utsname utsname;
+ int sock_fd = -1, arptype;
struct ifreq ifr;
do {
@@ -1079,24 +1430,22 @@ live_open_old(pcap_t *handle, char *device, int promisc,
}
}
- /* Compute the buffersize */
-
- mtu = iface_get_mtu(sock_fd, device, ebuf);
- if (mtu == -1)
- break;
- handle->bufsize = MAX_LINKHEADER_SIZE + mtu;
- if (handle->bufsize < handle->snapshot)
- handle->bufsize = handle->snapshot;
-
/* All done - fill in the pcap handle */
arptype = iface_get_arptype(sock_fd, device, ebuf);
if (arptype == -1)
break;
+ /* Save the socket FD in the pcap structure */
+
handle->fd = sock_fd;
+
+ /*
+ * Default value for offset to align link-layer payload
+ * on a 4-byte boundary.
+ */
handle->offset = 0;
- handle->linktype = map_arphrd_to_dlt(arptype);
+
/*
* XXX - handle ISDN types here? We can't fall back on
* cooked sockets, so we'd have to figure out from the
@@ -1108,62 +1457,14 @@ live_open_old(pcap_t *handle, char *device, int promisc,
* type that has only an Ethernet packet type as
* a link-layer header.
*/
- if (handle->linktype == -1) {
+ map_arphrd_to_dlt(handle, arptype);
+ if (handle->linktype == -1 ||
+ handle->linktype == DLT_LINUX_SLL) {
snprintf(ebuf, PCAP_ERRBUF_SIZE,
"interface type of %s not supported", device);
break;
}
- handle->buffer = malloc(handle->bufsize);
- if (!handle->buffer) {
- snprintf(ebuf, PCAP_ERRBUF_SIZE,
- "malloc: %s", pcap_strerror(errno));
- break;
- }
- /*
- * This might be a 2.0[.x] kernel - check.
- */
- if (uname(&utsname) < 0 ||
- strncmp(utsname.release, "2.0", 3) == 0) {
- /*
- * Either we couldn't find out what kernel release
- * this is, or it's a 2.0[.x] kernel.
- *
- * In the 2.0[.x] kernel, a "recvfrom()" on
- * a SOCK_PACKET socket, with MSG_TRUNC set, will
- * return the number of bytes read, so if we pass
- * a length based on the snapshot length, it'll
- * return the number of bytes from the packet
- * copied to userland, not the actual length
- * of the packet.
- *
- * This means that, for example, the IP dissector
- * in tcpdump will get handed a packet length less
- * than the length in the IP header, and will
- * complain about "truncated-ip".
- *
- * So we don't bother trying to copy from the
- * kernel only the bytes in which we're interested,
- * but instead copy them all, just as the older
- * versions of libpcap for Linux did.
- *
- * Just one of many problems with packet capture
- * on 2.0[.x] kernels; you really want a 2.2[.x]
- * or later kernel if you want packet capture to
- * work well.
- */
- handle->md.readlen = handle->bufsize;
- } else {
- /*
- * This is a 2.2[.x] or later kernel (although
- * why we're using SOCK_PACKET on such a system
- * is unknown to me).
- *
- * We can safely pass "recvfrom()" a byte count
- * based on the snapshot length.
- */
- handle->md.readlen = handle->snapshot;
- }
return 1;
} while (0);
@@ -1239,7 +1540,7 @@ iface_get_arptype(int fd, const char *device, char *ebuf)
return ifr.ifr_hwaddr.sa_family;
}
-#ifdef HAVE_PF_PACKET_SOCKETS
+#ifdef SO_ATTACH_FILTER
static int
fix_program(pcap_t *handle, struct sock_fprog *fcode)
{
@@ -1363,4 +1664,108 @@ fix_offset(struct bpf_insn *p)
}
return 0;
}
+
+static int
+set_kernel_filter(pcap_t *handle, struct sock_fprog *fcode)
+{
+ int total_filter_on = 0;
+ int save_mode;
+ int ret;
+ int save_errno;
+
+ /*
+ * The socket filter code doesn't discard all packets queued
+ * up on the socket when the filter is changed; this means
+ * that packets that don't match the new filter may show up
+ * after the new filter is put onto the socket, if those
+ * packets haven't yet been read.
+ *
+ * This means, for example, that if you do a tcpdump capture
+ * with a filter, the first few packets in the capture might
+ * be packets that wouldn't have passed the filter.
+ *
+ * We therefore discard all packets queued up on the socket
+ * when setting a kernel filter. (This isn't an issue for
+ * userland filters, as the userland filtering is done after
+ * packets are queued up.)
+ *
+ * To flush those packets, we put the socket in read-only mode,
+ * and read packets from the socket until there are no more to
+ * read.
+ *
+ * In order to keep that from being an infinite loop - i.e.,
+ * to keep more packets from arriving while we're draining
+ * the queue - we put the "total filter", which is a filter
+ * that rejects all packets, onto the socket before draining
+ * the queue.
+ *
+ * This code deliberately ignores any errors, so that you may
+ * get bogus packets if an error occurs, rather than having
+ * the filtering done in userland even if it could have been
+ * done in the kernel.
+ */
+ if (setsockopt(handle->fd, SOL_SOCKET, SO_ATTACH_FILTER,
+ &total_fcode, sizeof(total_fcode)) == 0) {
+ char drain[1];
+
+ /*
+ * Note that we've put the total filter onto the socket.
+ */
+ total_filter_on = 1;
+
+ /*
+ * Save the socket's current mode, and put it in
+ * non-blocking mode; we drain it by reading packets
+ * until we get an error (which we assume is a
+ * "nothing more to be read" error).
+ */
+ save_mode = fcntl(handle->fd, F_GETFL, 0);
+ if (save_mode != -1 &&
+ fcntl(handle->fd, F_SETFL, save_mode | O_NONBLOCK) >= 0) {
+ while (recv(handle->fd, &drain, sizeof drain,
+ MSG_TRUNC) >= 0)
+ ;
+ fcntl(handle->fd, F_SETFL, save_mode);
+ }
+ }
+
+ /*
+ * Now attach the new filter.
+ */
+ ret = setsockopt(handle->fd, SOL_SOCKET, SO_ATTACH_FILTER,
+ fcode, sizeof(*fcode));
+ if (ret == -1 && total_filter_on) {
+ /*
+ * Well, we couldn't set that filter on the socket,
+ * but we could set the total filter on the socket.
+ *
+ * This could, for example, mean that the filter was
+ * too big to put into the kernel, so we'll have to
+ * filter in userland; in any case, we'll be doing
+ * filtering in userland, so we need to remove the
+ * total filter so we see packets.
+ */
+ save_errno = errno;
+
+ /*
+ * XXX - if this fails, we're really screwed;
+ * we have the total filter on the socket,
+ * and it won't come off. What do we do then?
+ */
+ reset_kernel_filter(handle);
+
+ errno = save_errno;
+ }
+ return ret;
+}
+
+static int
+reset_kernel_filter(pcap_t *handle)
+{
+ /* setsockopt() barfs unless it get a dummy parameter */
+ int dummy;
+
+ return setsockopt(handle->fd, SOL_SOCKET, SO_DETACH_FILTER,
+ &dummy, sizeof(dummy));
+}
#endif
diff --git a/contrib/libpcap/pcap-nit.c b/contrib/libpcap/pcap-nit.c
index 6be658d..fe67299 100644
--- a/contrib/libpcap/pcap-nit.c
+++ b/contrib/libpcap/pcap-nit.c
@@ -20,7 +20,7 @@
*/
#ifndef lint
static const char rcsid[] =
- "@(#) $Header: /tcpdump/master/libpcap/pcap-nit.c,v 1.39 2000/10/28 00:01:29 guy Exp $ (LBL)";
+ "@(#) $Header: /tcpdump/master/libpcap/pcap-nit.c,v 1.41 2001/12/10 07:14:18 guy Exp $ (LBL)";
#endif
#ifdef HAVE_CONFIG_H
@@ -75,6 +75,22 @@ int
pcap_stats(pcap_t *p, struct pcap_stat *ps)
{
+ /*
+ * "ps_recv" counts packets handed to the filter, not packets
+ * that passed the filter. As filtering is done in userland,
+ * this does not include packets dropped because we ran out
+ * of buffer space.
+ *
+ * "ps_drop" presumably counts packets dropped by the socket
+ * because of flow control requirements or resource exhaustion;
+ * it doesn't count packets dropped by the interface driver.
+ * As filtering is done in userland, it counts packets regardless
+ * of whether they would've passed the filter.
+ *
+ * These statistics don't include packets not yet read from the
+ * kernel by libpcap or packets not yet read from libpcap by the
+ * application.
+ */
*ps = p->md.stat;
return (0);
}
diff --git a/contrib/libpcap/pcap-pf.c b/contrib/libpcap/pcap-pf.c
index 2dec908..f29bc99 100644
--- a/contrib/libpcap/pcap-pf.c
+++ b/contrib/libpcap/pcap-pf.c
@@ -24,7 +24,7 @@
#ifndef lint
static const char rcsid[] =
- "@(#) $Header: /tcpdump/master/libpcap/pcap-pf.c,v 1.62 2000/10/28 00:01:30 guy Exp $ (LBL)";
+ "@(#) $Header: /tcpdump/master/libpcap/pcap-pf.c,v 1.65 2001/12/10 07:14:19 guy Exp $ (LBL)";
#endif
#ifdef HAVE_CONFIG_H
@@ -195,6 +195,42 @@ int
pcap_stats(pcap_t *p, struct pcap_stat *ps)
{
+ /*
+ * If packet filtering is being done in the kernel:
+ *
+ * "ps_recv" counts only packets that passed the filter.
+ * This does not include packets dropped because we
+ * ran out of buffer space. (XXX - perhaps it should,
+ * by adding "ps_drop" to "ps_recv", for compatibility
+ * with some other platforms. On the other hand, on
+ * some platforms "ps_recv" counts only packets that
+ * passed the filter, and on others it counts packets
+ * that didn't pass the filter....)
+ *
+ * "ps_drop" counts packets that passed the kernel filter
+ * (if any) but were dropped because the input queue was
+ * full.
+ *
+ * "ps_ifdrop" counts packets dropped by the network
+ * inteface (regardless of whether they would have passed
+ * the input filter, of course).
+ *
+ * If packet filtering is not being done in the kernel:
+ *
+ * "ps_recv" counts only packets that passed the filter.
+ *
+ * "ps_drop" counts packets that were dropped because the
+ * input queue was full, regardless of whether they passed
+ * the userland filter.
+ *
+ * "ps_ifdrop" counts packets dropped by the network
+ * inteface (regardless of whether they would have passed
+ * the input filter, of course).
+ *
+ * These statistics don't include packets not yet read from
+ * the kernel by libpcap, but they may include packets not
+ * yet read from libpcap by the application.
+ */
ps->ps_recv = p->md.TotAccepted;
ps->ps_drop = p->md.TotDrops;
ps->ps_ifdrop = p->md.TotMissed - p->md.OrigMissed;
@@ -265,21 +301,53 @@ your system may not be properly configured; see \"man packetfilter(4)\"\n",
p->linktype = DLT_FDDI;
break;
- default:
+#ifdef ENDT_SLIP
+ case ENDT_SLIP:
+ p->linktype = DLT_SLIP;
+ break;
+#endif
+
+#ifdef ENDT_PPP
+ case ENDT_PPP:
+ p->linktype = DLT_PPP;
+ break;
+#endif
+
+#ifdef ENDT_LOOPBACK
+ case ENDT_LOOPBACK:
/*
- * XXX
- * Currently, the Ultrix packet filter supports only
- * Ethernet and FDDI. Eventually, support for SLIP and PPP
- * (and possibly others: T1?) should be added.
+ * It appears to use Ethernet framing, at least on
+ * Digital UNIX 4.0.
*/
-#ifdef notdef
- warning(
- "Packet filter data-link type %d unknown, assuming Ethernet",
- devparams.end_dev_type);
-#endif
p->linktype = DLT_EN10MB;
p->offset = 2;
break;
+#endif
+
+#ifdef ENDT_TRN
+ case ENDT_TRN:
+ p->linktype = DLT_IEEE802;
+ break;
+#endif
+
+ default:
+ /*
+ * XXX - what about ENDT_IEEE802? The pfilt.h header
+ * file calls this "IEEE 802 networks (non-Ethernet)",
+ * but that doesn't specify a specific link layer type;
+ * it could be 802.4, or 802.5 (except that 802.5 is
+ * ENDT_TRN), or 802.6, or 802.11, or.... That's why
+ * DLT_IEEE802 was hijacked to mean Token Ring in various
+ * BSDs, and why we went along with that hijacking.
+ *
+ * XXX - what about ENDT_HDLC and ENDT_NULL?
+ * Presumably, as ENDT_OTHER is just "Miscellaneous
+ * framing", there's not much we can do, as that
+ * doesn't specify a particular type of header.
+ */
+ snprintf(ebuf, PCAP_ERRBUF_SIZE, "unknown data-link type %lu",
+ devparams.end_dev_type);
+ goto bad;
}
/* set truncation */
#ifdef PCAP_FDDIPAD
@@ -318,6 +386,8 @@ your system may not be properly configured; see \"man packetfilter(4)\"\n",
return (p);
bad:
+ if (p->fd >= 0)
+ close(p->fd);
free(p);
return (NULL);
}
diff --git a/contrib/libpcap/pcap-snit.c b/contrib/libpcap/pcap-snit.c
index 59cf3ac..d3aaf1d 100644
--- a/contrib/libpcap/pcap-snit.c
+++ b/contrib/libpcap/pcap-snit.c
@@ -25,7 +25,7 @@
#ifndef lint
static const char rcsid[] =
- "@(#) $Header: /tcpdump/master/libpcap/pcap-snit.c,v 1.54 2000/10/28 00:01:30 guy Exp $ (LBL)";
+ "@(#) $Header: /tcpdump/master/libpcap/pcap-snit.c,v 1.56 2001/12/10 07:14:20 guy Exp $ (LBL)";
#endif
#ifdef HAVE_CONFIG_H
@@ -88,6 +88,23 @@ int
pcap_stats(pcap_t *p, struct pcap_stat *ps)
{
+ /*
+ * "ps_recv" counts packets handed to the filter, not packets
+ * that passed the filter. As filtering is done in userland,
+ * this does not include packets dropped because we ran out
+ * of buffer space.
+ *
+ * "ps_drop" counts packets dropped inside the "/dev/nit"
+ * device because of flow control requirements or resource
+ * exhaustion; it doesn't count packets dropped by the
+ * interface driver, or packets dropped upstream. As filtering
+ * is done in userland, it counts packets regardless of whether
+ * they would've passed the filter.
+ *
+ * These statistics don't include packets not yet read from the
+ * kernel by libpcap or packets not yet read from libpcap by the
+ * application.
+ */
*ps = p->md.stat;
return (0);
}
diff --git a/contrib/libpcap/pcap-snoop.c b/contrib/libpcap/pcap-snoop.c
index 65ad273..5d58ba3 100644
--- a/contrib/libpcap/pcap-snoop.c
+++ b/contrib/libpcap/pcap-snoop.c
@@ -20,7 +20,7 @@
*/
#ifndef lint
static const char rcsid[] =
- "@(#) $Header: /tcpdump/master/libpcap/pcap-snoop.c,v 1.30 2000/10/28 00:01:30 guy Exp $ (LBL)";
+ "@(#) $Header: /tcpdump/master/libpcap/pcap-snoop.c,v 1.33 2001/12/10 07:14:21 guy Exp $ (LBL)";
#endif
#ifdef HAVE_CONFIG_H
@@ -115,10 +115,28 @@ pcap_stats(pcap_t *p, struct pcap_stat *ps)
return (-1);
}
+ /*
+ * "ifdrops" are those dropped by the network interface
+ * due to resource shortages or hardware errors.
+ *
+ * "sbdrops" are those dropped due to socket buffer limits.
+ *
+ * As filter is done in userland, "sbdrops" counts packets
+ * regardless of whether they would've passed the filter.
+ *
+ * XXX - does this count *all* Snoop or Drain sockets,
+ * rather than just this socket? If not, why does it have
+ * both Snoop and Drain statistics?
+ */
p->md.stat.ps_drop =
rs->rs_snoop.ss_ifdrops + rs->rs_snoop.ss_sbdrops +
rs->rs_drain.ds_ifdrops + rs->rs_drain.ds_sbdrops;
+ /*
+ * "ps_recv" counts only packets that passed the filter.
+ * As filtering is done in userland, this does not include
+ * packets dropped because we ran out of buffer space.
+ */
*ps = p->md.stat;
return (0);
}
@@ -179,6 +197,7 @@ pcap_open_live(char *device, int snaplen, int promisc, int to_ms, char *ebuf)
strncmp("vfe", device, 3) == 0 || /* Challenge VME 100Mbit */
strncmp("fa", device, 2) == 0 ||
strncmp("qaa", device, 3) == 0 ||
+ strncmp("cip", device, 3) == 0 ||
strncmp("el", device, 2) == 0) {
p->linktype = DLT_EN10MB;
p->offset = RAW_HDRPAD(sizeof(struct ether_header));
diff --git a/contrib/libpcap/pcap.c b/contrib/libpcap/pcap.c
index 9f32721..6b82453 100644
--- a/contrib/libpcap/pcap.c
+++ b/contrib/libpcap/pcap.c
@@ -33,7 +33,7 @@
#ifndef lint
static const char rcsid[] =
- "@(#) $Header: /tcpdump/master/libpcap/pcap.c,v 1.36 2000/12/16 10:43:31 guy Exp $ (LBL)";
+ "@(#) $Header: /tcpdump/master/libpcap/pcap.c,v 1.38 2001/12/29 21:55:32 guy Exp $ (LBL)";
#endif
#ifdef HAVE_CONFIG_H
@@ -46,6 +46,8 @@ static const char rcsid[] =
#include <stdlib.h>
#include <string.h>
#include <unistd.h>
+#include <fcntl.h>
+#include <errno.h>
#ifdef HAVE_OS_PROTO_H
#include "os-proto.h"
@@ -169,6 +171,65 @@ pcap_geterr(pcap_t *p)
}
/*
+ * NOTE: in the future, these may need to call platform-dependent routines,
+ * e.g. on platforms with memory-mapped packet-capture mechanisms where
+ * "pcap_read()" uses "select()" or "poll()" to wait for packets to arrive.
+ */
+int
+pcap_getnonblock(pcap_t *p, char *errbuf)
+{
+ int fdflags;
+
+ if (p->sf.rfile != NULL) {
+ /*
+ * This is a savefile, not a live capture file, so
+ * never say it's in non-blocking mode.
+ */
+ return (0);
+ }
+ fdflags = fcntl(p->fd, F_GETFL, 0);
+ if (fdflags == -1) {
+ snprintf(p->errbuf, PCAP_ERRBUF_SIZE, "F_GETFL: %s",
+ pcap_strerror(errno));
+ return (-1);
+ }
+ if (fdflags & O_NONBLOCK)
+ return (1);
+ else
+ return (0);
+}
+
+int
+pcap_setnonblock(pcap_t *p, int nonblock, char *errbuf)
+{
+ int fdflags;
+
+ if (p->sf.rfile != NULL) {
+ /*
+ * This is a savefile, not a live capture file, so
+ * ignore requests to put it in non-blocking mode.
+ */
+ return (0);
+ }
+ fdflags = fcntl(p->fd, F_GETFL, 0);
+ if (fdflags == -1) {
+ snprintf(p->errbuf, PCAP_ERRBUF_SIZE, "F_GETFL: %s",
+ pcap_strerror(errno));
+ return (-1);
+ }
+ if (nonblock)
+ fdflags |= O_NONBLOCK;
+ else
+ fdflags &= ~O_NONBLOCK;
+ if (fcntl(p->fd, F_SETFL, fdflags) == -1) {
+ snprintf(p->errbuf, PCAP_ERRBUF_SIZE, "F_SETFL: %s",
+ pcap_strerror(errno));
+ return (-1);
+ }
+ return (0);
+}
+
+/*
* Not all systems have strerror().
*/
char *
diff --git a/contrib/libpcap/savefile.c b/contrib/libpcap/savefile.c
index cc5b47e..f952a19 100644
--- a/contrib/libpcap/savefile.c
+++ b/contrib/libpcap/savefile.c
@@ -30,7 +30,7 @@
#ifndef lint
static const char rcsid[] =
- "@(#) $Header: /tcpdump/master/libpcap/savefile.c,v 1.49 2000/12/21 10:29:23 guy Exp $ (LBL)";
+ "@(#) $Header: /tcpdump/master/libpcap/savefile.c,v 1.55 2001/11/28 07:16:53 guy Exp $ (LBL)";
#endif
#ifdef HAVE_CONFIG_H
@@ -149,25 +149,35 @@ static const char rcsid[] =
*/
#define LINKTYPE_PPP_HDLC 50 /* PPP in HDLC-like framing */
+#define LINKTYPE_PPP_ETHER 51 /* NetBSD PPP-over-Ethernet */
+
#define LINKTYPE_ATM_RFC1483 100 /* LLC/SNAP-encapsulated ATM */
#define LINKTYPE_RAW 101 /* raw IP */
#define LINKTYPE_SLIP_BSDOS 102 /* BSD/OS SLIP BPF header */
#define LINKTYPE_PPP_BSDOS 103 /* BSD/OS PPP BPF header */
#define LINKTYPE_C_HDLC 104 /* Cisco HDLC */
+#define LINKTYPE_IEEE802_11 105 /* IEEE 802.11 (wireless) */
#define LINKTYPE_ATM_CLIP 106 /* Linux Classical IP over ATM */
+#define LINKTYPE_LOOP 108 /* OpenBSD loopback */
+
+#define LINKTYPE_LINUX_SLL 113 /* Linux cooked socket capture */
+#define LINKTYPE_LTALK 114 /* Apple LocalTalk hardware */
+#define LINKTYPE_ECONET 115 /* Acorn Econet */
+
+#define LINKTYPE_CISCO_IOS 118 /* For Cisco-internal use */
+#define LINKTYPE_PRISM_HEADER 119 /* 802.11+Prism II monitor mode */
+#define LINKTYPE_AIRONET_HEADER 120 /* FreeBSD Aironet driver stuff */
/*
- * Reserved for future use.
+ * These types are reserved for future use.
*/
-#define LINKTYPE_IEEE802_11 105 /* IEEE 802.11 (wireless) */
#define LINKTYPE_FR 107 /* BSD/OS Frame Relay */
-#define LINKTYPE_LOOP 108 /* OpenBSD loopback */
#define LINKTYPE_ENC 109 /* OpenBSD IPSEC enc */
#define LINKTYPE_LANE8023 110 /* ATM LANE + 802.3 */
#define LINKTYPE_HIPPI 111 /* NetBSD HIPPI */
#define LINKTYPE_HDLC 112 /* NetBSD HDLC framing */
-
-#define LINKTYPE_LINUX_SLL 113 /* Linux cooked socket capture */
+#define LINKTYPE_IPFILTER 116 /* IP Filter capture files */
+#define LINKTYPE_PFLOG 117 /* OpenBSD DLT_PFLOG */
static struct linktype_map {
int dlt;
@@ -216,6 +226,9 @@ static struct linktype_map {
/* NetBSD sync/async serial PPP (or Cisco HDLC) */
{ DLT_PPP_SERIAL, LINKTYPE_PPP_HDLC },
+ /* NetBSD PPP over Ethernet */
+ { DLT_PPP_ETHER, LINKTYPE_PPP_ETHER },
+
/* IEEE 802.11 wireless */
{ DLT_IEEE802_11, LINKTYPE_IEEE802_11 },
@@ -225,6 +238,21 @@ static struct linktype_map {
/* Linux cooked socket capture */
{ DLT_LINUX_SLL, LINKTYPE_LINUX_SLL },
+ /* Apple LocalTalk hardware */
+ { DLT_LTALK, LINKTYPE_LTALK },
+
+ /* Acorn Econet */
+ { DLT_ECONET, LINKTYPE_ECONET },
+
+ /* For Cisco-internal use */
+ { DLT_CISCO_IOS, LINKTYPE_CISCO_IOS },
+
+ /* Prism II monitor-mode header plus 802.11 header */
+ { DLT_PRISM_HEADER, LINKTYPE_PRISM_HEADER },
+
+ /* FreeBSD Aironet driver stuff */
+ { DLT_AIRONET_HEADER, LINKTYPE_AIRONET_HEADER },
+
/*
* Any platform that defines additional DLT_* codes should:
*
OpenPOWER on IntegriCloud