1
0
mirror of https://github.com/nmap/nmap.git synced 2025-12-06 04:31:29 +00:00

Update to libpcap 1.9.1 (initial commit, no Nmap-specific patches)

This commit is contained in:
dmiller
2019-11-19 17:53:36 +00:00
parent 42bb2feed8
commit f1107301e8
125 changed files with 7238 additions and 13624 deletions

View File

@@ -1,3 +1,75 @@
Sunday, July 22, 2018
Summary for 1.9.1 libpcap release
Mention pcap_get_required_select_timeout() in the main pcap man page
Fix pcap-usb-linux.c build on systems with musl
Fix assorted man page and other documentation issues
Plug assorted memory leaks
Documentation changes to use https:
Changes to how time stamp calculations are done
Lots of tweaks to make newer compilers happier and warning-free and
to fix instances of C undefined behavior
Warn if AC_PROG_CC_C99 can't enable C99 support
Rename pcap_set_protocol() to pcap_set_protocol_linux().
Align pcap_t private data on an 8-byte boundary.
Fix various error messages
Use 64-bit clean API in dag_findalldevs()
Fix cleaning up after some errors
Work around some ethtool ioctl bugs in newer Linux kernels (GitHub
issue #689)
Add backwards compatibility sections to some man pages (GitHub issue
#745)
Fix autotool configuration on AIX and macOS
Don't export bpf_filter_with_aux_data() or struct bpf_aux_data;
they're internal-only and subject to change
Fix pcapng block size checking
On macOS, don't build rpcapd or test programs any fatter than they
need to be
Fix reading of capture statistics for Linux USB
Fix packet size values for Linux USB packets (GitHub issue #808)
Check only VID in VLAN test in filterss (GitHub issue #461)
Fix pcap_list_datalinks on 802.11 devices on macOS
Fix overflows with very large snapshot length in pcap file
Improve parsing of rpcapd configuration file (GitHub issue #767)
Handle systems without strlcpy() or strlcat() better
Fix crashes and other errors with invalid filter expressions
Fix use of uninitialized file descriptor in remote capture
Fix some CMake issues
Fix some divide-by-zero issues with the filter compiler
Work around a GNU libc bug in pcap_nametonetaddr()
Add support for DLT_LINUX_SLL2
Fix handling of the packet-count argument for Myricom SNF devices
Fix --disable-rdma in configure script (GitHub issue #782)
Fix compilation of TurboCap support (GitHub issue #764)
Constify first argument to pcap_findalldevs_ex()
Fix a number of issues when running rpcapd as an inetd-style daemon
Fix CMake issues with D-Bus libraries
In rpcapd, clean up termination of a capture session
Redo remote capture protocol negotiation
In rpcapd, report the same error for "invalid user name" and
"invalid password", to make brute-forcing harder
For remote captures, add an error code for "the server requires TLS"
Fix pcap_dump_fopen() on Windows to avoid clashes between
{Win,N}Pcap and application C runtimes
Fix exporting of functions from Windows DLLs (GitHub issue #810)
Fix building as part of Npcap
Allow rpcapd to rebind more rapidly
Fix building shared libpcap library on midipix (midipix.org)
Fix hack to detect UTF-16LE adapter names on Windows not to go past
the end of the string
Fix handling of "wireless WAN" (mobile phone network modems) on
Windows with WinPcap/Npcap (GitHub issue #824)
Have pcap_dump_open_append() create the dump file if it doesn't
exists (GitHub issue #247)
Fix the maxmum snapshot length for DLT_USBPCAP
Use -fPIC when building for 64-bit SPARC on Linux (GitHub issue #837)
Fix CMake 64-bit library installation directory on some Linux
distributions
Boost the TPACKET_V3 timeout to the maximum if a timeout of 0 was
specified
Five CVE-2019-15161, CVE-2019-15162, CVE-2019-15163, CVE-2019-15164, CVE-2019-15165
Fixes for CVE-2018-16301, errors in pcapng reading.
PCAPNG reader applies some sanity checks before doing malloc().
Sunday, June 24, 2018, by mcr@sandelman.ca
Summary for 1.9.0 libpcap release
Added testing system to libpcap, independent of tcpdump

View File

@@ -9,7 +9,7 @@ if(POLICY CMP0042)
cmake_policy(SET CMP0042 OLD)
endif()
set(CMAKE_MODULE_PATH ${CMAKE_SOURCE_DIR}/cmake/Modules)
set(CMAKE_MODULE_PATH ${CMAKE_CURRENT_SOURCE_DIR}/cmake/Modules)
project(pcap)
@@ -135,83 +135,6 @@ if(CMAKE_SYSTEM_NAME STREQUAL "Linux")
option(BUILD_WITH_LIBNL "Build with libnl" ON)
endif()
#
# By default, build universal with the appropriate set of architectures
# for the OS on which we're doing the build.
#
if(APPLE AND "${CMAKE_OSX_ARCHITECTURES}" STREQUAL "")
#
# Get the major version of Darwin.
#
string(REGEX MATCH "^([0-9]+)" SYSTEM_VERSION_MAJOR "${CMAKE_SYSTEM_VERSION}")
if(SYSTEM_VERSION_MAJOR LESS 8)
#
# Pre-Tiger. Build only for 32-bit PowerPC.
#
set(CMAKE_OSX_ARCHITECTURES "ppc")
elseif(SYSTEM_VERSION_MAJOR EQUAL 8)
#
# Tiger. Is this prior to, or with, Intel support?
#
# Get the minor version of Darwin.
#
string(REPLACE "${SYSTEM_VERSION_MAJOR}." "" SYSTEM_MINOR_AND_PATCH_VERSION ${CMAKE_SYSTEM_VERSION})
string(REGEX MATCH "^([0-9]+)" SYSTEM_VERSION_MINOR "${SYSTEM_MINOR_AND_PATCH_VERSION}")
if(SYSTEM_VERSION_MINOR LESS 4)
#
# Prior to Intel support. Build for 32-bit
# PowerPC and 64-bit PowerPC, with 32-bit PowerPC
# first. (I'm guessing that's what Apple does.)
#
set(CMAKE_OSX_ARCHITECTURES "ppc;ppc64")
elseif(SYSTEM_VERSION_MINOR LESS 7)
#
# With Intel support but prior to x86-64 support.
# Build for 32-bit PowerPC, 64-bit PowerPC, and x86,
# with 32-bit PowerPC first.
# (I'm guessing that's what Apple does.)
#
set(CMAKE_OSX_ARCHITECTURES "ppc;ppc64;i386")
else()
#
# With Intel support including x86-64 support.
# Build for 32-bit PowerPC, 64-bit PowerPC, x86,
# and x86-64, with 32-bit PowerPC first.
# (I'm guessing that's what Apple does.)
#
set(CMAKE_OSX_ARCHITECTURES "ppc;ppc64;i386;x86_64")
endif()
elseif(SYSTEM_VERSION_MAJOR EQUAL 9)
#
# Leopard. Build for 32-bit PowerPC, 64-bit
# PowerPC, x86, and x86-64, with 32-bit PowerPC
# first. (That's what Apple does.)
#
set(CMAKE_OSX_ARCHITECTURES "ppc;ppc64;i386;x86_64")
elseif(SYSTEM_VERSION_MAJOR EQUAL 10)
#
# Snow Leopard. Build for x86-64, x86, and
# 32-bit PowerPC, with x86-64 first. (That's
# what Apple does, even though Snow Leopard
# doesn't run on PPC, so PPC libpcap runs under
# Rosetta, and Rosetta doesn't support BPF
# ioctls, so PPC programs can't do live
# captures.)
#
set(CMAKE_OSX_ARCHITECTURES "x86_64;i386;ppc")
else()
#
# Post-Snow Leopard. Build for x86-64 and
# x86, with x86-64 first. (That's probably what
# Apple does, given that Rosetta is gone.)
# XXX - update if and when Apple drops support
# for 32-bit x86 code.
#
set(CMAKE_OSX_ARCHITECTURES "x86_64;i386")
endif()
endif()
#
# Additional capture modules.
#
@@ -233,7 +156,7 @@ option(DISABLE_RDMA "Disable RDMA sniffing support" OFF)
option(DISABLE_DAG "Disable Endace DAG card support" OFF)
option(DISABLE_SEPTEL "Disable Septel card support" OFF)
set(SEPTEL_ROOT "${CMAKE_SOURCE_DIR}/../septel" CACHE PATH "Path to directory with include and lib subdirectories for Septel API")
set(SEPTEL_ROOT "${CMAKE_CURRENT_SOURCE_DIR}/../septel" CACHE PATH "Path to directory with include and lib subdirectories for Septel API")
option(DISABLE_SNF "Disable Myricom SNF support" OFF)
@@ -289,6 +212,7 @@ include_directories(
include(CheckFunctionExists)
include(CMakePushCheckState)
include(CheckSymbolExists)
if(WIN32)
@@ -310,6 +234,14 @@ if(WIN32)
cmake_pop_check_state()
endif(PACKET_FOUND)
message(STATUS "checking for Npcap's version.h")
check_symbol_exists(WINPCAP_PRODUCT_NAME "../../version.h" HAVE_VERSION_H)
if(HAVE_VERSION_H)
message(STATUS "HAVE version.h")
else(HAVE_VERSION_H)
message(STATUS "MISSING version.h")
endif(HAVE_VERSION_H)
endif(WIN32)
if(MSVC)
@@ -343,6 +275,11 @@ include(CheckIncludeFiles)
include(CheckStructHasMember)
include(CheckTypeSize)
#
# Tests are a bit expensive with Visual Studio on Windows, so, on
# Windows, we skip tests for UN*X-only headers and functions.
#
#
# Header files.
#
@@ -395,12 +332,44 @@ endif(NOT WIN32)
#
check_function_exists(strerror HAVE_STRERROR)
check_function_exists(strerror_r HAVE_STRERROR_R)
check_function_exists(strerror_s HAVE_STRERROR_S)
if(HAVE_STRERROR_R)
#
# We have strerror_r; if we define _GNU_SOURCE, is it a
# POSIX-compliant strerror_r() or a GNU strerror_r()?
#
check_c_source_compiles(
"#define _GNU_SOURCE
#include <string.h>
/* Define it GNU-style; that will cause an error if it's not GNU-style */
extern char *strerror_r(int, char *, size_t);
int
main(void)
{
return 0;
}
"
HAVE_GNU_STRERROR_R)
if(NOT HAVE_GNU_STRERROR_R)
set(HAVE_POSIX_STRERROR_R YES)
endif(NOT HAVE_GNU_STRERROR_R)
else(HAVE_STRERROR_R)
#
# We don't have strerror_r; do we have strerror_s?
#
check_function_exists(strerror_s HAVE_STRERROR_S)
endif(HAVE_STRERROR_R)
check_function_exists(strlcpy HAVE_STRLCPY)
check_function_exists(strlcat HAVE_STRLCAT)
check_function_exists(snprintf HAVE_SNPRINTF)
check_function_exists(vsnprintf HAVE_VSNPRINTF)
check_function_exists(asprintf HAVE_ASPRINTF)
check_function_exists(vasprintf HAVE_VASPRINTF)
check_function_exists(strtok_r HAVE_STRTOK_R)
if(NOT WIN32)
check_function_exists(vsyslog HAVE_VSYSLOG)
endif()
#
# These tests are for network applications that need socket functions
@@ -429,7 +398,6 @@ check_function_exists(strtok_r HAVE_STRTOK_R)
#
set(PCAP_LINK_LIBRARIES "")
include(CheckLibraryExists)
include(CheckSymbolExists)
if(WIN32)
#
# We need winsock2.h and ws2tcpip.h.
@@ -865,11 +833,61 @@ set(PROJECT_SOURCE_LIST_C
)
if(WIN32)
set(PROJECT_SOURCE_LIST_C ${PROJECT_SOURCE_LIST_C} missing/win_snprintf.c)
#
# For now, we assume we don't have snprintf() or that it's not one
# that behaves enough like C99's snprintf() for our purposes (i.e.,
# it doesn't null-terminate the string if it truncates it to fit in
# the buffer), so we have to provide our own (a wrapper around
# _snprintf() that null-terminates the buffer).
#
# We also assume we don't have asprintf(), and provide an implementation
# that uses _vscprintf() to determine how big the string needs to be.
#
set(PROJECT_SOURCE_LIST_C ${PROJECT_SOURCE_LIST_C}
missing/win_snprintf.c missing/win_asprintf.c)
else()
#
# Either:
#
# we have snprintf() and vsnprintf(), and have asprintf() and
# vasprintf();
#
# we have snprintf() and vsnprintf(), but don't have asprintf()
# or vasprintf();
#
# we have neither snprintf() nor vsnprintf(), and don't have
# asprintf() or vasprintf(), either.
#
# We assume that if we have asprintf() we have vasprintf(), as well
# as snprintf() and vsnprintf(), and that if we have snprintf() we
# have vsnprintf().
#
# For the first case, we don't need any replacement routines.
# For the second case, we need replacement asprintf()/vasprintf()
# routines.
# For the third case, we need replacement snprintf()/vsnprintf() and
# asprintf()/vasprintf() routines.
#
if(NOT HAVE_SNPRINTF)
#
# We assume we have none of them; missing/snprintf.c supplies
# all of them.
#
set(PROJECT_SOURCE_LIST_C ${PROJECT_SOURCE_LIST_C} missing/snprintf.c)
endif(NOT HAVE_SNPRINTF)
elif(NOT HAVE_ASPRINTF)
#
# We assume we have snprintf()/vsnprintf() but lack
# asprintf()/vasprintf(); missing/asprintf.c supplies
# the latter (using vsnprintf()).
#
set(PROJECT_SOURCE_LIST_C ${PROJECT_SOURCE_LIST_C} missing/asprintf.c)
endif()
if(NOT HAVE_STRLCAT)
set(PROJECT_SOURCE_LIST_C ${PROJECT_SOURCE_LIST_C} missing/strlcat.c)
endif(NOT HAVE_STRLCAT)
if(NOT HAVE_STRLCPY)
set(PROJECT_SOURCE_LIST_C ${PROJECT_SOURCE_LIST_C} missing/strlcpy.c)
endif(NOT HAVE_STRLCPY)
if(NOT HAVE_STRTOK_R)
set(PROJECT_SOURCE_LIST_C ${PROJECT_SOURCE_LIST_C} missing/strtok_r.c)
endif(NOT HAVE_STRTOK_R)
@@ -931,13 +949,16 @@ else()
# as it's a Linux, it should use packet sockets,
# instead.
#
#
# We need:
#
# sys/types.h, because FreeBSD 10's net/bpf.h
# requires that various BSD-style integer types
# be defined;
#
# sys/time.h, because AIX 5.2 and 5.3's net/bpf.h
# doesn't include it but does use struct timeval
# in ioctl definitions;
#
# sys/ioctl.h and, if we have it, sys/ioccom.h,
# because net/bpf.h defines ioctls;
#
@@ -952,9 +973,9 @@ else()
# of those headers itself.
#
if(HAVE_SYS_IOCCOM_H)
check_symbol_exists(BIOCSETIF "sys/types.h;sys/ioctl.h;sys/socket.h;sys/ioccom.h;net/bpf.h;net/if.h" BPF_H_DEFINES_BIOCSETIF)
check_symbol_exists(BIOCSETIF "sys/types.h;sys/time.h;sys/ioctl.h;sys/socket.h;sys/ioccom.h;net/bpf.h;net/if.h" BPF_H_DEFINES_BIOCSETIF)
else(HAVE_SYS_IOCCOM_H)
check_symbol_exists(BIOCSETIF "sys/types.h;sys/ioctl.h;sys/socket.h;net/bpf.h;net/if.h" BPF_H_DEFINES_BIOCSETIF)
check_symbol_exists(BIOCSETIF "sys/types.h;sys/time.h;sys/ioctl.h;sys/socket.h;net/bpf.h;net/if.h" BPF_H_DEFINES_BIOCSETIF)
endif(HAVE_SYS_IOCCOM_H)
endif(HAVE_NET_BPF_H)
check_include_file(net/pfilt.h HAVE_NET_PFILT_H)
@@ -1436,7 +1457,28 @@ if(NOT DISABLE_DBUS)
set(PCAP_SUPPORT_DBUS TRUE)
set(PROJECT_SOURCE_LIST_C ${PROJECT_SOURCE_LIST_C} pcap-dbus.c)
include_directories(${DBUS_INCLUDE_DIRS})
set(PCAP_LINK_LIBRARIES ${PCAP_LINK_LIBRARIES} ${DBUS_LIBRARIES})
#
# This "helpfully" supplies DBUS_LIBRARIES as a bunch of
# library names - not paths - and DBUS_LIBRARY_DIRS as
# a bunch of directories.
#
# CMake *really* doesn't like the notion of specifying "here are
# the directories in which to look for libraries" except in
# find_library() calls; it *really* prefers using full paths to
# library files, rather than library names.
#
# Find the libraries and add their full paths.
#
set(DBUS_LIBRARY_FULLPATHS)
foreach(_lib IN LISTS DBUS_LIBRARIES)
#
# Try to find this library, so we get its full path.
#
find_library(_libfullpath ${_lib} HINTS ${DBUS_LIBRARY_DIRS})
list(APPEND DBUS_LIBRARY_FULLPATHS ${_libfullpath})
endforeach()
set(PCAP_LINK_LIBRARIES ${PCAP_LINK_LIBRARIES} ${DBUS_LIBRARY_FULLPATHS})
endif(DBUS_FOUND)
endif(NOT DISABLE_DBUS)
@@ -1582,7 +1624,7 @@ if(ENABLE_REMOTE)
# the check.
#
cmake_push_check_state()
set(CMAKE_REQUIRED_INCLUDES ${CMAKE_SOURCE_DIR})
set(CMAKE_REQUIRED_INCLUDES ${CMAKE_CURRENT_SOURCE_DIR})
check_struct_has_member("struct msghdr" msg_control "ftmacros.h;sys/socket.h" HAVE_STRUCT_MSGHDR_MSG_CONTROL)
check_struct_has_member("struct msghdr" msg_flags "ftmacros.h;sys/socket.h" HAVE_STRUCT_MSGHDR_MSG_FLAGS)
cmake_pop_check_state()
@@ -1597,7 +1639,7 @@ endif(ENABLE_REMOTE)
#
# Check and add warning options if we have a .devel file.
#
if(EXISTS ${CMAKE_SOURCE_DIR}/.devel OR EXISTS ${CMAKE_BINARY_DIR}/.devel)
if(EXISTS ${CMAKE_CURRENT_SOURCE_DIR}/.devel OR EXISTS ${CMAKE_BINARY_DIR}/.devel)
#
# Warning options.
#
@@ -1808,10 +1850,12 @@ set_source_files_properties(${CMAKE_CURRENT_BINARY_DIR}/grammar.c PROPERTIES
#
# Assume, by default, no support for shared libraries and V7/BSD
# convention for man pages (file formats in section 5, miscellaneous
# info in section 7, administrative commands and daemons in section 8).
# convention for man pages (devices in section 4, file formats in
# section 5, miscellaneous info in section 7, administrative commands
# and daemons in section 8). Individual cases can override this.
# Individual cases can override this.
#
set(MAN_DEVICES 4)
set(MAN_FILE_FORMATS 5)
set(MAN_MISC_INFO 7)
set(MAN_ADMIN_COMMANDS 8)
@@ -1869,6 +1913,7 @@ elseif(CMAKE_SYSTEM_NAME STREQUAL "OSF1")
#
set(MAN_FILE_FORMATS 4)
set(MAN_MISC_INFO 5)
set(MAN_DEVICES 7)
elseif(CMAKE_SYSTEM_NAME STREQUAL "SunOS" AND CMAKE_SYSTEM_VERSION MATCHES "5[.][0-9.]*")
#
# SunOS 5.x.
@@ -1892,6 +1937,7 @@ elseif(CMAKE_SYSTEM_NAME STREQUAL "SunOS" AND CMAKE_SYSTEM_VERSION MATCHES "5[.]
set(MAN_ADMIN_COMMANDS 1m)
set(MAN_FILE_FORMATS 4)
set(MAN_MISC_INFO 5)
set(MAN_DEVICES 7D)
endif()
endif()
@@ -1944,6 +1990,16 @@ if(BUILD_SHARED_LIBS)
add_dependencies(${LIBRARY_NAME} SerializeTarget)
set_target_properties(${LIBRARY_NAME} PROPERTIES
COMPILE_DEFINITIONS BUILDING_PCAP)
#
# No matter what the library is called - it might be called "wpcap"
# in a Windows build - the symbol to define to indicate that we're
# building the library, rather than a program using the library,
# and thus that we're exporting functions defined in our public
# header files, rather than importing those functions, is
# pcap_EXPORTS.
#
set_target_properties(${LIBRARY_NAME} PROPERTIES
DEFINE_SYMBOL pcap_EXPORTS)
endif(BUILD_SHARED_LIBS)
add_library(${LIBRARY_NAME}_static STATIC
@@ -2020,6 +2076,118 @@ if(NOT C_ADDITIONAL_FLAGS STREQUAL "")
set_target_properties(${LIBRARY_NAME}_static PROPERTIES COMPILE_FLAGS ${C_ADDITIONAL_FLAGS})
endif()
#
# On macOS, build libpcap for the appropriate architectures, if
# CMAKE_OSX_ARCHITECTURES isn't set (if it is, let that control
# the architectures for which to build it).
#
if(APPLE AND "${CMAKE_OSX_ARCHITECTURES}" STREQUAL "")
#
# Get the major version of Darwin.
#
string(REGEX MATCH "^([0-9]+)" SYSTEM_VERSION_MAJOR "${CMAKE_SYSTEM_VERSION}")
if(SYSTEM_VERSION_MAJOR LESS 8)
#
# Pre-Tiger. Build only for 32-bit PowerPC.
#
set(OSX_LIBRARY_ARCHITECTURES "ppc")
elseif(SYSTEM_VERSION_MAJOR EQUAL 8)
#
# Tiger. Is this prior to, or with, Intel support?
#
# Get the minor version of Darwin.
#
string(REPLACE "${SYSTEM_VERSION_MAJOR}." "" SYSTEM_MINOR_AND_PATCH_VERSION ${CMAKE_SYSTEM_VERSION})
string(REGEX MATCH "^([0-9]+)" SYSTEM_VERSION_MINOR "${SYSTEM_MINOR_AND_PATCH_VERSION}")
if(SYSTEM_VERSION_MINOR LESS 4)
#
# Prior to Intel support. Build for 32-bit
# PowerPC and 64-bit PowerPC, with 32-bit PowerPC
# first. (I'm guessing that's what Apple does.)
#
set(OSX_LIBRARY_ARCHITECTURES "ppc;ppc64")
elseif(SYSTEM_VERSION_MINOR LESS 7)
#
# With Intel support but prior to x86-64 support.
# Build for 32-bit PowerPC, 64-bit PowerPC, and 32-bit x86,
# with 32-bit PowerPC first.
# (I'm guessing that's what Apple does.)
#
set(OSX_LIBRARY_ARCHITECTURES "ppc;ppc64;i386")
else()
#
# With Intel support including x86-64 support.
# Build for 32-bit PowerPC, 64-bit PowerPC, 32-bit x86,
# and x86-64, with 32-bit PowerPC first.
# (I'm guessing that's what Apple does.)
#
set(OSX_LIBRARY_ARCHITECTURES "ppc;ppc64;i386;x86_64")
endif()
elseif(SYSTEM_VERSION_MAJOR EQUAL 9)
#
# Leopard. Build for 32-bit PowerPC, 64-bit
# PowerPC, 32-bit x86, and x86-64, with 32-bit PowerPC
# first. (That's what Apple does.)
#
set(OSX_LIBRARY_ARCHITECTURES "ppc;ppc64;i386;x86_64")
elseif(SYSTEM_VERSION_MAJOR EQUAL 10)
#
# Snow Leopard. Build for x86-64, 32-bit x86, and
# 32-bit PowerPC, with x86-64 first. (That's
# what Apple does, even though Snow Leopard
# doesn't run on PPC, so PPC libpcap runs under
# Rosetta, and Rosetta doesn't support BPF
# ioctls, so PPC programs can't do live
# captures.)
#
set(OSX_LIBRARY_ARCHITECTURES "x86_64;i386;ppc")
else()
#
# Post-Snow Leopard. Build for x86-64 and 32-bit x86,
# with x86-64 first. (That's what Apple does)
# XXX - update if and when Apple drops support
# for 32-bit x86 code and if and when Apple adds
# ARM-based Macs. (You're on your own for iOS etc.)
#
# XXX - check whether we *can* build for i386 and, if not,
# suggest that the user install the /usr/include headers if
# they want to build fat.
#
cmake_push_check_state()
set(CMAKE_REQUIRED_FLAGS "-arch i386")
check_c_source_compiles(
"int
main(void)
{
return 0;
}
"
X86_32_BIT_SUPPORTED)
cmake_pop_check_state()
if(X86_32_BIT_SUPPORTED)
set(OSX_LIBRARY_ARCHITECTURES "x86_64;i386")
else()
set(OSX_LIBRARY_ARCHITECTURES "x86_64")
if(SYSTEM_VERSION_MAJOR LESS 18)
#
# Pre-Mojave; the command-line tools should be sufficient to
# enable 32-bit x86 builds.
#
message(WARNING "Compiling for 32-bit x86 gives an error; try installing the command-line tools")
else()
message(WARNING "Compiling for 32-bit x86 gives an error; try installing the command-line tools and, after that, installing the /usr/include headers from the /Library/Developer/CommandLineTools/Packages/macOS_SDK_headers_for_macOS_10.14.pkg package")
endif()
endif()
endif()
if(BUILD_SHARED_LIBS)
set_target_properties(${LIBRARY_NAME} PROPERTIES
OSX_ARCHITECTURES "${OSX_LIBRARY_ARCHITECTURES}")
endif(BUILD_SHARED_LIBS)
set_target_properties(${LIBRARY_NAME}_static PROPERTIES
OSX_ARCHITECTURES "${OSX_LIBRARY_ARCHITECTURES}")
endif()
######################################
# Write out the config.h file
######################################
@@ -2079,6 +2247,7 @@ set(MAN3PCAP_EXPAND
pcap_list_tstamp_types.3pcap.in
pcap_open_dead.3pcap.in
pcap_open_offline.3pcap.in
pcap_set_immediate_mode.3pcap.in
pcap_set_tstamp_precision.3pcap.in
pcap_set_tstamp_type.3pcap.in
)
@@ -2114,7 +2283,6 @@ set(MAN3PCAP_NOEXPAND
pcap_open_live.3pcap
pcap_set_buffer_size.3pcap
pcap_set_datalink.3pcap
pcap_set_immediate_mode.3pcap
pcap_set_promisc.3pcap
pcap_set_protocol_linux.3pcap
pcap_set_rfmon.3pcap
@@ -2179,7 +2347,7 @@ if(WIN32)
endif(NOT MINGW)
endif(MSVC AND CMAKE_SIZEOF_VOID_P EQUAL 8)
else(WIN32)
install(TARGETS ${LIBRARY_NAME} ${LIBRARY_NAME_STATIC} DESTINATION lib)
install(TARGETS ${LIBRARY_NAME} ${LIBRARY_NAME_STATIC} DESTINATION ${CMAKE_INSTALL_FULL_LIBDIR})
endif(WIN32)
install(DIRECTORY ${CMAKE_CURRENT_SOURCE_DIR}/pcap/ DESTINATION include/pcap)
@@ -2225,8 +2393,8 @@ if(NOT MSVC)
foreach(LIB ${PCAP_LINK_LIBRARIES})
set(LIBS "${LIBS} -l${LIB}")
endforeach(LIB)
configure_file(${CMAKE_SOURCE_DIR}/pcap-config.in ${CMAKE_CURRENT_BINARY_DIR}/pcap-config @ONLY)
configure_file(${CMAKE_SOURCE_DIR}/libpcap.pc.in ${CMAKE_CURRENT_BINARY_DIR}/libpcap.pc @ONLY)
configure_file(${CMAKE_CURRENT_SOURCE_DIR}/pcap-config.in ${CMAKE_CURRENT_BINARY_DIR}/pcap-config @ONLY)
configure_file(${CMAKE_CURRENT_SOURCE_DIR}/libpcap.pc.in ${CMAKE_CURRENT_BINARY_DIR}/libpcap.pc @ONLY)
install(PROGRAMS ${CMAKE_CURRENT_BINARY_DIR}/pcap-config DESTINATION bin)
install(FILES ${CMAKE_CURRENT_BINARY_DIR}/libpcap.pc DESTINATION lib/pkgconfig)
@@ -2238,17 +2406,17 @@ if(NOT MSVC)
#
set(MAN1 "")
foreach(MANPAGE ${MAN1_NOEXPAND})
set(MAN1 ${MAN1} ${CMAKE_SOURCE_DIR}/${MANPAGE})
set(MAN1 ${MAN1} ${CMAKE_CURRENT_SOURCE_DIR}/${MANPAGE})
endforeach(MANPAGE)
install(FILES ${MAN1} DESTINATION ${CMAKE_INSTALL_MANDIR}/man1)
set(MAN3PCAP "")
foreach(MANPAGE ${MAN3PCAP_NOEXPAND})
set(MAN3PCAP ${MAN3PCAP} ${CMAKE_SOURCE_DIR}/${MANPAGE})
set(MAN3PCAP ${MAN3PCAP} ${CMAKE_CURRENT_SOURCE_DIR}/${MANPAGE})
endforeach(MANPAGE)
foreach(TEMPLATE_MANPAGE ${MAN3PCAP_EXPAND})
string(REPLACE ".in" "" MANPAGE ${TEMPLATE_MANPAGE})
configure_file(${CMAKE_SOURCE_DIR}/${TEMPLATE_MANPAGE} ${CMAKE_CURRENT_BINARY_DIR}/${MANPAGE} @ONLY)
configure_file(${CMAKE_CURRENT_SOURCE_DIR}/${TEMPLATE_MANPAGE} ${CMAKE_CURRENT_BINARY_DIR}/${MANPAGE} @ONLY)
set(MAN3PCAP ${MAN3PCAP} ${CMAKE_CURRENT_BINARY_DIR}/${MANPAGE})
endforeach(TEMPLATE_MANPAGE)
install(FILES ${MAN3PCAP} DESTINATION ${CMAKE_INSTALL_MANDIR}/man3)
@@ -2272,7 +2440,7 @@ if(NOT MSVC)
set(MANFILE "")
foreach(TEMPLATE_MANPAGE ${MANFILE_EXPAND})
string(REPLACE ".manfile.in" ".${MAN_FILE_FORMATS}" MANPAGE ${TEMPLATE_MANPAGE})
configure_file(${CMAKE_SOURCE_DIR}/${TEMPLATE_MANPAGE} ${CMAKE_CURRENT_BINARY_DIR}/${MANPAGE} @ONLY)
configure_file(${CMAKE_CURRENT_SOURCE_DIR}/${TEMPLATE_MANPAGE} ${CMAKE_CURRENT_BINARY_DIR}/${MANPAGE} @ONLY)
set(MANFILE ${MANFILE} ${CMAKE_CURRENT_BINARY_DIR}/${MANPAGE})
endforeach(TEMPLATE_MANPAGE)
install(FILES ${MANFILE} DESTINATION ${CMAKE_INSTALL_MANDIR}/man${MAN_FILE_FORMATS})
@@ -2280,7 +2448,7 @@ if(NOT MSVC)
set(MANMISC "")
foreach(TEMPLATE_MANPAGE ${MANMISC_EXPAND})
string(REPLACE ".manmisc.in" ".${MAN_MISC_INFO}" MANPAGE ${TEMPLATE_MANPAGE})
configure_file(${CMAKE_SOURCE_DIR}/${TEMPLATE_MANPAGE} ${CMAKE_CURRENT_BINARY_DIR}/${MANPAGE} @ONLY)
configure_file(${CMAKE_CURRENT_SOURCE_DIR}/${TEMPLATE_MANPAGE} ${CMAKE_CURRENT_BINARY_DIR}/${MANPAGE} @ONLY)
set(MANMISC ${MANMISC} ${CMAKE_CURRENT_BINARY_DIR}/${MANPAGE})
endforeach(TEMPLATE_MANPAGE)
install(FILES ${MANMISC} DESTINATION ${CMAKE_INSTALL_MANDIR}/man${MAN_MISC_INFO})

View File

@@ -129,7 +129,7 @@ Additional people who have contributed patches (in alphabetical order):
Olaf Kirch <okir at caldera dot de>
Ollie Wild <aaw at users dot sourceforge dot net>
Onno van der Linden <onno at simplex dot nl>
Paolo Abeni <paolo dot abeni at email dot it> and redhat dot com
Paolo Abeni <pabeni at redhat dot com>
Patrick Marie <mycroft at virgaria dot org>
Patrick McHardy <kaber at trash not net>
Paul Mundt <lethal at linux-sh dot org>

View File

@@ -266,15 +266,14 @@ doc/README.macos - notes on using libpcap on macOS
doc/README.septel - notes on using libpcap to capture on Intel/Septel devices
doc/README.sita - notes on using libpcap to capture on SITA devices
doc/README.tru64 - notes on using libpcap on Digital/Tru64 UNIX
doc/README.Win32 - notes on using libpcap on Win32 systems (with WinPcap)
doc/README.Win32 - notes on using libpcap on Win32 systems (with Npcap)
VERSION - version of this release
acconfig.h - support for post-2.13 autoconf
aclocal.m4 - autoconf macros
arcnet.h - ARCNET definitions
atmuni31.h - ATM Q.2931 definitions
bpf/net - copy of bpf_filter.c
bpf_dump.c - BPF program printing routines
bpf_filter.c - symlink to bpf/net/bpf_filter.c
bpf_filter.c - BPF filtering routines
bpf_image.c - BPF disassembly routine
config.guess - autoconf support
config.h.in - autoconf input

View File

@@ -69,13 +69,16 @@ INSTALL_RPCAPD=@INSTALL_RPCAPD@
EXTRA_NETWORK_LIBS=@EXTRA_NETWORK_LIBS@
# Standard CFLAGS for building members of a shared library
FULL_CFLAGS = $(CCOPT) $(SHLIB_CCOPT) $(INCLS) $(DEFS) $(CFLAGS)
FULL_CFLAGS = $(CCOPT) @V_LIB_CCOPT_FAT@ $(SHLIB_CCOPT) $(INCLS) $(DEFS) $(CFLAGS)
INSTALL = @INSTALL@
INSTALL_PROGRAM = @INSTALL_PROGRAM@
INSTALL_DATA = @INSTALL_DATA@
RANLIB = @RANLIB@
LEX = @LEX@
YACC = @YACC@
# Explicitly define compilation rule since SunOS 4's make doesn't like gcc.
# Also, gcc does not remove the .o before forking 'as', which can be a
# problem if you don't own the file but can write to the directory.
@@ -114,6 +117,7 @@ PUBHDR = \
pcap/nflog.h \
pcap/pcap.h \
pcap/sll.h \
pcap/socket.h \
pcap/vlan.h \
pcap/usb.h
@@ -150,7 +154,7 @@ TAGFILES = \
$(SRC) $(HDR)
CLEANFILES = $(OBJ) libpcap.a libpcap.so.`cat $(srcdir)/VERSION` \
$(PROG)-`cat $(srcdir)/VERSION`.tar.gz \
$(PROG)-`cat $(srcdir)/VERSION`.tar.gz $(GENSRC) $(GENHDR) \
lex.yy.c pcap-config libpcap.pc
MAN1 = pcap-config.1
@@ -165,6 +169,7 @@ MAN3PCAP_EXPAND = \
pcap_list_tstamp_types.3pcap.in \
pcap_open_dead.3pcap.in \
pcap_open_offline.3pcap.in \
pcap_set_immediate_mode.3pcap.in \
pcap_set_tstamp_precision.3pcap.in \
pcap_set_tstamp_type.3pcap.in
@@ -200,7 +205,6 @@ MAN3PCAP_NOEXPAND = \
pcap_open_live.3pcap \
pcap_set_buffer_size.3pcap \
pcap_set_datalink.3pcap \
pcap_set_immediate_mode.3pcap \
pcap_set_promisc.3pcap \
pcap_set_protocol_linux.3pcap \
pcap_set_rfmon.3pcap \
@@ -273,10 +277,14 @@ EXTRA_DIST = \
lbl/os-sunos4.h \
lbl/os-ultrix4.h \
libpcap.pc.in \
missing/asprintf.c \
missing/getopt.c \
missing/getopt.h \
missing/snprintf.c \
missing/strlcat.c \
missing/strlcpy.c \
missing/strtok_r.c \
missing/win_asprintf.c \
missing/win_snprintf.c \
mkdep \
msdos/bin2c.c \
@@ -344,12 +352,13 @@ EXTRA_DIST = \
rpcapd/fileconf.c \
rpcapd/fileconf.h \
rpcapd/log.h \
rpcapd/log-stderr.c \
rpcapd/log.c \
rpcapd/org.tcpdump.rpcapd.plist \
rpcapd/rpcapd.c \
rpcapd/rpcapd.h \
rpcapd/rpcapd.inetd.conf \
rpcapd/rpcapd.manadmin.in \
rpcapd/rpcapd-config.manfile.in \
rpcapd/rpcapd.rc \
rpcapd/rpcapd.socket \
rpcapd/rpcapd.xinetd.conf \
@@ -378,15 +387,6 @@ EXTRA_DIST = \
all: libpcap.a shared $(BUILD_RPCAPD) libpcap.pc pcap-config
# Inhibit implicit rule Make seems to have for using yacc/lex to
# recompile new scanner.c/grammar.c -- we ship ones which we want to
# use instead.
grammar.c:
echo "Not rebuilding grammar.c"
scanner.c:
echo "Not rebuilding scanner.c"
libpcap.a: $(OBJ)
@rm -f $@
$(AR) rc $@ $(OBJ) $(ADDLARCHIVEOBJS)
@@ -423,7 +423,7 @@ libpcap.dylib: $(OBJ)
MAJOR_VER=A; \
COMPAT_VER=1; \
CURRENT_VER=`sed 's/[^0-9.].*$$//' $(srcdir)/VERSION`; \
$(CC) -dynamiclib -undefined error $(LDFLAGS) \
$(CC) -dynamiclib -undefined error $(LDFLAGS) @V_LIB_LDFLAGS_FAT@ \
-o libpcap.$$VER.dylib $(OBJ) $(ADDLOBJS) $(LIBS) \
-install_name $(libdir)/libpcap.$$MAJOR_VER.dylib \
-compatibility_version $$COMPAT_VER \
@@ -468,18 +468,45 @@ libpcap.shareda: $(OBJ)
#
libpcap.none:
scanner.c: $(srcdir)/scanner.l
$(LEX) -P pcap_ --header-file=scanner.h --nounput -o scanner.c $<
scanner.h: scanner.c
## Recover from the removal of $@
@if test -f $@; then :; else \
rm -f scanner.c; \
$(MAKE) $(MAKEFLAGS) scanner.c; \
fi
scanner.o: scanner.c grammar.h
$(CC) $(FULL_CFLAGS) -c scanner.c
grammar.c: $(srcdir)/grammar.y
$(YACC) -p pcap_ -o grammar.c -d $<
grammar.h: grammar.c
## Recover from the removal of $@
@if test -f $@; then :; else \
rm -f grammar.c; \
$(MAKE) $(MAKEFLAGS) grammar.c; \
fi
grammar.o: grammar.c scanner.h
$(CC) $(FULL_CFLAGS) -c grammar.c
gencode.o: $(srcdir)/gencode.c grammar.h scanner.h
$(CC) $(FULL_CFLAGS) -c $(srcdir)/gencode.c
asprintf.o: $(srcdir)/missing/asprintf.c
$(CC) $(FULL_CFLAGS) -o $@ -c $(srcdir)/missing/asprintf.c
snprintf.o: $(srcdir)/missing/snprintf.c
$(CC) $(FULL_CFLAGS) -o $@ -c $(srcdir)/missing/snprintf.c
strlcat.o: $(srcdir)/missing/strlcat.c
$(CC) $(FULL_CFLAGS) -o $@ -c $(srcdir)/missing/strlcat.c
strlcpy.o: $(srcdir)/missing/strlcpy.c
$(CC) $(FULL_CFLAGS) -o $@ -c $(srcdir)/missing/strlcpy.c
strtok_r.o: $(srcdir)/missing/strtok_r.c
$(CC) $(FULL_CFLAGS) -o $@ -c $(srcdir)/missing/strtok_r.c
@@ -563,6 +590,9 @@ install: install-shared install-archive libpcap.pc pcap-config @INSTALL_RPCAPD@
rm -f pcap_datalink_val_to_description.3pcap && \
$(LN_S) pcap_datalink_val_to_name.3pcap \
pcap_datalink_val_to_description.3pcap && \
rm -f pcap_datalink_val_to_description_or_dlt.3pcap && \
$(LN_S) pcap_datalink_val_to_name.3pcap \
pcap_datalink_val_to_description_or_dlt.3pcap && \
rm -f pcap_dump_fopen.3pcap && \
$(LN_S) pcap_dump_open.3pcap pcap_dump_fopen.3pcap && \
rm -f pcap_freealldevs.3pcap && \
@@ -711,8 +741,8 @@ uninstall-rpcapd:
clean:
rm -f $(CLEANFILES)
cd rpcapd && $(MAKE) clean
cd testprogs && $(MAKE) clean
cd rpcapd; $(MAKE) clean
cd testprogs; $(MAKE) clean
distclean: clean
rm -f Makefile config.cache config.log config.status \

View File

@@ -1,103 +0,0 @@
diff --git a/libpcap/Makefile.in b/libpcap/Makefile.in
index dff75ec..38e7bb1 100644
--- a/libpcap/Makefile.in
+++ b/libpcap/Makefile.in
@@ -76,9 +76,6 @@ INSTALL_PROGRAM = @INSTALL_PROGRAM@
INSTALL_DATA = @INSTALL_DATA@
RANLIB = @RANLIB@
-LEX = @LEX@
-YACC = @YACC@
-
# Explicitly define compilation rule since SunOS 4's make doesn't like gcc.
# Also, gcc does not remove the .o before forking 'as', which can be a
# problem if you don't own the file but can write to the directory.
@@ -153,7 +150,7 @@ TAGFILES = \
$(SRC) $(HDR)
CLEANFILES = $(OBJ) libpcap.a libpcap.so.`cat $(srcdir)/VERSION` \
- $(PROG)-`cat $(srcdir)/VERSION`.tar.gz $(GENSRC) $(GENHDR) \
+ $(PROG)-`cat $(srcdir)/VERSION`.tar.gz \
lex.yy.c pcap-config libpcap.pc
MAN1 = pcap-config.1
@@ -381,6 +378,15 @@ EXTRA_DIST = \
all: libpcap.a shared $(BUILD_RPCAPD) libpcap.pc pcap-config
+# Inhibit implicit rule Make seems to have for using yacc/lex to
+# recompile new scanner.c/grammar.c -- we ship ones which we want to
+# use instead.
+grammar.c:
+ echo "Not rebuilding grammar.c"
+
+scanner.c:
+ echo "Not rebuilding scanner.c"
+
libpcap.a: $(OBJ)
@rm -f $@
$(AR) rc $@ $(OBJ) $(ADDLARCHIVEOBJS)
@@ -462,27 +468,9 @@ libpcap.shareda: $(OBJ)
#
libpcap.none:
-scanner.c: $(srcdir)/scanner.l
- $(LEX) -P pcap_ --header-file=scanner.h --nounput -o scanner.c $<
-scanner.h: scanner.c
-## Recover from the removal of $@
- @if test -f $@; then :; else \
- rm -f scanner.c; \
- $(MAKE) $(MAKEFLAGS) scanner.c; \
- fi
-
scanner.o: scanner.c grammar.h
$(CC) $(FULL_CFLAGS) -c scanner.c
-grammar.c: $(srcdir)/grammar.y
- $(YACC) -p pcap_ -o grammar.c -d $<
-grammar.h: grammar.c
-## Recover from the removal of $@
- @if test -f $@; then :; else \
- rm -f grammar.c; \
- $(MAKE) $(MAKEFLAGS) grammar.c; \
- fi
-
grammar.o: grammar.c scanner.h
$(CC) $(FULL_CFLAGS) -c grammar.c
diff --git a/libpcap/configure.ac b/libpcap/configure.ac
index eff6eb8..0127f0a 100644
--- a/libpcap/configure.ac
+++ b/libpcap/configure.ac
@@ -1462,7 +1462,7 @@ yes) AC_MSG_RESULT(yes)
#include "ftmacros.h"
#include <sys/socket.h>
])
-
+ AC_CONFIG_FILES([rpcapd/Makefile rpcapd/rpcapd.manadmin])
AC_DEFINE(ENABLE_REMOTE,,
[Define to 1 if remote packet capture is to be supported])
SSRC="$SSRC pcap-new.c pcap-rpcap.c rpcap-protocol.c sockutils.c"
@@ -1867,14 +1867,12 @@ AC_SUBST(V_CCOPT)
AC_SUBST(V_DEFS)
AC_SUBST(V_FINDALLDEVS)
AC_SUBST(V_INCLS)
-AC_SUBST(V_LEX)
AC_SUBST(V_PCAP)
AC_SUBST(V_SHLIB_CCOPT)
AC_SUBST(V_SHLIB_CMD)
AC_SUBST(V_SHLIB_OPT)
AC_SUBST(V_SONAME_OPT)
AC_SUBST(V_RPATH_OPT)
-AC_SUBST(V_YACC)
AC_SUBST(ADDLOBJS)
AC_SUBST(ADDLARCHIVEOBJS)
AC_SUBST(SSRC)
@@ -2275,6 +2273,6 @@ AC_OUTPUT(Makefile pcap-filter.manmisc pcap-linktype.manmisc
pcap_get_tstamp_precision.3pcap pcap_list_datalinks.3pcap
pcap_list_tstamp_types.3pcap pcap_open_dead.3pcap
pcap_open_offline.3pcap pcap_set_tstamp_precision.3pcap
- pcap_set_tstamp_type.3pcap rpcapd/Makefile rpcapd/rpcapd.manadmin
+ pcap_set_tstamp_type.3pcap
testprogs/Makefile)
exit 0

View File

@@ -1,64 +0,0 @@
diff --git a/libpcap/configure.ac b/libpcap/configure.ac
index 0127f0a..4b35daa 100644
--- a/libpcap/configure.ac
+++ b/libpcap/configure.ac
@@ -743,10 +743,10 @@ linux)
# Do we have libnl?
#
AC_ARG_WITH(libnl,
- AC_HELP_STRING([--without-libnl],[disable libnl support @<:@default=yes, on Linux, if present@:>@]),
+ AC_HELP_STRING([--without-libnl],[disable libnl support @<:@default=disabled@:>@]),
with_libnl=$withval,with_libnl=if_available)
- if test x$with_libnl != xno ; then
+ if test x$with_libnl = xyes ; then
have_any_nl="no"
incdir=-I/usr/include/libnl3
@@ -1814,8 +1814,8 @@ solaris*)
esac
AC_ARG_ENABLE(shared,
-AC_HELP_STRING([--enable-shared],[build shared libraries @<:@default=yes, if support available@:>@]))
-test "x$enable_shared" = "xno" && DYEXT="none"
+AC_HELP_STRING([--enable-shared],[build shared libraries @<:@default=no@:>@]))
+test "x$enable_shared" != "xyes" && DYEXT="none"
AC_PROG_RANLIB
AC_CHECK_TOOL([AR], [ar])
@@ -1887,9 +1887,9 @@ AC_SUBST(RPCAPD_LIBS)
AC_SUBST(EXTRA_NETWORK_LIBS)
AC_ARG_ENABLE([usb],
-[AC_HELP_STRING([--enable-usb],[enable USB capture support @<:@default=yes, if support available@:>@])],
+[AC_HELP_STRING([--enable-usb],[enable USB capture support @<:@default=no@:>@])],
[],
- [enable_usb=yes])
+ [enable_usb=no])
if test "xxx_only" = yes; then
# User requested something-else-only pcap, so they don't
@@ -2035,9 +2035,9 @@ fi
AC_ARG_ENABLE([bluetooth],
-[AC_HELP_STRING([--enable-bluetooth],[enable Bluetooth support @<:@default=yes, if support available@:>@])],
+[AC_HELP_STRING([--enable-bluetooth],[enable Bluetooth support @<:@default=no@:>@])],
[],
- [enable_bluetooth=ifsupportavailable])
+ [enable_bluetooth=no])
if test "xxx_only" = yes; then
# User requested something-else-only pcap, so they don't
@@ -2120,9 +2120,9 @@ if test "x$enable_bluetooth" != "xno" ; then
fi
AC_ARG_ENABLE([dbus],
-[AC_HELP_STRING([--enable-dbus],[enable D-Bus capture support @<:@default=yes, if support available@:>@])],
+[AC_HELP_STRING([--enable-dbus],[enable D-Bus capture support @<:@default=no@:>@])],
[],
- [enable_dbus=ifavailable])
+ [enable_dbus=no])
if test "xxx_only" = yes; then
# User requested something-else-only pcap, so they don't

View File

@@ -1,25 +0,0 @@
Download libpcap-X.Y.tar.gz from http://www.tcpdump.org/#latest-release
and verify the signature.
cd
# Make a copy of this directory.
cp -r ~/nmap/libpcap/NMAP_MODIFICATIONS .
tar xzvf libpcap-X.Y.tar.gz
cd nmap
rsync -rv --delete ~/libpcap-X.Y/ ~/nmap/libpcap/
git add -A libpcap
cd libpcap
./configure
make grammar.c scanner.c scanner.h
git add grammar.c scanner.c scanner.h
cd ..
# Apply patches.
git apply ~/NMAP_MODIFICATIONS/000*
# Make changes as necessary and update the patch files
cd libpcap
autoconf
cd ..
git add -u libpcap
mv ~/NMAP_MODIFICATIONS libpcap/
git add libpcap/NMAP_MODIFICATIONS
git commit -m "Upgrade libpcap to X.Y."

View File

@@ -1 +1 @@
1.9.0
1.9.1

25
libpcap/aclocal.m4 vendored
View File

@@ -484,7 +484,7 @@ AC_DEFUN(AC_LBL_SHLIBS_INIT,
aix*)
;;
freebsd*|netbsd*|openbsd*|dragonfly*|linux*|osf*)
freebsd*|netbsd*|openbsd*|dragonfly*|linux*|osf*|midipix*)
#
# Platforms where the linker is the GNU linker
# or accepts command-line arguments like
@@ -501,7 +501,7 @@ AC_DEFUN(AC_LBL_SHLIBS_INIT,
sparc64*)
case "$host_os" in
freebsd*|openbsd*)
freebsd*|openbsd*|linux*)
PIC_OPT=-fPIC
;;
esac
@@ -878,22 +878,23 @@ AC_DEFUN(AC_LBL_DEVEL,
#
if test "$ac_lbl_cc_dont_try_gcc_dashW" != yes; then
AC_LBL_CHECK_UNKNOWN_WARNING_OPTION_ERROR()
AC_LBL_CHECK_COMPILER_OPT($1, -W)
AC_LBL_CHECK_COMPILER_OPT($1, -Wall)
AC_LBL_CHECK_COMPILER_OPT($1, -Wsign-compare)
AC_LBL_CHECK_COMPILER_OPT($1, -Wmissing-prototypes)
AC_LBL_CHECK_COMPILER_OPT($1, -Wstrict-prototypes)
AC_LBL_CHECK_COMPILER_OPT($1, -Wshadow)
AC_LBL_CHECK_COMPILER_OPT($1, -Wdeclaration-after-statement)
AC_LBL_CHECK_COMPILER_OPT($1, -Wused-but-marked-unused)
AC_LBL_CHECK_COMPILER_OPT($1, -Wdocumentation)
AC_LBL_CHECK_COMPILER_OPT($1, -Wcomma)
AC_LBL_CHECK_COMPILER_OPT($1, -Wdeclaration-after-statement)
AC_LBL_CHECK_COMPILER_OPT($1, -Wdocumentation)
AC_LBL_CHECK_COMPILER_OPT($1, -Wformat-nonliteral)
AC_LBL_CHECK_COMPILER_OPT($1, -Wmissing-noreturn)
AC_LBL_CHECK_COMPILER_OPT($1, -Wmissing-prototypes)
AC_LBL_CHECK_COMPILER_OPT($1, -Wmissing-variable-declarations)
AC_LBL_CHECK_COMPILER_OPT($1, -Wshadow)
AC_LBL_CHECK_COMPILER_OPT($1, -Wsign-compare)
AC_LBL_CHECK_COMPILER_OPT($1, -Wstrict-prototypes)
AC_LBL_CHECK_COMPILER_OPT($1, -Wunused-parameter)
AC_LBL_CHECK_COMPILER_OPT($1, -Wused-but-marked-unused)
# Warns about safeguards added in case the enums are
# extended
# AC_LBL_CHECK_COMPILER_OPT($1, -Wcovered-switch-default)
AC_LBL_CHECK_COMPILER_OPT($1, -Wmissing-variable-declarations)
AC_LBL_CHECK_COMPILER_OPT($1, -Wunused-parameter)
AC_LBL_CHECK_COMPILER_OPT($1, -Wformat-nonliteral)
#
# This can cause problems with ntohs(), ntohl(),
# htons(), and htonl() on some platforms, such

View File

@@ -51,7 +51,7 @@
#include <sys/time.h>
#endif /* _WIN32 */
#include <pcap/bpf.h>
#include <pcap-int.h>
#include <stdlib.h>
@@ -328,11 +328,17 @@ bpf_filter_with_aux_data(const struct bpf_insn *pc, const u_char *p,
continue;
case BPF_ALU|BPF_LSH|BPF_X:
A <<= X;
if (X < 32)
A <<= X;
else
A = 0;
continue;
case BPF_ALU|BPF_RSH|BPF_X:
A >>= X;
if (X < 32)
A >>= X;
else
A = 0;
continue;
case BPF_ALU|BPF_ADD|BPF_K:
@@ -378,10 +384,13 @@ bpf_filter_with_aux_data(const struct bpf_insn *pc, const u_char *p,
case BPF_ALU|BPF_NEG:
/*
* Most BPF arithmetic is unsigned, but negation
* can't be unsigned; throw some casts to
* specify what we're trying to do.
* can't be unsigned; respecify it as subtracting
* the accumulator from 0U, so that 1) we don't
* get compiler warnings about negating an unsigned
* value and 2) don't get UBSan warnings about
* the result of negating 0x80000000 being undefined.
*/
A = (u_int32)(-(int32)A);
A = (0U - A);
continue;
case BPF_MISC|BPF_TAX:

View File

@@ -49,9 +49,17 @@
#
# The 64-bit Packet.lib is located under /x64
set(64BIT_SUBDIR "")
if(CMAKE_SIZEOF_VOID_P EQUAL 8)
set(64BIT_SUBDIR "/x64")
#
# For the WinPcap and Npcap SDKs, the Lib subdirectory of the top-level
# directory contains 32-bit libraries; the 64-bit libraries are in the
# Lib/x64 directory.
#
# The only way to *FORCE* CMake to look in the Lib/x64 directory
# without searching in the Lib directory first appears to be to set
# CMAKE_LIBRARY_ARCHITECTURE to "x64".
#
set(CMAKE_LIBRARY_ARCHITECTURE "x64")
endif()
# Find the header
@@ -64,7 +72,6 @@ find_path(PACKET_INCLUDE_DIR Packet32.h
find_library(PACKET_LIBRARY
NAMES Packet packet
HINTS "${PACKET_DLL_DIR}" ENV PACKET_DLL_DIR
PATH_SUFFIXES Lib${64BIT_SUBDIR} lib${64BIT_SUBDIR}
)
# Set PACKET_FOUND to TRUE if PACKET_INCLUDE_DIR and PACKET_LIBRARY are TRUE.

View File

@@ -15,6 +15,9 @@
/* define if we have the AIX getprotobyname_r() */
#cmakedefine HAVE_AIX_GETPROTOBYNAME_R 1
/* Define to 1 if you have the `asprintf' function. */
#cmakedefine HAVE_ASPRINTF 1
/* define if you have the DAG API */
#cmakedefine HAVE_DAG_API 1
@@ -48,6 +51,9 @@
/* Define to 1 if you have the `getspnam' function. */
#cmakedefine HAVE_GETSPNAM 1
/* Define to 1 if you have a GNU-style `strerror_r' function. */
#cmakedefine HAVE_GNU_STRERROR_R 1
/* on HP-UX 10.20 or later */
#cmakedefine HAVE_HPUX10_20_OR_LATER 1
@@ -138,9 +144,15 @@
/* if there's an os_proto.h for this platform, to use additional prototypes */
#cmakedefine HAVE_OS_PROTO_H 1
/* Define to 1 if Packet32 API (WinPcap NPF driver) is available */
/* Define to 1 if Packet32 API (Npcap driver) is available */
#cmakedefine HAVE_PACKET32 1
/* Define to 1 if NPcap's version.h is available */
#cmakedefine HAVE_VERSION_H 1
/* Define to 1 if you have a POSIX-style `strerror_r' function. */
#cmakedefine HAVE_POSIX_STRERROR_R 1
/* define if net/pfvar.h defines PF_NAT through PF_NORDR */
#cmakedefine HAVE_PF_NAT_THROUGH_PF_NORDR 1
@@ -174,9 +186,6 @@
/* Define to 1 if you have the `strerror' function. */
#cmakedefine HAVE_STRERROR 1
/* Define to 1 if you have the `strerror_r' function. */
#cmakedefine HAVE_STRERROR_R 1
/* Define to 1 if you have the `strerror_s' function. */
#cmakedefine HAVE_STRERROR_S 1
@@ -256,9 +265,15 @@
/* Define to 1 if you have the <unistd.h> header file. */
#cmakedefine HAVE_UNISTD_H 1
/* Define to 1 if you have the `vasprintf' function. */
#cmakedefine HAVE_VASPRINTF 1
/* Define to 1 if you have the `vsnprintf' function. */
#cmakedefine HAVE_VSNPRINTF 1
/* Define to 1 if you have the `vsyslog' function. */
#undef HAVE_VSYSLOG
/* Define to 1 if you have the `PacketIsLoopbackAdapter' function. */
#cmakedefine HAVE_PACKET_IS_LOOPBACK_ADAPTER 1

View File

@@ -15,6 +15,9 @@
/* define if we have the AIX getprotobyname_r() */
#undef HAVE_AIX_GETPROTOBYNAME_R
/* Define to 1 if you have the `asprintf' function. */
#undef HAVE_ASPRINTF
/* Define to 1 if you have the <dagapi.h> header file. */
#undef HAVE_DAGAPI_H
@@ -54,6 +57,9 @@
/* Define to 1 if you have the `getspnam' function. */
#undef HAVE_GETSPNAM
/* Define to 1 if you have a GNU-style `strerror_r' function. */
#undef HAVE_GNU_STRERROR_R
/* on HP-UX 10.20 or later */
#undef HAVE_HPUX10_20_OR_LATER
@@ -150,6 +156,9 @@
/* define if net/pfvar.h defines PF_NAT through PF_NORDR */
#undef HAVE_PF_NAT_THROUGH_PF_NORDR
/* Define to 1 if you have a POSIX-style `strerror_r' function. */
#undef HAVE_POSIX_STRERROR_R
/* define if you have the Septel API */
#undef HAVE_SEPTEL_API
@@ -180,9 +189,6 @@
/* Define to 1 if you have the `strerror' function. */
#undef HAVE_STRERROR
/* Define to 1 if you have the `strerror_r' function. */
#undef HAVE_STRERROR_R
/* Define to 1 if you have the `strerror_s' function. */
#undef HAVE_STRERROR_S
@@ -262,9 +268,15 @@
/* Define to 1 if you have the <unistd.h> header file. */
#undef HAVE_UNISTD_H
/* Define to 1 if you have the `vasprintf' function. */
#undef HAVE_VASPRINTF
/* Define to 1 if you have the `vsnprintf' function. */
#undef HAVE_VSNPRINTF
/* Define to 1 if you have the `vsyslog' function. */
#undef HAVE_VSYSLOG
/* IPv6 */
#undef INET6

1990
libpcap/configure vendored

File diff suppressed because it is too large Load Diff

View File

@@ -28,6 +28,9 @@ AC_LBL_C_INIT_BEFORE_CC(V_CCOPT, V_INCLS)
# At minimum, we want C++/C99-style // comments.
#
AC_PROG_CC_C99
if test "$ac_cv_prog_cc_c99" = "no"; then
AC_MSG_WARN([The C compiler does not support C99; there may be compiler errors])
fi
AC_LBL_C_INIT(V_CCOPT, V_INCLS)
AC_LBL_SHLIBS_INIT
AC_LBL_C_INLINE
@@ -83,13 +86,109 @@ esac
AC_LBL_FIXINCLUDES
AC_CHECK_FUNCS(strerror strerror_r strerror_s strlcpy strlcat)
AC_CHECK_FUNCS(strerror)
AC_CHECK_FUNC(strerror_r,
[
#
# We have strerror_r; if we define _GNU_SOURCE, is it a
# POSIX-compliant strerror_r() or a GNU strerror_r()?
#
AC_MSG_CHECKING(whether strerror_r is GNU-style)
AC_COMPILE_IFELSE(
[
AC_LANG_SOURCE(
#define _GNU_SOURCE
#include <string.h>
/* Define it GNU-style; that will cause an error if it's not GNU-style */
extern char *strerror_r(int, char *, size_t);
int
main(void)
{
return 0;
}
)
],
[
# GNU-style
AC_MSG_RESULT(yes)
AC_DEFINE(HAVE_GNU_STRERROR_R,,
[Define to 1 if you have a GNU-style `strerror_r' function.])
],
[
AC_MSG_RESULT(no)
AC_DEFINE(HAVE_POSIX_STRERROR_R,,
[Define to 1 if you have a POSIX-style `strerror_r' function.])
])
],
[
#
# We don't have strerror_r; do we have strerror_s?
#
AC_CHECK_FUNCS(strerror_s)
])
#
# Thanks, IBM, for not providing vsyslog() in AIX!
#
AC_CHECK_FUNCS(vsyslog)
#
# Either:
#
# we have snprintf() and vsnprintf(), and have asprintf() and
# vasprintf();
#
# we have snprintf() and vsnprintf(), but don't have asprintf()
# or vasprintf();
#
# we have neither snprintf() nor vsnprintf(), and don't have
# asprintf() or vasprintf(), either.
#
# We assume that if we have asprintf() we have vasprintf(), as well
# as snprintf() and vsnprintf(), and that if we have snprintf() we
# have vsnprintf().
#
# For the first case, we don't need any replacement routines.
# For the second case, we need replacement asprintf()/vasprintf()
# routines.
# For the third case, we need replacement snprintf()/vsnprintf() and
# asprintf()/vasprintf() routines.
#
needsnprintf=no
AC_CHECK_FUNCS(vsnprintf snprintf,,
[needsnprintf=yes])
needasprintf=no
AC_CHECK_FUNCS(vasprintf asprintf,,
[needasprintf=yes])
if test $needsnprintf = yes; then
#
# We assume we have none of them; missing/snprintf.c supplies
# all of them.
#
AC_LIBOBJ([snprintf])
elif test $needasprintf = yes; then
#
# We assume we have snprintf()/vsnprintf() but lack
# asprintf()/vasprintf(); missing/asprintf.c supplies
# the latter (using vsnprintf()).
#
AC_LIBOBJ([asprintf])
fi
needstrlcat=no
AC_CHECK_FUNCS(strlcat,,
[needstrlcat=yes])
if test $needstrlcat = yes; then
AC_LIBOBJ([strlcat])
fi
needstrlcpy=no
AC_CHECK_FUNCS(strlcpy,,
[needstrlcpy=yes])
if test $needstrlcpy = yes; then
AC_LIBOBJ([strlcpy])
fi
needstrtok_r=no
@@ -550,6 +649,10 @@ else
# requires that various BSD-style integer types
# be defined;
#
# sys/time.h, because AIX 5.2 and 5.3's net/bpf.h
# doesn't include it but does use struct timeval
# in ioctl definitions;
#
# sys/ioctl.h and, if we have it, sys/ioccom.h,
# because net/bpf.h defines ioctls;
#
@@ -568,6 +671,7 @@ else
AC_TRY_COMPILE(
[
#include <sys/types.h>
#include <sys/time.h>
#include <sys/ioctl.h>
#include <sys/socket.h>
#ifdef HAVE_SYS_IOCCOM_H
@@ -743,10 +847,10 @@ linux)
# Do we have libnl?
#
AC_ARG_WITH(libnl,
AC_HELP_STRING([--without-libnl],[disable libnl support @<:@default=disabled@:>@]),
AC_HELP_STRING([--without-libnl],[disable libnl support @<:@default=yes, on Linux, if present@:>@]),
with_libnl=$withval,with_libnl=if_available)
if test x$with_libnl = xyes ; then
if test x$with_libnl != xno ; then
have_any_nl="no"
incdir=-I/usr/include/libnl3
@@ -1462,7 +1566,7 @@ yes) AC_MSG_RESULT(yes)
#include "ftmacros.h"
#include <sys/socket.h>
])
AC_CONFIG_FILES([rpcapd/Makefile rpcapd/rpcapd.manadmin])
AC_DEFINE(ENABLE_REMOTE,,
[Define to 1 if remote packet capture is to be supported])
SSRC="$SSRC pcap-new.c pcap-rpcap.c rpcap-protocol.c sockutils.c"
@@ -1489,15 +1593,60 @@ if test "$enable_yydebug" = "yes"; then
fi
AC_MSG_RESULT(${enable_yydebug-no})
#
# Look for {f}lex.
#
AC_PROG_LEX
if test "$LEX" = ":"; then
AC_MSG_ERROR([Neither flex nor lex was found.])
fi
#
# Make sure {f}lex supports the -P, --header-file, and --nounput flags
# and supports processing our scanner.l.
#
AC_CACHE_CHECK([for capable lex], tcpdump_cv_capable_lex,
if $LEX -P pcap_ --header-file=/dev/null --nounput -t $srcdir/scanner.l > /dev/null 2>&1; then
tcpdump_cv_capable_lex=yes
else
tcpdump_cv_capable_lex=insufficient
fi)
if test $tcpdump_cv_capable_lex = insufficient ; then
AC_MSG_ERROR([$LEX is insufficient to compile libpcap.
libpcap requires Flex 2.5.31 or later, or a compatible version of lex.])
fi
#
# Look for yacc/bison/byacc.
#
AC_PROG_YACC
#
# Make sure it supports the -p flag and supports processing our
# grammar.y.
#
AC_CACHE_CHECK([for capable yacc/bison], tcpdump_cv_capable_yacc,
if $YACC -p pcap_ -o /dev/null $srcdir/grammar.y >/dev/null 2>&1; then
tcpdump_cv_capable_yacc=yes
else
tcpdump_cv_capable_yacc=insufficient
fi)
if test $tcpdump_cv_capable_yacc = insufficient ; then
AC_MSG_ERROR([$YACC is insufficient to compile libpcap.
libpcap requires Bison, a newer version of Berkeley YACC with support
for reentrant parsers, or another YACC compatible with them.])
fi
#
# Do various checks for various OSes and versions of those OSes.
#
# Assume, by default, no support for shared libraries and V7/BSD
# convention for man pages (file formats in section 5, miscellaneous
# info in section 7, administrative commands and daemons in section 8).
# Individual cases can override this.
# convention for man pages (devices in section 4, file formats in
# section 5, miscellaneous info in section 7, administrative commands
# and daemons in section 8). Individual cases can override this.
#
DYEXT="none"
MAN_DEVICES=4
MAN_FILE_FORMATS=5
MAN_MISC_INFO=7
MAN_ADMIN_COMMANDS=8
@@ -1553,79 +1702,151 @@ darwin*)
if test "$enable_universal" != "no"; then
case "$host_os" in
darwin[0-7].*)
darwin[[0-7]].*)
#
# Pre-Tiger. Build only for 32-bit PowerPC; no
# need for any special compiler or linker flags.
#
;;
darwin8.[0123]*)
darwin8.[[0123]]|darwin8.[[0123]].*)
#
# Tiger, prior to Intel support. Build for 32-bit
# PowerPC and 64-bit PowerPC, with 32-bit PowerPC
# first. (I'm guessing that's what Apple does.)
#
V_CCOPT="$V_CCOPT -arch ppc -arch ppc64"
LDFLAGS="$LDFLAGS -arch ppc -arch ppc64"
;;
darwin8.[456]*)
#
# Tiger, subsequent to Intel support but prior to
# x86-64 support. Build for 32-bit PowerPC, 64-bit
# PowerPC, and x86, with 32-bit PowerPC first.
# Tiger, prior to Intel support. Build
# libraries and executables for 32-bit PowerPC
# and 64-bit PowerPC, with 32-bit PowerPC first.
# (I'm guessing that's what Apple does.)
#
V_CCOPT="$V_CCOPT -arch ppc -arch ppc64 -arch i386"
LDFLAGS="$LDFLAGS -arch ppc -arch ppc64 -arch i386"
# (The double brackets are needed because
# autotools/m4 use brackets as a quoting
# character; the double brackets turn into
# single brackets in the generated configure
# file.)
#
V_LIB_CCOPT_FAT="-arch ppc -arch ppc64"
V_LIB_LDFLAGS_FAT="-arch ppc -arch ppc64"
V_PROG_CCOPT_FAT="-arch ppc -arch ppc64"
V_PROG_LDFLAGS_FAT="-arch ppc -arch ppc64"
;;
darwin8.[[456]]|darwin.[[456]].*)
#
# Tiger, subsequent to Intel support but prior
# to x86-64 support. Build libraries and
# executables for 32-bit PowerPC, 64-bit
# PowerPC, and 32-bit x86, with 32-bit PowerPC
# first. (I'm guessing that's what Apple does.)
#
# (The double brackets are needed because
# autotools/m4 use brackets as a quoting
# character; the double brackets turn into
# single brackets in the generated configure
# file.)
#
V_LIB_CCOPT_FAT="-arch ppc -arch ppc64 -arch i386"
V_LIB_LDFLAGS_FAT="-arch ppc -arch ppc64 -arch i386"
V_PROG_CCOPT_FAT="-arch ppc -arch ppc64 -arch i386"
V_PROG_LDFLAGS_FAT="-arch ppc -arch ppc64 -arch i386"
;;
darwin8.*)
#
# All other Tiger, so subsequent to x86-64
# support. Build for 32-bit PowerPC, 64-bit
# PowerPC, x86, and x86-64, and with 32-bit PowerPC
# first. (I'm guessing that's what Apple does.)
# support. Build libraries and executables for
# 32-bit PowerPC, 64-bit PowerPC, 32-bit x86,
# and x86-64, with 32-bit PowerPC first. (I'm
# guessing that's what Apple does.)
#
V_CCOPT="$V_CCOPT -arch ppc -arch ppc64 -arch i386 -arch x86_64"
LDFLAGS="$LDFLAGS -arch ppc -arch ppc64 -arch i386 -arch x86_64"
V_LIB_CCOPT_FAT="-arch ppc -arch ppc64 -arch i386 -arch x86_64"
V_LIB_LDFLAGS_FAT="-arch ppc -arch ppc64 -arch i386 -arch x86_64"
V_PROG_CCOPT_FAT="-arch ppc -arch ppc64 -arch i386 -arch x86_64"
V_PROG_LDFLAGS_FAT="-arch ppc -arch ppc64 -arch i386 -arch x86_64"
;;
darwin9.*)
#
# Leopard. Build for 32-bit PowerPC, 64-bit
# PowerPC, x86, and x86-64, with 32-bit PowerPC
# first. (That's what Apple does.)
# Leopard. Build libraries for 32-bit PowerPC,
# 64-bit PowerPC, 32-bit x86, and x86-64, with
# 32-bit PowerPC first, and build executables
# for 32-bit x86 and 32-bit PowerPC, with 32-bit
# x86 first. (That's what Apple does.)
#
V_CCOPT="$V_CCOPT -arch ppc -arch ppc64 -arch i386 -arch x86_64"
LDFLAGS="$LDFLAGS -arch ppc -arch ppc64 -arch i386 -arch x86_64"
V_LIB_CCOPT_FAT="-arch ppc -arch ppc64 -arch i386 -arch x86_64"
V_LIB_LDFLAGS_FAT="-arch ppc -arch ppc64 -arch i386 -arch x86_64"
V_PROG_CCOPT_FAT="-arch i386 -arch ppc"
V_PROG_LDFLAGS_FAT="-arch i386 -arch ppc"
;;
darwin10.*)
#
# Snow Leopard. Build for x86-64, x86, and
# 32-bit PowerPC, with x86-64 first. (That's
# what Apple does, even though Snow Leopard
# doesn't run on PPC, so PPC libpcap runs under
# Rosetta, and Rosetta doesn't support BPF
# ioctls, so PPC programs can't do live
# captures.)
# Snow Leopard. Build libraries for x86-64,
# 32-bit x86, and 32-bit PowerPC, with x86-64
# first, and build executables for x86-64 and
# 32-bit x86, with x86-64 first. (That's what
# Apple does, even though Snow Leopard doesn't
# run on PPC, so PPC libpcap runs under Rosetta,
# and Rosetta doesn't support BPF ioctls, so PPC
# programs can't do live captures.)
#
V_CCOPT="$V_CCOPT -arch x86_64 -arch i386 -arch ppc"
LDFLAGS="$LDFLAGS -arch x86_64 -arch i386 -arch ppc"
V_LIB_CCOPT_FAT="-arch x86_64 -arch i386 -arch ppc"
V_LIB_LDFLAGS_FAT="-arch x86_64 -arch i386 -arch ppc"
V_PROG_CCOPT_FAT="-arch x86_64 -arch i386"
V_PROG_LDFLAGS_FAT="-arch x86_64 -arch i386"
;;
darwin*)
#
# Post-Snow Leopard. Build for x86-64 and
# x86, with x86-64 first. (That's probably what
# Apple does, given that Rosetta is gone.)
# Post-Snow Leopard. Build libraries for x86-64
# and 32-bit x86, with x86-64 first, and build
# executables only for x86-64. (That's what
# Apple does.) This requires no special flags
# for programs.
# XXX - update if and when Apple drops support
# for 32-bit x86 code.
# for 32-bit x86 code and if and when Apple adds
# ARM-based Macs. (You're on your own for iOS
# etc.)
#
V_CCOPT="$V_CCOPT -arch x86_64 -arch i386"
LDFLAGS="$LDFLAGS -arch x86_64 -arch i386"
# XXX - check whether we *can* build for
# i386 and, if not, suggest that the user
# install the /usr/include headers if they
# want to build fat.
#
AC_MSG_CHECKING(whether building for 32-bit x86 is supported)
save_CFLAGS="$CFLAGS"
CFLAGS="$CFLAGS -arch i386"
AC_TRY_COMPILE(
[],
[return 0;],
[
AC_MSG_RESULT(yes)
V_LIB_CCOPT_FAT="-arch x86_64 -arch i386"
V_LIB_LDFLAGS_FAT="-arch x86_64 -arch i386"
],
[
AC_MSG_RESULT(no)
V_LIB_CCOPT_FAT="-arch x86_64"
V_LIB_LDFLAGS_FAT="-arch x86_64"
case "$host_os" in
darwin18.*)
#
# Mojave; you need to install the
# /usr/include headers to get
# 32-bit x86 builds to work.
#
AC_MSG_WARN([Compiling for 32-bit x86 gives an error; try installing the command-line tools and, after that, installing the /usr/include headers from the /Library/Developer/CommandLineTools/Packages/macOS_SDK_headers_for_macOS_10.14.pkg package])
;;
*)
#
# Pre-Mojave; the command-line
# tools should be sufficient to
# enable 32-bit x86 builds.
#
AC_MSG_WARN([Compiling for 32-bit x86 gives an error; try installing the command-line tools])
;;
esac
])
CFLAGS="$save_CFLAGS"
;;
esac
fi
@@ -1699,7 +1920,7 @@ irix*)
MAN_MISC_INFO=5
;;
linux*|freebsd*|netbsd*|openbsd*|dragonfly*|kfreebsd*|gnu*)
linux*|freebsd*|netbsd*|openbsd*|dragonfly*|kfreebsd*|gnu*|midipix*)
DYEXT="so"
#
@@ -1722,6 +1943,7 @@ osf*)
#
MAN_FILE_FORMATS=4
MAN_MISC_INFO=5
MAN_DEVICES=7
;;
sinix*)
@@ -1765,13 +1987,14 @@ solaris*)
MAN_ADMIN_COMMANDS=1m
MAN_FILE_FORMATS=4
MAN_MISC_INFO=5
MAN_DEVICES=7D
esac
;;
esac
AC_ARG_ENABLE(shared,
AC_HELP_STRING([--enable-shared],[build shared libraries @<:@default=no@:>@]))
test "x$enable_shared" != "xyes" && DYEXT="none"
AC_HELP_STRING([--enable-shared],[build shared libraries @<:@default=yes, if support available@:>@]))
test "x$enable_shared" = "xno" && DYEXT="none"
AC_PROG_RANLIB
AC_CHECK_TOOL([AR], [ar])
@@ -1820,19 +2043,26 @@ AC_CHECK_MEMBERS([dl_hp_ppa_info_t.dl_module_id_1],,,
AC_LBL_UNALIGNED_ACCESS
AC_SUBST(V_CCOPT)
AC_SUBST(V_LIB_CCOPT_FAT)
AC_SUBST(V_LIB_LDFLAGS_FAT)
AC_SUBST(V_PROG_CCOPT_FAT)
AC_SUBST(V_PROG_LDFLAGS_FAT)
AC_SUBST(V_DEFS)
AC_SUBST(V_FINDALLDEVS)
AC_SUBST(V_INCLS)
AC_SUBST(V_LEX)
AC_SUBST(V_PCAP)
AC_SUBST(V_SHLIB_CCOPT)
AC_SUBST(V_SHLIB_CMD)
AC_SUBST(V_SHLIB_OPT)
AC_SUBST(V_SONAME_OPT)
AC_SUBST(V_RPATH_OPT)
AC_SUBST(V_YACC)
AC_SUBST(ADDLOBJS)
AC_SUBST(ADDLARCHIVEOBJS)
AC_SUBST(SSRC)
AC_SUBST(DYEXT)
AC_SUBST(MAN_DEVICES)
AC_SUBST(MAN_FILE_FORMATS)
AC_SUBST(MAN_MISC_INFO)
AC_SUBST(MAN_ADMIN_COMMANDS)
@@ -1843,9 +2073,9 @@ AC_SUBST(RPCAPD_LIBS)
AC_SUBST(EXTRA_NETWORK_LIBS)
AC_ARG_ENABLE([usb],
[AC_HELP_STRING([--enable-usb],[enable USB capture support @<:@default=no@:>@])],
[AC_HELP_STRING([--enable-usb],[enable USB capture support @<:@default=yes, if support available@:>@])],
[],
[enable_usb=no])
[enable_usb=yes])
if test "xxx_only" = yes; then
# User requested something-else-only pcap, so they don't
@@ -1991,9 +2221,9 @@ fi
AC_ARG_ENABLE([bluetooth],
[AC_HELP_STRING([--enable-bluetooth],[enable Bluetooth support @<:@default=no@:>@])],
[AC_HELP_STRING([--enable-bluetooth],[enable Bluetooth support @<:@default=yes, if support available@:>@])],
[],
[enable_bluetooth=no])
[enable_bluetooth=ifsupportavailable])
if test "xxx_only" = yes; then
# User requested something-else-only pcap, so they don't
@@ -2076,9 +2306,9 @@ if test "x$enable_bluetooth" != "xno" ; then
fi
AC_ARG_ENABLE([dbus],
[AC_HELP_STRING([--enable-dbus],[enable D-Bus capture support @<:@default=no@:>@])],
[AC_HELP_STRING([--enable-dbus],[enable D-Bus capture support @<:@default=yes, if support available@:>@])],
[],
[enable_dbus=no])
[enable_dbus=ifavailable])
if test "xxx_only" = yes; then
# User requested something-else-only pcap, so they don't
@@ -2167,15 +2397,15 @@ fi
AC_ARG_ENABLE([rdma],
[AC_HELP_STRING([--enable-rdma],[enable RDMA capture support @<:@default=yes, if support available@:>@])],
[],
[enable_rdmasniff=ifavailable])
[enable_rdma=ifavailable])
if test "xxx_only" = yes; then
# User requested something-else-only pcap, so they don't
# want RDMA support.
enable_rdmasniff=no
enable_rdma=no
fi
if test "x$enable_rdmasniff" != "xno"; then
if test "x$enable_rdma" != "xno"; then
AC_CHECK_LIB(ibverbs, ibv_get_device_list, [
AC_CHECK_HEADER(infiniband/verbs.h, [
#
@@ -2228,7 +2458,8 @@ AC_OUTPUT(Makefile pcap-filter.manmisc pcap-linktype.manmisc
pcap_compile.3pcap pcap_datalink.3pcap pcap_dump_open.3pcap
pcap_get_tstamp_precision.3pcap pcap_list_datalinks.3pcap
pcap_list_tstamp_types.3pcap pcap_open_dead.3pcap
pcap_open_offline.3pcap pcap_set_tstamp_precision.3pcap
pcap_set_tstamp_type.3pcap
pcap_open_offline.3pcap pcap_set_immediate_mode.3pcap
pcap_set_tstamp_precision.3pcap pcap_set_tstamp_type.3pcap
rpcapd/Makefile rpcapd/rpcapd.manadmin rpcapd/rpcapd-config.manfile
testprogs/Makefile)
exit 0

View File

@@ -65,11 +65,6 @@ pcap_fmt_errmsg_for_errno(char *errbuf, size_t errbuflen, int errnum,
size_t msglen;
char *p;
size_t errbuflen_remaining;
#if defined(HAVE_STRERROR_S)
errno_t err;
#elif defined(HAVE_STRERROR_R)
int err;
#endif
va_start(ap, fmt);
pcap_vsnprintf(errbuf, errbuflen, fmt, ap);
@@ -96,7 +91,10 @@ pcap_fmt_errmsg_for_errno(char *errbuf, size_t errbuflen, int errnum,
* Now append the string for the error code.
*/
#if defined(HAVE_STRERROR_S)
err = strerror_s(p, errbuflen_remaining, errnum);
/*
* We have a Windows-style strerror_s().
*/
errno_t err = strerror_s(p, errbuflen_remaining, errnum);
if (err != 0) {
/*
* It doesn't appear to be documented anywhere obvious
@@ -104,8 +102,24 @@ pcap_fmt_errmsg_for_errno(char *errbuf, size_t errbuflen, int errnum,
*/
pcap_snprintf(p, errbuflen_remaining, "Error %d", errnum);
}
#elif defined(HAVE_STRERROR_R)
err = strerror_r(errnum, p, errbuflen_remaining);
#elif defined(HAVE_GNU_STRERROR_R)
/*
* We have a GNU-style strerror_r(), which is *not* guaranteed to
* do anything to the buffer handed to it, and which returns a
* pointer to the error string, which may or may not be in
* the buffer.
*
* It is, however, guaranteed to succeed.
*/
char strerror_buf[PCAP_ERRBUF_SIZE];
char *errstring = strerror_r(errnum, strerror_buf, PCAP_ERRBUF_SIZE);
pcap_snprintf(p, errbuflen_remaining, "%s", errstring);
#elif defined(HAVE_POSIX_STRERROR_R)
/*
* We have a POSIX-style strerror_r(), which is guaranteed to fill
* in the buffer, but is not guaranteed to succeed.
*/
int err = strerror_r(errnum, p, errbuflen_remaining);
if (err == EINVAL) {
/*
* UNIX 03 says this isn't guaranteed to produce a
@@ -129,3 +143,72 @@ pcap_fmt_errmsg_for_errno(char *errbuf, size_t errbuflen, int errnum,
pcap_snprintf(p, errbuflen_remaining, "%s", pcap_strerror(errnum));
#endif
}
#ifdef _WIN32
/*
* Generate an error message based on a format, arguments, and a
* Win32 error, with a message for the Win32 error after the formatted output.
*/
void
pcap_fmt_errmsg_for_win32_err(char *errbuf, size_t errbuflen, DWORD errnum,
const char *fmt, ...)
{
va_list ap;
size_t msglen;
char *p;
size_t errbuflen_remaining;
DWORD retval;
char win32_errbuf[PCAP_ERRBUF_SIZE+1];
va_start(ap, fmt);
pcap_vsnprintf(errbuf, errbuflen, fmt, ap);
va_end(ap);
msglen = strlen(errbuf);
/*
* Do we have enough space to append ": "?
* Including the terminating '\0', that's 3 bytes.
*/
if (msglen + 3 > errbuflen) {
/* No - just give them what we've produced. */
return;
}
p = errbuf + msglen;
errbuflen_remaining = errbuflen - msglen;
*p++ = ':';
*p++ = ' ';
*p = '\0';
msglen += 2;
errbuflen_remaining -= 2;
/*
* Now append the string for the error code.
*
* XXX - what language ID to use?
*
* For UN*Xes, pcap_strerror() may or may not return localized
* strings.
*
* We currently don't have localized messages for libpcap, but
* we might want to do so. On the other hand, if most of these
* messages are going to be read by libpcap developers and
* perhaps by developers of libpcap-based applications, English
* might be a better choice, so the developer doesn't have to
* get the message translated if it's in a language they don't
* happen to understand.
*/
retval = FormatMessageA(FORMAT_MESSAGE_FROM_SYSTEM|FORMAT_MESSAGE_IGNORE_INSERTS|FORMAT_MESSAGE_MAX_WIDTH_MASK,
NULL, errnum, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
win32_errbuf, PCAP_ERRBUF_SIZE, NULL);
if (retval == 0) {
/*
* Failed.
*/
pcap_snprintf(p, errbuflen_remaining,
"Couldn't get error message for error (%lu)", errnum);
return;
}
pcap_snprintf(p, errbuflen_remaining, "%s (%lu)", win32_errbuf, errnum);
}
#endif

View File

@@ -43,6 +43,11 @@ extern "C" {
void pcap_fmt_errmsg_for_errno(char *, size_t, int,
PCAP_FORMAT_STRING(const char *), ...) PCAP_PRINTFLIKE(4, 5);
#ifdef _WIN32
void pcap_fmt_errmsg_for_win32_err(char *, size_t, DWORD,
PCAP_FORMAT_STRING(const char *), ...) PCAP_PRINTFLIKE(4, 5);
#endif
#ifdef __cplusplus
}
#endif

View File

@@ -85,20 +85,14 @@
*/
#elif defined(__linux__) || defined(linux) || defined(__linux)
/*
* We can't turn _GNU_SOURCE on because some versions of GNU Libc
* will give the GNU version of strerror_r(), which returns a
* string pointer and doesn't necessarily fill in the buffer,
* rather than the standard version of strerror_r(), which
* returns 0 or an errno and always fills in the buffer. We
* require both of the latter behaviors.
* Turn on _GNU_SOURCE to get everything GNU libc has to offer,
* including asprintf().
*
* So we try turning everything else on that we can. This includes
* defining _XOPEN_SOURCE as 600, because we want to force crypt()
* to be declared on systems that use GNU libc, such as most Linux
* distributions.
* Unfortunately, one thing it has to offer is a strerror_r()
* that's not POSIX-compliant, but we deal with that in
* pcap_fmt_errmsg_for_errno().
*/
#define _POSIX_C_SOURCE 200809L
#define _XOPEN_SOURCE 600
#define _GNU_SOURCE
/*
* We turn on both _DEFAULT_SOURCE and _BSD_SOURCE to try to get

File diff suppressed because it is too large Load Diff

View File

@@ -113,16 +113,14 @@
#define Q_ISIS_L2 32
/* PDU types */
#define Q_ISIS_IIH 33
#define Q_ISIS_LAN_IIH 34
#define Q_ISIS_PTP_IIH 35
#define Q_ISIS_SNP 36
#define Q_ISIS_CSNP 37
#define Q_ISIS_PSNP 38
#define Q_ISIS_LSP 39
#define Q_ISIS_SNP 34
#define Q_ISIS_CSNP 35
#define Q_ISIS_PSNP 36
#define Q_ISIS_LSP 37
#define Q_RADIO 40
#define Q_RADIO 38
#define Q_CARP 41
#define Q_CARP 39
/* Directional qualifiers. */
@@ -299,8 +297,8 @@ void gen_or(struct block *, struct block *);
void gen_not(struct block *);
struct block *gen_scode(compiler_state_t *, const char *, struct qual);
struct block *gen_ecode(compiler_state_t *, const u_char *, struct qual);
struct block *gen_acode(compiler_state_t *, const u_char *, struct qual);
struct block *gen_ecode(compiler_state_t *, const char *, struct qual);
struct block *gen_acode(compiler_state_t *, const char *, struct qual);
struct block *gen_mcode(compiler_state_t *, const char *, const char *,
unsigned int, struct qual);
#ifdef INET6
@@ -326,13 +324,13 @@ struct block *gen_llc_u(compiler_state_t *);
struct block *gen_llc_s_subtype(compiler_state_t *, bpf_u_int32);
struct block *gen_llc_u_subtype(compiler_state_t *, bpf_u_int32);
struct block *gen_vlan(compiler_state_t *, int);
struct block *gen_mpls(compiler_state_t *, int);
struct block *gen_vlan(compiler_state_t *, bpf_u_int32, int);
struct block *gen_mpls(compiler_state_t *, bpf_u_int32, int);
struct block *gen_pppoed(compiler_state_t *);
struct block *gen_pppoes(compiler_state_t *, int);
struct block *gen_pppoes(compiler_state_t *, bpf_u_int32, int);
struct block *gen_geneve(compiler_state_t *, int);
struct block *gen_geneve(compiler_state_t *, bpf_u_int32, int);
struct block *gen_atmfield_code(compiler_state_t *, int, bpf_int32,
bpf_u_int32, int);
@@ -343,29 +341,11 @@ struct block *gen_mtp2type_abbrev(compiler_state_t *, int type);
struct block *gen_mtp3field_code(compiler_state_t *, int, bpf_u_int32,
bpf_u_int32, int);
#ifndef HAVE_NET_PFVAR_H
PCAP_NORETURN
#endif
struct block *gen_pf_ifname(compiler_state_t *, const char *);
#ifndef HAVE_NET_PFVAR_H
PCAP_NORETURN
#endif
struct block *gen_pf_rnr(compiler_state_t *, int);
#ifndef HAVE_NET_PFVAR_H
PCAP_NORETURN
#endif
struct block *gen_pf_srnr(compiler_state_t *, int);
#ifndef HAVE_NET_PFVAR_H
PCAP_NORETURN
#endif
struct block *gen_pf_ruleset(compiler_state_t *, char *);
#ifndef HAVE_NET_PFVAR_H
PCAP_NORETURN
#endif
struct block *gen_pf_reason(compiler_state_t *, int);
#ifndef HAVE_NET_PFVAR_H
PCAP_NORETURN
#endif
struct block *gen_pf_action(compiler_state_t *, int);
struct block *gen_p80211_type(compiler_state_t *, int, int);
@@ -386,16 +366,15 @@ struct icode {
int cur_mark;
};
void bpf_optimize(compiler_state_t *, struct icode *ic);
void PCAP_NORETURN bpf_syntax_error(compiler_state_t *, const char *);
void PCAP_NORETURN bpf_error(compiler_state_t *, const char *, ...)
int bpf_optimize(struct icode *, char *);
void bpf_set_error(compiler_state_t *, const char *, ...)
PCAP_PRINTFLIKE(2, 3);
void finish_parse(compiler_state_t *, struct block *);
int finish_parse(compiler_state_t *, struct block *);
char *sdup(compiler_state_t *, const char *);
struct bpf_insn *icode_to_fcode(compiler_state_t *, struct icode *,
struct block *, u_int *);
struct bpf_insn *icode_to_fcode(struct icode *, struct block *, u_int *,
char *);
void sappend(struct slist *, struct slist *);
/*

File diff suppressed because it is too large Load Diff

View File

@@ -1,323 +0,0 @@
/* A Bison parser, made by GNU Bison 3.0.4. */
/* Bison interface for Yacc-like parsers in C
Copyright (C) 1984, 1989-1990, 2000-2015 Free Software Foundation, Inc.
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>. */
/* As a special exception, you may create a larger work that contains
part or all of the Bison parser skeleton and distribute that work
under terms of your choice, so long as that work isn't itself a
parser generator using the skeleton or a modified version thereof
as a parser skeleton. Alternatively, if you modify or redistribute
the parser skeleton itself, you may (at your option) remove this
special exception, which will cause the skeleton and the resulting
Bison output files to be licensed under the GNU General Public
License without this special exception.
This special exception was added by the Free Software Foundation in
version 2.2 of Bison. */
#ifndef YY_PCAP_GRAMMAR_H_INCLUDED
# define YY_PCAP_GRAMMAR_H_INCLUDED
/* Debug traces. */
#ifndef YYDEBUG
# define YYDEBUG 0
#endif
#if YYDEBUG
extern int pcap_debug;
#endif
/* Token type. */
#ifndef YYTOKENTYPE
# define YYTOKENTYPE
enum yytokentype
{
DST = 258,
SRC = 259,
HOST = 260,
GATEWAY = 261,
NET = 262,
NETMASK = 263,
PORT = 264,
PORTRANGE = 265,
LESS = 266,
GREATER = 267,
PROTO = 268,
PROTOCHAIN = 269,
CBYTE = 270,
ARP = 271,
RARP = 272,
IP = 273,
SCTP = 274,
TCP = 275,
UDP = 276,
ICMP = 277,
IGMP = 278,
IGRP = 279,
PIM = 280,
VRRP = 281,
CARP = 282,
ATALK = 283,
AARP = 284,
DECNET = 285,
LAT = 286,
SCA = 287,
MOPRC = 288,
MOPDL = 289,
TK_BROADCAST = 290,
TK_MULTICAST = 291,
NUM = 292,
INBOUND = 293,
OUTBOUND = 294,
PF_IFNAME = 295,
PF_RSET = 296,
PF_RNR = 297,
PF_SRNR = 298,
PF_REASON = 299,
PF_ACTION = 300,
TYPE = 301,
SUBTYPE = 302,
DIR = 303,
ADDR1 = 304,
ADDR2 = 305,
ADDR3 = 306,
ADDR4 = 307,
RA = 308,
TA = 309,
LINK = 310,
GEQ = 311,
LEQ = 312,
NEQ = 313,
ID = 314,
EID = 315,
HID = 316,
HID6 = 317,
AID = 318,
LSH = 319,
RSH = 320,
LEN = 321,
IPV6 = 322,
ICMPV6 = 323,
AH = 324,
ESP = 325,
VLAN = 326,
MPLS = 327,
PPPOED = 328,
PPPOES = 329,
GENEVE = 330,
ISO = 331,
ESIS = 332,
CLNP = 333,
ISIS = 334,
L1 = 335,
L2 = 336,
IIH = 337,
LSP = 338,
SNP = 339,
CSNP = 340,
PSNP = 341,
STP = 342,
IPX = 343,
NETBEUI = 344,
LANE = 345,
LLC = 346,
METAC = 347,
BCC = 348,
SC = 349,
ILMIC = 350,
OAMF4EC = 351,
OAMF4SC = 352,
OAM = 353,
OAMF4 = 354,
CONNECTMSG = 355,
METACONNECT = 356,
VPI = 357,
VCI = 358,
RADIO = 359,
FISU = 360,
LSSU = 361,
MSU = 362,
HFISU = 363,
HLSSU = 364,
HMSU = 365,
SIO = 366,
OPC = 367,
DPC = 368,
SLS = 369,
HSIO = 370,
HOPC = 371,
HDPC = 372,
HSLS = 373,
OR = 374,
AND = 375,
UMINUS = 376
};
#endif
/* Tokens. */
#define DST 258
#define SRC 259
#define HOST 260
#define GATEWAY 261
#define NET 262
#define NETMASK 263
#define PORT 264
#define PORTRANGE 265
#define LESS 266
#define GREATER 267
#define PROTO 268
#define PROTOCHAIN 269
#define CBYTE 270
#define ARP 271
#define RARP 272
#define IP 273
#define SCTP 274
#define TCP 275
#define UDP 276
#define ICMP 277
#define IGMP 278
#define IGRP 279
#define PIM 280
#define VRRP 281
#define CARP 282
#define ATALK 283
#define AARP 284
#define DECNET 285
#define LAT 286
#define SCA 287
#define MOPRC 288
#define MOPDL 289
#define TK_BROADCAST 290
#define TK_MULTICAST 291
#define NUM 292
#define INBOUND 293
#define OUTBOUND 294
#define PF_IFNAME 295
#define PF_RSET 296
#define PF_RNR 297
#define PF_SRNR 298
#define PF_REASON 299
#define PF_ACTION 300
#define TYPE 301
#define SUBTYPE 302
#define DIR 303
#define ADDR1 304
#define ADDR2 305
#define ADDR3 306
#define ADDR4 307
#define RA 308
#define TA 309
#define LINK 310
#define GEQ 311
#define LEQ 312
#define NEQ 313
#define ID 314
#define EID 315
#define HID 316
#define HID6 317
#define AID 318
#define LSH 319
#define RSH 320
#define LEN 321
#define IPV6 322
#define ICMPV6 323
#define AH 324
#define ESP 325
#define VLAN 326
#define MPLS 327
#define PPPOED 328
#define PPPOES 329
#define GENEVE 330
#define ISO 331
#define ESIS 332
#define CLNP 333
#define ISIS 334
#define L1 335
#define L2 336
#define IIH 337
#define LSP 338
#define SNP 339
#define CSNP 340
#define PSNP 341
#define STP 342
#define IPX 343
#define NETBEUI 344
#define LANE 345
#define LLC 346
#define METAC 347
#define BCC 348
#define SC 349
#define ILMIC 350
#define OAMF4EC 351
#define OAMF4SC 352
#define OAM 353
#define OAMF4 354
#define CONNECTMSG 355
#define METACONNECT 356
#define VPI 357
#define VCI 358
#define RADIO 359
#define FISU 360
#define LSSU 361
#define MSU 362
#define HFISU 363
#define HLSSU 364
#define HMSU 365
#define SIO 366
#define OPC 367
#define DPC 368
#define SLS 369
#define HSIO 370
#define HOPC 371
#define HDPC 372
#define HSLS 373
#define OR 374
#define AND 375
#define UMINUS 376
/* Value type. */
#if ! defined YYSTYPE && ! defined YYSTYPE_IS_DECLARED
union YYSTYPE
{
#line 286 "grammar.y" /* yacc.c:1909 */
int i;
bpf_u_int32 h;
u_char *e;
char *s;
struct stmt *stmt;
struct arth *a;
struct {
struct qual q;
int atmfieldtype;
int mtp3fieldtype;
struct block *b;
} blk;
struct block *rblk;
#line 312 "grammar.h" /* yacc.c:1909 */
};
typedef union YYSTYPE YYSTYPE;
# define YYSTYPE_IS_TRIVIAL 1
# define YYSTYPE_IS_DECLARED 1
#endif
int pcap_parse (void *yyscanner, compiler_state_t *cstate);
#endif /* !YY_PCAP_GRAMMAR_H_INCLUDED */

View File

@@ -216,13 +216,12 @@ str2tok(const char *str, const struct tok *toks)
return (-1);
}
static struct qual qerr = { Q_UNDEF, Q_UNDEF, Q_UNDEF, Q_UNDEF };
static const struct qual qerr = { Q_UNDEF, Q_UNDEF, Q_UNDEF, Q_UNDEF };
static PCAP_NORETURN_DEF void
static void
yyerror(void *yyscanner _U_, compiler_state_t *cstate, const char *msg)
{
bpf_syntax_error(cstate, msg);
/* NOTREACHED */
bpf_set_error(cstate, "can't parse filter expression: %s", msg);
}
#ifdef HAVE_NET_PFVAR_H
@@ -236,8 +235,8 @@ pfreason_to_num(compiler_state_t *cstate, const char *reason)
if (pcap_strcasecmp(reason, reasons[i]) == 0)
return (i);
}
bpf_error(cstate, "unknown PF reason");
/*NOTREACHED*/
bpf_set_error(cstate, "unknown PF reason");
return (-1);
}
static int
@@ -260,33 +259,38 @@ pfaction_to_num(compiler_state_t *cstate, const char *action)
return (PF_NORDR);
#endif
else {
bpf_error(cstate, "unknown PF action");
/*NOTREACHED*/
bpf_set_error(cstate, "unknown PF action");
return (-1);
}
}
#else /* !HAVE_NET_PFVAR_H */
static PCAP_NORETURN_DEF int
static int
pfreason_to_num(compiler_state_t *cstate, const char *reason _U_)
{
bpf_error(cstate, "libpcap was compiled on a machine without pf support");
/*NOTREACHED*/
bpf_set_error(cstate, "libpcap was compiled on a machine without pf support");
return (-1);
}
static PCAP_NORETURN_DEF int
static int
pfaction_to_num(compiler_state_t *cstate, const char *action _U_)
{
bpf_error(cstate, "libpcap was compiled on a machine without pf support");
/*NOTREACHED*/
bpf_set_error(cstate, "libpcap was compiled on a machine without pf support");
return (-1);
}
#endif /* HAVE_NET_PFVAR_H */
/*
* For calls that might return an "an error occurred" value.
*/
#define CHECK_INT_VAL(val) if (val == -1) YYABORT
#define CHECK_PTR_VAL(val) if (val == NULL) YYABORT
DIAG_OFF_BISON_BYACC
%}
%union {
int i;
bpf_u_int32 h;
u_char *e;
char *s;
struct stmt *stmt;
struct arth *a;
@@ -340,11 +344,9 @@ DIAG_OFF_BISON_BYACC
%token RADIO
%token FISU LSSU MSU HFISU HLSSU HMSU
%token SIO OPC DPC SLS HSIO HOPC HDPC HSLS
%token LEX_ERROR
%type <s> ID
%type <e> EID
%type <e> AID
%type <s> ID EID AID
%type <s> HID HID6
%type <i> NUM action reason type subtype type_subtype dir
@@ -359,7 +361,7 @@ DIAG_OFF_BISON_BYACC
%%
prog: null expr
{
finish_parse(cstate, $2.b);
CHECK_INT_VAL(finish_parse(cstate, $2.b));
}
| null
;
@@ -376,64 +378,58 @@ and: AND { $$ = $<blk>0; }
or: OR { $$ = $<blk>0; }
;
id: nid
| pnum { $$.b = gen_ncode(cstate, NULL, (bpf_u_int32)$1,
$$.q = $<blk>0.q); }
| pnum { CHECK_PTR_VAL(($$.b = gen_ncode(cstate, NULL, (bpf_u_int32)$1,
$$.q = $<blk>0.q))); }
| paren pid ')' { $$ = $2; }
;
nid: ID { $$.b = gen_scode(cstate, $1, $$.q = $<blk>0.q); }
| HID '/' NUM { $$.b = gen_mcode(cstate, $1, NULL, $3,
$$.q = $<blk>0.q); }
| HID NETMASK HID { $$.b = gen_mcode(cstate, $1, $3, 0,
$$.q = $<blk>0.q); }
nid: ID { CHECK_PTR_VAL($1); CHECK_PTR_VAL(($$.b = gen_scode(cstate, $1, $$.q = $<blk>0.q))); }
| HID '/' NUM { CHECK_PTR_VAL($1); CHECK_PTR_VAL(($$.b = gen_mcode(cstate, $1, NULL, $3,
$$.q = $<blk>0.q))); }
| HID NETMASK HID { CHECK_PTR_VAL($1); CHECK_PTR_VAL(($$.b = gen_mcode(cstate, $1, $3, 0,
$$.q = $<blk>0.q))); }
| HID {
CHECK_PTR_VAL($1);
/* Decide how to parse HID based on proto */
$$.q = $<blk>0.q;
if ($$.q.addr == Q_PORT)
bpf_error(cstate, "'port' modifier applied to ip host");
else if ($$.q.addr == Q_PORTRANGE)
bpf_error(cstate, "'portrange' modifier applied to ip host");
else if ($$.q.addr == Q_PROTO)
bpf_error(cstate, "'proto' modifier applied to ip host");
else if ($$.q.addr == Q_PROTOCHAIN)
bpf_error(cstate, "'protochain' modifier applied to ip host");
$$.b = gen_ncode(cstate, $1, 0, $$.q);
if ($$.q.addr == Q_PORT) {
bpf_set_error(cstate, "'port' modifier applied to ip host");
YYABORT;
} else if ($$.q.addr == Q_PORTRANGE) {
bpf_set_error(cstate, "'portrange' modifier applied to ip host");
YYABORT;
} else if ($$.q.addr == Q_PROTO) {
bpf_set_error(cstate, "'proto' modifier applied to ip host");
YYABORT;
} else if ($$.q.addr == Q_PROTOCHAIN) {
bpf_set_error(cstate, "'protochain' modifier applied to ip host");
YYABORT;
}
CHECK_PTR_VAL(($$.b = gen_ncode(cstate, $1, 0, $$.q)));
}
| HID6 '/' NUM {
CHECK_PTR_VAL($1);
#ifdef INET6
$$.b = gen_mcode6(cstate, $1, NULL, $3,
$$.q = $<blk>0.q);
CHECK_PTR_VAL(($$.b = gen_mcode6(cstate, $1, NULL, $3,
$$.q = $<blk>0.q)));
#else
bpf_error(cstate, "'ip6addr/prefixlen' not supported "
bpf_set_error(cstate, "'ip6addr/prefixlen' not supported "
"in this configuration");
YYABORT;
#endif /*INET6*/
}
| HID6 {
CHECK_PTR_VAL($1);
#ifdef INET6
$$.b = gen_mcode6(cstate, $1, 0, 128,
$$.q = $<blk>0.q);
CHECK_PTR_VAL(($$.b = gen_mcode6(cstate, $1, 0, 128,
$$.q = $<blk>0.q)));
#else
bpf_error(cstate, "'ip6addr' not supported "
bpf_set_error(cstate, "'ip6addr' not supported "
"in this configuration");
YYABORT;
#endif /*INET6*/
}
| EID {
$$.b = gen_ecode(cstate, $1, $$.q = $<blk>0.q);
/*
* $1 was allocated by "pcap_ether_aton()",
* so we must free it now that we're done
* with it.
*/
free($1);
}
| AID {
$$.b = gen_acode(cstate, $1, $$.q = $<blk>0.q);
/*
* $1 was allocated by "pcap_ether_aton()",
* so we must free it now that we're done
* with it.
*/
free($1);
}
| EID { CHECK_PTR_VAL($1); CHECK_PTR_VAL(($$.b = gen_ecode(cstate, $1, $$.q = $<blk>0.q))); }
| AID { CHECK_PTR_VAL($1); CHECK_PTR_VAL(($$.b = gen_acode(cstate, $1, $$.q = $<blk>0.q))); }
| not id { gen_not($2.b); $$ = $2; }
;
not: '!' { $$ = $<blk>0; }
@@ -444,8 +440,8 @@ pid: nid
| qid and id { gen_and($1.b, $3.b); $$ = $3; }
| qid or id { gen_or($1.b, $3.b); $$ = $3; }
;
qid: pnum { $$.b = gen_ncode(cstate, NULL, (bpf_u_int32)$1,
$$.q = $<blk>0.q); }
qid: pnum { CHECK_PTR_VAL(($$.b = gen_ncode(cstate, NULL, (bpf_u_int32)$1,
$$.q = $<blk>0.q))); }
| pid
;
term: rterm
@@ -455,21 +451,28 @@ head: pqual dqual aqual { QSET($$.q, $1, $2, $3); }
| pqual dqual { QSET($$.q, $1, $2, Q_DEFAULT); }
| pqual aqual { QSET($$.q, $1, Q_DEFAULT, $2); }
| pqual PROTO { QSET($$.q, $1, Q_DEFAULT, Q_PROTO); }
| pqual PROTOCHAIN { QSET($$.q, $1, Q_DEFAULT, Q_PROTOCHAIN); }
| pqual PROTOCHAIN {
#ifdef NO_PROTOCHAIN
bpf_set_error(cstate, "protochain not supported");
YYABORT;
#else
QSET($$.q, $1, Q_DEFAULT, Q_PROTOCHAIN);
#endif
}
| pqual ndaqual { QSET($$.q, $1, Q_DEFAULT, $2); }
;
rterm: head id { $$ = $2; }
| paren expr ')' { $$.b = $2.b; $$.q = $1.q; }
| pname { $$.b = gen_proto_abbrev(cstate, $1); $$.q = qerr; }
| arth relop arth { $$.b = gen_relation(cstate, $2, $1, $3, 0);
| pname { CHECK_PTR_VAL(($$.b = gen_proto_abbrev(cstate, $1))); $$.q = qerr; }
| arth relop arth { CHECK_PTR_VAL(($$.b = gen_relation(cstate, $2, $1, $3, 0)));
$$.q = qerr; }
| arth irelop arth { $$.b = gen_relation(cstate, $2, $1, $3, 1);
| arth irelop arth { CHECK_PTR_VAL(($$.b = gen_relation(cstate, $2, $1, $3, 1)));
$$.q = qerr; }
| other { $$.b = $1; $$.q = qerr; }
| atmtype { $$.b = gen_atmtype_abbrev(cstate, $1); $$.q = qerr; }
| atmmultitype { $$.b = gen_atmmulti_abbrev(cstate, $1); $$.q = qerr; }
| atmtype { CHECK_PTR_VAL(($$.b = gen_atmtype_abbrev(cstate, $1))); $$.q = qerr; }
| atmmultitype { CHECK_PTR_VAL(($$.b = gen_atmmulti_abbrev(cstate, $1))); $$.q = qerr; }
| atmfield atmvalue { $$.b = $2.b; $$.q = qerr; }
| mtp2type { $$.b = gen_mtp2type_abbrev(cstate, $1); $$.q = qerr; }
| mtp2type { CHECK_PTR_VAL(($$.b = gen_mtp2type_abbrev(cstate, $1))); $$.q = qerr; }
| mtp3field mtp3value { $$.b = $2.b; $$.q = qerr; }
;
/* protocol level qualifiers */
@@ -539,65 +542,69 @@ pname: LINK { $$ = Q_LINK; }
| NETBEUI { $$ = Q_NETBEUI; }
| RADIO { $$ = Q_RADIO; }
;
other: pqual TK_BROADCAST { $$ = gen_broadcast(cstate, $1); }
| pqual TK_MULTICAST { $$ = gen_multicast(cstate, $1); }
| LESS NUM { $$ = gen_less(cstate, $2); }
| GREATER NUM { $$ = gen_greater(cstate, $2); }
| CBYTE NUM byteop NUM { $$ = gen_byteop(cstate, $3, $2, $4); }
| INBOUND { $$ = gen_inbound(cstate, 0); }
| OUTBOUND { $$ = gen_inbound(cstate, 1); }
| VLAN pnum { $$ = gen_vlan(cstate, $2); }
| VLAN { $$ = gen_vlan(cstate, -1); }
| MPLS pnum { $$ = gen_mpls(cstate, $2); }
| MPLS { $$ = gen_mpls(cstate, -1); }
| PPPOED { $$ = gen_pppoed(cstate); }
| PPPOES pnum { $$ = gen_pppoes(cstate, $2); }
| PPPOES { $$ = gen_pppoes(cstate, -1); }
| GENEVE pnum { $$ = gen_geneve(cstate, $2); }
| GENEVE { $$ = gen_geneve(cstate, -1); }
other: pqual TK_BROADCAST { CHECK_PTR_VAL(($$ = gen_broadcast(cstate, $1))); }
| pqual TK_MULTICAST { CHECK_PTR_VAL(($$ = gen_multicast(cstate, $1))); }
| LESS NUM { CHECK_PTR_VAL(($$ = gen_less(cstate, $2))); }
| GREATER NUM { CHECK_PTR_VAL(($$ = gen_greater(cstate, $2))); }
| CBYTE NUM byteop NUM { CHECK_PTR_VAL(($$ = gen_byteop(cstate, $3, $2, $4))); }
| INBOUND { CHECK_PTR_VAL(($$ = gen_inbound(cstate, 0))); }
| OUTBOUND { CHECK_PTR_VAL(($$ = gen_inbound(cstate, 1))); }
| VLAN pnum { CHECK_PTR_VAL(($$ = gen_vlan(cstate, (bpf_u_int32)$2, 1))); }
| VLAN { CHECK_PTR_VAL(($$ = gen_vlan(cstate, 0, 0))); }
| MPLS pnum { CHECK_PTR_VAL(($$ = gen_mpls(cstate, (bpf_u_int32)$2, 1))); }
| MPLS { CHECK_PTR_VAL(($$ = gen_mpls(cstate, 0, 0))); }
| PPPOED { CHECK_PTR_VAL(($$ = gen_pppoed(cstate))); }
| PPPOES pnum { CHECK_PTR_VAL(($$ = gen_pppoes(cstate, (bpf_u_int32)$2, 1))); }
| PPPOES { CHECK_PTR_VAL(($$ = gen_pppoes(cstate, 0, 0))); }
| GENEVE pnum { CHECK_PTR_VAL(($$ = gen_geneve(cstate, (bpf_u_int32)$2, 1))); }
| GENEVE { CHECK_PTR_VAL(($$ = gen_geneve(cstate, 0, 0))); }
| pfvar { $$ = $1; }
| pqual p80211 { $$ = $2; }
| pllc { $$ = $1; }
;
pfvar: PF_IFNAME ID { $$ = gen_pf_ifname(cstate, $2); }
| PF_RSET ID { $$ = gen_pf_ruleset(cstate, $2); }
| PF_RNR NUM { $$ = gen_pf_rnr(cstate, $2); }
| PF_SRNR NUM { $$ = gen_pf_srnr(cstate, $2); }
| PF_REASON reason { $$ = gen_pf_reason(cstate, $2); }
| PF_ACTION action { $$ = gen_pf_action(cstate, $2); }
pfvar: PF_IFNAME ID { CHECK_PTR_VAL($2); CHECK_PTR_VAL(($$ = gen_pf_ifname(cstate, $2))); }
| PF_RSET ID { CHECK_PTR_VAL($2); CHECK_PTR_VAL(($$ = gen_pf_ruleset(cstate, $2))); }
| PF_RNR NUM { CHECK_PTR_VAL(($$ = gen_pf_rnr(cstate, $2))); }
| PF_SRNR NUM { CHECK_PTR_VAL(($$ = gen_pf_srnr(cstate, $2))); }
| PF_REASON reason { CHECK_PTR_VAL(($$ = gen_pf_reason(cstate, $2))); }
| PF_ACTION action { CHECK_PTR_VAL(($$ = gen_pf_action(cstate, $2))); }
;
p80211: TYPE type SUBTYPE subtype
{ $$ = gen_p80211_type(cstate, $2 | $4,
{ CHECK_PTR_VAL(($$ = gen_p80211_type(cstate, $2 | $4,
IEEE80211_FC0_TYPE_MASK |
IEEE80211_FC0_SUBTYPE_MASK);
IEEE80211_FC0_SUBTYPE_MASK)));
}
| TYPE type { $$ = gen_p80211_type(cstate, $2,
IEEE80211_FC0_TYPE_MASK);
| TYPE type { CHECK_PTR_VAL(($$ = gen_p80211_type(cstate, $2,
IEEE80211_FC0_TYPE_MASK)));
}
| SUBTYPE type_subtype { $$ = gen_p80211_type(cstate, $2,
| SUBTYPE type_subtype { CHECK_PTR_VAL(($$ = gen_p80211_type(cstate, $2,
IEEE80211_FC0_TYPE_MASK |
IEEE80211_FC0_SUBTYPE_MASK);
IEEE80211_FC0_SUBTYPE_MASK)));
}
| DIR dir { $$ = gen_p80211_fcdir(cstate, $2); }
| DIR dir { CHECK_PTR_VAL(($$ = gen_p80211_fcdir(cstate, $2))); }
;
type: NUM
| ID { $$ = str2tok($1, ieee80211_types);
if ($$ == -1)
bpf_error(cstate, "unknown 802.11 type name");
| ID { CHECK_PTR_VAL($1);
$$ = str2tok($1, ieee80211_types);
if ($$ == -1) {
bpf_set_error(cstate, "unknown 802.11 type name");
YYABORT;
}
}
;
subtype: NUM
| ID { const struct tok *types = NULL;
int i;
CHECK_PTR_VAL($1);
for (i = 0;; i++) {
if (ieee80211_type_subtypes[i].tok == NULL) {
/* Ran out of types */
bpf_error(cstate, "unknown 802.11 type");
break;
bpf_set_error(cstate, "unknown 802.11 type");
YYABORT;
}
if ($<i>-1 == ieee80211_type_subtypes[i].type) {
types = ieee80211_type_subtypes[i].tok;
@@ -606,17 +613,20 @@ subtype: NUM
}
$$ = str2tok($1, types);
if ($$ == -1)
bpf_error(cstate, "unknown 802.11 subtype name");
if ($$ == -1) {
bpf_set_error(cstate, "unknown 802.11 subtype name");
YYABORT;
}
}
;
type_subtype: ID { int i;
CHECK_PTR_VAL($1);
for (i = 0;; i++) {
if (ieee80211_type_subtypes[i].tok == NULL) {
/* Ran out of types */
bpf_error(cstate, "unknown 802.11 type name");
break;
bpf_set_error(cstate, "unknown 802.11 type name");
YYABORT;
}
$$ = str2tok($1, ieee80211_type_subtypes[i].tok);
if ($$ != -1) {
@@ -627,33 +637,37 @@ type_subtype: ID { int i;
}
;
pllc: LLC { $$ = gen_llc(cstate); }
| LLC ID { if (pcap_strcasecmp($2, "i") == 0)
$$ = gen_llc_i(cstate);
else if (pcap_strcasecmp($2, "s") == 0)
$$ = gen_llc_s(cstate);
else if (pcap_strcasecmp($2, "u") == 0)
$$ = gen_llc_u(cstate);
else {
pllc: LLC { CHECK_PTR_VAL(($$ = gen_llc(cstate))); }
| LLC ID { CHECK_PTR_VAL($2);
if (pcap_strcasecmp($2, "i") == 0) {
CHECK_PTR_VAL(($$ = gen_llc_i(cstate)));
} else if (pcap_strcasecmp($2, "s") == 0) {
CHECK_PTR_VAL(($$ = gen_llc_s(cstate)));
} else if (pcap_strcasecmp($2, "u") == 0) {
CHECK_PTR_VAL(($$ = gen_llc_u(cstate)));
} else {
int subtype;
subtype = str2tok($2, llc_s_subtypes);
if (subtype != -1)
$$ = gen_llc_s_subtype(cstate, subtype);
else {
if (subtype != -1) {
CHECK_PTR_VAL(($$ = gen_llc_s_subtype(cstate, subtype)));
} else {
subtype = str2tok($2, llc_u_subtypes);
if (subtype == -1)
bpf_error(cstate, "unknown LLC type name \"%s\"", $2);
$$ = gen_llc_u_subtype(cstate, subtype);
if (subtype == -1) {
bpf_set_error(cstate, "unknown LLC type name \"%s\"", $2);
YYABORT;
}
CHECK_PTR_VAL(($$ = gen_llc_u_subtype(cstate, subtype)));
}
}
}
/* sigh, "rnr" is already a keyword for PF */
| LLC PF_RNR { $$ = gen_llc_s_subtype(cstate, LLC_RNR); }
| LLC PF_RNR { CHECK_PTR_VAL(($$ = gen_llc_s_subtype(cstate, LLC_RNR))); }
;
dir: NUM
| ID { if (pcap_strcasecmp($1, "nods") == 0)
| ID { CHECK_PTR_VAL($1);
if (pcap_strcasecmp($1, "nods") == 0)
$$ = IEEE80211_FC1_DIR_NODS;
else if (pcap_strcasecmp($1, "tods") == 0)
$$ = IEEE80211_FC1_DIR_TODS;
@@ -661,16 +675,18 @@ dir: NUM
$$ = IEEE80211_FC1_DIR_FROMDS;
else if (pcap_strcasecmp($1, "dstods") == 0)
$$ = IEEE80211_FC1_DIR_DSTODS;
else
bpf_error(cstate, "unknown 802.11 direction");
else {
bpf_set_error(cstate, "unknown 802.11 direction");
YYABORT;
}
}
;
reason: NUM { $$ = $1; }
| ID { $$ = pfreason_to_num(cstate, $1); }
| ID { CHECK_PTR_VAL($1); CHECK_INT_VAL(($$ = pfreason_to_num(cstate, $1))); }
;
action: ID { $$ = pfaction_to_num(cstate, $1); }
action: ID { CHECK_PTR_VAL($1); CHECK_INT_VAL(($$ = pfaction_to_num(cstate, $1))); }
;
relop: '>' { $$ = BPF_JGT; }
@@ -681,24 +697,24 @@ irelop: LEQ { $$ = BPF_JGT; }
| '<' { $$ = BPF_JGE; }
| NEQ { $$ = BPF_JEQ; }
;
arth: pnum { $$ = gen_loadi(cstate, $1); }
arth: pnum { CHECK_PTR_VAL(($$ = gen_loadi(cstate, $1))); }
| narth
;
narth: pname '[' arth ']' { $$ = gen_load(cstate, $1, $3, 1); }
| pname '[' arth ':' NUM ']' { $$ = gen_load(cstate, $1, $3, $5); }
| arth '+' arth { $$ = gen_arth(cstate, BPF_ADD, $1, $3); }
| arth '-' arth { $$ = gen_arth(cstate, BPF_SUB, $1, $3); }
| arth '*' arth { $$ = gen_arth(cstate, BPF_MUL, $1, $3); }
| arth '/' arth { $$ = gen_arth(cstate, BPF_DIV, $1, $3); }
| arth '%' arth { $$ = gen_arth(cstate, BPF_MOD, $1, $3); }
| arth '&' arth { $$ = gen_arth(cstate, BPF_AND, $1, $3); }
| arth '|' arth { $$ = gen_arth(cstate, BPF_OR, $1, $3); }
| arth '^' arth { $$ = gen_arth(cstate, BPF_XOR, $1, $3); }
| arth LSH arth { $$ = gen_arth(cstate, BPF_LSH, $1, $3); }
| arth RSH arth { $$ = gen_arth(cstate, BPF_RSH, $1, $3); }
| '-' arth %prec UMINUS { $$ = gen_neg(cstate, $2); }
narth: pname '[' arth ']' { CHECK_PTR_VAL(($$ = gen_load(cstate, $1, $3, 1))); }
| pname '[' arth ':' NUM ']' { CHECK_PTR_VAL(($$ = gen_load(cstate, $1, $3, $5))); }
| arth '+' arth { CHECK_PTR_VAL(($$ = gen_arth(cstate, BPF_ADD, $1, $3))); }
| arth '-' arth { CHECK_PTR_VAL(($$ = gen_arth(cstate, BPF_SUB, $1, $3))); }
| arth '*' arth { CHECK_PTR_VAL(($$ = gen_arth(cstate, BPF_MUL, $1, $3))); }
| arth '/' arth { CHECK_PTR_VAL(($$ = gen_arth(cstate, BPF_DIV, $1, $3))); }
| arth '%' arth { CHECK_PTR_VAL(($$ = gen_arth(cstate, BPF_MOD, $1, $3))); }
| arth '&' arth { CHECK_PTR_VAL(($$ = gen_arth(cstate, BPF_AND, $1, $3))); }
| arth '|' arth { CHECK_PTR_VAL(($$ = gen_arth(cstate, BPF_OR, $1, $3))); }
| arth '^' arth { CHECK_PTR_VAL(($$ = gen_arth(cstate, BPF_XOR, $1, $3))); }
| arth LSH arth { CHECK_PTR_VAL(($$ = gen_arth(cstate, BPF_LSH, $1, $3))); }
| arth RSH arth { CHECK_PTR_VAL(($$ = gen_arth(cstate, BPF_RSH, $1, $3))); }
| '-' arth %prec UMINUS { CHECK_PTR_VAL(($$ = gen_neg(cstate, $2))); }
| paren narth ')' { $$ = $2; }
| LEN { $$ = gen_loadlen(cstate); }
| LEN { CHECK_PTR_VAL(($$ = gen_loadlen(cstate))); }
;
byteop: '&' { $$ = '&'; }
| '|' { $$ = '|'; }
@@ -727,15 +743,15 @@ atmfield: VPI { $$.atmfieldtype = A_VPI; }
| VCI { $$.atmfieldtype = A_VCI; }
;
atmvalue: atmfieldvalue
| relop NUM { $$.b = gen_atmfield_code(cstate, $<blk>0.atmfieldtype, (bpf_int32)$2, (bpf_u_int32)$1, 0); }
| irelop NUM { $$.b = gen_atmfield_code(cstate, $<blk>0.atmfieldtype, (bpf_int32)$2, (bpf_u_int32)$1, 1); }
| relop NUM { CHECK_PTR_VAL(($$.b = gen_atmfield_code(cstate, $<blk>0.atmfieldtype, (bpf_int32)$2, (bpf_u_int32)$1, 0))); }
| irelop NUM { CHECK_PTR_VAL(($$.b = gen_atmfield_code(cstate, $<blk>0.atmfieldtype, (bpf_int32)$2, (bpf_u_int32)$1, 1))); }
| paren atmlistvalue ')' { $$.b = $2.b; $$.q = qerr; }
;
atmfieldvalue: NUM {
$$.atmfieldtype = $<blk>0.atmfieldtype;
if ($$.atmfieldtype == A_VPI ||
$$.atmfieldtype == A_VCI)
$$.b = gen_atmfield_code(cstate, $$.atmfieldtype, (bpf_int32) $1, BPF_JEQ, 0);
CHECK_PTR_VAL(($$.b = gen_atmfield_code(cstate, $$.atmfieldtype, (bpf_int32) $1, BPF_JEQ, 0)));
}
;
atmlistvalue: atmfieldvalue
@@ -760,8 +776,8 @@ mtp3field: SIO { $$.mtp3fieldtype = M_SIO; }
| HSLS { $$.mtp3fieldtype = MH_SLS; }
;
mtp3value: mtp3fieldvalue
| relop NUM { $$.b = gen_mtp3field_code(cstate, $<blk>0.mtp3fieldtype, (u_int)$2, (u_int)$1, 0); }
| irelop NUM { $$.b = gen_mtp3field_code(cstate, $<blk>0.mtp3fieldtype, (u_int)$2, (u_int)$1, 1); }
| relop NUM { CHECK_PTR_VAL(($$.b = gen_mtp3field_code(cstate, $<blk>0.mtp3fieldtype, (u_int)$2, (u_int)$1, 0))); }
| irelop NUM { CHECK_PTR_VAL(($$.b = gen_mtp3field_code(cstate, $<blk>0.mtp3fieldtype, (u_int)$2, (u_int)$1, 1))); }
| paren mtp3listvalue ')' { $$.b = $2.b; $$.q = qerr; }
;
mtp3fieldvalue: NUM {
@@ -774,7 +790,7 @@ mtp3fieldvalue: NUM {
$$.mtp3fieldtype == MH_OPC ||
$$.mtp3fieldtype == MH_DPC ||
$$.mtp3fieldtype == MH_SLS)
$$.b = gen_mtp3field_code(cstate, $$.mtp3fieldtype, (u_int) $1, BPF_JEQ, 0);
CHECK_PTR_VAL(($$.b = gen_mtp3field_code(cstate, $$.mtp3fieldtype, (u_int) $1, BPF_JEQ, 0)));
}
;
mtp3listvalue: mtp3fieldvalue

101
libpcap/missing/asprintf.c Normal file
View File

@@ -0,0 +1,101 @@
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include "portability.h"
/*
* vasprintf() and asprintf() for platforms with a C99-compliant
* snprintf() - so that, if you format into a 1-byte buffer, it
* will return how many characters it would have produced had
* it been given an infinite-sized buffer.
*/
int
pcap_vasprintf(char **strp, const char *format, va_list args)
{
char buf;
int len;
size_t str_size;
char *str;
int ret;
/*
* XXX - the C99 standard says, in section 7.19.6.5 "Thes
* nprintf function":
*
* The snprintf function is equivalent to fprintf, except that
* the output is written into an array (specified by argument s)
* rather than to a stream. If n is zero, nothing is written,
* and s may be a null pointer. Otherwise, output characters
* beyond the n-1st are discarded rather than being written
* to the array, and a null character is written at the end
* of the characters actually written into the array.
*
* ...
*
* The snprintf function returns the number of characters that
* would have been written had n been sufficiently large, not
* counting the terminating null character, or a negative value
* if an encoding error occurred. Thus, the null-terminated
* output has been completely written if and only if the returned
* value is nonnegative and less than n.
*
* That doesn't make it entirely clear whether, if a null buffer
* pointer and a zero count are passed, it will return the number
* of characters that would have been written had a buffer been
* passed.
*
* And, even if C99 *does*, in fact, say it has to work, it
* doesn't work in Solaris 8, for example - it returns -1 for
* NULL/0, but returns the correct character count for a 1-byte
* buffer.
*
* So we pass a one-character pointer in order to find out how
* many characters this format and those arguments will need
* without actually generating any more of those characters
* than we need.
*
* (The fact that it might happen to work with GNU libc or with
* various BSD libcs is completely uninteresting, as those tend
* to have asprintf() already and thus don't even *need* this
* code; this is for use in those UN*Xes that *don't* have
* asprintf().)
*/
len = vsnprintf(&buf, sizeof buf, format, args);
if (len == -1) {
*strp = NULL;
return (-1);
}
str_size = len + 1;
str = malloc(str_size);
if (str == NULL) {
*strp = NULL;
return (-1);
}
ret = vsnprintf(str, str_size, format, args);
if (ret == -1) {
free(str);
*strp = NULL;
return (-1);
}
*strp = str;
/*
* vsnprintf() shouldn't truncate the string, as we have
* allocated a buffer large enough to hold the string, so its
* return value should be the number of characters written.
*/
return (ret);
}
int
pcap_asprintf(char **strp, const char *format, ...)
{
va_list args;
int ret;
va_start(args, format);
ret = pcap_vasprintf(strp, format, args);
va_end(args);
return (ret);
}

View File

@@ -1,5 +1,5 @@
/*
* Copyright (c) 1995-1999 Kungliga Tekniska H<EFBFBD>gskolan
* Copyright (c) 1995-1999 Kungliga Tekniska Högskolan
* (Royal Institute of Technology, Stockholm, Sweden).
* All rights reserved.
*
@@ -31,6 +31,10 @@
* SUCH DAMAGE.
*/
/*
* We use this for platforms that don't have snprintf() at all.
*/
#ifdef HAVE_CONFIG_H
#include <config.h>
#endif
@@ -42,7 +46,7 @@
#include <ctype.h>
#include <sys/types.h>
#include <pcap-int.h>
#include "portability.h"
enum format_flags {
minus_flag = 1,
@@ -525,6 +529,7 @@ pcap_asnprintf (char **ret, size_t max_sz, const char *format, ...)
va_start(args, format);
val = pcap_vasnprintf (ret, max_sz, format, args);
va_end(args);
#ifdef PARANOIA
{
@@ -534,14 +539,15 @@ pcap_asnprintf (char **ret, size_t max_sz, const char *format, ...)
if (tmp == NULL)
abort ();
va_start(args, format);
ret2 = pcap_vsprintf (tmp, format, args);
va_end(args);
if (val != ret2 || strcmp(*ret, tmp))
abort ();
free (tmp);
}
#endif
va_end(args);
return val;
}
#endif

61
libpcap/missing/strlcat.c Normal file
View File

@@ -0,0 +1,61 @@
/* $OpenBSD: pcap_strlcat.c,v 1.15 2015/03/02 21:41:08 millert Exp $ */
/*
* Copyright (c) 1998, 2015 Todd C. Miller <Todd.Miller@courtesan.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#ifdef HAVE_CONFIG_H
#include <config.h>
#endif
#include <stddef.h>
#include <string.h>
#include "portability.h"
/*
* Appends src to string dst of size dsize (unlike strncat, dsize is the
* full size of dst, not space left). At most dsize-1 characters
* will be copied. Always NUL terminates (unless dsize <= strlen(dst)).
* Returns strlen(src) + MIN(dsize, strlen(initial dst)).
* If retval >= dsize, truncation occurred.
*/
size_t
pcap_strlcat(char * restrict dst, const char * restrict src, size_t dsize)
{
const char *odst = dst;
const char *osrc = src;
size_t n = dsize;
size_t dlen;
/* Find the end of dst and adjust bytes left but don't go past end. */
while (n-- != 0 && *dst != '\0')
dst++;
dlen = dst - odst;
n = dsize - dlen;
if (n-- == 0)
return(dlen + strlen(src));
while (*src != '\0') {
if (n != 0) {
*dst++ = *src;
n--;
}
src++;
}
*dst = '\0';
return(dlen + (src - osrc)); /* count does not include NUL */
}

56
libpcap/missing/strlcpy.c Normal file
View File

@@ -0,0 +1,56 @@
/* $OpenBSD: pcap_strlcpy.c,v 1.12 2015/01/15 03:54:12 millert Exp $ */
/*
* Copyright (c) 1998, 2015 Todd C. Miller <Todd.Miller@courtesan.com>
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
* OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*/
#ifdef HAVE_CONFIG_H
#include <config.h>
#endif
#include <stddef.h>
#include <string.h>
#include "portability.h"
/*
* Copy string src to buffer dst of size dsize. At most dsize-1
* chars will be copied. Always NUL terminates (unless dsize == 0).
* Returns strlen(src); if retval >= dsize, truncation occurred.
*/
size_t
pcap_strlcpy(char * restrict dst, const char * restrict src, size_t dsize)
{
const char *osrc = src;
size_t nleft = dsize;
/* Copy as many bytes as will fit. */
if (nleft != 0) {
while (--nleft != 0) {
if ((*dst++ = *src++) == '\0')
break;
}
}
/* Not enough room in dst, add NUL and traverse rest of src. */
if (nleft == 0) {
if (dsize != 0)
*dst = '\0'; /* NUL-terminate dst */
while (*src++)
;
}
return(src - osrc - 1); /* count does not include NUL */
}

View File

@@ -0,0 +1,51 @@
#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include "portability.h"
int
pcap_vasprintf(char **strp, const char *format, va_list args)
{
int len;
size_t str_size;
char *str;
int ret;
len = _vscprintf(format, args);
if (len == -1) {
*strp = NULL;
return (-1);
}
str_size = len + 1;
str = malloc(str_size);
if (str == NULL) {
*strp = NULL;
return (-1);
}
ret = pcap_vsnprintf(str, str_size, format, args);
if (ret == -1) {
free(str);
*strp = NULL;
return (-1);
}
*strp = str;
/*
* pcap_vsnprintf() shouldn't truncate the string, as we have
* allocated a buffer large enough to hold the string, so its
* return value should be the number of characters printed.
*/
return (ret);
}
int
pcap_asprintf(char **strp, const char *format, ...)
{
va_list args;
int ret;
va_start(args, format);
ret = pcap_vasprintf(strp, format, args);
va_end(args);
return (ret);
}

View File

@@ -1,6 +1,8 @@
#include <stdio.h>
#include <stdarg.h>
#include "portability.h"
int
pcap_vsnprintf(char *str, size_t str_size, const char *format, va_list args)
{
@@ -13,6 +15,16 @@ pcap_vsnprintf(char *str, size_t str_size, const char *format, va_list args)
* that str is null-terminated, but C99's vsnprintf()
* and snprintf() do, and we want to offer C99 behavior,
* so forcibly null-terminate the string.
*
* We don't, however, offer C99 behavior for the return
* value; _vsnprintf_s() returns -1, not the number of
* characters that would have been put into the buffer
* had it been large enough, if the string is truncated.
* The only way to get that value is to use _vscprintf();
* getting that count isn't worth the re-formatting.
*
* XXX - does _vsnprintf_s() return -1 on a formatting
* error?
*/
str[str_size - 1] = '\0';
return (ret);

View File

@@ -231,7 +231,22 @@ pcap_nametonetaddr(const char *name)
int h_errnoval;
int err;
err = getnetbyname_r(name, &result_buf, buf, sizeof buf, &np,
/*
* Apparently, the man page at
*
* http://man7.org/linux/man-pages/man3/getnetbyname_r.3.html
*
* lies when it says
*
* If the function call successfully obtains a network record,
* then *result is set pointing to result_buf; otherwise, *result
* is set to NULL.
*
* and, in fact, at least in some versions of GNU libc, it does
* *not* always get set if getnetbyname_r() succeeds.
*/
np = NULL;
err = getnetbyname_r(name, &result_buf, buf, sizeof buf, &np,
&h_errnoval);
if (err != 0) {
/*

View File

@@ -30,6 +30,7 @@
#include <stdio.h>
#include <stdlib.h>
#include <memory.h>
#include <setjmp.h>
#include <string.h>
#include <errno.h>
@@ -226,6 +227,16 @@ struct vmapinfo {
};
typedef struct {
/*
* Place to longjmp to on an error.
*/
jmp_buf top_ctx;
/*
* The buffer into which to put error message.
*/
char *errbuf;
/*
* A flag to indicate that further optimization is needed.
* Iterative passes are continued until a given pass yields no
@@ -252,19 +263,19 @@ typedef struct {
* True if a is in uset {p}
*/
#define SET_MEMBER(p, a) \
((p)[(unsigned)(a) / BITS_PER_WORD] & (1 << ((unsigned)(a) % BITS_PER_WORD)))
((p)[(unsigned)(a) / BITS_PER_WORD] & ((bpf_u_int32)1 << ((unsigned)(a) % BITS_PER_WORD)))
/*
* Add 'a' to uset p.
*/
#define SET_INSERT(p, a) \
(p)[(unsigned)(a) / BITS_PER_WORD] |= (1 << ((unsigned)(a) % BITS_PER_WORD))
(p)[(unsigned)(a) / BITS_PER_WORD] |= ((bpf_u_int32)1 << ((unsigned)(a) % BITS_PER_WORD))
/*
* Delete 'a' from uset p.
*/
#define SET_DELETE(p, a) \
(p)[(unsigned)(a) / BITS_PER_WORD] &= ~(1 << ((unsigned)(a) % BITS_PER_WORD))
(p)[(unsigned)(a) / BITS_PER_WORD] &= ~((bpf_u_int32)1 << ((unsigned)(a) % BITS_PER_WORD))
/*
* a := a intersect b
@@ -311,6 +322,16 @@ typedef struct {
} opt_state_t;
typedef struct {
/*
* Place to longjmp to on an error.
*/
jmp_buf top_ctx;
/*
* The buffer into which to put error message.
*/
char *errbuf;
/*
* Some pointers used to convert the basic block form of the code,
* into the array form that BPF requires. 'fstart' will point to
@@ -321,14 +342,16 @@ typedef struct {
struct bpf_insn *ftail;
} conv_state_t;
static void opt_init(compiler_state_t *, opt_state_t *, struct icode *);
static void opt_init(opt_state_t *, struct icode *);
static void opt_cleanup(opt_state_t *);
static void PCAP_NORETURN opt_error(opt_state_t *, const char *, ...)
PCAP_PRINTFLIKE(2, 3);
static void intern_blocks(opt_state_t *, struct icode *);
static void find_inedges(opt_state_t *, struct block *);
#ifdef BDEBUG
static void opt_dump(compiler_state_t *, struct icode *);
static void opt_dump(opt_state_t *, struct icode *);
#endif
#ifndef MAX
@@ -699,8 +722,7 @@ vstore(struct stmt *s, int *valp, int newval, int alter)
* (Unary operators are handled elsewhere.)
*/
static void
fold_op(compiler_state_t *cstate, opt_state_t *opt_state,
struct stmt *s, int v0, int v1)
fold_op(opt_state_t *opt_state, struct stmt *s, int v0, int v1)
{
bpf_u_int32 a, b;
@@ -722,13 +744,13 @@ fold_op(compiler_state_t *cstate, opt_state_t *opt_state,
case BPF_DIV:
if (b == 0)
bpf_error(cstate, "division by zero");
opt_error(opt_state, "division by zero");
a /= b;
break;
case BPF_MOD:
if (b == 0)
bpf_error(cstate, "modulus by zero");
opt_error(opt_state, "modulus by zero");
a %= b;
break;
@@ -745,11 +767,39 @@ fold_op(compiler_state_t *cstate, opt_state_t *opt_state,
break;
case BPF_LSH:
a <<= b;
/*
* A left shift of more than the width of the type
* is undefined in C; we'll just treat it as shifting
* all the bits out.
*
* XXX - the BPF interpreter doesn't check for this,
* so its behavior is dependent on the behavior of
* the processor on which it's running. There are
* processors on which it shifts all the bits out
* and processors on which it does no shift.
*/
if (b < 32)
a <<= b;
else
a = 0;
break;
case BPF_RSH:
a >>= b;
/*
* A right shift of more than the width of the type
* is undefined in C; we'll just treat it as shifting
* all the bits out.
*
* XXX - the BPF interpreter doesn't check for this,
* so its behavior is dependent on the behavior of
* the processor on which it's running. There are
* processors on which it shifts all the bits out
* and processors on which it does no shift.
*/
if (b < 32)
a >>= b;
else
a = 0;
break;
default:
@@ -1041,8 +1091,7 @@ opt_peep(opt_state_t *opt_state, struct block *b)
* evaluation and code transformations weren't folded together.
*/
static void
opt_stmt(compiler_state_t *cstate, opt_state_t *opt_state,
struct stmt *s, int val[], int alter)
opt_stmt(opt_state_t *opt_state, struct stmt *s, int val[], int alter)
{
int op;
int v;
@@ -1094,7 +1143,23 @@ opt_stmt(compiler_state_t *cstate, opt_state_t *opt_state,
case BPF_ALU|BPF_NEG:
if (alter && opt_state->vmap[val[A_ATOM]].is_const) {
s->code = BPF_LD|BPF_IMM;
s->k = -opt_state->vmap[val[A_ATOM]].const_val;
/*
* Do this negation as unsigned arithmetic; that's
* what modern BPF engines do, and it guarantees
* that all possible values can be negated. (Yeah,
* negating 0x80000000, the minimum signed 32-bit
* two's-complement value, results in 0x80000000,
* so it's still negative, but we *should* be doing
* all unsigned arithmetic here, to match what
* modern BPF engines do.)
*
* Express it as 0U - (unsigned value) so that we
* don't get compiler warnings about negating an
* unsigned value and don't get UBSan warnings
* about the result of negating 0x80000000 being
* undefined.
*/
s->k = 0U - (bpf_u_int32)(opt_state->vmap[val[A_ATOM]].const_val);
val[A_ATOM] = K(s->k);
}
else
@@ -1114,9 +1179,17 @@ opt_stmt(compiler_state_t *cstate, opt_state_t *opt_state,
op = BPF_OP(s->code);
if (alter) {
if (s->k == 0) {
/* don't optimize away "sub #0"
/*
* Optimize operations where the constant
* is zero.
*
* Don't optimize away "sub #0"
* as it may be needed later to
* fixup the generated math code */
* fixup the generated math code.
*
* Fail if we're dividing by zero or taking
* a modulus by zero.
*/
if (op == BPF_ADD ||
op == BPF_LSH || op == BPF_RSH ||
op == BPF_OR || op == BPF_XOR) {
@@ -1128,9 +1201,15 @@ opt_stmt(compiler_state_t *cstate, opt_state_t *opt_state,
val[A_ATOM] = K(s->k);
break;
}
if (op == BPF_DIV)
opt_error(opt_state,
"division by zero");
if (op == BPF_MOD)
opt_error(opt_state,
"modulus by zero");
}
if (opt_state->vmap[val[A_ATOM]].is_const) {
fold_op(cstate, opt_state, s, val[A_ATOM], K(s->k));
fold_op(opt_state, s, val[A_ATOM], K(s->k));
val[A_ATOM] = K(s->k);
break;
}
@@ -1151,12 +1230,22 @@ opt_stmt(compiler_state_t *cstate, opt_state_t *opt_state,
op = BPF_OP(s->code);
if (alter && opt_state->vmap[val[X_ATOM]].is_const) {
if (opt_state->vmap[val[A_ATOM]].is_const) {
fold_op(cstate, opt_state, s, val[A_ATOM], val[X_ATOM]);
fold_op(opt_state, s, val[A_ATOM], val[X_ATOM]);
val[A_ATOM] = K(s->k);
}
else {
s->code = BPF_ALU|BPF_K|op;
s->k = opt_state->vmap[val[X_ATOM]].const_val;
/*
* XXX - we need to make up our minds
* as to what integers are signed and
* what integers are unsigned in BPF
* programs and in our IR.
*/
if ((op == BPF_LSH || op == BPF_RSH) &&
(s->k < 0 || s->k > 31))
opt_error(opt_state,
"shift by more than 31 bits");
opt_state->done = 0;
val[A_ATOM] =
F(opt_state, s->code, val[A_ATOM], K(s->k));
@@ -1275,8 +1364,7 @@ opt_deadstores(opt_state_t *opt_state, register struct block *b)
}
static void
opt_blk(compiler_state_t *cstate, opt_state_t *opt_state,
struct block *b, int do_stmts)
opt_blk(opt_state_t *opt_state, struct block *b, int do_stmts)
{
struct slist *s;
struct edge *p;
@@ -1326,7 +1414,7 @@ opt_blk(compiler_state_t *cstate, opt_state_t *opt_state,
aval = b->val[A_ATOM];
xval = b->val[X_ATOM];
for (s = b->stmts; s; s = s->next)
opt_stmt(cstate, opt_state, &s->s, b->val, do_stmts);
opt_stmt(opt_state, &s->s, b->val, do_stmts);
/*
* This is a special case: if we don't use anything from this
@@ -1480,7 +1568,7 @@ opt_j(opt_state_t *opt_state, struct edge *ep)
while (x != 0) {
k = lowest_set_bit(x);
x &=~ (1 << k);
x &=~ ((bpf_u_int32)1 << k);
k += i * BITS_PER_WORD;
target = fold_edge(ep->succ, opt_state->edges[k]);
@@ -1687,8 +1775,7 @@ and_pullup(opt_state_t *opt_state, struct block *b)
}
static void
opt_blks(compiler_state_t *cstate, opt_state_t *opt_state, struct icode *ic,
int do_stmts)
opt_blks(opt_state_t *opt_state, struct icode *ic, int do_stmts)
{
int i, maxlevel;
struct block *p;
@@ -1699,7 +1786,7 @@ opt_blks(compiler_state_t *cstate, opt_state_t *opt_state, struct icode *ic,
find_inedges(opt_state, ic->root);
for (i = maxlevel; i >= 0; --i)
for (p = opt_state->levels[i]; p; p = p->link)
opt_blk(cstate, opt_state, p, do_stmts);
opt_blk(opt_state, p, do_stmts);
if (do_stmts)
/*
@@ -1777,14 +1864,13 @@ opt_root(struct block **b)
}
static void
opt_loop(compiler_state_t *cstate, opt_state_t *opt_state, struct icode *ic,
int do_stmts)
opt_loop(opt_state_t *opt_state, struct icode *ic, int do_stmts)
{
#ifdef BDEBUG
if (pcap_optimizer_debug > 1 || pcap_print_dot_graph) {
printf("opt_loop(root, %d) begin\n", do_stmts);
opt_dump(cstate, ic);
opt_dump(opt_state, ic);
}
#endif
do {
@@ -1794,11 +1880,11 @@ opt_loop(compiler_state_t *cstate, opt_state_t *opt_state, struct icode *ic,
find_closure(opt_state, ic->root);
find_ud(opt_state, ic->root);
find_edom(opt_state, ic->root);
opt_blks(cstate, opt_state, ic, do_stmts);
opt_blks(opt_state, ic, do_stmts);
#ifdef BDEBUG
if (pcap_optimizer_debug > 1 || pcap_print_dot_graph) {
printf("opt_loop(root, %d) bottom, done=%d\n", do_stmts, opt_state->done);
opt_dump(cstate, ic);
opt_dump(opt_state, ic);
}
#endif
} while (!opt_state->done);
@@ -1806,30 +1892,38 @@ opt_loop(compiler_state_t *cstate, opt_state_t *opt_state, struct icode *ic,
/*
* Optimize the filter code in its dag representation.
* Return 0 on success, -1 on error.
*/
void
bpf_optimize(compiler_state_t *cstate, struct icode *ic)
int
bpf_optimize(struct icode *ic, char *errbuf)
{
opt_state_t opt_state;
opt_init(cstate, &opt_state, ic);
opt_loop(cstate, &opt_state, ic, 0);
opt_loop(cstate, &opt_state, ic, 1);
memset(&opt_state, 0, sizeof(opt_state));
opt_state.errbuf = errbuf;
if (setjmp(opt_state.top_ctx)) {
opt_cleanup(&opt_state);
return -1;
}
opt_init(&opt_state, ic);
opt_loop(&opt_state, ic, 0);
opt_loop(&opt_state, ic, 1);
intern_blocks(&opt_state, ic);
#ifdef BDEBUG
if (pcap_optimizer_debug > 1 || pcap_print_dot_graph) {
printf("after intern_blocks()\n");
opt_dump(cstate, ic);
opt_dump(&opt_state, ic);
}
#endif
opt_root(&ic->root);
#ifdef BDEBUG
if (pcap_optimizer_debug > 1 || pcap_print_dot_graph) {
printf("after opt_root()\n");
opt_dump(cstate, ic);
opt_dump(&opt_state, ic);
}
#endif
opt_cleanup(&opt_state);
return 0;
}
static void
@@ -1943,6 +2037,24 @@ opt_cleanup(opt_state_t *opt_state)
free((void *)opt_state->blocks);
}
/*
* For optimizer errors.
*/
static void PCAP_NORETURN
opt_error(opt_state_t *opt_state, const char *fmt, ...)
{
va_list ap;
if (opt_state->errbuf != NULL) {
va_start(ap, fmt);
(void)pcap_vsnprintf(opt_state->errbuf,
PCAP_ERRBUF_SIZE, fmt, ap);
va_end(ap);
}
longjmp(opt_state->top_ctx, 1);
/* NOTREACHED */
}
/*
* Return the number of stmts in 's'.
*/
@@ -2027,7 +2139,7 @@ count_stmts(struct icode *ic, struct block *p)
* from the total number of blocks and/or statements.
*/
static void
opt_init(compiler_state_t *cstate, opt_state_t *opt_state, struct icode *ic)
opt_init(opt_state_t *opt_state, struct icode *ic)
{
bpf_u_int32 *p;
int i, n, max_stmts;
@@ -2040,22 +2152,24 @@ opt_init(compiler_state_t *cstate, opt_state_t *opt_state, struct icode *ic)
n = count_blocks(ic, ic->root);
opt_state->blocks = (struct block **)calloc(n, sizeof(*opt_state->blocks));
if (opt_state->blocks == NULL)
bpf_error(cstate, "malloc");
opt_error(opt_state, "malloc");
unMarkAll(ic);
opt_state->n_blocks = 0;
number_blks_r(opt_state, ic, ic->root);
opt_state->n_edges = 2 * opt_state->n_blocks;
opt_state->edges = (struct edge **)calloc(opt_state->n_edges, sizeof(*opt_state->edges));
if (opt_state->edges == NULL)
bpf_error(cstate, "malloc");
if (opt_state->edges == NULL) {
opt_error(opt_state, "malloc");
}
/*
* The number of levels is bounded by the number of nodes.
*/
opt_state->levels = (struct block **)calloc(opt_state->n_blocks, sizeof(*opt_state->levels));
if (opt_state->levels == NULL)
bpf_error(cstate, "malloc");
if (opt_state->levels == NULL) {
opt_error(opt_state, "malloc");
}
opt_state->edgewords = opt_state->n_edges / (8 * sizeof(bpf_u_int32)) + 1;
opt_state->nodewords = opt_state->n_blocks / (8 * sizeof(bpf_u_int32)) + 1;
@@ -2063,8 +2177,9 @@ opt_init(compiler_state_t *cstate, opt_state_t *opt_state, struct icode *ic)
/* XXX */
opt_state->space = (bpf_u_int32 *)malloc(2 * opt_state->n_blocks * opt_state->nodewords * sizeof(*opt_state->space)
+ opt_state->n_edges * opt_state->edgewords * sizeof(*opt_state->space));
if (opt_state->space == NULL)
bpf_error(cstate, "malloc");
if (opt_state->space == NULL) {
opt_error(opt_state, "malloc");
}
p = opt_state->space;
opt_state->all_dom_sets = p;
for (i = 0; i < n; ++i) {
@@ -2101,9 +2216,13 @@ opt_init(compiler_state_t *cstate, opt_state_t *opt_state, struct icode *ic)
*/
opt_state->maxval = 3 * max_stmts;
opt_state->vmap = (struct vmapinfo *)calloc(opt_state->maxval, sizeof(*opt_state->vmap));
if (opt_state->vmap == NULL) {
opt_error(opt_state, "malloc");
}
opt_state->vnode_base = (struct valnode *)calloc(opt_state->maxval, sizeof(*opt_state->vnode_base));
if (opt_state->vmap == NULL || opt_state->vnode_base == NULL)
bpf_error(cstate, "malloc");
if (opt_state->vnode_base == NULL) {
opt_error(opt_state, "malloc");
}
}
/*
@@ -2115,6 +2234,9 @@ opt_init(compiler_state_t *cstate, opt_state_t *opt_state, struct icode *ic)
int bids[NBIDS];
#endif
static void PCAP_NORETURN conv_error(conv_state_t *, const char *, ...)
PCAP_PRINTFLIKE(2, 3);
/*
* Returns true if successful. Returns false if a branch has
* an offset that is too large. If so, we have marked that
@@ -2122,8 +2244,7 @@ int bids[NBIDS];
* properly.
*/
static int
convert_code_r(compiler_state_t *cstate, conv_state_t *conv_state,
struct icode *ic, struct block *p)
convert_code_r(conv_state_t *conv_state, struct icode *ic, struct block *p)
{
struct bpf_insn *dst;
struct slist *src;
@@ -2136,9 +2257,9 @@ convert_code_r(compiler_state_t *cstate, conv_state_t *conv_state,
return (1);
Mark(ic, p);
if (convert_code_r(cstate, conv_state, ic, JF(p)) == 0)
if (convert_code_r(conv_state, ic, JF(p)) == 0)
return (0);
if (convert_code_r(cstate, conv_state, ic, JT(p)) == 0)
if (convert_code_r(conv_state, ic, JT(p)) == 0)
return (0);
slen = slength(p->stmts);
@@ -2151,7 +2272,7 @@ convert_code_r(compiler_state_t *cstate, conv_state_t *conv_state,
if (slen) {
offset = (struct slist **)calloc(slen, sizeof(struct slist *));
if (!offset) {
bpf_error(cstate, "not enough core");
conv_error(conv_state, "not enough core");
/*NOTREACHED*/
}
}
@@ -2175,7 +2296,8 @@ convert_code_r(compiler_state_t *cstate, conv_state_t *conv_state,
if (BPF_CLASS(src->s.code) != BPF_JMP || src->s.code == (BPF_JMP|BPF_JA)) {
#if 0
if (src->s.jt || src->s.jf) {
bpf_error(cstate, "illegal jmp destination");
free(offset);
conv_error(conv_state, "illegal jmp destination");
/*NOTREACHED*/
}
#endif
@@ -2195,7 +2317,8 @@ convert_code_r(compiler_state_t *cstate, conv_state_t *conv_state,
#endif
if (!src->s.jt || !src->s.jf) {
bpf_error(cstate, ljerr, "no jmp destination", off);
free(offset);
conv_error(conv_state, ljerr, "no jmp destination", off);
/*NOTREACHED*/
}
@@ -2203,12 +2326,14 @@ convert_code_r(compiler_state_t *cstate, conv_state_t *conv_state,
for (i = 0; i < slen; i++) {
if (offset[i] == src->s.jt) {
if (jt) {
bpf_error(cstate, ljerr, "multiple matches", off);
free(offset);
conv_error(conv_state, ljerr, "multiple matches", off);
/*NOTREACHED*/
}
if (i - off - 1 >= 256) {
bpf_error(cstate, ljerr, "out-of-range jump", off);
free(offset);
conv_error(conv_state, ljerr, "out-of-range jump", off);
/*NOTREACHED*/
}
dst->jt = (u_char)(i - off - 1);
@@ -2216,11 +2341,13 @@ convert_code_r(compiler_state_t *cstate, conv_state_t *conv_state,
}
if (offset[i] == src->s.jf) {
if (jf) {
bpf_error(cstate, ljerr, "multiple matches", off);
free(offset);
conv_error(conv_state, ljerr, "multiple matches", off);
/*NOTREACHED*/
}
if (i - off - 1 >= 256) {
bpf_error(cstate, ljerr, "out-of-range jump", off);
free(offset);
conv_error(conv_state, ljerr, "out-of-range jump", off);
/*NOTREACHED*/
}
dst->jf = (u_char)(i - off - 1);
@@ -2228,7 +2355,8 @@ convert_code_r(compiler_state_t *cstate, conv_state_t *conv_state,
}
}
if (!jt || !jf) {
bpf_error(cstate, ljerr, "no destination found", off);
free(offset);
conv_error(conv_state, ljerr, "no destination found", off);
/*NOTREACHED*/
}
}
@@ -2257,7 +2385,7 @@ filled:
}
/* branch if T to following jump */
if (extrajmps >= 256) {
bpf_error(cstate, "too many extra jumps");
conv_error(conv_state, "too many extra jumps");
/*NOTREACHED*/
}
dst->jt = (u_char)extrajmps;
@@ -2278,7 +2406,7 @@ filled:
/* branch if F to following jump */
/* if two jumps are inserted, F goes to second one */
if (extrajmps >= 256) {
bpf_error(cstate, "too many extra jumps");
conv_error(conv_state, "too many extra jumps");
/*NOTREACHED*/
}
dst->jf = (u_char)extrajmps;
@@ -2312,13 +2440,20 @@ filled:
* done with the filter program. See the pcap man page.
*/
struct bpf_insn *
icode_to_fcode(compiler_state_t *cstate, struct icode *ic,
struct block *root, u_int *lenp)
icode_to_fcode(struct icode *ic, struct block *root, u_int *lenp,
char *errbuf)
{
u_int n;
struct bpf_insn *fp;
conv_state_t conv_state;
conv_state.fstart = NULL;
conv_state.errbuf = errbuf;
if (setjmp(conv_state.top_ctx) != 0) {
free(conv_state.fstart);
return NULL;
}
/*
* Loop doing convert_code_r() until no branches remain
* with too-large offsets.
@@ -2328,14 +2463,18 @@ icode_to_fcode(compiler_state_t *cstate, struct icode *ic,
n = *lenp = count_stmts(ic, root);
fp = (struct bpf_insn *)malloc(sizeof(*fp) * n);
if (fp == NULL)
bpf_error(cstate, "malloc");
if (fp == NULL) {
(void)pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE,
"malloc");
free(fp);
return NULL;
}
memset((char *)fp, 0, sizeof(*fp) * n);
conv_state.fstart = fp;
conv_state.ftail = fp + n;
unMarkAll(ic);
if (convert_code_r(cstate, &conv_state, ic, root))
if (convert_code_r(&conv_state, ic, root))
break;
free(fp);
}
@@ -2343,6 +2482,22 @@ icode_to_fcode(compiler_state_t *cstate, struct icode *ic,
return fp;
}
/*
* For iconv_to_fconv() errors.
*/
static void PCAP_NORETURN
conv_error(conv_state_t *conv_state, const char *fmt, ...)
{
va_list ap;
va_start(ap, fmt);
(void)pcap_vsnprintf(conv_state->errbuf,
PCAP_ERRBUF_SIZE, fmt, ap);
va_end(ap);
longjmp(conv_state->top_ctx, 1);
/* NOTREACHED */
}
/*
* Make a copy of a BPF program and put it in the "fcode" member of
* a "pcap_t".
@@ -2452,14 +2607,16 @@ dot_dump_edge(struct icode *ic, struct block *block, FILE *out)
* After install graphviz on http://www.graphviz.org/, save it as bpf.dot
* and run `dot -Tpng -O bpf.dot' to draw the graph.
*/
static void
dot_dump(compiler_state_t *cstate, struct icode *ic)
static int
dot_dump(struct icode *ic, char *errbuf)
{
struct bpf_program f;
FILE *out = stdout;
memset(bids, 0, sizeof bids);
f.bf_insns = icode_to_fcode(cstate, ic, ic->root, &f.bf_len);
f.bf_insns = icode_to_fcode(ic, ic->root, &f.bf_len, errbuf);
if (f.bf_insns == NULL)
return -1;
fprintf(out, "digraph BPF {\n");
unMarkAll(ic);
@@ -2469,30 +2626,39 @@ dot_dump(compiler_state_t *cstate, struct icode *ic)
fprintf(out, "}\n");
free((char *)f.bf_insns);
return 0;
}
static void
plain_dump(compiler_state_t *cstate, struct icode *ic)
static int
plain_dump(struct icode *ic, char *errbuf)
{
struct bpf_program f;
memset(bids, 0, sizeof bids);
f.bf_insns = icode_to_fcode(cstate, ic, ic->root, &f.bf_len);
f.bf_insns = icode_to_fcode(ic, ic->root, &f.bf_len, errbuf);
if (f.bf_insns == NULL)
return -1;
bpf_dump(&f, 1);
putchar('\n');
free((char *)f.bf_insns);
return 0;
}
static void
opt_dump(compiler_state_t *cstate, struct icode *ic)
opt_dump(opt_state_t *opt_state, struct icode *ic)
{
int status;
char errbuf[PCAP_ERRBUF_SIZE];
/*
* If the CFG, in DOT format, is requested, output it rather than
* the code that would be generated from that graph.
*/
if (pcap_print_dot_graph)
dot_dump(cstate, ic);
status = dot_dump(ic, errbuf);
else
plain_dump(cstate, ic);
status = plain_dump(ic, errbuf);
if (status == -1)
opt_error(opt_state, "opt_dump: icode_to_fcode failed: %s", errbuf);
}
#endif

View File

@@ -206,7 +206,7 @@ static int monitor_mode(pcap_t *, int);
# endif
# if defined(__APPLE__)
static void remove_en(pcap_t *);
static void remove_non_802_11(pcap_t *);
static void remove_802_11(pcap_t *);
# endif
@@ -737,10 +737,10 @@ get_dlt_list(int fd, int v, struct bpf_dltlist *bdlp, char *ebuf)
}
#endif
#if defined(__APPLE__)
static int
pcap_can_set_rfmon_bpf(pcap_t *p)
{
#if defined(__APPLE__)
struct utsname osinfo;
struct ifreq ifr;
int fd;
@@ -799,8 +799,8 @@ pcap_can_set_rfmon_bpf(pcap_t *p)
errno, "socket");
return (PCAP_ERROR);
}
strlcpy(ifr.ifr_name, "wlt", sizeof(ifr.ifr_name));
strlcat(ifr.ifr_name, p->opt.device + 2, sizeof(ifr.ifr_name));
pcap_strlcpy(ifr.ifr_name, "wlt", sizeof(ifr.ifr_name));
pcap_strlcat(ifr.ifr_name, p->opt.device + 2, sizeof(ifr.ifr_name));
if (ioctl(fd, SIOCGIFFLAGS, (char *)&ifr) < 0) {
/*
* No such device?
@@ -880,7 +880,11 @@ pcap_can_set_rfmon_bpf(pcap_t *p)
close(fd);
#endif /* BIOCGDLTLIST */
return (0);
}
#elif defined(HAVE_BSD_IEEE80211)
static int
pcap_can_set_rfmon_bpf(pcap_t *p)
{
int ret;
ret = monitor_mode(p, 0);
@@ -889,10 +893,14 @@ pcap_can_set_rfmon_bpf(pcap_t *p)
if (ret == 0)
return (1); /* success */
return (ret);
#else
return (0);
#endif
}
#else
static int
pcap_can_set_rfmon_bpf(pcap_t *p _U_)
{
return (0);
}
#endif
static int
pcap_stats_bpf(pcap_t *p, struct pcap_stat *ps)
@@ -1012,18 +1020,21 @@ pcap_read_bpf(pcap_t *p, int cnt, pcap_handler callback, u_char *user)
case EWOULDBLOCK:
return (0);
case ENXIO:
case ENXIO: /* FreeBSD, DragonFly BSD, and Darwin */
case EIO: /* OpenBSD */
/* NetBSD appears not to return an error in this case */
/*
* The device on which we're capturing
* went away.
*
* XXX - we should really return
* PCAP_ERROR_IFACE_NOT_UP, but
* pcap_dispatch() etc. aren't
* defined to retur that.
* an appropriate error for that,
* but pcap_dispatch() etc. aren't
* documented as having error returns
* other than PCAP_ERROR or PCAP_ERROR_BREAK.
*/
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
"The interface went down");
"The interface disappeared");
return (PCAP_ERROR);
#if defined(sun) && !defined(BSD) && !defined(__svr4__) && !defined(__SVR4)
@@ -1358,8 +1369,8 @@ bpf_load(char *errbuf)
/* Check if the driver is loaded */
memset(&cfg_ld, 0x0, sizeof(cfg_ld));
pcap_snprintf(buf, sizeof(buf), "%s/%s", DRIVER_PATH, BPF_NAME);
cfg_ld.path = buf;
pcap_snprintf(cfg_ld.path, sizeof(cfg_ld.path), "%s/%s", DRIVER_PATH, BPF_NAME);
if ((sysconfig(SYS_QUERYLOAD, (void *)&cfg_ld, sizeof(cfg_ld)) == -1) ||
(cfg_ld.kmid == 0)) {
/* Driver isn't loaded, load it now */
@@ -1469,7 +1480,7 @@ pcap_cleanup_bpf(pcap_t *p)
s = socket(AF_LOCAL, SOCK_DGRAM, 0);
if (s >= 0) {
strlcpy(ifr.ifr_name, pb->device,
pcap_strlcpy(ifr.ifr_name, pb->device,
sizeof(ifr.ifr_name));
ioctl(s, SIOCIFDESTROY, &ifr);
close(s);
@@ -1532,9 +1543,9 @@ check_setif_failure(pcap_t *p, int error)
*/
fd = socket(AF_INET, SOCK_DGRAM, 0);
if (fd != -1) {
strlcpy(ifr.ifr_name, "en",
pcap_strlcpy(ifr.ifr_name, "en",
sizeof(ifr.ifr_name));
strlcat(ifr.ifr_name, p->opt.device + 3,
pcap_strlcat(ifr.ifr_name, p->opt.device + 3,
sizeof(ifr.ifr_name));
if (ioctl(fd, SIOCGIFFLAGS, (char *)&ifr) < 0) {
/*
@@ -1721,7 +1732,7 @@ pcap_activate_bpf(pcap_t *p)
goto bad;
}
znamelen = zonesep - p->opt.device;
(void) strlcpy(path_zname, p->opt.device, znamelen + 1);
(void) pcap_strlcpy(path_zname, p->opt.device, znamelen + 1);
ifr.lifr_zoneid = getzoneidbyname(path_zname);
if (ifr.lifr_zoneid == -1) {
pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
@@ -1786,7 +1797,7 @@ pcap_activate_bpf(pcap_t *p)
*/
sockfd = socket(AF_INET, SOCK_DGRAM, 0);
if (sockfd != -1) {
strlcpy(ifrname,
pcap_strlcpy(ifrname,
p->opt.device, ifnamsiz);
if (ioctl(sockfd, SIOCGIFFLAGS,
(char *)&ifr) < 0) {
@@ -1888,7 +1899,7 @@ pcap_activate_bpf(pcap_t *p)
/*
* Create the interface.
*/
strlcpy(ifr.ifr_name, p->opt.device, sizeof(ifr.ifr_name));
pcap_strlcpy(ifr.ifr_name, p->opt.device, sizeof(ifr.ifr_name));
if (ioctl(s, SIOCIFCREATE2, &ifr) < 0) {
if (errno == EINVAL) {
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
@@ -2187,7 +2198,7 @@ pcap_activate_bpf(pcap_t *p)
* of link-layer types, as selecting
* it will keep monitor mode off.
*/
remove_en(p);
remove_non_802_11(p);
/*
* If the new mode we want isn't
@@ -2748,12 +2759,21 @@ get_if_flags(const char *name, bpf_u_int32 *flags, char *errbuf)
strncpy(req.ifm_name, name, sizeof(req.ifm_name));
if (ioctl(sock, SIOCGIFMEDIA, &req) < 0) {
if (errno == EOPNOTSUPP || errno == EINVAL || errno == ENOTTY ||
errno == ENODEV) {
errno == ENODEV || errno == EPERM) {
/*
* Not supported, so we can't provide any
* additional information. Assume that
* this means that "connected" vs.
* "disconnected" doesn't apply.
*
* The ioctl routine for Apple's pktap devices,
* annoyingly, checks for "are you root?" before
* checking whether the ioctl is valid, so it
* returns EPERM, rather than ENOTSUP, for the
* invalid SIOCGIFMEDIA, unless you're root.
* So, just as we do for some ethtool ioctls
* on Linux, which makes the same mistake, we
* also treat EPERM as meaning "not supported".
*/
*flags |= PCAP_IF_CONNECTION_STATUS_NOT_APPLICABLE;
close(sock);
@@ -2890,7 +2910,7 @@ monitor_mode(pcap_t *p, int set)
default:
pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
errno, "SIOCGIFMEDIA 1");
errno, "SIOCGIFMEDIA");
close(sock);
return (PCAP_ERROR);
}
@@ -3032,8 +3052,12 @@ find_802_11(struct bpf_dltlist *bdlp)
new_dlt = bdlp->bfl_list[i];
break;
#ifdef DLT_PRISM_HEADER
case DLT_PRISM_HEADER:
#endif
#ifdef DLT_AIRONET_HEADER
case DLT_AIRONET_HEADER:
#endif
case DLT_IEEE802_11_RADIO_AVS:
/*
* 802.11 with radio, but not radiotap.
@@ -3068,24 +3092,25 @@ find_802_11(struct bpf_dltlist *bdlp)
#if defined(__APPLE__) && defined(BIOCGDLTLIST)
/*
* Remove DLT_EN10MB from the list of DLT_ values, as we're in monitor mode,
* and DLT_EN10MB isn't supported in monitor mode.
* Remove non-802.11 header types from the list of DLT_ values, as we're in
* monitor mode, and those header types aren't supported in monitor mode.
*/
static void
remove_en(pcap_t *p)
remove_non_802_11(pcap_t *p)
{
int i, j;
/*
* Scan the list of DLT_ values and discard DLT_EN10MB.
* Scan the list of DLT_ values and discard non-802.11 ones.
*/
j = 0;
for (i = 0; i < p->dlt_count; i++) {
switch (p->dlt_list[i]) {
case DLT_EN10MB:
case DLT_RAW:
/*
* Don't offer this one.
* Not 802.11. Don't offer this one.
*/
continue;
@@ -3127,10 +3152,17 @@ remove_802_11(pcap_t *p)
switch (p->dlt_list[i]) {
case DLT_IEEE802_11:
#ifdef DLT_PRISM_HEADER
case DLT_PRISM_HEADER:
#endif
#ifdef DLT_AIRONET_HEADER
case DLT_AIRONET_HEADER:
#endif
case DLT_IEEE802_11_RADIO:
case DLT_IEEE802_11_RADIO_AVS:
#ifdef DLT_PPI
case DLT_PPI:
#endif
/*
* 802.11. Don't offer this one.
*/
@@ -3222,10 +3254,10 @@ pcap_setfilter_bpf(pcap_t *p, struct bpf_program *fp)
* Set direction flag: Which packets do we accept on a forwarding
* single device? IN, OUT or both?
*/
#if defined(BIOCSDIRECTION)
static int
pcap_setdirection_bpf(pcap_t *p, pcap_direction_t d)
{
#if defined(BIOCSDIRECTION)
u_int direction;
direction = (d == PCAP_D_IN) ? BPF_D_IN :
@@ -3238,7 +3270,11 @@ pcap_setdirection_bpf(pcap_t *p, pcap_direction_t d)
return (-1);
}
return (0);
}
#elif defined(BIOCSSEESENT)
static int
pcap_setdirection_bpf(pcap_t *p, pcap_direction_t d)
{
u_int seesent;
/*
@@ -3258,25 +3294,35 @@ pcap_setdirection_bpf(pcap_t *p, pcap_direction_t d)
return (-1);
}
return (0);
}
#else
static int
pcap_setdirection_bpf(pcap_t *p, pcap_direction_t d _U_)
{
(void) pcap_snprintf(p->errbuf, sizeof(p->errbuf),
"This system doesn't support BIOCSSEESENT, so the direction can't be set");
return (-1);
#endif
}
#endif
#ifdef BIOCSDLT
static int
pcap_set_datalink_bpf(pcap_t *p, int dlt)
{
#ifdef BIOCSDLT
if (ioctl(p->fd, BIOCSDLT, &dlt) == -1) {
pcap_fmt_errmsg_for_errno(p->errbuf, sizeof(p->errbuf),
errno, "Cannot set DLT %d", dlt);
return (-1);
}
#endif
return (0);
}
#else
static int
pcap_set_datalink_bpf(pcap_t *p _U_, int dlt _U_)
{
return (0);
}
#endif
/*
* Platform-specific information.

View File

@@ -74,13 +74,14 @@ bt_findalldevs(pcap_if_list_t *devlistp, char *err_str)
{
struct hci_dev_list_req *dev_list;
struct hci_dev_req *dev_req;
int i, sock;
int sock;
unsigned i;
int ret = 0;
sock = socket(AF_BLUETOOTH, SOCK_RAW, BTPROTO_HCI);
if (sock < 0)
{
/* if bluetooth is not supported this this is not fatal*/
/* if bluetooth is not supported this is not fatal*/
if (errno == EAFNOSUPPORT)
return 0;
pcap_fmt_errmsg_for_errno(err_str, PCAP_ERRBUF_SIZE,
@@ -109,10 +110,10 @@ bt_findalldevs(pcap_if_list_t *devlistp, char *err_str)
dev_req = dev_list->dev_req;
for (i = 0; i < dev_list->dev_num; i++, dev_req++) {
char dev_name[20], dev_descr[30];
char dev_name[20], dev_descr[40];
pcap_snprintf(dev_name, 20, BT_IFACE"%d", dev_req->dev_id);
pcap_snprintf(dev_descr, 30, "Bluetooth adapter number %d", i);
pcap_snprintf(dev_name, sizeof(dev_name), BT_IFACE"%u", dev_req->dev_id);
pcap_snprintf(dev_descr, sizeof(dev_descr), "Bluetooth adapter number %u", i);
/*
* Bluetooth is a wireless technology.
@@ -379,8 +380,8 @@ bt_read_linux(pcap_t *handle, int max_packets _U_, pcap_handler callback, u_char
static int
bt_inject_linux(pcap_t *handle, const void *buf _U_, size_t size _U_)
{
pcap_snprintf(handle->errbuf, PCAP_ERRBUF_SIZE, "inject not supported on "
"bluetooth devices");
pcap_snprintf(handle->errbuf, PCAP_ERRBUF_SIZE,
"Packet injection is not supported on Bluetooth devices");
return (-1);
}

View File

@@ -149,7 +149,8 @@ bt_monitor_read(pcap_t *handle, int max_packets _U_, pcap_handler callback, u_ch
static int
bt_monitor_inject(pcap_t *handle, const void *buf _U_, size_t size _U_)
{
pcap_snprintf(handle->errbuf, PCAP_ERRBUF_SIZE, "inject not supported yet");
pcap_snprintf(handle->errbuf, PCAP_ERRBUF_SIZE,
"Packet injection is not supported yet on Bluetooth monitor devices");
return -1;
}

View File

@@ -514,11 +514,20 @@
#define LINKTYPE_RAIF1 198
/*
* IPMB packet for IPMI, beginning with the I2C slave address, followed
* by the netFn and LUN, etc.. Requested by Chanthy Toeung
* <chanthy.toeung@ca.kontron.com>.
* IPMB packet for IPMI, beginning with a 2-byte header, followed by
* the I2C slave address, followed by the netFn and LUN, etc..
* Requested by Chanthy Toeung <chanthy.toeung@ca.kontron.com>.
*
* XXX - its DLT_ value used to be called DLT_IPMB, back when we got the
* impression from the email thread requesting it that the packet
* had no extra 2-byte header. We've renamed it; if anybody used
* DLT_IPMB and assumed no 2-byte header, this will cause the compile
* to fail, at which point we'll have to figure out what to do about
* the two header types using the same DLT_/LINKTYPE_ value. If that
* doesn't happen, we'll assume nobody used it and that the redefinition
* is safe.
*/
#define LINKTYPE_IPMB 199
#define LINKTYPE_IPMB_KONTRON 199
/*
* Juniper-private data link type, as per request from
@@ -549,15 +558,35 @@
*/
#define LINKTYPE_LAPD 203
/*
* Variants of various link-layer headers, with a one-byte direction
* pseudo-header prepended - zero means "received by this host",
* non-zero (any non-zero value) means "sent by this host" - as per
* Will Barker <w.barker@zen.co.uk>.
* PPP, with a one-byte direction pseudo-header prepended - zero means
* "received by this host", non-zero (any non-zero value) means "sent by
* this host" - as per Will Barker <w.barker@zen.co.uk>.
*/
#define LINKTYPE_PPP_WITH_DIR 204 /* Don't confuse with LINKTYPE_PPP_PPPD */
/*
* Cisco HDLC, with a one-byte direction pseudo-header prepended - zero
* means "received by this host", non-zero (any non-zero value) means
* "sent by this host" - as per Will Barker <w.barker@zen.co.uk>.
*/
#define LINKTYPE_PPP_WITH_DIR 204 /* PPP */
#define LINKTYPE_C_HDLC_WITH_DIR 205 /* Cisco HDLC */
/*
* Frame Relay, with a one-byte direction pseudo-header prepended - zero
* means "received by this host" (DCE -> DTE), non-zero (any non-zero
* value) means "sent by this host" (DTE -> DCE) - as per Will Barker
* <w.barker@zen.co.uk>.
*/
#define LINKTYPE_FRELAY_WITH_DIR 206 /* Frame Relay */
/*
* LAPB, with a one-byte direction pseudo-header prepended - zero means
* "received by this host" (DCE -> DTE), non-zero (any non-zero value)
* means "sent by this host" (DTE -> DCE)- as per Will Barker
* <w.barker@zen.co.uk>.
*/
#define LINKTYPE_LAPB_WITH_DIR 207 /* LAPB */
/*
@@ -1081,7 +1110,12 @@
*/
#define LINKTYPE_DISPLAYPORT_AUX 275
#define LINKTYPE_MATCHING_MAX 275 /* highest value in the "matching" range */
/*
* Linux cooked sockets v2.
*/
#define LINKTYPE_LINUX_SLL2 276
#define LINKTYPE_MATCHING_MAX 276 /* highest value in the "matching" range */
/*
* The DLT_ and LINKTYPE_ values in the "matching" range should be the
@@ -1240,18 +1274,30 @@ linktype_to_dlt(int linktype)
/*
* Return the maximum snapshot length for a given DLT_ value.
*
* For most link-layer types, we use MAXIMUM_SNAPLEN, but for DLT_DBUS,
* the maximum is 134217728, as per
* For most link-layer types, we use MAXIMUM_SNAPLEN.
*
* For DLT_DBUS, the maximum is 128MiB, as per
*
* https://dbus.freedesktop.org/doc/dbus-specification.html#message-protocol-messages
*
* For DLT_USBPCAP, the maximum is 1MiB, as per
*
* https://bugs.wireshark.org/bugzilla/show_bug.cgi?id=15985
*/
u_int
max_snaplen_for_dlt(int dlt)
{
if (dlt == DLT_DBUS)
return 134217728;
else
switch (dlt) {
case DLT_DBUS:
return 128*1024*1024;
case DLT_USBPCAP:
return 1024*1024;
default:
return MAXIMUM_SNAPLEN;
}
}
/*

View File

@@ -1,14 +1,6 @@
/*
* pcap-dag.c: Packet capture interface for Endace DAG cards.
*
* The functionality of this code attempts to mimic that of pcap-linux as much
* as possible. This code is compiled in several different ways depending on
* whether DAG_ONLY and HAVE_DAG_API are defined. If HAVE_DAG_API is not
* defined it should not get compiled in, otherwise if DAG_ONLY is defined then
* the 'dag_' function calls are renamed to 'pcap_' equivalents. If DAG_ONLY
* is not defined then nothing is altered - the dag_ functions will be
* called as required from their pcap-linux/bpf equivalents.
*
* Authors: Richard Littin, Sean Irvine ({richard,sean}@reeltwo.com)
* Modifications: Jesper Peterson
* Koryn Grant
@@ -258,12 +250,18 @@ dag_platform_cleanup(pcap_t *p)
if(pd->dag_ref != NULL) {
dag_config_dispose(pd->dag_ref);
/*
* Note: we don't need to call close(p->fd) or
* dag_close(p->fd), as dag_config_dispose(pd->dag_ref)
* does this.
*
* Set p->fd to -1 to make sure that's not done.
*/
p->fd = -1;
pd->dag_ref = NULL;
}
delete_pcap_dag(p);
pcap_cleanup_live_common(p);
/* Note: don't need to call close(p->fd) or dag_close(p->fd) as dag_config_dispose(pd->dag_ref) does this. */
}
static void
@@ -722,7 +720,7 @@ dag_read(pcap_t *p, int cnt, pcap_handler callback, u_char *user)
static int
dag_inject(pcap_t *p, const void *buf _U_, size_t size _U_)
{
strlcpy(p->errbuf, "Sending packets isn't supported on DAG cards",
pcap_strlcpy(p->errbuf, "Sending packets isn't supported on DAG cards",
PCAP_ERRBUF_SIZE);
return (-1);
}
@@ -746,18 +744,20 @@ static int dag_activate(pcap_t* p)
daginf_t* daginf;
char * newDev = NULL;
char * device = p->opt.device;
int ret;
dag_size_t mindata;
struct timeval maxwait;
struct timeval poll;
if (device == NULL) {
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE, "device is NULL");
return -1;
return PCAP_ERROR;
}
/* Initialize some components of the pcap structure. */
newDev = (char *)malloc(strlen(device) + 16);
if (newDev == NULL) {
ret = PCAP_ERROR;
pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
errno, "Can't allocate string for device name");
goto fail;
@@ -765,6 +765,13 @@ static int dag_activate(pcap_t* p)
/* Parse input name to get dag device and stream number if provided */
if (dag_parse_name(device, newDev, strlen(device) + 16, &pd->dag_stream) < 0) {
/*
* XXX - it'd be nice if this indicated what was wrong
* with the name. Does this reliably set errno?
* Should this return PCAP_ERROR_NO_SUCH_DEVICE in some
* cases?
*/
ret = PCAP_ERROR;
pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
errno, "dag_parse_name");
goto fail;
@@ -772,25 +779,40 @@ static int dag_activate(pcap_t* p)
device = newDev;
if (pd->dag_stream%2) {
ret = PCAP_ERROR;
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE, "dag_parse_name: tx (even numbered) streams not supported for capture");
goto fail;
}
/* setup device parameters */
if((pd->dag_ref = dag_config_init((char *)device)) == NULL) {
/*
* XXX - does this reliably set errno?
*/
if (errno == ENOENT)
ret = PCAP_ERROR_NO_SUCH_DEVICE;
else if (errno == EPERM || errno == EACCES)
ret = PCAP_ERROR_PERM_DENIED;
else
ret = PCAP_ERROR;
pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
errno, "dag_config_init %s", device);
goto fail;
}
if((p->fd = dag_config_get_card_fd(pd->dag_ref)) < 0) {
/*
* XXX - does this reliably set errno?
*/
ret = PCAP_ERROR;
pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
errno, "dag_config_get_card_fd %s", device);
goto fail;
goto failclose;
}
/* Open requested stream. Can fail if already locked or on error */
if (dag_attach_stream64(p->fd, pd->dag_stream, 0, 0) < 0) {
ret = PCAP_ERROR;
pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
errno, "dag_attach_stream");
goto failclose;
@@ -809,6 +831,7 @@ static int dag_activate(pcap_t* p)
*/
if (dag_get_stream_poll64(p->fd, pd->dag_stream,
&mindata, &maxwait, &poll) < 0) {
ret = PCAP_ERROR;
pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
errno, "dag_get_stream_poll");
goto faildetach;
@@ -853,6 +876,7 @@ static int dag_activate(pcap_t* p)
if (dag_set_stream_poll64(p->fd, pd->dag_stream,
mindata, &maxwait, &poll) < 0) {
ret = PCAP_ERROR;
pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
errno, "dag_set_stream_poll");
goto faildetach;
@@ -875,6 +899,7 @@ static int dag_activate(pcap_t* p)
#endif
if(dag_start_stream(p->fd, pd->dag_stream) < 0) {
ret = PCAP_ERROR;
pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
errno, "dag_start_stream %s", device);
goto faildetach;
@@ -910,6 +935,7 @@ static int dag_activate(pcap_t* p)
if ((n = atoi(s)) == 0 || n == 16 || n == 32) {
pd->dag_fcs_bits = n;
} else {
ret = PCAP_ERROR;
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
"pcap_activate %s: bad ERF_FCS_BITS value (%d) in environment", device, n);
goto failstop;
@@ -932,12 +958,15 @@ static int dag_activate(pcap_t* p)
pd->dag_timeout = p->opt.timeout;
p->linktype = -1;
if (dag_get_datalink(p) < 0)
if (dag_get_datalink(p) < 0) {
ret = PCAP_ERROR;
goto failstop;
}
p->bufsize = 0;
if (new_pcap_dag(p) < 0) {
ret = PCAP_ERROR;
pcap_fmt_errmsg_for_errno(p->errbuf, PCAP_ERRBUF_SIZE,
errno, "new_pcap_dag %s", device);
goto failstop;
@@ -977,6 +1006,14 @@ faildetach:
failclose:
dag_config_dispose(pd->dag_ref);
/*
* Note: we don't need to call close(p->fd) or dag_close(p->fd),
* as dag_config_dispose(pd->dag_ref) does this.
*
* Set p->fd to -1 to make sure that's not done.
*/
p->fd = -1;
pd->dag_ref = NULL;
delete_pcap_dag(p);
fail:
@@ -985,7 +1022,7 @@ fail:
free((char *)newDev);
}
return PCAP_ERROR;
return ret;
}
pcap_t *dag_create(const char *device, char *ebuf, int *is_ours)
@@ -1137,7 +1174,7 @@ dag_findalldevs(pcap_if_list_t *devlistp, char *errbuf)
}
rxstreams = dag_rx_get_stream_count(dagfd);
for(stream=0;stream<DAG_STREAM_MAX;stream+=2) {
if (0 == dag_attach_stream(dagfd, stream, 0, 0)) {
if (0 == dag_attach_stream64(dagfd, stream, 0, 0)) {
dag_detach_stream(dagfd, stream);
pcap_snprintf(name, 10, "dag%d:%d", c, stream);

View File

@@ -307,7 +307,7 @@ pcap_inject_dlpi(pcap_t *p, const void *buf, size_t size)
* it should check "p->linktype" and reject the send request if
* it's anything other than DLT_EN10MB.
*/
strlcpy(p->errbuf, "send: Not supported on this version of this OS",
pcap_strlcpy(p->errbuf, "send: Not supported on this version of this OS",
PCAP_ERRBUF_SIZE);
ret = -1;
#endif /* raw mode */
@@ -363,9 +363,9 @@ open_dlpi_device(const char *name, u_int *ppa, char *errbuf)
*/
cp = strrchr(name, '/');
if (cp == NULL)
strlcpy(dname, name, sizeof(dname));
pcap_strlcpy(dname, name, sizeof(dname));
else
strlcpy(dname, cp + 1, sizeof(dname));
pcap_strlcpy(dname, cp + 1, sizeof(dname));
/*
* Split the device name into a device type name and a unit number;
@@ -415,7 +415,7 @@ open_dlpi_device(const char *name, u_int *ppa, char *errbuf)
* device name.
*/
if (*name == '/')
strlcpy(dname, name, sizeof(dname));
pcap_strlcpy(dname, name, sizeof(dname));
else
pcap_snprintf(dname, sizeof(dname), "%s/%s", PCAP_DEV_PREFIX,
name);
@@ -432,7 +432,7 @@ open_dlpi_device(const char *name, u_int *ppa, char *errbuf)
* Make a copy of the device pathname, and then remove the unit
* number from the device pathname.
*/
strlcpy(dname2, dname, sizeof(dname));
pcap_strlcpy(dname2, dname, sizeof(dname));
*cp = '\0';
/* Try device without unit number */
@@ -968,7 +968,7 @@ dl_dohpuxbind(int fd, char *ebuf)
*ebuf = '\0';
hpsap++;
if (hpsap > 100) {
strlcpy(ebuf,
pcap_strlcpy(ebuf,
"All SAPs from 22 through 100 are in use",
PCAP_ERRBUF_SIZE);
return (-1);
@@ -1547,7 +1547,7 @@ get_release(char *buf, size_t bufsize, bpf_u_int32 *majorp,
*minorp = 0;
*microp = 0;
if (sysinfo(SI_RELEASE, buf, bufsize) < 0) {
strlcpy(buf, "?", bufsize);
pcap_strlcpy(buf, "?", bufsize);
return;
}
cp = buf;

View File

@@ -413,14 +413,14 @@ int pcap_stats_ex (pcap_t *p, struct pcap_stat_ex *se)
if (!dev || !dev->get_stats)
{
strlcpy (p->errbuf, "detailed device statistics not available",
pcap_strlcpy (p->errbuf, "detailed device statistics not available",
PCAP_ERRBUF_SIZE);
return (-1);
}
if (!strnicmp(dev->name,"pkt",3))
{
strlcpy (p->errbuf, "pktdrvr doesn't have detailed statistics",
pcap_strlcpy (p->errbuf, "pktdrvr doesn't have detailed statistics",
PCAP_ERRBUF_SIZE);
return (-1);
}

View File

@@ -29,11 +29,11 @@ pcap-filter \- packet filter syntax
is used to compile a string into a filter program.
The resulting filter program can then be applied to
some stream of packets to determine which packets will be supplied to
.BR pcap_loop() ,
.BR pcap_dispatch() ,
.BR pcap_next() ,
.BR pcap_loop(3PCAP) ,
.BR pcap_dispatch(3PCAP) ,
.BR pcap_next(3PCAP) ,
or
.BR pcap_next_ex() .
.BR pcap_next_ex(3PCAP) .
.LP
The \fIfilter expression\fP consists of one or more
.IR primitives .
@@ -86,12 +86,6 @@ The
and
.B addr4
qualifiers are only valid for IEEE 802.11 Wireless LAN link layers.
For some link layers, such as SLIP and the ``cooked'' Linux capture mode
used for the ``any'' device and for some other device types, the
.B inbound
and
.B outbound
qualifiers can be used to specify a desired direction.
.IP \fIproto\fP
.I proto
qualifiers restrict the match to a particular protocol.
@@ -466,8 +460,6 @@ Token Ring packets (no check is done for LLC frames);
FDDI packets (no check is done for LLC frames);
.IP
LLC-encapsulated ATM packets, for SunATM on Solaris.
.IP
.IP "\fBllc\fP \Fitype\fR"
True if the packet has an 802.2 LLC header and has the specified
.IR type .
@@ -514,6 +506,16 @@ Exchange Identification (XID) U PDUs
\fBfrmr\fR
Frame Reject (FRMR) U PDUs
.RE
.IP \fBinbound\fP
Packet was received by the host performing the capture rather than being
sent by that host. This is only supported for certain link-layer types,
such as SLIP and the ``cooked'' Linux capture mode
used for the ``any'' device and for some other device types.
.IP \fBoutbound\fP
Packet was sent by the host performing the capture rather than being
received by that host. This is only supported for certain link-layer types,
such as SLIP and the ``cooked'' Linux capture mode
used for the ``any'' device and for some other device types.
.IP "\fBifname \fIinterface\fR"
True if the packet was logged as coming from the specified interface (applies
only to packets logged by OpenBSD's or FreeBSD's

View File

@@ -86,7 +86,12 @@ extern "C" {
* 2) small enough not to cause attempts to allocate huge amounts of
* memory; some applications might use the snapshot length in a
* savefile header to control the size of the buffer they allocate,
* so a size of, say, 2^31-1 might not work well.
* so a size of, say, 2^31-1 might not work well. (libpcap uses it
* as a hint, but doesn't start out allocating a buffer bigger than
* 2 KiB, and grows the buffer as necessary, but not beyond the
* per-linktype maximum snapshot length. Other code might naively
* use it; we want to avoid writing a too-large snapshot length,
* in order not to cause that code problems.)
*
* We don't enforce this in pcap_set_snaplen(), but we use it internally.
*/
@@ -472,13 +477,38 @@ int add_addr_to_if(pcap_if_list_t *, const char *, bpf_u_int32,
* "pcap_open_offline_common()" allocates and fills in a pcap_t, for use
* by pcap_open_offline routines.
*
* "pcap_adjust_snapshot()" adjusts the snapshot to be non-zero and
* fit within an int.
*
* "sf_cleanup()" closes the file handle associated with a pcap_t, if
* appropriate, and frees all data common to all modules for handling
* savefile types.
*/
pcap_t *pcap_open_offline_common(char *ebuf, size_t size);
bpf_u_int32 pcap_adjust_snapshot(bpf_u_int32 linktype, bpf_u_int32 snaplen);
void sf_cleanup(pcap_t *p);
/*
* Internal interfaces for doing user-mode filtering of packets and
* validating filter programs.
*/
/*
* Auxiliary data, for use when interpreting a filter intended for the
* Linux kernel when the kernel rejects the filter (requiring us to
* run it in userland). It contains VLAN tag information.
*/
struct bpf_aux_data {
u_short vlan_tag_present;
u_short vlan_tag;
};
/*
* Filtering routine that takes the auxiliary data as an additional
* argument.
*/
u_int bpf_filter_with_aux_data(const struct bpf_insn *,
const u_char *, u_int, u_int, const struct bpf_aux_data *);
/*
* Internal interfaces for both "pcap_create()" and routines that
* open savefiles.
@@ -488,10 +518,6 @@ void sf_cleanup(pcap_t *p);
*/
void pcap_oneshot(u_char *, const struct pcap_pkthdr *, const u_char *);
#ifdef _WIN32
void pcap_win32_err_to_str(DWORD, char *);
#endif
int install_bpf_program(pcap_t *, struct bpf_program *);
int pcap_strcasecmp(const char *, const char *);

View File

@@ -80,7 +80,7 @@ list_interfaces(const char *linkname, void *arg)
lwp->lw_err = ENOMEM;
return (B_TRUE);
}
(void) strlcpy(entry->linkname, linkname, DLPI_LINKNAME_MAX);
(void) pcap_strlcpy(entry->linkname, linkname, DLPI_LINKNAME_MAX);
if (lwp->lw_list == NULL) {
lwp->lw_list = entry;

View File

@@ -45,4 +45,4 @@ The names for those values begin with
The link-layer header types supported by libpcap are described at
https://www.tcpdump.org/linktypes.html.
.SH SEE ALSO
pcap_datalink(3PCAP)
pcap(3PCAP)

File diff suppressed because it is too large Load Diff

View File

@@ -301,7 +301,8 @@ netfilter_stats_linux(pcap_t *handle, struct pcap_stat *stats)
static int
netfilter_inject_linux(pcap_t *handle, const void *buf _U_, size_t size _U_)
{
pcap_snprintf(handle->errbuf, PCAP_ERRBUF_SIZE, "inject not supported on netfilter devices");
pcap_snprintf(handle->errbuf, PCAP_ERRBUF_SIZE,
"Packet injection is not supported on netfilter devices");
return (-1);
}
@@ -315,6 +316,7 @@ static int
netfilter_send_config_msg(const pcap_t *handle, uint16_t msg_type, int ack, u_int8_t family, u_int16_t res_id, const struct my_nfattr *mynfa)
{
char buf[1024] __attribute__ ((aligned));
memset(buf, 0, sizeof(buf));
struct nlmsghdr *nlh = (struct nlmsghdr *) buf;
struct nfgenmsg *nfg = (struct nfgenmsg *) (buf + sizeof(struct nlmsghdr));

View File

@@ -67,7 +67,7 @@ pcap_netmap_stats(pcap_t *p, struct pcap_stat *ps)
{
struct pcap_netmap *pn = p->priv;
ps->ps_recv = pn->rx_pkts;
ps->ps_recv = (u_int)pn->rx_pkts;
ps->ps_drop = 0;
ps->ps_ifdrop = 0;
return 0;

View File

@@ -35,6 +35,8 @@
#include <config.h>
#endif
#include "ftmacros.h"
/*
* sockutils.h may include <crtdbg.h> on Windows, and pcap-int.h will
* include portability.h, and portability.h, on Windows, expects that
@@ -54,11 +56,14 @@
/* String identifier to be used in the pcap_findalldevs_ex() */
#define PCAP_TEXT_SOURCE_FILE "File"
#define PCAP_TEXT_SOURCE_FILE_LEN (sizeof PCAP_TEXT_SOURCE_FILE - 1)
/* String identifier to be used in the pcap_findalldevs_ex() */
#define PCAP_TEXT_SOURCE_ADAPTER "Network adapter"
#define PCAP_TEXT_SOURCE_ADAPTER_LEN (sizeof "Network adapter" - 1)
/* String identifier to be used in the pcap_findalldevs_ex() */
#define PCAP_TEXT_SOURCE_ON_LOCAL_HOST "on local host"
#define PCAP_TEXT_SOURCE_ON_LOCAL_HOST_LEN (sizeof PCAP_TEXT_SOURCE_ON_LOCAL_HOST + 1)
/****************************************************
* *
@@ -66,10 +71,12 @@
* *
****************************************************/
int pcap_findalldevs_ex(char *source, struct pcap_rmtauth *auth, pcap_if_t **alldevs, char *errbuf)
int pcap_findalldevs_ex(const char *source, struct pcap_rmtauth *auth, pcap_if_t **alldevs, char *errbuf)
{
int type;
char name[PCAP_BUF_SIZE], path[PCAP_BUF_SIZE], filename[PCAP_BUF_SIZE];
size_t pathlen;
size_t stringlen;
pcap_t *fp;
char tmpstring[PCAP_BUF_SIZE + 1]; /* Needed to convert names and descriptions from 'old' syntax to the 'new' one */
pcap_if_t *lastdev; /* Last device in the pcap_if_t list */
@@ -113,7 +120,7 @@ int pcap_findalldevs_ex(char *source, struct pcap_rmtauth *auth, pcap_if_t **all
if (*alldevs == NULL)
{
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE,
"No interfaces found! Make sure libpcap/WinPcap is properly installed"
"No interfaces found! Make sure libpcap/Npcap is properly installed"
" on the local machine.");
return -1;
}
@@ -123,6 +130,8 @@ int pcap_findalldevs_ex(char *source, struct pcap_rmtauth *auth, pcap_if_t **all
dev = *alldevs;
while (dev)
{
char *localdesc, *desc;
/* Create the new device identifier */
if (pcap_createsrcstr(tmpstring, PCAP_SRC_IFLOCAL, NULL, NULL, dev->name, errbuf) == -1)
return -1;
@@ -141,20 +150,16 @@ int pcap_findalldevs_ex(char *source, struct pcap_rmtauth *auth, pcap_if_t **all
return -1;
}
/* Create the new device description */
/*
* Create the description.
*/
if ((dev->description == NULL) || (dev->description[0] == 0))
pcap_snprintf(tmpstring, sizeof(tmpstring) - 1, "%s '%s' %s", PCAP_TEXT_SOURCE_ADAPTER,
dev->name, PCAP_TEXT_SOURCE_ON_LOCAL_HOST);
localdesc = dev->name;
else
pcap_snprintf(tmpstring, sizeof(tmpstring) - 1, "%s '%s' %s", PCAP_TEXT_SOURCE_ADAPTER,
dev->description, PCAP_TEXT_SOURCE_ON_LOCAL_HOST);
/* Delete the old pointer */
free(dev->description);
/* Make a copy of the description */
dev->description = strdup(tmpstring);
if (dev->description == NULL)
localdesc = dev->description;
if (pcap_asprintf(&desc, "%s '%s' %s",
PCAP_TEXT_SOURCE_ADAPTER, localdesc,
PCAP_TEXT_SOURCE_ON_LOCAL_HOST) == -1)
{
pcap_fmt_errmsg_for_errno(errbuf,
PCAP_ERRBUF_SIZE, errno,
@@ -163,6 +168,10 @@ int pcap_findalldevs_ex(char *source, struct pcap_rmtauth *auth, pcap_if_t **all
return -1;
}
/* Now overwrite the description */
free(dev->description);
dev->description = desc;
dev = dev->next;
}
@@ -170,7 +179,6 @@ int pcap_findalldevs_ex(char *source, struct pcap_rmtauth *auth, pcap_if_t **all
case PCAP_SRC_FILE:
{
size_t stringlen;
#ifdef _WIN32
WIN32_FIND_DATA filedata;
HANDLE filehandle;
@@ -202,6 +210,7 @@ int pcap_findalldevs_ex(char *source, struct pcap_rmtauth *auth, pcap_if_t **all
/* Save the path for future reference */
pcap_snprintf(path, sizeof(path), "%s", name);
pathlen = strlen(path);
#ifdef _WIN32
/* To perform directory listing, Win32 must have an 'asterisk' as ending char */
@@ -236,10 +245,14 @@ int pcap_findalldevs_ex(char *source, struct pcap_rmtauth *auth, pcap_if_t **all
/* Add all files we find to the list. */
do
{
#ifdef _WIN32
/* Skip the file if the pathname won't fit in the buffer */
if (pathlen + strlen(filedata.cFileName) >= sizeof(filename))
continue;
pcap_snprintf(filename, sizeof(filename), "%s%s", path, filedata.cFileName);
#else
if (pathlen + strlen(filedata->d_name) >= sizeof(filename))
continue;
pcap_snprintf(filename, sizeof(filename), "%s%s", path, filedata->d_name);
#endif
@@ -287,9 +300,7 @@ int pcap_findalldevs_ex(char *source, struct pcap_rmtauth *auth, pcap_if_t **all
return -1;
}
stringlen = strlen(tmpstring);
dev->name = (char *)malloc(stringlen + 1);
dev->name = strdup(tmpstring);
if (dev->name == NULL)
{
pcap_fmt_errmsg_for_errno(errbuf,
@@ -299,19 +310,12 @@ int pcap_findalldevs_ex(char *source, struct pcap_rmtauth *auth, pcap_if_t **all
return -1;
}
strlcpy(dev->name, tmpstring, stringlen);
dev->name[stringlen] = 0;
/* Create the description */
pcap_snprintf(tmpstring, sizeof(tmpstring) - 1, "%s '%s' %s", PCAP_TEXT_SOURCE_FILE,
filename, PCAP_TEXT_SOURCE_ON_LOCAL_HOST);
stringlen = strlen(tmpstring);
dev->description = (char *)malloc(stringlen + 1);
if (dev->description == NULL)
/*
* Create the description.
*/
if (pcap_asprintf(&dev->description,
"%s '%s' %s", PCAP_TEXT_SOURCE_FILE,
filename, PCAP_TEXT_SOURCE_ON_LOCAL_HOST) == -1)
{
pcap_fmt_errmsg_for_errno(errbuf,
PCAP_ERRBUF_SIZE, errno,
@@ -320,9 +324,6 @@ int pcap_findalldevs_ex(char *source, struct pcap_rmtauth *auth, pcap_if_t **all
return -1;
}
/* Copy the new device description into the correct memory location */
strlcpy(dev->description, tmpstring, stringlen + 1);
pcap_close(fp);
}
}
@@ -345,7 +346,7 @@ int pcap_findalldevs_ex(char *source, struct pcap_rmtauth *auth, pcap_if_t **all
return pcap_findalldevs_ex_remote(source, auth, alldevs, errbuf);
default:
strlcpy(errbuf, "Source type not supported", PCAP_ERRBUF_SIZE);
pcap_strlcpy(errbuf, "Source type not supported", PCAP_ERRBUF_SIZE);
return -1;
}
}
@@ -357,6 +358,16 @@ pcap_t *pcap_open(const char *source, int snaplen, int flags, int read_timeout,
pcap_t *fp;
int status;
/*
* A null device name is equivalent to the "any" device -
* which might not be supported on this platform, but
* this means that you'll get a "not supported" error
* rather than, say, a crash when we try to dereference
* the null pointer.
*/
if (source == NULL)
source = "any";
if (strlen(source) > PCAP_BUF_SIZE)
{
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "The source string is too long. Cannot handle it correctly.");
@@ -389,7 +400,7 @@ pcap_t *pcap_open(const char *source, int snaplen, int flags, int read_timeout,
return pcap_open_rpcap(source, snaplen, flags, read_timeout, auth, errbuf);
default:
strlcpy(errbuf, "Source type not supported", PCAP_ERRBUF_SIZE);
pcap_strlcpy(errbuf, "Source type not supported", PCAP_ERRBUF_SIZE);
return NULL;
}

View File

@@ -70,7 +70,7 @@ static int pcap_setnonblock_npf(pcap_t *, int);
#define SWAPS(_X) ((_X & 0xff) << 8) | (_X >> 8)
/*
* Private data for capturing on WinPcap devices.
* Private data for capturing on WinPcap/Npcap devices.
*/
struct pcap_win {
ADAPTER *adapter; /* the packet32 ADAPTER for the device */
@@ -166,11 +166,8 @@ oid_get_request(ADAPTER *adapter, bpf_u_int32 oid, void *data, size_t *lenp,
oid_data_arg->Oid = oid;
oid_data_arg->Length = (ULONG)(*lenp); /* XXX - check for ridiculously large value? */
if (!PacketRequest(adapter, FALSE, oid_data_arg)) {
char errmsgbuf[PCAP_ERRBUF_SIZE+1];
pcap_win32_err_to_str(GetLastError(), errmsgbuf);
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE,
"Error calling PacketRequest: %s", errmsgbuf);
pcap_fmt_errmsg_for_win32_err(errbuf, PCAP_ERRBUF_SIZE,
GetLastError(), "Error calling PacketRequest");
free(oid_data_arg);
return (-1);
}
@@ -193,7 +190,6 @@ pcap_stats_npf(pcap_t *p, struct pcap_stat *ps)
{
struct pcap_win *pw = p->priv;
struct bpf_stat bstats;
char errbuf[PCAP_ERRBUF_SIZE+1];
/*
* Try to get statistics.
@@ -209,9 +205,8 @@ pcap_stats_npf(pcap_t *p, struct pcap_stat *ps)
* to us.
*/
if (!PacketGetStats(pw->adapter, &bstats)) {
pcap_win32_err_to_str(GetLastError(), errbuf);
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
"PacketGetStats error: %s", errbuf);
pcap_fmt_errmsg_for_win32_err(p->errbuf, PCAP_ERRBUF_SIZE,
GetLastError(), "PacketGetStats error");
return (-1);
}
ps->ps_recv = bstats.bs_recv;
@@ -256,7 +251,6 @@ pcap_stats_ex_npf(pcap_t *p, int *pcap_stat_size)
{
struct pcap_win *pw = p->priv;
struct bpf_stat bstats;
char errbuf[PCAP_ERRBUF_SIZE+1];
*pcap_stat_size = sizeof (p->stat);
@@ -268,9 +262,8 @@ pcap_stats_ex_npf(pcap_t *p, int *pcap_stat_size)
* same layout, but let's not cheat.)
*/
if (!PacketGetStatsEx(pw->adapter, &bstats)) {
pcap_win32_err_to_str(GetLastError(), errbuf);
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
"PacketGetStatsEx error: %s", errbuf);
pcap_fmt_errmsg_for_win32_err(p->errbuf, PCAP_ERRBUF_SIZE,
GetLastError(), "PacketGetStatsEx error");
return (NULL);
}
p->stat.ps_recv = bstats.bs_recv;
@@ -347,7 +340,6 @@ pcap_oid_set_request_npf(pcap_t *p, bpf_u_int32 oid, const void *data,
{
struct pcap_win *pw = p->priv;
PACKET_OID_DATA *oid_data_arg;
char errbuf[PCAP_ERRBUF_SIZE+1];
/*
* Allocate a PACKET_OID_DATA structure to hand to PacketRequest().
@@ -367,9 +359,8 @@ pcap_oid_set_request_npf(pcap_t *p, bpf_u_int32 oid, const void *data,
oid_data_arg->Length = (ULONG)(*lenp); /* XXX - check for ridiculously large value? */
memcpy(oid_data_arg->Data, data, *lenp);
if (!PacketRequest(pw->adapter, TRUE, oid_data_arg)) {
pcap_win32_err_to_str(GetLastError(), errbuf);
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
"Error calling PacketRequest: %s", errbuf);
pcap_fmt_errmsg_for_win32_err(p->errbuf, PCAP_ERRBUF_SIZE,
GetLastError(), "Error calling PacketRequest");
free(oid_data_arg);
return (PCAP_ERROR);
}
@@ -391,7 +382,6 @@ pcap_sendqueue_transmit_npf(pcap_t *p, pcap_send_queue *queue, int sync)
{
struct pcap_win *pw = p->priv;
u_int res;
char errbuf[PCAP_ERRBUF_SIZE+1];
if (pw->adapter==NULL) {
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
@@ -405,9 +395,8 @@ pcap_sendqueue_transmit_npf(pcap_t *p, pcap_send_queue *queue, int sync)
(BOOLEAN)sync);
if(res != queue->len){
pcap_win32_err_to_str(GetLastError(), errbuf);
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
"Error opening adapter: %s", errbuf);
pcap_fmt_errmsg_for_win32_err(p->errbuf, PCAP_ERRBUF_SIZE,
GetLastError(), "Error opening adapter");
}
return (res);
@@ -534,7 +523,34 @@ pcap_read_npf(pcap_t *p, int cnt, pcap_handler callback, u_char *user)
*/
PacketInitPacket(&Packet, (BYTE *)p->buffer, p->bufsize);
if (!PacketReceivePacket(pw->adapter, &Packet, TRUE)) {
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE, "read error: PacketReceivePacket failed");
/*
* Did the device go away?
* If so, the error we get is ERROR_GEN_FAILURE.
*/
DWORD errcode = GetLastError();
if (errcode == ERROR_GEN_FAILURE) {
/*
* The device on which we're capturing
* went away, or it became unusable
* by NPF due to a suspend/resume.
*
* XXX - hopefully no other error
* conditions are indicated by this.
*
* XXX - we really should return an
* appropriate error for that, but
* pcap_dispatch() etc. aren't
* documented as having error returns
* other than PCAP_ERROR or PCAP_ERROR_BREAK.
*/
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
"The interface disappeared");
} else {
pcap_fmt_errmsg_for_win32_err(p->errbuf,
PCAP_ERRBUF_SIZE, errcode,
"PacketReceivePacket error");
}
return (PCAP_ERROR);
}
@@ -873,7 +889,7 @@ pcap_activate_npf(pcap_t *p)
struct pcap_win *pw = p->priv;
NetType type;
int res;
char errbuf[PCAP_ERRBUF_SIZE+1];
int status = 0;
if (p->opt.rfmon) {
/*
@@ -912,23 +928,35 @@ pcap_activate_npf(pcap_t *p)
if (pw->adapter == NULL)
{
/* Adapter detected but we are not able to open it. Return failure. */
pcap_win32_err_to_str(GetLastError(), errbuf);
if (pw->rfmon_selfstart)
{
PacketSetMonitorMode(p->opt.device, 0);
DWORD errcode = GetLastError();
/*
* What error did we get when trying to open the adapter?
*/
if (errcode == ERROR_BAD_UNIT) {
/*
* There's no such device.
*/
return (PCAP_ERROR_NO_SUCH_DEVICE);
} else {
/*
* Unknown - report details.
*/
pcap_fmt_errmsg_for_win32_err(p->errbuf, PCAP_ERRBUF_SIZE,
errcode, "Error opening adapter");
if (pw->rfmon_selfstart)
{
PacketSetMonitorMode(p->opt.device, 0);
}
return (PCAP_ERROR);
}
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
"Error opening adapter: %s", errbuf);
return (PCAP_ERROR);
}
/*get network type*/
if(PacketGetNetType (pw->adapter,&type) == FALSE)
{
pcap_win32_err_to_str(GetLastError(), errbuf);
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
"Cannot determine the network type: %s", errbuf);
pcap_fmt_errmsg_for_win32_err(p->errbuf, PCAP_ERRBUF_SIZE,
GetLastError(), "Cannot determine the network type");
goto bad;
}
@@ -1006,8 +1034,29 @@ pcap_activate_npf(pcap_t *p)
p->linktype = DLT_PPI;
break;
#ifdef NdisMediumWirelessWan
case NdisMediumWirelessWan:
p->linktype = DLT_RAW;
break;
#endif
default:
p->linktype = DLT_EN10MB; /*an unknown adapter is assumed to be ethernet*/
/*
* An unknown medium type is assumed to supply Ethernet
* headers; if not, the user will have to report it,
* so that the medium type and link-layer header type
* can be determined. If we were to fail here, we
* might get the link-layer type in the error, but
* the user wouldn't get a capture, so we wouldn't
* be able to determine the link-layer type; we report
* a warning with the link-layer type, so at least
* some programs will report the warning.
*/
p->linktype = DLT_EN10MB;
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
"Unknown NdisMedium value %d, defaulting to DLT_EN10MB",
type.LinkType);
status = PCAP_WARNING;
break;
}
@@ -1085,10 +1134,9 @@ pcap_activate_npf(pcap_t *p)
/* tell the driver to copy the buffer as soon as data arrives */
if(PacketSetMinToCopy(pw->adapter,0)==FALSE)
{
pcap_win32_err_to_str(GetLastError(), errbuf);
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
"Error calling PacketSetMinToCopy: %s",
errbuf);
pcap_fmt_errmsg_for_win32_err(p->errbuf,
PCAP_ERRBUF_SIZE, GetLastError(),
"Error calling PacketSetMinToCopy");
goto bad;
}
}
@@ -1097,10 +1145,9 @@ pcap_activate_npf(pcap_t *p)
/* tell the driver to copy the buffer only if it contains at least 16K */
if(PacketSetMinToCopy(pw->adapter,16000)==FALSE)
{
pcap_win32_err_to_str(GetLastError(), errbuf);
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
"Error calling PacketSetMinToCopy: %s",
errbuf);
pcap_fmt_errmsg_for_win32_err(p->errbuf,
PCAP_ERRBUF_SIZE, GetLastError(),
"Error calling PacketSetMinToCopy");
goto bad;
}
}
@@ -1221,7 +1268,7 @@ pcap_activate_npf(pcap_t *p)
*/
p->handle = pw->adapter->hFile;
return (0);
return (status);
bad:
pcap_cleanup_npf(p);
return (PCAP_ERROR);
@@ -1316,7 +1363,7 @@ pcap_setfilter_win32_dag(pcap_t *p, struct bpf_program *fp) {
if(!fp)
{
strlcpy(p->errbuf, "setfilter: No filter specified", sizeof(p->errbuf));
pcap_strlcpy(p->errbuf, "setfilter: No filter specified", sizeof(p->errbuf));
return (-1);
}
@@ -1345,7 +1392,6 @@ pcap_setnonblock_npf(pcap_t *p, int nonblock)
{
struct pcap_win *pw = p->priv;
int newtimeout;
char win_errbuf[PCAP_ERRBUF_SIZE+1];
if (nonblock) {
/*
@@ -1365,9 +1411,8 @@ pcap_setnonblock_npf(pcap_t *p, int nonblock)
newtimeout = p->opt.timeout;
}
if (!PacketSetReadTimeout(pw->adapter, newtimeout)) {
pcap_win32_err_to_str(GetLastError(), win_errbuf);
pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE,
"PacketSetReadTimeout: %s", win_errbuf);
pcap_fmt_errmsg_for_win32_err(p->errbuf, PCAP_ERRBUF_SIZE,
GetLastError(), "PacketSetReadTimeout");
return (-1);
}
pw->nonblock = (newtimeout == -1);
@@ -1684,7 +1729,6 @@ pcap_platform_finddevs(pcap_if_list_t *devlistp, char *errbuf)
char *AdaptersName;
ULONG NameLength;
char *name;
char our_errbuf[PCAP_ERRBUF_SIZE+1];
/*
* Find out how big a buffer we need.
@@ -1710,9 +1754,8 @@ pcap_platform_finddevs(pcap_if_list_t *devlistp, char *errbuf)
if (last_error != ERROR_INSUFFICIENT_BUFFER)
{
pcap_win32_err_to_str(last_error, our_errbuf);
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE,
"PacketGetAdapterNames: %s", our_errbuf);
pcap_fmt_errmsg_for_win32_err(errbuf, PCAP_ERRBUF_SIZE,
last_error, "PacketGetAdapterNames");
return (-1);
}
}
@@ -1727,9 +1770,8 @@ pcap_platform_finddevs(pcap_if_list_t *devlistp, char *errbuf)
}
if (!PacketGetAdapterNames(AdaptersName, &NameLength)) {
pcap_win32_err_to_str(GetLastError(), our_errbuf);
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "PacketGetAdapterNames: %s",
our_errbuf);
pcap_fmt_errmsg_for_win32_err(errbuf, PCAP_ERRBUF_SIZE,
GetLastError(), "PacketGetAdapterNames");
free(AdaptersName);
return (-1);
}
@@ -1818,7 +1860,6 @@ pcap_lookupdev(char *errbuf)
{
DWORD dwVersion;
DWORD dwWindowsMajorVersion;
char our_errbuf[PCAP_ERRBUF_SIZE+1];
#pragma warning (push)
#pragma warning (disable: 4996) /* disable MSVC's GetVersion() deprecated warning here */
@@ -1860,9 +1901,8 @@ pcap_lookupdev(char *errbuf)
if ( !PacketGetAdapterNames((PTSTR)TAdaptersName,&NameLength) )
{
pcap_win32_err_to_str(GetLastError(), our_errbuf);
(void)pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE,
"PacketGetAdapterNames: %s", our_errbuf);
pcap_fmt_errmsg_for_win32_err(errbuf, PCAP_ERRBUF_SIZE,
GetLastError(), "PacketGetAdapterNames");
free(TAdaptersName);
return NULL;
}
@@ -2000,59 +2040,48 @@ static const char *pcap_lib_version_string;
* tree. Include version.h from that source tree to get the WinPcap/Npcap
* version.
*
* XXX - it'd be nice if we could somehow generate the WinPcap version number
* when building WinPcap. (It'd be nice to do so for the packet.dll version
* number as well.)
* XXX - it'd be nice if we could somehow generate the WinPcap/Npcap version
* number when building as part of WinPcap/Npcap. (It'd be nice to do so
* for the packet.dll version number as well.)
*/
#include "../../version.h"
static const char pcap_version_string[] =
WINPCAP_PRODUCT_NAME " version " WINPCAP_VER_STRING ", based on " PCAP_VERSION_STRING;
static const char pcap_version_string_packet_dll_fmt[] =
WINPCAP_PRODUCT_NAME " version " WINPCAP_VER_STRING " (packet.dll version %s), based on " PCAP_VERSION_STRING;
const char *
pcap_lib_version(void)
{
char *packet_version_string;
size_t full_pcap_version_string_len;
char *full_pcap_version_string;
if (pcap_lib_version_string == NULL) {
/*
* Generate the version string.
*/
packet_version_string = PacketGetVersion();
char *packet_version_string = PacketGetVersion();
if (strcmp(WINPCAP_VER_STRING, packet_version_string) == 0) {
/*
* WinPcap version string and packet.dll version
* string are the same; just report the WinPcap
* WinPcap/Npcap version string and packet.dll version
* string are the same; just report the WinPcap/Npcap
* version.
*/
pcap_lib_version_string = pcap_version_string;
} else {
/*
* WinPcap version string and packet.dll version
* WinPcap/Npcap version string and packet.dll version
* string are different; that shouldn't be the
* case (the two libraries should come from the
* same version of WinPcap), so we report both
* same version of WinPcap/Npcap), so we report both
* versions.
*
* The -2 is for the %s in the format string,
* which will be replaced by packet_version_string.
*/
full_pcap_version_string_len =
(sizeof pcap_version_string_packet_dll_fmt - 2) +
strlen(packet_version_string);
full_pcap_version_string = malloc(full_pcap_version_string_len);
if (full_pcap_version_string == NULL)
return (NULL);
pcap_snprintf(full_pcap_version_string,
full_pcap_version_string_len,
pcap_version_string_packet_dll_fmt,
packet_version_string);
char *full_pcap_version_string;
if (pcap_asprintf(&full_pcap_version_string,
WINPCAP_PRODUCT_NAME " version " WINPCAP_VER_STRING " (packet.dll version %s), based on " PCAP_VERSION_STRING,
packet_version_string) != -1) {
/* Success */
pcap_lib_version_string = full_pcap_version_string;
}
}
pcap_lib_version_string = full_pcap_version_string;
}
return (pcap_lib_version_string);
}
@@ -2063,35 +2092,22 @@ pcap_lib_version(void)
* libpcap being built for Windows, not as part of a WinPcap/Npcap source
* tree.
*/
static const char pcap_version_string_packet_dll_fmt[] =
PCAP_VERSION_STRING " (packet.dll version %s)";
const char *
pcap_lib_version(void)
{
char *packet_version_string;
size_t full_pcap_version_string_len;
char *full_pcap_version_string;
if (pcap_lib_version_string == NULL) {
/*
* Generate the version string. Report the packet.dll
* version.
*
* The -2 is for the %s in the format string, which will
* be replaced by packet_version_string.
*/
packet_version_string = PacketGetVersion();
full_pcap_version_string_len =
(sizeof pcap_version_string_packet_dll_fmt - 2) +
strlen(packet_version_string);
full_pcap_version_string = malloc(full_pcap_version_string_len);
if (full_pcap_version_string == NULL)
return (NULL);
pcap_snprintf(full_pcap_version_string,
full_pcap_version_string_len,
pcap_version_string_packet_dll_fmt,
packet_version_string);
pcap_lib_version_string = full_pcap_version_string;
char *full_pcap_version_string;
if (pcap_asprintf(&full_pcap_version_string,
PCAP_VERSION_STRING " (packet.dll version %s)",
PacketGetVersion()) != -1) {
/* Success */
pcap_lib_version_string = full_pcap_version_string;
}
}
return (pcap_lib_version_string);
}

View File

@@ -32,12 +32,12 @@ static char nosup[] = "live packet capture not supported on this system";
pcap_t *
pcap_create_interface(const char *device _U_, char *ebuf)
{
(void)strlcpy(ebuf, nosup, PCAP_ERRBUF_SIZE);
(void)pcap_strlcpy(ebuf, nosup, PCAP_ERRBUF_SIZE);
return (NULL);
}
int
pcap_platform_finddevs(pcap_if_list_t *devlistp, char *errbuf)
pcap_platform_finddevs(pcap_if_list_t *devlistp _U_, char *errbuf _U_)
{
/*
* There are no interfaces on which we can capture.
@@ -50,7 +50,7 @@ int
pcap_lookupnet(const char *device _U_, bpf_u_int32 *netp _U_,
bpf_u_int32 *maskp _U_, char *errbuf)
{
(void)strlcpy(errbuf, nosup, PCAP_ERRBUF_SIZE);
(void)pcap_strlcpy(errbuf, nosup, PCAP_ERRBUF_SIZE);
return (-1);
}
#endif

View File

@@ -155,7 +155,6 @@ static void pcap_save_current_filter_rpcap(pcap_t *fp, const char *filter);
static int pcap_setfilter_rpcap(pcap_t *fp, struct bpf_program *prog);
static int pcap_setsampling_remote(pcap_t *fp);
static int pcap_startcapture_remote(pcap_t *fp);
static int rpcap_sendauth(SOCKET sock, uint8 *ver, struct pcap_rmtauth *auth, char *errbuf);
static int rpcap_recv_msg_header(SOCKET sock, struct rpcap_header *header, char *errbuf);
static int rpcap_check_msg_ver(SOCKET sock, uint8 expected_ver, struct rpcap_header *header, char *errbuf);
static int rpcap_check_msg_type(SOCKET sock, uint8 request_type, struct rpcap_header *header, uint16 *errcode, char *errbuf);
@@ -409,7 +408,7 @@ static int pcap_read_nocb_remote(pcap_t *p, struct pcap_pkthdr *pkt_header, u_ch
return 0;
}
#endif
sock_geterror("select(): ", p->errbuf, PCAP_ERRBUF_SIZE);
sock_geterror("select()", p->errbuf, PCAP_ERRBUF_SIZE);
return -1;
}
@@ -763,6 +762,8 @@ static void pcap_cleanup_rpcap(pcap_t *fp)
pr->currentfilter = NULL;
}
pcap_cleanup_live_common(fp);
/* To avoid inconsistencies in the number of sock_init() */
sock_cleanup();
}
@@ -1069,7 +1070,7 @@ static int pcap_startcapture_remote(pcap_t *fp)
saddrlen = sizeof(struct sockaddr_storage);
if (getpeername(pr->rmt_sockctrl, (struct sockaddr *) &saddr, &saddrlen) == -1)
{
sock_geterror("getsockname(): ", fp->errbuf, PCAP_ERRBUF_SIZE);
sock_geterror("getsockname()", fp->errbuf, PCAP_ERRBUF_SIZE);
goto error_nodiscard;
}
ai_family = ((struct sockaddr_storage *) &saddr)->ss_family;
@@ -1078,7 +1079,7 @@ static int pcap_startcapture_remote(pcap_t *fp)
if (getnameinfo((struct sockaddr *) &saddr, saddrlen, host,
sizeof(host), NULL, 0, NI_NUMERICHOST))
{
sock_geterror("getnameinfo(): ", fp->errbuf, PCAP_ERRBUF_SIZE);
sock_geterror("getnameinfo()", fp->errbuf, PCAP_ERRBUF_SIZE);
goto error_nodiscard;
}
@@ -1116,7 +1117,7 @@ static int pcap_startcapture_remote(pcap_t *fp)
saddrlen = sizeof(struct sockaddr_storage);
if (getsockname(sockdata, (struct sockaddr *) &saddr, &saddrlen) == -1)
{
sock_geterror("getsockname(): ", fp->errbuf, PCAP_ERRBUF_SIZE);
sock_geterror("getsockname()", fp->errbuf, PCAP_ERRBUF_SIZE);
goto error_nodiscard;
}
@@ -1124,7 +1125,7 @@ static int pcap_startcapture_remote(pcap_t *fp)
if (getnameinfo((struct sockaddr *) &saddr, saddrlen, NULL,
0, portdata, sizeof(portdata), NI_NUMERICSERV))
{
sock_geterror("getnameinfo(): ", fp->errbuf, PCAP_ERRBUF_SIZE);
sock_geterror("getnameinfo()", fp->errbuf, PCAP_ERRBUF_SIZE);
goto error_nodiscard;
}
}
@@ -1234,7 +1235,7 @@ static int pcap_startcapture_remote(pcap_t *fp)
if (socktemp == INVALID_SOCKET)
{
sock_geterror("accept(): ", fp->errbuf, PCAP_ERRBUF_SIZE);
sock_geterror("accept()", fp->errbuf, PCAP_ERRBUF_SIZE);
goto error;
}
@@ -1260,8 +1261,8 @@ static int pcap_startcapture_remote(pcap_t *fp)
res = getsockopt(sockdata, SOL_SOCKET, SO_RCVBUF, (char *)&sockbufsize, &itemp);
if (res == -1)
{
sock_geterror("pcap_startcapture_remote()", fp->errbuf, PCAP_ERRBUF_SIZE);
SOCK_DEBUG_MESSAGE(fp->errbuf);
sock_geterror("pcap_startcapture_remote(): getsockopt() failed", fp->errbuf, PCAP_ERRBUF_SIZE);
goto error;
}
/*
@@ -1612,21 +1613,19 @@ static int pcap_createfilter_norpcappkt(pcap_t *fp, struct bpf_program *prog)
char peeraddress[128];
char peerctrlport[128];
char *newfilter;
const int newstringsize = 1024;
size_t currentfiltersize;
/* Get the name/port of our peer */
saddrlen = sizeof(struct sockaddr_storage);
if (getpeername(pr->rmt_sockctrl, (struct sockaddr *) &saddr, &saddrlen) == -1)
{
sock_geterror("getpeername(): ", fp->errbuf, PCAP_ERRBUF_SIZE);
sock_geterror("getpeername()", fp->errbuf, PCAP_ERRBUF_SIZE);
return -1;
}
if (getnameinfo((struct sockaddr *) &saddr, saddrlen, peeraddress,
sizeof(peeraddress), peerctrlport, sizeof(peerctrlport), NI_NUMERICHOST | NI_NUMERICSERV))
{
sock_geterror("getnameinfo(): ", fp->errbuf, PCAP_ERRBUF_SIZE);
sock_geterror("getnameinfo()", fp->errbuf, PCAP_ERRBUF_SIZE);
return -1;
}
@@ -1634,7 +1633,7 @@ static int pcap_createfilter_norpcappkt(pcap_t *fp, struct bpf_program *prog)
/* Get the name/port of the current host */
if (getsockname(pr->rmt_sockctrl, (struct sockaddr *) &saddr, &saddrlen) == -1)
{
sock_geterror("getsockname(): ", fp->errbuf, PCAP_ERRBUF_SIZE);
sock_geterror("getsockname()", fp->errbuf, PCAP_ERRBUF_SIZE);
return -1;
}
@@ -1642,43 +1641,60 @@ static int pcap_createfilter_norpcappkt(pcap_t *fp, struct bpf_program *prog)
if (getnameinfo((struct sockaddr *) &saddr, saddrlen, myaddress,
sizeof(myaddress), myctrlport, sizeof(myctrlport), NI_NUMERICHOST | NI_NUMERICSERV))
{
sock_geterror("getnameinfo(): ", fp->errbuf, PCAP_ERRBUF_SIZE);
sock_geterror("getnameinfo()", fp->errbuf, PCAP_ERRBUF_SIZE);
return -1;
}
/* Let's now check the data port */
if (getsockname(pr->rmt_sockdata, (struct sockaddr *) &saddr, &saddrlen) == -1)
{
sock_geterror("getsockname(): ", fp->errbuf, PCAP_ERRBUF_SIZE);
sock_geterror("getsockname()", fp->errbuf, PCAP_ERRBUF_SIZE);
return -1;
}
/* Get the local port the system picked up */
if (getnameinfo((struct sockaddr *) &saddr, saddrlen, NULL, 0, mydataport, sizeof(mydataport), NI_NUMERICSERV))
{
sock_geterror("getnameinfo(): ", fp->errbuf, PCAP_ERRBUF_SIZE);
sock_geterror("getnameinfo()", fp->errbuf, PCAP_ERRBUF_SIZE);
return -1;
}
currentfiltersize = pr->currentfilter ? strlen(pr->currentfilter) : 0;
newfilter = (char *)malloc(currentfiltersize + newstringsize + 1);
if (currentfiltersize)
if (pr->currentfilter && pr->currentfilter[0] != '\0')
{
pcap_snprintf(newfilter, currentfiltersize + newstringsize,
"(%s) and not (host %s and host %s and port %s and port %s) and not (host %s and host %s and port %s)",
pr->currentfilter, myaddress, peeraddress, myctrlport, peerctrlport, myaddress, peeraddress, mydataport);
/*
* We have a current filter; add items to it to
* filter out this rpcap session.
*/
if (pcap_asprintf(&newfilter,
"(%s) and not (host %s and host %s and port %s and port %s) and not (host %s and host %s and port %s)",
pr->currentfilter, myaddress, peeraddress,
myctrlport, peerctrlport, myaddress, peeraddress,
mydataport) == -1)
{
/* Failed. */
pcap_snprintf(fp->errbuf, PCAP_ERRBUF_SIZE,
"Can't allocate memory for new filter");
return -1;
}
}
else
{
pcap_snprintf(newfilter, currentfiltersize + newstringsize,
"not (host %s and host %s and port %s and port %s) and not (host %s and host %s and port %s)",
myaddress, peeraddress, myctrlport, peerctrlport, myaddress, peeraddress, mydataport);
/*
* We have no current filter; construct a filter to
* filter out this rpcap session.
*/
if (pcap_asprintf(&newfilter,
"not (host %s and host %s and port %s and port %s) and not (host %s and host %s and port %s)",
myaddress, peeraddress, myctrlport, peerctrlport,
myaddress, peeraddress, mydataport) == -1)
{
/* Failed. */
pcap_snprintf(fp->errbuf, PCAP_ERRBUF_SIZE,
"Can't allocate memory for new filter");
return -1;
}
}
newfilter[currentfiltersize + newstringsize] = 0;
/*
* This is only an hack to prevent the save_current_filter
* routine, which will be called when we call pcap_compile(),
@@ -1785,16 +1801,25 @@ static int pcap_setsampling_remote(pcap_t *fp)
/*
* This function performs authentication and protocol version
* negotiation. It first tries to authenticate with the maximum
* version we support and, if that fails with an "I don't support
* that version" error from the server, and the version number in
* the reply from the server is one we support, tries again with
* that version.
* negotiation. It is required in order to open the connection
* with the other end party.
*
* It sends authentication parameters on the control socket and
* reads the reply. If the reply is a success indication, it
* checks whether the reply includes minimum and maximum supported
* versions from the server; if not, it assumes both are 0, as
* that means it's an older server that doesn't return supported
* version numbers in authentication replies, so it only supports
* version 0. It then tries to determine the maximum version
* supported both by us and by the server. If it can find such a
* version, it sets us up to use that version; otherwise, it fails,
* indicating that there is no version supported by us and by the
* server.
*
* \param sock: the socket we are currently using.
*
* \param ver: pointer to variable holding protocol version number to send
* and to set to the protocol version number in the reply.
* \param ver: pointer to variable to which to set the protocol version
* number we selected.
*
* \param auth: authentication parameters that have to be sent.
*
@@ -1807,96 +1832,17 @@ static int pcap_setsampling_remote(pcap_t *fp)
* an error message string is returned in the 'errbuf' variable.
*/
static int rpcap_doauth(SOCKET sockctrl, uint8 *ver, struct pcap_rmtauth *auth, char *errbuf)
{
int status;
/*
* Send authentication to the remote machine.
*
* First try with the maximum version number we support.
*/
*ver = RPCAP_MAX_VERSION;
status = rpcap_sendauth(sockctrl, ver, auth, errbuf);
if (status == 0)
{
//
// Success.
//
return 0;
}
if (status == -1)
{
/* Unrecoverable error. */
return -1;
}
/*
* The server doesn't support the version we used in the initial
* message, and it sent us back a reply either with the maximum
* version they do support, or with the version we sent, and we
* support that version. *ver has been set to that version; try
* authenticating again with that version.
*/
status = rpcap_sendauth(sockctrl, ver, auth, errbuf);
if (status == 0)
{
//
// Success.
//
return 0;
}
if (status == -1)
{
/* Unrecoverable error. */
return -1;
}
if (status == -2)
{
/*
* The server doesn't support that version, which
* means there is no version we both support, so
* this is a fatal error.
*/
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "The server doesn't support any protocol version that we support");
return -1;
}
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "rpcap_sendauth() returned %d", status);
return -1;
}
/*
* This function sends the authentication message.
*
* It sends the authentication parameters on the control socket.
* It is required in order to open the connection with the other end party.
*
* \param sock: the socket we are currently using.
*
* \param ver: pointer to variable holding protocol version number to send
* and to set to the protocol version number in the reply.
*
* \param auth: authentication parameters that have to be sent.
*
* \param errbuf: a pointer to a user-allocated buffer (of size
* PCAP_ERRBUF_SIZE) that will contain the error message (in case there
* is one). It could be a network problem or the fact that the authorization
* failed.
*
* \return '0' if everything is fine, '-2' if the server didn't reply with
* the protocol version we requested but replied with a version we do
* support, or '-1' for other errors. For errors, an error message string
* is returned in the 'errbuf' variable.
*/
static int rpcap_sendauth(SOCKET sock, uint8 *ver, struct pcap_rmtauth *auth, char *errbuf)
{
char sendbuf[RPCAP_NETBUF_SIZE]; /* temporary buffer in which data that has to be sent is buffered */
int sendbufidx = 0; /* index which keeps the number of bytes currently buffered */
uint16 length; /* length of the payload of this message */
uint16 errcode;
struct rpcap_auth *rpauth;
uint16 auth_type;
struct rpcap_header header;
size_t str_length;
uint32 plen;
struct rpcap_authreply authreply; /* authentication reply message */
uint8 ourvers;
if (auth)
{
@@ -1943,12 +1889,11 @@ static int rpcap_sendauth(SOCKET sock, uint8 *ver, struct pcap_rmtauth *auth, ch
length = sizeof(struct rpcap_auth);
}
if (sock_bufferize(NULL, sizeof(struct rpcap_header), NULL,
&sendbufidx, RPCAP_NETBUF_SIZE, SOCKBUF_CHECKONLY, errbuf, PCAP_ERRBUF_SIZE))
return -1;
rpcap_createhdr((struct rpcap_header *) sendbuf, *ver,
rpcap_createhdr((struct rpcap_header *) sendbuf, 0,
RPCAP_MSG_AUTH_REQ, 0, length);
rpauth = (struct rpcap_auth *) &sendbuf[sendbufidx];
@@ -1985,62 +1930,104 @@ static int rpcap_sendauth(SOCKET sock, uint8 *ver, struct pcap_rmtauth *auth, ch
rpauth->slen2 = htons(rpauth->slen2);
}
if (sock_send(sock, sendbuf, sendbufidx, errbuf, PCAP_ERRBUF_SIZE) < 0)
if (sock_send(sockctrl, sendbuf, sendbufidx, errbuf,
PCAP_ERRBUF_SIZE) < 0)
return -1;
/* Receive the reply */
if (rpcap_recv_msg_header(sock, &header, errbuf) == -1)
/* Receive and process the reply message header */
if (rpcap_process_msg_header(sockctrl, 0, RPCAP_MSG_AUTH_REQ,
&header, errbuf) == -1)
return -1;
if (rpcap_check_msg_type(sock, RPCAP_MSG_AUTH_REQ, &header,
&errcode, errbuf) == -1)
/*
* OK, it's an authentication reply, so we're logged in.
*
* Did it send any additional information?
*/
plen = header.plen;
if (plen != 0)
{
/* Error message - or something else, which is a protocol error. */
if (header.type == RPCAP_MSG_ERROR &&
errcode == PCAP_ERR_WRONGVER)
/* Yes - is it big enough to be version information? */
if (plen < sizeof(struct rpcap_authreply))
{
/*
* The server didn't support the version we sent,
* and replied with the maximum version it supports
* if our version was too big or with the version
* we sent if out version was too small.
*
* Do we also support it?
*/
if (!RPCAP_VERSION_IS_SUPPORTED(header.ver))
{
/*
* No, so there's no version we both support.
* This is an unrecoverable error.
*/
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "The server doesn't support any protocol version that we support");
return -1;
}
/*
* OK, use that version, and tell our caller to
* try again.
*/
*ver = header.ver;
return -2;
/* No - discard it and fail. */
(void)rpcap_discard(sockctrl, plen, NULL);
return -1;
}
/* Read the reply body */
if (rpcap_recv(sockctrl, (char *)&authreply,
sizeof(struct rpcap_authreply), &plen, errbuf) == -1)
{
(void)rpcap_discard(sockctrl, plen, NULL);
return -1;
}
/* Discard the rest of the message, if there is any. */
if (rpcap_discard(sockctrl, plen, errbuf) == -1)
return -1;
/*
* Other error - unrecoverable.
* Check the minimum and maximum versions for sanity;
* the minimum must be <= the maximum.
*/
return -1;
if (authreply.minvers > authreply.maxvers)
{
/*
* Bogus - give up on this server.
*/
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE,
"The server's minimum supported protocol version is greater than its maximum supported protocol version");
return -1;
}
}
else
{
/* No - it supports only version 0. */
authreply.minvers = 0;
authreply.maxvers = 0;
}
/*
* OK, it's an authentication reply, so they're OK with the
* protocol version we sent.
*
* Discard the rest of it.
* OK, let's start with the maximum version the server supports.
*/
if (rpcap_discard(sock, header.plen, errbuf) == -1)
return -1;
ourvers = authreply.maxvers;
#if RPCAP_MIN_VERSION != 0
/*
* If that's less than the minimum version we support, we
* can't communicate.
*/
if (ourvers < RPCAP_MIN_VERSION)
goto novers;
#endif
/*
* If that's greater than the maximum version we support,
* choose the maximum version we support.
*/
if (ourvers > RPCAP_MAX_VERSION)
{
ourvers = RPCAP_MAX_VERSION;
/*
* If that's less than the minimum version they
* support, we can't communicate.
*/
if (ourvers < authreply.minvers)
goto novers;
}
*ver = ourvers;
return 0;
novers:
/*
* There is no version we both support; that is a fatal error.
*/
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE,
"The server doesn't support any protocol version that we support");
return -1;
}
/* We don't currently support non-blocking mode. */
@@ -2060,6 +2047,103 @@ pcap_setnonblock_rpcap(pcap_t *p, int nonblock _U_)
return (-1);
}
static int
rpcap_setup_session(const char *source, struct pcap_rmtauth *auth,
int *activep, SOCKET *sockctrlp, uint8 *protocol_versionp,
char *host, char *port, char *iface, char *errbuf)
{
int type;
struct activehosts *activeconn; /* active connection, if there is one */
int error; /* 1 if rpcap_remoteact_getsock got an error */
/*
* Determine the type of the source (NULL, file, local, remote).
* You must have a valid source string even if we're in active mode,
* because otherwise the call to the following function will fail.
*/
if (pcap_parsesrcstr(source, &type, host, port, iface, errbuf) == -1)
return -1;
/*
* It must be remote.
*/
if (type != PCAP_SRC_IFREMOTE)
{
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE,
"Non-remote interface passed to remote capture routine");
return -1;
}
/* Warning: this call can be the first one called by the user. */
/* For this reason, we have to initialize the WinSock support. */
if (sock_init(errbuf, PCAP_ERRBUF_SIZE) == -1)
return -1;
/* Check for active mode */
activeconn = rpcap_remoteact_getsock(host, &error, errbuf);
if (activeconn != NULL)
{
*activep = 1;
*sockctrlp = activeconn->sockctrl;
*protocol_versionp = activeconn->protocol_version;
}
else
{
*activep = 0;
struct addrinfo hints; /* temp variable needed to resolve hostnames into to socket representation */
struct addrinfo *addrinfo; /* temp variable needed to resolve hostnames into to socket representation */
if (error)
{
/*
* Call failed.
*/
return -1;
}
/*
* We're not in active mode; let's try to open a new
* control connection.
*/
memset(&hints, 0, sizeof(struct addrinfo));
hints.ai_family = PF_UNSPEC;
hints.ai_socktype = SOCK_STREAM;
if (port[0] == 0)
{
/* the user chose not to specify the port */
if (sock_initaddress(host, RPCAP_DEFAULT_NETPORT,
&hints, &addrinfo, errbuf, PCAP_ERRBUF_SIZE) == -1)
return -1;
}
else
{
if (sock_initaddress(host, port, &hints, &addrinfo,
errbuf, PCAP_ERRBUF_SIZE) == -1)
return -1;
}
if ((*sockctrlp = sock_open(addrinfo, SOCKOPEN_CLIENT, 0,
errbuf, PCAP_ERRBUF_SIZE)) == INVALID_SOCKET)
{
freeaddrinfo(addrinfo);
return -1;
}
/* addrinfo is no longer used */
freeaddrinfo(addrinfo);
addrinfo = NULL;
if (rpcap_doauth(*sockctrlp, protocol_versionp, auth,
errbuf) == -1)
{
sock_close(*sockctrlp, NULL, 0);
return -1;
}
}
return 0;
}
/*
* This function opens a remote adapter by opening an RPCAP connection and
* so on.
@@ -2105,15 +2189,12 @@ pcap_t *pcap_open_rpcap(const char *source, int snaplen, int flags, int read_tim
char *source_str;
struct pcap_rpcap *pr; /* structure used when doing a remote live capture */
char host[PCAP_BUF_SIZE], ctrlport[PCAP_BUF_SIZE], iface[PCAP_BUF_SIZE];
struct activehosts *activeconn; /* active connection, if there is one */
int error; /* '1' if rpcap_remoteact_getsock returned an error */
SOCKET sockctrl;
uint8 protocol_version; /* negotiated protocol version */
int active;
uint32 plen;
char sendbuf[RPCAP_NETBUF_SIZE]; /* temporary buffer in which data to be sent is buffered */
int sendbufidx = 0; /* index which keeps the number of bytes currently buffered */
int retval; /* store the return value of the functions */
/* RPCAP-related variables */
struct rpcap_header header; /* header of the RPCAP packet */
@@ -2152,100 +2233,16 @@ pcap_t *pcap_open_rpcap(const char *source, int snaplen, int flags, int read_tim
pr->rmt_flags = flags;
/*
* determine the type of the source (NULL, file, local, remote)
* You must have a valid source string even if we're in active mode, because otherwise
* the call to the following function will fail.
* Attempt to set up the session with the server.
*/
if (pcap_parsesrcstr(fp->opt.device, &retval, host, ctrlport, iface, errbuf) == -1)
if (rpcap_setup_session(fp->opt.device, auth, &active, &sockctrl,
&protocol_version, host, ctrlport, iface, errbuf) == -1)
{
/* Session setup failed. */
pcap_close(fp);
return NULL;
}
if (retval != PCAP_SRC_IFREMOTE)
{
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "This function is able to open only remote interfaces");
pcap_close(fp);
return NULL;
}
/*
* Warning: this call can be the first one called by the user.
* For this reason, we have to initialize the WinSock support.
*/
if (sock_init(errbuf, PCAP_ERRBUF_SIZE) == -1)
{
pcap_close(fp);
return NULL;
}
/* Check for active mode */
activeconn = rpcap_remoteact_getsock(host, &error, errbuf);
if (activeconn != NULL)
{
sockctrl = activeconn->sockctrl;
protocol_version = activeconn->protocol_version;
active = 1;
}
else
{
struct addrinfo hints; /* temp, needed to open a socket connection */
struct addrinfo *addrinfo; /* temp, needed to open a socket connection */
if (error)
{
/*
* Call failed.
*/
pcap_close(fp);
return NULL;
}
/*
* We're not in active mode; let's try to open a new
* control connection.
*/
memset(&hints, 0, sizeof(struct addrinfo));
hints.ai_family = PF_UNSPEC;
hints.ai_socktype = SOCK_STREAM;
if (ctrlport[0] == 0)
{
/* the user chose not to specify the port */
if (sock_initaddress(host, RPCAP_DEFAULT_NETPORT, &hints, &addrinfo, errbuf, PCAP_ERRBUF_SIZE) == -1)
{
pcap_close(fp);
return NULL;
}
}
else
{
if (sock_initaddress(host, ctrlport, &hints, &addrinfo, errbuf, PCAP_ERRBUF_SIZE) == -1)
{
pcap_close(fp);
return NULL;
}
}
if ((sockctrl = sock_open(addrinfo, SOCKOPEN_CLIENT, 0, errbuf, PCAP_ERRBUF_SIZE)) == INVALID_SOCKET)
{
freeaddrinfo(addrinfo);
pcap_close(fp);
return NULL;
}
/* addrinfo is no longer used */
freeaddrinfo(addrinfo);
if (rpcap_doauth(sockctrl, &protocol_version, auth, errbuf) == -1)
{
sock_close(sockctrl, NULL, 0);
pcap_close(fp);
return NULL;
}
active = 0;
}
/*
* Now it's time to start playing with the RPCAP protocol
* RPCAP open command: create the request message
@@ -2277,7 +2274,7 @@ pcap_t *pcap_open_rpcap(const char *source, int snaplen, int flags, int read_tim
goto error;
/* Discard the rest of the message, if there is any. */
if (rpcap_discard(pr->rmt_sockctrl, plen, errbuf) == -1)
if (rpcap_discard(sockctrl, plen, errbuf) == -1)
goto error_nodiscard;
/* Set proper fields into the pcap_t struct */
@@ -2315,7 +2312,7 @@ error:
* We already reported an error; if this gets an error, just
* drive on.
*/
(void)rpcap_discard(pr->rmt_sockctrl, plen, NULL);
(void)rpcap_discard(sockctrl, plen, NULL);
error_nodiscard:
if (!active)
@@ -2327,8 +2324,10 @@ error_nodiscard:
/* String identifier to be used in the pcap_findalldevs_ex() */
#define PCAP_TEXT_SOURCE_ADAPTER "Network adapter"
#define PCAP_TEXT_SOURCE_ADAPTER_LEN (sizeof PCAP_TEXT_SOURCE_ADAPTER - 1)
/* String identifier to be used in the pcap_findalldevs_ex() */
#define PCAP_TEXT_SOURCE_ON_REMOTE_HOST "on remote node"
#define PCAP_TEXT_SOURCE_ON_REMOTE_HOST_LEN (sizeof PCAP_TEXT_SOURCE_ON_REMOTE_HOST - 1)
static void
freeaddr(struct pcap_addr *addr)
@@ -2341,10 +2340,8 @@ freeaddr(struct pcap_addr *addr)
}
int
pcap_findalldevs_ex_remote(char *source, struct pcap_rmtauth *auth, pcap_if_t **alldevs, char *errbuf)
pcap_findalldevs_ex_remote(const char *source, struct pcap_rmtauth *auth, pcap_if_t **alldevs, char *errbuf)
{
struct activehosts *activeconn; /* active connection, if there is one */
int error; /* '1' if rpcap_remoteact_getsock returned an error */
uint8 protocol_version; /* protocol version */
SOCKET sockctrl; /* socket descriptor of the control connection */
uint32 plen;
@@ -2352,7 +2349,6 @@ pcap_findalldevs_ex_remote(char *source, struct pcap_rmtauth *auth, pcap_if_t **
int i, j; /* temp variables */
int nif; /* Number of interfaces listed */
int active; /* 'true' if we the other end-party is in active mode */
int type;
char host[PCAP_BUF_SIZE], port[PCAP_BUF_SIZE];
char tmpstring[PCAP_BUF_SIZE + 1]; /* Needed to convert names and descriptions from 'old' syntax to the 'new' one */
pcap_if_t *lastdev; /* Last device in the pcap_if_t list */
@@ -2362,72 +2358,14 @@ pcap_findalldevs_ex_remote(char *source, struct pcap_rmtauth *auth, pcap_if_t **
(*alldevs) = NULL;
lastdev = NULL;
/* Retrieve the needed data for getting adapter list */
if (pcap_parsesrcstr(source, &type, host, port, NULL, errbuf) == -1)
return -1;
/* Warning: this call can be the first one called by the user. */
/* For this reason, we have to initialize the WinSock support. */
if (sock_init(errbuf, PCAP_ERRBUF_SIZE) == -1)
return -1;
/* Check for active mode */
activeconn = rpcap_remoteact_getsock(host, &error, errbuf);
if (activeconn != NULL)
/*
* Attempt to set up the session with the server.
*/
if (rpcap_setup_session(source, auth, &active, &sockctrl,
&protocol_version, host, port, NULL, errbuf) == -1)
{
sockctrl = activeconn->sockctrl;
protocol_version = activeconn->protocol_version;
active = 1;
}
else
{
struct addrinfo hints; /* temp variable needed to resolve hostnames into to socket representation */
struct addrinfo *addrinfo; /* temp variable needed to resolve hostnames into to socket representation */
if (error)
{
/*
* Call failed.
*/
return -1;
}
/*
* We're not in active mode; let's try to open a new
* control connection.
*/
memset(&hints, 0, sizeof(struct addrinfo));
hints.ai_family = PF_UNSPEC;
hints.ai_socktype = SOCK_STREAM;
if (port[0] == 0)
{
/* the user chose not to specify the port */
if (sock_initaddress(host, RPCAP_DEFAULT_NETPORT, &hints, &addrinfo, errbuf, PCAP_ERRBUF_SIZE) == -1)
return -1;
}
else
{
if (sock_initaddress(host, port, &hints, &addrinfo, errbuf, PCAP_ERRBUF_SIZE) == -1)
return -1;
}
if ((sockctrl = sock_open(addrinfo, SOCKOPEN_CLIENT, 0, errbuf, PCAP_ERRBUF_SIZE)) == INVALID_SOCKET)
{
freeaddrinfo(addrinfo);
return -1;
}
/* addrinfo is no longer used */
freeaddrinfo(addrinfo);
addrinfo = NULL;
if (rpcap_doauth(sockctrl, &protocol_version, auth, errbuf) == -1)
{
sock_close(sockctrl, NULL, 0);
return -1;
}
active = 0;
/* Session setup failed. */
return -1;
}
/* RPCAP findalldevs command */
@@ -2453,7 +2391,6 @@ pcap_findalldevs_ex_remote(char *source, struct pcap_rmtauth *auth, pcap_if_t **
{
struct rpcap_findalldevs_if findalldevs_if;
char tmpstring2[PCAP_BUF_SIZE + 1]; /* Needed to convert names and descriptions from 'old' syntax to the 'new' one */
size_t stringlen;
struct pcap_addr *addr, *prevaddr;
tmpstring2[PCAP_BUF_SIZE] = 0;
@@ -2515,21 +2452,17 @@ pcap_findalldevs_ex_remote(char *source, struct pcap_rmtauth *auth, pcap_if_t **
tmpstring[findalldevs_if.namelen] = 0;
/* Create the new device identifier */
if (pcap_createsrcstr(tmpstring2, PCAP_SRC_IFREMOTE, host, port, tmpstring, errbuf) == -1)
return -1;
if (pcap_createsrcstr(tmpstring2, PCAP_SRC_IFREMOTE,
host, port, tmpstring, errbuf) == -1)
goto error;
stringlen = strlen(tmpstring2);
dev->name = (char *)malloc(stringlen + 1);
dev->name = strdup(tmpstring2);
if (dev->name == NULL)
{
pcap_fmt_errmsg_for_errno(errbuf,
PCAP_ERRBUF_SIZE, errno, "malloc() failed");
goto error;
}
/* Copy the new device name into the correct memory location */
strlcpy(dev->name, tmpstring2, stringlen + 1);
}
if (findalldevs_if.desclen)
@@ -2547,22 +2480,14 @@ pcap_findalldevs_ex_remote(char *source, struct pcap_rmtauth *auth, pcap_if_t **
tmpstring[findalldevs_if.desclen] = 0;
pcap_snprintf(tmpstring2, sizeof(tmpstring2) - 1, "%s '%s' %s %s", PCAP_TEXT_SOURCE_ADAPTER,
tmpstring, PCAP_TEXT_SOURCE_ON_REMOTE_HOST, host);
stringlen = strlen(tmpstring2);
dev->description = (char *)malloc(stringlen + 1);
if (dev->description == NULL)
if (pcap_asprintf(&dev->description,
"%s '%s' %s %s", PCAP_TEXT_SOURCE_ADAPTER,
tmpstring, PCAP_TEXT_SOURCE_ON_REMOTE_HOST, host) == -1)
{
pcap_fmt_errmsg_for_errno(errbuf,
PCAP_ERRBUF_SIZE, errno, "malloc() failed");
goto error;
}
/* Copy the new device description into the correct memory location */
strlcpy(dev->description, tmpstring2, stringlen + 1);
}
dev->flags = ntohl(findalldevs_if.flags);
@@ -2731,7 +2656,6 @@ SOCKET pcap_remoteact_accept(const char *address, const char *port, const char *
{
if (sock_initaddress(address, RPCAP_DEFAULT_NETPORT_ACTIVE, &hints, &addrinfo, errbuf, PCAP_ERRBUF_SIZE) == -1)
{
SOCK_DEBUG_MESSAGE(errbuf);
return (SOCKET)-2;
}
}
@@ -2739,7 +2663,6 @@ SOCKET pcap_remoteact_accept(const char *address, const char *port, const char *
{
if (sock_initaddress(address, port, &hints, &addrinfo, errbuf, PCAP_ERRBUF_SIZE) == -1)
{
SOCK_DEBUG_MESSAGE(errbuf);
return (SOCKET)-2;
}
}
@@ -2747,7 +2670,6 @@ SOCKET pcap_remoteact_accept(const char *address, const char *port, const char *
if ((sockmain = sock_open(addrinfo, SOCKOPEN_SERVER, 1, errbuf, PCAP_ERRBUF_SIZE)) == INVALID_SOCKET)
{
SOCK_DEBUG_MESSAGE(errbuf);
freeaddrinfo(addrinfo);
return (SOCKET)-2;
}
@@ -2765,14 +2687,14 @@ SOCKET pcap_remoteact_accept(const char *address, const char *port, const char *
if (sockctrl == INVALID_SOCKET)
{
sock_geterror("accept(): ", errbuf, PCAP_ERRBUF_SIZE);
sock_geterror("accept()", errbuf, PCAP_ERRBUF_SIZE);
return (SOCKET)-2;
}
/* Get the numeric for of the name of the connecting host */
if (getnameinfo((struct sockaddr *) &from, fromlen, connectinghost, RPCAP_HOSTLIST_SIZE, NULL, 0, NI_NUMERICHOST))
{
sock_geterror("getnameinfo(): ", errbuf, PCAP_ERRBUF_SIZE);
sock_geterror("getnameinfo()", errbuf, PCAP_ERRBUF_SIZE);
rpcap_senderror(sockctrl, 0, PCAP_ERR_REMOTEACCEPT, errbuf, NULL);
sock_close(sockctrl, NULL, 0);
return (SOCKET)-1;
@@ -2971,7 +2893,7 @@ int pcap_remoteact_list(char *hostlist, char sep, int size, char *errbuf)
/* if (getnameinfo( (struct sockaddr *) &temp->host, sizeof (struct sockaddr_storage), hoststr, */
/* RPCAP_HOSTLIST_SIZE, NULL, 0, NI_NUMERICHOST) ) */
{
/* sock_geterror("getnameinfo(): ", errbuf, PCAP_ERRBUF_SIZE); */
/* sock_geterror("getnameinfo()", errbuf, PCAP_ERRBUF_SIZE); */
return -1;
}
@@ -2984,7 +2906,7 @@ int pcap_remoteact_list(char *hostlist, char sep, int size, char *errbuf)
return -1;
}
strlcat(hostlist, hoststr, PCAP_ERRBUF_SIZE);
pcap_strlcat(hostlist, hoststr, PCAP_ERRBUF_SIZE);
hostlist[len - 1] = sep;
hostlist[len] = 0;

View File

@@ -43,7 +43,7 @@ pcap_t *pcap_open_rpcap(const char *source, int snaplen, int flags,
/*
* Internal interfaces for "pcap_findalldevs_ex()".
*/
int pcap_findalldevs_ex_remote(char *source, struct pcap_rmtauth *auth,
pcap_if_t **alldevs, char *errbuf);
int pcap_findalldevs_ex_remote(const char *source,
struct pcap_rmtauth *auth, pcap_if_t **alldevs, char *errbuf);
#endif

View File

@@ -130,4 +130,4 @@ the packet not been truncated by the snapshot length. The two lengths
will be equal if the number of bytes of packet data are less than or
equal to the snapshot length.
.SH SEE ALSO
pcap(3PCAP), pcap-linktype(@MAN_MISC_INFO@)
pcap(3PCAP)

View File

@@ -1,15 +1,6 @@
/*
* pcap-septel.c: Packet capture interface for Intel/Septel card.
*
* The functionality of this code attempts to mimic that of pcap-linux as much
* as possible. This code is compiled in several different ways depending on
* whether SEPTEL_ONLY and HAVE_SEPTEL_API are defined. If HAVE_SEPTEL_API is
* not defined it should not get compiled in, otherwise if SEPTEL_ONLY is
* defined then the 'septel_' function calls are renamed to 'pcap_'
* equivalents. If SEPTEL_ONLY is not defined then nothing is altered - the
* septel_ functions will be called as required from their
* pcap-linux/equivalents.
*
* Authors: Gilbert HOYEK (gil_hoyek@hotmail.com), Elias M. KHOURY
* (+961 3 485243)
*/
@@ -182,7 +173,7 @@ loop:
static int
septel_inject(pcap_t *handle, const void *buf _U_, size_t size _U_)
{
strlcpy(handle->errbuf, "Sending packets isn't supported on Septel cards",
pcap_strlcpy(handle->errbuf, "Sending packets isn't supported on Septel cards",
PCAP_ERRBUF_SIZE);
return (-1);
}

View File

@@ -884,7 +884,7 @@ static void acn_start_monitor(int fd, int snaplen, int timeout, int promiscuous,
}
static int pcap_inject_acn(pcap_t *p, const void *buf _U_, size_t size _U_) {
strlcpy(p->errbuf, "Sending packets isn't supported on ACN adapters",
pcap_strlcpy(p->errbuf, "Sending packets isn't supported on ACN adapters",
PCAP_ERRBUF_SIZE);
return (-1);
}

View File

@@ -411,7 +411,7 @@ A { text-decoration:none }
<TR>
<TD VALIGN=TOP>Interface ID</TD>
<TD VALIGN=TOP ALIGN=CENTER>1</TD>
<TD VALIGN=TOP>A NULL to indicate an an empty 'interface ID'.</TD>
<TD VALIGN=TOP>A NULL to indicate an empty 'interface ID'.</TD>
</TR>
</TABLE>
</TD>

View File

@@ -182,8 +182,8 @@ snf_read(pcap_t *p, int cnt, pcap_handler callback, u_char *user)
hdr.caplen = caplen;
hdr.len = req.length;
callback(user, &hdr, req.pkt_addr);
n++;
}
n++;
/* After one successful packet is received, we won't block
* again for that timeout. */
@@ -237,7 +237,7 @@ snf_inject(pcap_t *p, const void *buf _U_, size_t size _U_)
return (-1);
}
#else
strlcpy(p->errbuf, "Sending packets isn't supported with this snf version",
pcap_strlcpy(p->errbuf, "Sending packets isn't supported with this snf version",
PCAP_ERRBUF_SIZE);
return (-1);
#endif

View File

@@ -123,7 +123,7 @@ static int TcSetDatalink(pcap_t *p, int dlt);
static int TcGetNonBlock(pcap_t *p);
static int TcSetNonBlock(pcap_t *p, int nonblock);
static void TcCleanup(pcap_t *p);
static int TcInject(pcap_t *p, const void *buf, size_t size);
static int TcInject(pcap_t *p, const void *buf, int size);
static int TcRead(pcap_t *p, int cnt, pcap_handler callback, u_char *user);
static int TcStats(pcap_t *p, struct pcap_stat *ps);
static int TcSetFilter(pcap_t *p, struct bpf_program *fp);
@@ -440,7 +440,7 @@ TcFindAllDevs(pcap_if_list_t *devlist, char *errbuf)
PTC_PORT pPorts = NULL;
TC_STATUS status;
int result = 0;
pcap_if_t *dev, *cursor;
pcap_if_t *dev;
ULONG i;
do
@@ -472,22 +472,7 @@ TcFindAllDevs(pcap_if_list_t *devlist, char *errbuf)
dev = TcCreatePcapIfFromPort(pPorts[i]);
if (dev != NULL)
{
/*
* append it at the end
*/
if (devlistp->beginning == NULL)
{
devlistp->beginning = dev;
}
else
{
for (cursor = devlistp->beginning;
cursor->next != NULL;
cursor = cursor->next);
cursor->next = dev;
}
}
add_dev(devlist, dev->name, dev->flags, dev->description, errbuf);
}
if (numPorts > 0)
@@ -846,7 +831,7 @@ static void TcCleanup(pcap_t *p)
}
/* Send a packet to the network */
static int TcInject(pcap_t *p, const void *buf, size_t size)
static int TcInject(pcap_t *p, const void *buf, int size)
{
struct pcap_tc *pt = p->priv;
TC_STATUS status;

View File

@@ -93,9 +93,9 @@ call and before a
call to specify the type of time stamp to be used on the device.
The time stamp types are listed here; the first value is the #define to
use in code, the second value is the value returned by
.B pcap_tstamp_type_val_to_name()
.B pcap_tstamp_type_val_to_name(3PCAP)
and accepted by
.BR pcap_tstamp_type_name_to_val() .
.BR pcap_tstamp_type_name_to_val(3PCAP) .
.RS 5
.TP 5
.BR PCAP_TSTAMP_HOST " - " host
@@ -149,9 +149,9 @@ call will fail, and the time stamps supplied after the
call will have microsecond resolution.
.LP
When opening a savefile, the
.BR pcap_open_offline_with_tstamp_precision (3PCAP)
.BR \%pcap_open_offline_with_tstamp_precision (3PCAP)
and
.BR pcap_fopen_offline_with_tstamp_precision (3PCAP)
.BR \%pcap_fopen_offline_with_tstamp_precision (3PCAP)
routines can be used to specify the resolution of time stamps to be read
from the file; if the time stamps in the file have a lower resolution,
the fraction-of-a-second portion of the time stamps will be scaled to
@@ -165,13 +165,4 @@ the time stamp supplied by the hardware or operating system and, when
reading a savefile, this does not indicate the actual precision of time
stamps in the file.
.SH SEE ALSO
.na
pcap_set_tstamp_type(3PCAP),
pcap_list_tstamp_types(3PCAP),
pcap_tstamp_type_val_to_name(3PCAP),
pcap_tstamp_type_name_to_val(3PCAP),
pcap_set_tstamp_precision(3PCAP),
pcap_open_offline_with_tstamp_precision(3PCAP),
\%pcap_fopen_offline_with_tstamp_precision(3PCAP),
\%pcap_get_tstamp_precision(3PCAP)
.ad
pcap(3PCAP)

View File

@@ -50,6 +50,7 @@
#include <stdlib.h>
#include <unistd.h>
#include <fcntl.h>
#include <limits.h>
#include <string.h>
#include <dirent.h>
#include <byteswap.h>
@@ -241,7 +242,7 @@ usb_dev_add(pcap_if_list_t *devlistp, int n, char *err_str)
*/
if (add_dev(devlistp, dev_name,
PCAP_IF_CONNECTION_STATUS_NOT_APPLICABLE,
"All USB buses", err_str) == NULL)
"Raw USB traffic, all USB buses", err_str) == NULL)
return -1;
} else {
/*
@@ -250,7 +251,7 @@ usb_dev_add(pcap_if_list_t *devlistp, int n, char *err_str)
* PCAP_IF_CONNECTION_STATUS_CONNECTED or
* PCAP_IF_CONNECTION_STATUS_DISCONNECTED?
*/
pcap_snprintf(dev_descr, 30, "USB bus number %d", n);
pcap_snprintf(dev_descr, 30, "Raw USB traffic, bus number %d", n);
if (add_dev(devlistp, dev_name, 0, dev_descr, err_str) == NULL)
return -1;
}
@@ -278,7 +279,7 @@ usb_findalldevs(pcap_if_list_t *devlistp, char *err_str)
* Split LINUX_USB_MON_DEV into a directory that we'll
* scan and a file name prefix that we'll check for.
*/
strlcpy(usb_mon_dir, LINUX_USB_MON_DEV, sizeof usb_mon_dir);
pcap_strlcpy(usb_mon_dir, LINUX_USB_MON_DEV, sizeof usb_mon_dir);
usb_mon_prefix = strrchr(usb_mon_dir, '/');
if (usb_mon_prefix == NULL) {
/*
@@ -380,18 +381,102 @@ usb_findalldevs(pcap_if_list_t *devlistp, char *err_str)
}
}
/*
* Matches what's in mon_bin.c in the Linux kernel.
*/
#define MIN_RING_SIZE (8*1024)
#define MAX_RING_SIZE (1200*1024)
static int
usb_set_ring_size(pcap_t* handle, int header_size)
{
/*
* A packet from binary usbmon has:
*
* 1) a fixed-length header, of size header_size;
* 2) descriptors, for isochronous transfers;
* 3) the payload.
*
* The kernel buffer has a size, defaulting to 300KB, with a
* minimum of 8KB and a maximum of 1200KB. The size is set with
* the MON_IOCT_RING_SIZE ioctl; the size passed in is rounded up
* to a page size.
*
* No more than {buffer size}/5 bytes worth of payload is saved.
* Therefore, if we subtract the fixed-length size from the
* snapshot length, we have the biggest payload we want (we
* don't worry about the descriptors - if we have descriptors,
* we'll just discard the last bit of the payload to get it
* to fit). We multiply that result by 5 and set the buffer
* size to that value.
*/
int ring_size;
if (handle->snapshot < header_size)
handle->snapshot = header_size;
/* The maximum snapshot size is small enough that this won't overflow */
ring_size = (handle->snapshot - header_size) * 5;
/*
* Will this get an error?
* (There's no wqy to query the minimum or maximum, so we just
* copy the value from the kernel source. We don't round it
* up to a multiple of the page size.)
*/
if (ring_size > MAX_RING_SIZE) {
/*
* Yes. Lower the ring size to the maximum, and set the
* snapshot length to the value that would give us a
* maximum-size ring.
*/
ring_size = MAX_RING_SIZE;
handle->snapshot = header_size + (MAX_RING_SIZE/5);
} else if (ring_size < MIN_RING_SIZE) {
/*
* Yes. Raise the ring size to the minimum, but leave
* the snapshot length unchanged, so we show the
* callback no more data than specified by the
* snapshot length.
*/
ring_size = MIN_RING_SIZE;
}
if (ioctl(handle->fd, MON_IOCT_RING_SIZE, ring_size) == -1) {
pcap_fmt_errmsg_for_errno(handle->errbuf, PCAP_ERRBUF_SIZE,
errno, "Can't set ring size from fd %d", handle->fd);
return -1;
}
return ring_size;
}
static
int usb_mmap(pcap_t* handle)
{
struct pcap_usb_linux *handlep = handle->priv;
int len = ioctl(handle->fd, MON_IOCQ_RING_SIZE);
if (len < 0)
int len;
/*
* Attempt to set the ring size as appropriate for the snapshot
* length, reducing the snapshot length if that'd make the ring
* bigger than the kernel supports.
*/
len = usb_set_ring_size(handle, (int)sizeof(pcap_usb_header_mmapped));
if (len == -1) {
/* Failed. Fall back on non-memory-mapped access. */
return 0;
}
handlep->mmapbuflen = len;
handlep->mmapbuf = mmap(0, handlep->mmapbuflen, PROT_READ,
MAP_SHARED, handle->fd, 0);
return handlep->mmapbuf != MAP_FAILED;
if (handlep->mmapbuf == MAP_FAILED) {
/*
* Failed. We don't treat that as a fatal error, we
* just try to fall back on non-memory-mapped access.
*/
return 0;
}
return 1;
}
#ifdef HAVE_LINUX_USBDEVICE_FS_H
@@ -514,6 +599,7 @@ usb_activate(pcap_t* handle)
{
struct pcap_usb_linux *handlep = handle->priv;
char full_path[USB_LINE_LEN];
int ret;
/*
* Turn a negative snapshot value (invalid), a snapshot value of
@@ -604,6 +690,7 @@ usb_activate(pcap_t* handle)
/* try to use fast mmap access */
if (usb_mmap(handle))
{
/* We succeeded. */
handle->linktype = DLT_USB_LINUX_MMAPPED;
handle->stats_op = usb_stats_linux_bin;
handle->read_op = usb_read_linux_mmap;
@@ -620,7 +707,19 @@ usb_activate(pcap_t* handle)
return 0;
}
/* can't mmap, use plain binary interface access */
/*
* We failed; try plain binary interface access.
*
* Attempt to set the ring size as appropriate for
* the snapshot length, reducing the snapshot length
* if that'd make the ring bigger than the kernel
* supports.
*/
if (usb_set_ring_size(handle, (int)sizeof(pcap_usb_header)) == -1) {
/* Failed. */
close(handle->fd);
return PCAP_ERROR;
}
handle->stats_op = usb_stats_linux_bin;
handle->read_op = usb_read_linux_bin;
#ifdef HAVE_LINUX_USBDEVICE_FS_H
@@ -646,38 +745,38 @@ usb_activate(pcap_t* handle)
handle->fd = open(full_path, O_RDONLY, 0);
}
if (handle->fd < 0) {
/*
* Is the problem that we didn't have
* sufficient permission to open it?
*/
if (errno == EACCES) {
if (errno == ENOENT)
{
/*
* Yes - return that error.
* The problem is that the file
* doesn't exist. Report that as
* "no such device". (That could
* mean "no such USB bus" or
* "monitoring not supported".)
*/
return PCAP_ERROR_PERM_DENIED;
ret = PCAP_ERROR_NO_SUCH_DEVICE;
}
/*
* No - was the problem something other
* than "it doesn't exist"?
*/
if (errno != ENOENT) {
else if (errno == EACCES)
{
/*
* Yes - return *that* error.
* The problem is that we don't
* have sufficient permission to
* open the file. Report that.
*/
pcap_fmt_errmsg_for_errno(handle->errbuf,
PCAP_ERRBUF_SIZE, errno,
"Can't open USB bus file %s",
full_path);
return PCAP_ERROR;
ret = PCAP_ERROR_PERM_DENIED;
}
/*
* No. Report that as "no such device".
* (That could mean "no such USB bus"
* or "monitoring not supported".)
*/
return PCAP_ERROR_NO_SUCH_DEVICE;
else
{
/*
* Some other error.
*/
ret = PCAP_ERROR;
}
pcap_fmt_errmsg_for_errno(handle->errbuf,
PCAP_ERRBUF_SIZE, errno,
"Can't open USB bus file %s",
full_path);
return ret;
}
}
@@ -923,8 +1022,8 @@ got:
static int
usb_inject_linux(pcap_t *handle, const void *buf _U_, size_t size _U_)
{
pcap_snprintf(handle->errbuf, PCAP_ERRBUF_SIZE, "inject not supported on "
"USB devices");
pcap_snprintf(handle->errbuf, PCAP_ERRBUF_SIZE,
"Packet injection is not supported on USB devices");
return (-1);
}
@@ -973,6 +1072,10 @@ usb_stats_linux(pcap_t *handle, struct pcap_stat *stats)
}
string[ret] = 0;
stats->ps_recv = handlep->packets_read;
stats->ps_drop = 0; /* unless we find text_lost */
stats->ps_ifdrop = 0;
/* extract info on dropped urbs */
for (consumed=0; consumed < ret; ) {
/* from the sscanf man page:
@@ -989,18 +1092,16 @@ usb_stats_linux(pcap_t *handle, struct pcap_stat *stats)
break;
consumed += cnt;
ptr += cnt;
if (strcmp(token, "nreaders") == 0)
ret = sscanf(ptr, "%d", &stats->ps_drop);
if (strcmp(token, "text_lost") == 0)
ntok = sscanf(ptr, "%d%n", &stats->ps_drop, &cnt);
else
ret = sscanf(ptr, "%d", &dummy);
if (ntok != 1)
ntok = sscanf(ptr, "%d%n", &dummy, &cnt);
if ((ntok != 1) || (cnt < 0))
break;
consumed += cnt;
ptr += cnt;
}
stats->ps_recv = handlep->packets_read;
stats->ps_ifdrop = 0;
return 0;
}
@@ -1069,13 +1170,44 @@ usb_read_linux_bin(pcap_t *handle, int max_packets _U_, pcap_handler callback, u
return -1;
}
/* we can get less that than really captured from kernel, depending on
* snaplen, so adjust header accordingly */
/*
* info.hdr->data_len is the number of bytes of isochronous
* descriptors (if any) plus the number of bytes of data
* provided. There are no isochronous descriptors here,
* because we're using the old 48-byte header.
*
* If info.hdr->data_flag is non-zero, there's no URB data;
* info.hdr->urb_len is the size of the buffer into which
* data is to be placed; it does not represent the amount
* of data transferred. If info.hdr->data_flag is zero,
* there is URB data, and info.hdr->urb_len is the number
* of bytes transmitted or received; it doesn't include
* isochronous descriptors.
*
* The kernel may give us more data than the snaplen; if it did,
* reduce the data length so that the total number of bytes we
* tell our client we have is not greater than the snaplen.
*/
if (info.hdr->data_len < clen)
clen = info.hdr->data_len;
info.hdr->data_len = clen;
pkth.caplen = clen + sizeof(pcap_usb_header);
pkth.len = info.hdr->data_len + sizeof(pcap_usb_header);
pkth.caplen = sizeof(pcap_usb_header) + clen;
if (info.hdr->data_flag) {
/*
* No data; just base the on-the-wire length on
* info.hdr->data_len (so that it's >= the captured
* length).
*/
pkth.len = sizeof(pcap_usb_header) + info.hdr->data_len;
} else {
/*
* We got data; base the on-the-wire length on
* info.hdr->urb_len, so that it includes data
* discarded by the USB monitor device due to
* its buffer being too small.
*/
pkth.len = sizeof(pcap_usb_header) + info.hdr->urb_len;
}
pkth.ts.tv_sec = info.hdr->ts_sec;
pkth.ts.tv_usec = info.hdr->ts_usec;
@@ -1102,12 +1234,12 @@ usb_read_linux_mmap(pcap_t *handle, int max_packets, pcap_handler callback, u_ch
struct mon_bin_mfetch fetch;
int32_t vec[VEC_SIZE];
struct pcap_pkthdr pkth;
pcap_usb_header* hdr;
pcap_usb_header_mmapped* hdr;
int nflush = 0;
int packets = 0;
u_int clen, max_clen;
max_clen = handle->snapshot - sizeof(pcap_usb_header);
max_clen = handle->snapshot - sizeof(pcap_usb_header_mmapped);
for (;;) {
int i, ret;
@@ -1145,19 +1277,52 @@ usb_read_linux_mmap(pcap_t *handle, int max_packets, pcap_handler callback, u_ch
nflush = fetch.nfetch;
for (i=0; i<fetch.nfetch; ++i) {
/* discard filler */
hdr = (pcap_usb_header*) &handlep->mmapbuf[vec[i]];
hdr = (pcap_usb_header_mmapped*) &handlep->mmapbuf[vec[i]];
if (hdr->event_type == '@')
continue;
/* we can get less that than really captured from kernel, depending on
* snaplen, so adjust header accordingly */
/*
* hdr->data_len is the number of bytes of
* isochronous descriptors (if any) plus the
* number of bytes of data provided.
*
* If hdr->data_flag is non-zero, there's no
* URB data; hdr->urb_len is the size of the
* buffer into which data is to be placed; it does
* not represent the amount of data transferred.
* If hdr->data_flag is zero, there is URB data,
* and hdr->urb_len is the number of bytes
* transmitted or received; it doesn't include
* isochronous descriptors.
*
* The kernel may give us more data than the
* snaplen; if it did, reduce the data length
* so that the total number of bytes we
* tell our client we have is not greater than
* the snaplen.
*/
clen = max_clen;
if (hdr->data_len < clen)
clen = hdr->data_len;
/* get packet info from header*/
pkth.caplen = clen + sizeof(pcap_usb_header_mmapped);
pkth.len = hdr->data_len + sizeof(pcap_usb_header_mmapped);
pkth.caplen = sizeof(pcap_usb_header_mmapped) + clen;
if (hdr->data_flag) {
/*
* No data; just base the on-the-wire length
* on hdr->data_len (so that it's >= the
* captured length).
*/
pkth.len = sizeof(pcap_usb_header_mmapped) +
hdr->data_len;
} else {
/*
* We got data; base the on-the-wire length
* on hdr->urb_len, so that it includes
* data discarded by the USB monitor device
* due to its buffer being too small.
*/
pkth.len = sizeof(pcap_usb_header_mmapped) +
(hdr->ndesc * sizeof (usb_isodesc)) + hdr->urb_len;
}
pkth.ts.tv_sec = hdr->ts_sec;
pkth.ts.tv_usec = hdr->ts_usec;

View File

@@ -17,7 +17,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP 3PCAP "20 April 2018"
.TH PCAP 3PCAP "25 July 2018"
.SH NAME
pcap \- Packet Capture library
.SH SYNOPSIS
@@ -191,6 +191,10 @@ expires even if no packets have arrived.
.IP
The packet buffer timeout is set with
.BR pcap_set_timeout ().
.IP "immediate mode"
In immediate mode, packets are always delivered as soon as they arrive,
with no buffering. Immediate mode is set with
.BR pcap_set_immediate_mode ().
.IP "buffer size"
Packets that arrive for a capture are stored in a buffer, so that they
do not have to be read by the application as soon as they arrive. On
@@ -416,6 +420,11 @@ set packet buffer timeout for a not-yet-activated
.B pcap_t
for live capture
.TP
.BR pcap_set_immediate_mode (3PCAP)
set immediate mode for a not-yet-activated
.B pcap_t
for live capture
.TP
.BR pcap_set_buffer_size (3PCAP)
set buffer size for a not-yet-activated
.B pcap_t
@@ -632,9 +641,28 @@ or other routines a platform offers to wait for any of a set of
descriptors to be ready to read. To obtain, for a handle, a descriptor
that can be used in those routines, call
.BR pcap_get_selectable_fd ().
If the routine indicates that data is
available to read on the descriptor, an attempt should be made to read
from the device.
.PP
Not all handles have such a descriptor available;
.BR pcap_get_selectable_fd ()
will return \-1 if no such descriptor exists. In addition, for various
will return
.B PCAP_ERROR
if no such descriptor is available. If no such
descriptor is available, this may be because the device must be polled
periodically for packets; in that case,
.BR pcap_get_required_select_timeout ()
will return a pointer to a
.B struct timeval
whose value can be used as a timeout in those routines. When the
routine returns, an attmept should be made to read packets from the
device. If
.BR pcap_get_required_select_timeout ()
returns NULL, no such timeout is available, and those routines cannot be
used with the device.
.PP
In addition, for various
reasons, one or more of those routines will not work properly with the
descriptor; the documentation for
.BR pcap_get_selectable_fd ()
@@ -693,6 +721,15 @@ that can be used in calls such as
.BR select (2)
and
.BR poll (2)
.TP
.BR pcap_get_required_select_timeout (3PCAP)
if no descriptor usable with
.BR select (2)
and
.BR poll (2)
is available for the
.BR pcap_t ,
attempt to get a timeout usable with those routines
.RE
.SS Filters
In order to cause only certain packets to be returned when reading
@@ -890,7 +927,7 @@ To get a string giving version information about libpcap, call
.BR pcap_lib_version (3PCAP)
get library version string
.RE
.SH BACKWARDS COMPATIBILITY
.SH BACKWARD COMPATIBILITY
.PP
In versions of libpcap prior to 1.0, the
.B pcap.h

View File

@@ -139,7 +139,7 @@ BOOL WINAPI DllMain(
/*
* Start WinSock.
* Exported in case some applications using WinPcap called it,
* Exported in case some applications using WinPcap/Npcap called it,
* even though it wasn't exported.
*/
int
@@ -186,76 +186,165 @@ pcap_wsockinit(void)
PCAP_API char pcap_version[];
PCAP_API_DEF char pcap_version[] = PACKAGE_VERSION;
static int
pcap_not_initialized(pcap_t *pcap)
static void
pcap_set_not_initialized_message(pcap_t *pcap)
{
if (pcap->activated) {
/* A module probably forgot to set the function pointer */
(void)pcap_snprintf(pcap->errbuf, sizeof(pcap->errbuf),
"This operation isn't properly handled by that device");
return (PCAP_ERROR);
return;
}
/* in case the caller doesn't check for PCAP_ERROR_NOT_ACTIVATED */
(void)pcap_snprintf(pcap->errbuf, sizeof(pcap->errbuf),
"This handle hasn't been activated yet");
}
static int
pcap_read_not_initialized(pcap_t *pcap, int cnt _U_, pcap_handler callback _U_,
u_char *user _U_)
{
pcap_set_not_initialized_message(pcap);
/* this means 'not initialized' */
return (PCAP_ERROR_NOT_ACTIVATED);
}
static int
pcap_inject_not_initialized(pcap_t *pcap, const void * buf _U_, size_t size _U_)
{
pcap_set_not_initialized_message(pcap);
/* this means 'not initialized' */
return (PCAP_ERROR_NOT_ACTIVATED);
}
static int
pcap_setfilter_not_initialized(pcap_t *pcap, struct bpf_program *fp _U_)
{
pcap_set_not_initialized_message(pcap);
/* this means 'not initialized' */
return (PCAP_ERROR_NOT_ACTIVATED);
}
static int
pcap_setdirection_not_initialized(pcap_t *pcap, pcap_direction_t d _U_)
{
pcap_set_not_initialized_message(pcap);
/* this means 'not initialized' */
return (PCAP_ERROR_NOT_ACTIVATED);
}
static int
pcap_set_datalink_not_initialized(pcap_t *pcap, int dlt _U_)
{
pcap_set_not_initialized_message(pcap);
/* this means 'not initialized' */
return (PCAP_ERROR_NOT_ACTIVATED);
}
static int
pcap_getnonblock_not_initialized(pcap_t *pcap)
{
pcap_set_not_initialized_message(pcap);
/* this means 'not initialized' */
return (PCAP_ERROR_NOT_ACTIVATED);
}
static int
pcap_stats_not_initialized(pcap_t *pcap, struct pcap_stat *ps _U_)
{
pcap_set_not_initialized_message(pcap);
/* this means 'not initialized' */
return (PCAP_ERROR_NOT_ACTIVATED);
}
#ifdef _WIN32
static void *
pcap_not_initialized_ptr(pcap_t *pcap)
struct pcap_stat *
pcap_stats_ex_not_initialized(pcap_t *pcap, int *pcap_stat_size _U_)
{
if (pcap->activated) {
/* A module probably forgot to set the function pointer */
(void)pcap_snprintf(pcap->errbuf, sizeof(pcap->errbuf),
"This operation isn't properly handled by that device");
return (NULL);
}
(void)pcap_snprintf(pcap->errbuf, sizeof(pcap->errbuf),
"This handle hasn't been activated yet");
pcap_set_not_initialized_message(pcap);
return (NULL);
}
static int
pcap_setbuff_not_initialized(pcap_t *pcap, int dim _U_)
{
pcap_set_not_initialized_message(pcap);
/* this means 'not initialized' */
return (PCAP_ERROR_NOT_ACTIVATED);
}
static int
pcap_setmode_not_initialized(pcap_t *pcap, int mode _U_)
{
pcap_set_not_initialized_message(pcap);
/* this means 'not initialized' */
return (PCAP_ERROR_NOT_ACTIVATED);
}
static int
pcap_setmintocopy_not_initialized(pcap_t *pcap, int size _U_)
{
pcap_set_not_initialized_message(pcap);
/* this means 'not initialized' */
return (PCAP_ERROR_NOT_ACTIVATED);
}
static HANDLE
pcap_getevent_not_initialized(pcap_t *pcap)
{
if (pcap->activated) {
/* A module probably forgot to set the function pointer */
(void)pcap_snprintf(pcap->errbuf, sizeof(pcap->errbuf),
"This operation isn't properly handled by that device");
return (INVALID_HANDLE_VALUE);
}
(void)pcap_snprintf(pcap->errbuf, sizeof(pcap->errbuf),
"This handle hasn't been activated yet");
pcap_set_not_initialized_message(pcap);
return (INVALID_HANDLE_VALUE);
}
static int
pcap_oid_get_request_not_initialized(pcap_t *pcap, bpf_u_int32 oid _U_,
void *data _U_, size_t *lenp _U_)
{
pcap_set_not_initialized_message(pcap);
return (PCAP_ERROR_NOT_ACTIVATED);
}
static int
pcap_oid_set_request_not_initialized(pcap_t *pcap, bpf_u_int32 oid _U_,
const void *data _U_, size_t *lenp _U_)
{
pcap_set_not_initialized_message(pcap);
return (PCAP_ERROR_NOT_ACTIVATED);
}
static u_int
pcap_sendqueue_transmit_not_initialized(pcap_t *pcap, pcap_send_queue* queue, int sync)
{
if (pcap->activated) {
/* A module probably forgot to set the function pointer */
(void)pcap_snprintf(pcap->errbuf, sizeof(pcap->errbuf),
"This operation isn't properly handled by that device");
return (0);
}
(void)pcap_snprintf(pcap->errbuf, sizeof(pcap->errbuf),
"This handle hasn't been activated yet");
pcap_set_not_initialized_message(pcap);
return (0);
}
static int
pcap_setuserbuffer_not_initialized(pcap_t *pcap, int size _U_)
{
pcap_set_not_initialized_message(pcap);
return (PCAP_ERROR_NOT_ACTIVATED);
}
static int
pcap_live_dump_not_initialized(pcap_t *pcap, char *filename _U_, int maxsize _U_,
int maxpacks _U_)
{
pcap_set_not_initialized_message(pcap);
return (PCAP_ERROR_NOT_ACTIVATED);
}
static int
pcap_live_dump_ended_not_initialized(pcap_t *pcap, int sync _U_)
{
pcap_set_not_initialized_message(pcap);
return (PCAP_ERROR_NOT_ACTIVATED);
}
static PAirpcapHandle
pcap_get_airpcap_handle_not_initialized(pcap_t *pcap)
{
if (pcap->activated) {
/* A module probably forgot to set the function pointer */
(void)pcap_snprintf(pcap->errbuf, sizeof(pcap->errbuf),
"This operation isn't properly handled by that device");
return (NULL);
}
(void)pcap_snprintf(pcap->errbuf, sizeof(pcap->errbuf),
"This handle hasn't been activated yet");
pcap_set_not_initialized_message(pcap);
return (NULL);
}
#endif
@@ -296,8 +385,17 @@ pcap_list_tstamp_types(pcap_t *p, int **tstamp_typesp)
if (p->tstamp_type_count == 0) {
/*
* We don't support multiple time stamp types.
* That means the only type we support is PCAP_TSTAMP_HOST;
* set up a list containing only that type.
*/
*tstamp_typesp = NULL;
*tstamp_typesp = (int*)malloc(sizeof(**tstamp_typesp));
if (*tstamp_typesp == NULL) {
pcap_fmt_errmsg_for_errno(p->errbuf, sizeof(p->errbuf),
errno, "malloc");
return (PCAP_ERROR);
}
**tstamp_typesp = PCAP_TSTAMP_HOST;
return (1);
} else {
*tstamp_typesp = (int*)calloc(sizeof(**tstamp_typesp),
p->tstamp_type_count);
@@ -308,8 +406,8 @@ pcap_list_tstamp_types(pcap_t *p, int **tstamp_typesp)
}
(void)memcpy(*tstamp_typesp, p->tstamp_type_list,
sizeof(**tstamp_typesp) * p->tstamp_type_count);
return (p->tstamp_type_count);
}
return (p->tstamp_type_count);
}
/*
@@ -659,7 +757,7 @@ get_if_description(const char *name)
* Get the description for the interface.
*/
memset(&ifrdesc, 0, sizeof ifrdesc);
strlcpy(ifrdesc.ifr_name, name, sizeof ifrdesc.ifr_name);
pcap_strlcpy(ifrdesc.ifr_name, name, sizeof ifrdesc.ifr_name);
s = socket(AF_INET, SOCK_DGRAM, 0);
if (s >= 0) {
#ifdef __FreeBSD__
@@ -710,7 +808,7 @@ get_if_description(const char *name)
}
#endif /* __FreeBSD__ */
close(s);
if (description != NULL && strlen(description) == 0) {
if (description != NULL && description[0] == '\0') {
/*
* Description is empty, so discard it.
*/
@@ -741,20 +839,13 @@ get_if_description(const char *name)
* OK, it's a valid number that's not
* bigger than INT_MAX. Construct
* a description from it.
* (If that fails, we don't worry about
* it, we just return NULL.)
*/
static const char descr_prefix[] = "USB bus number ";
size_t descr_size;
/*
* Allow enough room for a 32-bit bus number.
* sizeof (descr_prefix) includes the
* terminating NUL.
*/
descr_size = sizeof (descr_prefix) + 10;
description = malloc(descr_size);
if (description != NULL) {
pcap_snprintf(description, descr_size,
"%s%ld", descr_prefix, busnum);
if (pcap_asprintf(&description,
"USB bus number %ld", busnum) == -1) {
/* Failed. */
description = NULL;
}
}
}
@@ -1292,14 +1383,14 @@ pcap_lookupdev(char *errbuf)
* 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",
(void)pcap_strlcpy(errbuf, "no suitable device found",
PCAP_ERRBUF_SIZE);
ret = NULL;
} else {
/*
* Return the name of the first device on the list.
*/
(void)strlcpy(device, alldevs->name, sizeof(device));
(void)pcap_strlcpy(device, alldevs->name, sizeof(device));
ret = device;
}
@@ -1366,7 +1457,7 @@ pcap_lookupnet(const char *device, bpf_u_int32 *netp, bpf_u_int32 *maskp,
/* XXX Work around Linux kernel bug */
ifr.ifr_addr.sa_family = AF_INET;
#endif
(void)strlcpy(ifr.ifr_name, device, sizeof(ifr.ifr_name));
(void)pcap_strlcpy(ifr.ifr_name, device, sizeof(ifr.ifr_name));
if (ioctl(fd, SIOCGIFADDR, (char *)&ifr) < 0) {
if (errno == EADDRNOTAVAIL) {
(void)pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE,
@@ -1385,7 +1476,7 @@ pcap_lookupnet(const char *device, bpf_u_int32 *netp, bpf_u_int32 *maskp,
/* XXX Work around Linux kernel bug */
ifr.ifr_addr.sa_family = AF_INET;
#endif
(void)strlcpy(ifr.ifr_name, device, sizeof(ifr.ifr_name));
(void)pcap_strlcpy(ifr.ifr_name, device, sizeof(ifr.ifr_name));
if (ioctl(fd, SIOCGIFNETMASK, (char *)&ifr) < 0) {
pcap_fmt_errmsg_for_errno(errbuf, PCAP_ERRBUF_SIZE,
errno, "SIOCGIFNETMASK: %s", device);
@@ -1575,13 +1666,14 @@ pcap_parse_source(const char *source, char **schemep, char **userinfop,
* the pathname.
*/
if (pcap_strcasecmp(scheme, "file") == 0) {
*schemep = scheme;
*pathp = strdup(colonp + 3);
if (*pathp == NULL) {
pcap_fmt_errmsg_for_errno(ebuf, PCAP_ERRBUF_SIZE,
errno, "malloc");
free(scheme);
return (-1);
}
*schemep = scheme;
return (0);
}
@@ -1684,7 +1776,12 @@ pcap_parse_source(const char *source, char **schemep, char **userinfop,
* Treat verything up to the closing square
* bracket as the IP-Literal; we don't worry
* about whether it's a valid IPv6address or
* IPvFuture.
* IPvFuture (or an IPv4address, for that
* matter, just in case we get handed a
* URL with an IPv4 IP-Literal, of the sort
* that pcap_createsrcstr() used to generate,
* and that pcap_parsesrcstr(), in the original
* WinPcap code, accepted).
*/
bracketp = strchr(parsep, ']');
if (bracketp == NULL) {
@@ -1805,9 +1902,9 @@ pcap_createsrcstr(char *source, int type, const char *host, const char *port,
switch (type) {
case PCAP_SRC_FILE:
strlcpy(source, PCAP_SRC_FILE_STRING, PCAP_BUF_SIZE);
pcap_strlcpy(source, PCAP_SRC_FILE_STRING, PCAP_BUF_SIZE);
if (name != NULL && *name != '\0') {
strlcat(source, name, PCAP_BUF_SIZE);
pcap_strlcat(source, name, PCAP_BUF_SIZE);
return (0);
} else {
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE,
@@ -1816,7 +1913,7 @@ pcap_createsrcstr(char *source, int type, const char *host, const char *port,
}
case PCAP_SRC_IFREMOTE:
strlcpy(source, PCAP_SRC_IF_STRING, PCAP_BUF_SIZE);
pcap_strlcpy(source, PCAP_SRC_IF_STRING, PCAP_BUF_SIZE);
if (host != NULL && *host != '\0') {
if (strchr(host, ':') != NULL) {
/*
@@ -1824,18 +1921,18 @@ pcap_createsrcstr(char *source, int type, const char *host, const char *port,
* probably an IPv6 address, and needs to
* be included in square brackets.
*/
strlcat(source, "[", PCAP_BUF_SIZE);
strlcat(source, host, PCAP_BUF_SIZE);
strlcat(source, "]", PCAP_BUF_SIZE);
pcap_strlcat(source, "[", PCAP_BUF_SIZE);
pcap_strlcat(source, host, PCAP_BUF_SIZE);
pcap_strlcat(source, "]", PCAP_BUF_SIZE);
} else
strlcat(source, host, PCAP_BUF_SIZE);
pcap_strlcat(source, host, PCAP_BUF_SIZE);
if (port != NULL && *port != '\0') {
strlcat(source, ":", PCAP_BUF_SIZE);
strlcat(source, port, PCAP_BUF_SIZE);
pcap_strlcat(source, ":", PCAP_BUF_SIZE);
pcap_strlcat(source, port, PCAP_BUF_SIZE);
}
strlcat(source, "/", PCAP_BUF_SIZE);
pcap_strlcat(source, "/", PCAP_BUF_SIZE);
} else {
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE,
"The host name cannot be NULL.");
@@ -1843,15 +1940,15 @@ pcap_createsrcstr(char *source, int type, const char *host, const char *port,
}
if (name != NULL && *name != '\0')
strlcat(source, name, PCAP_BUF_SIZE);
pcap_strlcat(source, name, PCAP_BUF_SIZE);
return (0);
case PCAP_SRC_IFLOCAL:
strlcpy(source, PCAP_SRC_IF_STRING, PCAP_BUF_SIZE);
pcap_strlcpy(source, PCAP_SRC_IF_STRING, PCAP_BUF_SIZE);
if (name != NULL && *name != '\0')
strlcat(source, name, PCAP_BUF_SIZE);
pcap_strlcat(source, name, PCAP_BUF_SIZE);
return (0);
@@ -1890,7 +1987,7 @@ pcap_parsesrcstr(const char *source, int *type, char *host, char *port,
* Local device.
*/
if (name && tmppath)
strlcpy(name, tmppath, PCAP_BUF_SIZE);
pcap_strlcpy(name, tmppath, PCAP_BUF_SIZE);
if (type)
*type = PCAP_SRC_IFLOCAL;
free(tmppath);
@@ -1912,12 +2009,12 @@ pcap_parsesrcstr(const char *source, int *type, char *host, char *port,
pcap_snprintf(host, PCAP_BUF_SIZE, "%s@%s",
tmpuserinfo, tmphost);
else
strlcpy(host, tmphost, PCAP_BUF_SIZE);
pcap_strlcpy(host, tmphost, PCAP_BUF_SIZE);
}
if (port && tmpport)
strlcpy(port, tmpport, PCAP_BUF_SIZE);
pcap_strlcpy(port, tmpport, PCAP_BUF_SIZE);
if (name && tmppath)
strlcpy(name, tmppath, PCAP_BUF_SIZE);
pcap_strlcpy(name, tmppath, PCAP_BUF_SIZE);
if (type)
*type = PCAP_SRC_IFREMOTE;
free(tmppath);
@@ -1933,7 +2030,7 @@ pcap_parsesrcstr(const char *source, int *type, char *host, char *port,
* file://
*/
if (name && tmppath)
strlcpy(name, tmppath, PCAP_BUF_SIZE);
pcap_strlcpy(name, tmppath, PCAP_BUF_SIZE);
if (type)
*type = PCAP_SRC_FILE;
free(tmppath);
@@ -1949,7 +2046,7 @@ pcap_parsesrcstr(const char *source, int *type, char *host, char *port,
* as a local device.
*/
if (name)
strlcpy(name, source, PCAP_BUF_SIZE);
pcap_strlcpy(name, source, PCAP_BUF_SIZE);
if (type)
*type = PCAP_SRC_IFLOCAL;
free(tmppath);
@@ -1981,11 +2078,28 @@ pcap_create(const char *device, char *errbuf)
else {
#ifdef _WIN32
/*
* If the string appears to be little-endian UCS-2/UTF-16,
* convert it to ASCII.
* On Windows, for backwards compatibility reasons,
* pcap_lookupdev() returns a pointer to a sequence of
* pairs of UTF-16LE device names and local code page
* description strings.
*
* XXX - to UTF-8 instead? Or report an error if any
* character isn't ASCII?
* This means that if a program uses pcap_lookupdev()
* to get a default device, and hands that to an API
* that opens devices, we'll get handed a UTF-16LE
* string, not a string in the local code page.
*
* To work around that, we check whether the string
* looks as if it might be a UTF-16LE strinh and, if
* so, convert it back to the local code page's
* extended ASCII.
*
* XXX - you *cannot* reliably detect whether a
* string is UTF-16LE or not; "a" could either
* be a one-character ASCII string or the first
* character of a UTF-16LE string. This particular
* version of this heuristic dates back to WinPcap
* 4.1.1; PacketOpenAdapter() does uses the same
* heuristic, with the exact same vulnerability.
*/
if (device[0] != '\0' && device[1] == '\0') {
size_t length;
@@ -2077,25 +2191,25 @@ initialize_ops(pcap_t *p)
* an activated pcap_t to point to a routine that returns
* a "this isn't activated" error.
*/
p->read_op = (read_op_t)pcap_not_initialized;
p->inject_op = (inject_op_t)pcap_not_initialized;
p->setfilter_op = (setfilter_op_t)pcap_not_initialized;
p->setdirection_op = (setdirection_op_t)pcap_not_initialized;
p->set_datalink_op = (set_datalink_op_t)pcap_not_initialized;
p->getnonblock_op = (getnonblock_op_t)pcap_not_initialized;
p->stats_op = (stats_op_t)pcap_not_initialized;
p->read_op = pcap_read_not_initialized;
p->inject_op = pcap_inject_not_initialized;
p->setfilter_op = pcap_setfilter_not_initialized;
p->setdirection_op = pcap_setdirection_not_initialized;
p->set_datalink_op = pcap_set_datalink_not_initialized;
p->getnonblock_op = pcap_getnonblock_not_initialized;
p->stats_op = pcap_stats_not_initialized;
#ifdef _WIN32
p->stats_ex_op = (stats_ex_op_t)pcap_not_initialized_ptr;
p->setbuff_op = (setbuff_op_t)pcap_not_initialized;
p->setmode_op = (setmode_op_t)pcap_not_initialized;
p->setmintocopy_op = (setmintocopy_op_t)pcap_not_initialized;
p->stats_ex_op = pcap_stats_ex_not_initialized;
p->setbuff_op = pcap_setbuff_not_initialized;
p->setmode_op = pcap_setmode_not_initialized;
p->setmintocopy_op = pcap_setmintocopy_not_initialized;
p->getevent_op = pcap_getevent_not_initialized;
p->oid_get_request_op = (oid_get_request_op_t)pcap_not_initialized;
p->oid_set_request_op = (oid_set_request_op_t)pcap_not_initialized;
p->oid_get_request_op = pcap_oid_get_request_not_initialized;
p->oid_set_request_op = pcap_oid_set_request_not_initialized;
p->sendqueue_transmit_op = pcap_sendqueue_transmit_not_initialized;
p->setuserbuffer_op = (setuserbuffer_op_t)pcap_not_initialized;
p->live_dump_op = (live_dump_op_t)pcap_not_initialized;
p->live_dump_ended_op = (live_dump_ended_op_t)pcap_not_initialized;
p->setuserbuffer_op = pcap_setuserbuffer_not_initialized;
p->live_dump_op = pcap_live_dump_not_initialized;
p->live_dump_ended_op = pcap_live_dump_ended_not_initialized;
p->get_airpcap_handle_op = pcap_get_airpcap_handle_not_initialized;
#endif
@@ -2133,7 +2247,7 @@ pcap_alloc_pcap_t(char *ebuf, size_t size)
* require 8-byte alignment even on platforms with 32-bit
* integers.
*/
#define PCAP_T_ALIGNED_SIZE ((sizeof(pcap_t) + 7) & ~0x7)
#define PCAP_T_ALIGNED_SIZE ((sizeof(pcap_t) + 7U) & ~0x7U)
chunk = malloc(PCAP_T_ALIGNED_SIZE + size);
if (chunk == NULL) {
pcap_fmt_errmsg_for_errno(ebuf, PCAP_ERRBUF_SIZE,
@@ -2460,6 +2574,16 @@ pcap_open_live(const char *device, int snaplen, int promisc, int to_ms, char *er
char name[PCAP_BUF_SIZE + 1];
int srctype;
/*
* A null device name is equivalent to the "any" device -
* which might not be supported on this platform, but
* this means that you'll get a "not supported" error
* rather than, say, a crash when we try to dereference
* the null pointer.
*/
if (device == NULL)
device = "any";
/*
* Retrofit - we have to make older applications compatible with
* remote capture.
@@ -2531,13 +2655,13 @@ pcap_open_live(const char *device, int snaplen, int promisc, int to_ms, char *er
return (p);
fail:
if (status == PCAP_ERROR)
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "%s: %s", device,
p->errbuf);
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "%s: %.*s", device,
PCAP_ERRBUF_SIZE - 3, p->errbuf);
else if (status == PCAP_ERROR_NO_SUCH_DEVICE ||
status == PCAP_ERROR_PERM_DENIED ||
status == PCAP_ERROR_PROMISC_PERM_DENIED)
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "%s: %s (%s)", device,
pcap_statustostr(status), p->errbuf);
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "%s: %s (%.*s)", device,
pcap_statustostr(status), PCAP_ERRBUF_SIZE - 6, p->errbuf);
else
pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "%s: %s", device,
pcap_statustostr(status));
@@ -2850,7 +2974,7 @@ static struct dlt_choice dlt_choices[] = {
DLT_CHOICE(FRELAY, "Frame Relay"),
DLT_CHOICE(LOOP, "OpenBSD loopback"),
DLT_CHOICE(ENC, "OpenBSD encapsulated IP"),
DLT_CHOICE(LINUX_SLL, "Linux cooked"),
DLT_CHOICE(LINUX_SLL, "Linux cooked v1"),
DLT_CHOICE(LTALK, "Localtalk"),
DLT_CHOICE(PFLOG, "OpenBSD pflog file"),
DLT_CHOICE(PFSYNC, "Packet filter state syncing"),
@@ -2884,7 +3008,7 @@ static struct dlt_choice dlt_choices[] = {
DLT_CHOICE(GPF_T, "GPF-T"),
DLT_CHOICE(GPF_F, "GPF-F"),
DLT_CHOICE(JUNIPER_PIC_PEER, "Juniper PIC Peer"),
DLT_CHOICE(ERF_ETH, "Ethernet with Endace ERF header"),
DLT_CHOICE(ERF_ETH, "Ethernet with Endace ERF header"),
DLT_CHOICE(ERF_POS, "Packet-over-SONET with Endace ERF header"),
DLT_CHOICE(LINUX_LAPD, "Linux vISDN LAPD"),
DLT_CHOICE(JUNIPER_ETHER, "Juniper Ethernet"),
@@ -2908,10 +3032,11 @@ static struct dlt_choice dlt_choices[] = {
DLT_CHOICE(SITA, "SITA pseudo-header"),
DLT_CHOICE(ERF, "Endace ERF header"),
DLT_CHOICE(RAIF1, "Ethernet with u10 Networks pseudo-header"),
DLT_CHOICE(IPMB, "IPMB"),
DLT_CHOICE(IPMB_KONTRON, "IPMB with Kontron pseudo-header"),
DLT_CHOICE(JUNIPER_ST, "Juniper Secure Tunnel"),
DLT_CHOICE(BLUETOOTH_HCI_H4_WITH_PHDR, "Bluetooth HCI UART transport layer plus pseudo-header"),
DLT_CHOICE(AX25_KISS, "AX.25 with KISS header"),
DLT_CHOICE(IPMB_LINUX, "IPMB with Linux/Pigeon Point pseudo-header"),
DLT_CHOICE(IEEE802_15_4_NONASK_PHY, "IEEE 802.15.4 with non-ASK PHY data"),
DLT_CHOICE(MPLS, "MPLS with label as link-layer header"),
DLT_CHOICE(LINUX_EVDEV, "Linux evdev events"),
@@ -2968,6 +3093,7 @@ static struct dlt_choice dlt_choices[] = {
DLT_CHOICE(DOCSIS31_XRA31, "Excentis XRA-31 DOCSIS 3.1 RF sniffer frames"),
DLT_CHOICE(ETHERNET_MPACKET, "802.3br mPackets"),
DLT_CHOICE(DISPLAYPORT_AUX, "DisplayPort AUX channel monitoring data"),
DLT_CHOICE(LINUX_SLL2, "Linux cooked v2"),
DLT_CHOICE_SENTINEL
};
@@ -3007,6 +3133,21 @@ pcap_datalink_val_to_description(int dlt)
return (NULL);
}
const char *
pcap_datalink_val_to_description_or_dlt(int dlt)
{
static char unkbuf[40];
const char *description;
description = pcap_datalink_val_to_description(dlt);
if (description != NULL) {
return description;
} else {
(void)pcap_snprintf(unkbuf, sizeof(unkbuf), "DLT %u", dlt);
return unkbuf;
}
}
struct tstamp_type_choice {
const char *name;
const char *description;
@@ -3159,7 +3300,7 @@ pcap_getnonblock(pcap_t *p, char *errbuf)
* We copy the error message to errbuf, so callers
* can find it in either place.
*/
strlcpy(errbuf, p->errbuf, PCAP_ERRBUF_SIZE);
pcap_strlcpy(errbuf, p->errbuf, PCAP_ERRBUF_SIZE);
}
return (ret);
}
@@ -3203,7 +3344,7 @@ pcap_setnonblock(pcap_t *p, int nonblock, char *errbuf)
* We copy the error message to errbuf, so callers
* can find it in either place.
*/
strlcpy(errbuf, p->errbuf, PCAP_ERRBUF_SIZE);
pcap_strlcpy(errbuf, p->errbuf, PCAP_ERRBUF_SIZE);
}
return (ret);
}
@@ -3239,35 +3380,6 @@ pcap_setnonblock_fd(pcap_t *p, int nonblock)
}
#endif
#ifdef _WIN32
/*
* Generate a string for a Win32-specific error (i.e. an error generated when
* calling a Win32 API).
* For errors occurred during standard C calls, we still use pcap_strerror()
*/
void
pcap_win32_err_to_str(DWORD error, char *errbuf)
{
size_t errlen;
char *p;
FormatMessageA(FORMAT_MESSAGE_FROM_SYSTEM, NULL, error, 0, errbuf,
PCAP_ERRBUF_SIZE, NULL);
/*
* "FormatMessage()" "helpfully" sticks CR/LF at the end of the
* message. Get rid of it.
*/
errlen = strlen(errbuf);
if (errlen >= 2) {
errbuf[errlen - 1] = '\0';
errbuf[errlen - 2] = '\0';
}
p = strchr(errbuf, '\0');
pcap_snprintf (p, PCAP_ERRBUF_SIZE+1-(p-errbuf), " (%lu)", error);
}
#endif
/*
* Generate error strings for PCAP_ERROR_ and PCAP_WARNING_ values.
*/
@@ -3339,7 +3451,7 @@ pcap_strerror(int errnum)
errno_t err = strerror_s(errbuf, PCAP_ERRBUF_SIZE, errnum);
if (err != 0) /* err = 0 if successful */
strlcpy(errbuf, "strerror_s() error", PCAP_ERRBUF_SIZE);
pcap_strlcpy(errbuf, "strerror_s() error", PCAP_ERRBUF_SIZE);
return (errbuf);
#else
return (strerror(errnum));
@@ -3561,7 +3673,7 @@ pcap_do_addexit(pcap_t *p)
/*
* "atexit()" failed; let our caller know.
*/
strlcpy(p->errbuf, "atexit failed", PCAP_ERRBUF_SIZE);
pcap_strlcpy(p->errbuf, "atexit failed", PCAP_ERRBUF_SIZE);
return (0);
}
did_atexit = 1;

View File

@@ -238,16 +238,6 @@ struct bpf_insn {
bpf_u_int32 k;
};
/*
* Auxiliary data, for use when interpreting a filter intended for the
* Linux kernel when the kernel rejects the filter (requiring us to
* run it in userland). It contains VLAN tag information.
*/
struct bpf_aux_data {
u_short vlan_tag_present;
u_short vlan_tag;
};
/*
* Macros for insn array initializers.
*/
@@ -256,7 +246,6 @@ struct bpf_aux_data {
PCAP_API int bpf_validate(const struct bpf_insn *, int);
PCAP_API u_int bpf_filter(const struct bpf_insn *, const u_char *, u_int, u_int);
extern u_int bpf_filter_with_aux_data(const struct bpf_insn *, const u_char *, u_int, u_int, const struct bpf_aux_data *);
/*
* Number of scratch memory words (for BPF_LD|BPF_MEM and BPF_ST).

View File

@@ -160,4 +160,4 @@
(__HP_aCC >= ((major)*10000 + (minor)*100))
#endif
#endif /* lib_pcap_funcattrs_h */
#endif /* lib_pcap_compiler_tests_h */

View File

@@ -246,7 +246,7 @@
*/
/*
* This is for Linux cooked sockets.
* Linux cooked sockets.
*/
#define DLT_LINUX_SLL 113
@@ -769,11 +769,20 @@
#define DLT_RAIF1 198
/*
* IPMB packet for IPMI, beginning with the I2C slave address, followed
* by the netFn and LUN, etc.. Requested by Chanthy Toeung
* <chanthy.toeung@ca.kontron.com>.
* IPMB packet for IPMI, beginning with a 2-byte header, followed by
* the I2C slave address, followed by the netFn and LUN, etc..
* Requested by Chanthy Toeung <chanthy.toeung@ca.kontron.com>.
*
* XXX - this used to be called DLT_IPMB, back when we got the
* impression from the email thread requesting it that the packet
* had no extra 2-byte header. We've renamed it; if anybody used
* DLT_IPMB and assumed no 2-byte header, this will cause the compile
* to fail, at which point we'll have to figure out what to do about
* the two header types using the same DLT_/LINKTYPE_ value. If that
* doesn't happen, we'll assume nobody used it and that the redefinition
* is safe.
*/
#define DLT_IPMB 199
#define DLT_IPMB_KONTRON 199
/*
* Juniper-private data link type, as per request from
@@ -805,15 +814,34 @@
#define DLT_LAPD 203
/*
* Variants of various link-layer headers, with a one-byte direction
* pseudo-header prepended - zero means "received by this host",
* non-zero (any non-zero value) means "sent by this host" - as per
* Will Barker <w.barker@zen.co.uk>.
* PPP, with a one-byte direction pseudo-header prepended - zero means
* "received by this host", non-zero (any non-zero value) means "sent by
* this host" - as per Will Barker <w.barker@zen.co.uk>.
*/
#define DLT_PPP_WITH_DIR 204 /* PPP - don't confuse with DLT_PPP_WITH_DIRECTION */
#define DLT_C_HDLC_WITH_DIR 205 /* Cisco HDLC */
#define DLT_FRELAY_WITH_DIR 206 /* Frame Relay */
#define DLT_LAPB_WITH_DIR 207 /* LAPB */
#define DLT_PPP_WITH_DIR 204 /* Don't confuse with DLT_PPP_WITH_DIRECTION */
/*
* Cisco HDLC, with a one-byte direction pseudo-header prepended - zero
* means "received by this host", non-zero (any non-zero value) means
* "sent by this host" - as per Will Barker <w.barker@zen.co.uk>.
*/
#define DLT_C_HDLC_WITH_DIR 205
/*
* Frame Relay, with a one-byte direction pseudo-header prepended - zero
* means "received by this host" (DCE -> DTE), non-zero (any non-zero
* value) means "sent by this host" (DTE -> DCE) - as per Will Barker
* <w.barker@zen.co.uk>.
*/
#define DLT_FRELAY_WITH_DIR 206
/*
* LAPB, with a one-byte direction pseudo-header prepended - zero means
* "received by this host" (DCE -> DTE), non-zero (any non-zero value)
* means "sent by this host" (DTE -> DCE)- as per Will Barker
* <w.barker@zen.co.uk>.
*/
#define DLT_LAPB_WITH_DIR 207
/*
* 208 is reserved for an as-yet-unspecified proprietary link-layer
@@ -1367,6 +1395,11 @@
*/
#define DLT_DISPLAYPORT_AUX 275
/*
* Linux cooked sockets v2.
*/
#define DLT_LINUX_SLL2 276
/*
* In case the code that includes this file (directly or indirectly)
* has also included OS files that happen to define DLT_MATCHING_MAX,
@@ -1377,7 +1410,7 @@
#ifdef DLT_MATCHING_MAX
#undef DLT_MATCHING_MAX
#endif
#define DLT_MATCHING_MAX 275 /* highest value in the "matching" range */
#define DLT_MATCHING_MAX 276 /* highest value in the "matching" range */
/*
* DLT and savefile link type values are split into a class and

View File

@@ -164,10 +164,11 @@
|| PCAP_IS_AT_LEAST_XL_C_VERSION(10,1) \
|| PCAP_IS_AT_LEAST_HP_C_VERSION(6,10)
/*
* Compiler with support for __attribute((noreturn)), or GCC 2.5 and
* later, or Solaris Studio 12 (Sun C 5.9) and later, or IBM XL C 10.1
* and later (do any earlier versions of XL C support this?), or
* HP aCC A.06.10 and later.
* Compiler with support for __attribute((noreturn)), or GCC 2.5 or
* later, or some compiler asserting compatibility with GCC 2.5 or
* later, or Solaris Studio 12 (Sun C 5.9) or later, or IBM XL C 10.1
* or later (do any earlier versions of XL C support this?), or HP aCC
* A.06.10 or later.
*/
#define PCAP_NORETURN __attribute((noreturn))
#define PCAP_NORETURN_DEF __attribute((noreturn))
@@ -193,7 +194,8 @@
|| PCAP_IS_AT_LEAST_XL_C_VERSION(10,1) \
|| PCAP_IS_AT_LEAST_HP_C_VERSION(6,10)
/*
* Compiler with support for it, or GCC 2.3 and later, or IBM XL C 10.1
* Compiler with support for it, or GCC 2.3 or later, or some compiler
* asserting compatibility with GCC 2.3 or later, or IBM XL C 10.1
* and later (do any earlier versions of XL C support this?),
* or HP aCC A.06.10 and later.
*/
@@ -216,7 +218,7 @@
|| PCAP_IS_AT_LEAST_SUNC_VERSION(5,13)
/*
* Compiler that supports __has_attribute and __attribute__((deprecated)),
* or GCC 4.5 and later, or Sun/Oracle C 12.4 (Sun C 5.13) or later.
* or GCC 4.5 or later, or Sun/Oracle C 12.4 (Sun C 5.13) or later.
*
* Those support __attribute__((deprecated(msg))) (we assume, perhaps
* incorrectly, that anything that supports __has_attribute() is

View File

@@ -106,12 +106,23 @@
#define PRIu64 "llu"
#endif
#endif
/*
* MSVC's support library doesn't support %zu to print a size_t until
* Visual Studio 2017, but supports %Iu earlier, so use that.
*/
#define PRIsize "Iu"
#elif defined(__MINGW32__) || !defined(_WIN32)
/*
* Compiler is MinGW or target is UN*X or MS-DOS. Just use
* <inttypes.h>.
*/
#include <inttypes.h>
/*
* Assume the support library supports %zu; it's required by C99.
*/
#define PRIsize "zu"
#endif
#endif /* pcap/pcap-inttypes.h */

View File

@@ -84,6 +84,8 @@
#include <sys/time.h>
#endif /* _WIN32/MSDOS/UN*X */
#include <pcap/socket.h> /* for SOCKET, as the active-mode rpcap APIs use it */
#ifndef PCAP_DONT_INCLUDE_PCAP_BPF_H
#include <pcap/bpf.h>
#endif
@@ -468,6 +470,7 @@ PCAP_API void pcap_free_datalinks(int *);
PCAP_API int pcap_datalink_name_to_val(const char *);
PCAP_API const char *pcap_datalink_val_to_name(int);
PCAP_API const char *pcap_datalink_val_to_description(int);
PCAP_API const char *pcap_datalink_val_to_description_or_dlt(int);
PCAP_API int pcap_snapshot(pcap_t *);
PCAP_API int pcap_is_swapped(pcap_t *);
PCAP_API int pcap_major_version(pcap_t *);
@@ -483,7 +486,28 @@ PCAP_API int pcap_fileno(pcap_t *);
#endif
PCAP_API pcap_dumper_t *pcap_dump_open(pcap_t *, const char *);
PCAP_API pcap_dumper_t *pcap_dump_fopen(pcap_t *, FILE *fp);
#ifdef _WIN32
PCAP_API pcap_dumper_t *pcap_dump_hopen(pcap_t *, intptr_t);
/*
* If we're building libpcap, this is an internal routine in sf-pcap.c, so
* we must not define it as a macro.
*
* If we're not building libpcap, given that the version of the C runtime
* with which libpcap was built might be different from the version
* of the C runtime with which an application using libpcap was built,
* and that a FILE structure may differ between the two versions of the
* C runtime, calls to _fileno() must use the version of _fileno() in
* the C runtime used to open the FILE *, not the version in the C
* runtime with which libpcap was built. (Maybe once the Universal CRT
* rules the world, this will cease to be a problem.)
*/
#ifndef BUILDING_PCAP
#define pcap_dump_fopen(p,f) \
pcap_dump_hopen(p, _get_osfhandle(_fileno(f)))
#endif
#else /*_WIN32*/
PCAP_API pcap_dumper_t *pcap_dump_fopen(pcap_t *, FILE *fp);
#endif /*_WIN32*/
PCAP_API pcap_dumper_t *pcap_dump_open_append(pcap_t *, const char *);
PCAP_API FILE *pcap_dump_file(pcap_dumper_t *);
PCAP_API long pcap_dump_ftell(pcap_dumper_t *);
@@ -858,8 +882,8 @@ PCAP_API int pcap_parsesrcstr(const char *source, int *type, char *host,
* For listing remote capture devices, pcap_findalldevs_ex() is currently
* the only API available.
*/
PCAP_API int pcap_findalldevs_ex(char *source, struct pcap_rmtauth *auth,
pcap_if_t **alldevs, char *errbuf);
PCAP_API int pcap_findalldevs_ex(const char *source,
struct pcap_rmtauth *auth, pcap_if_t **alldevs, char *errbuf);
/*
* Sampling methods.
@@ -937,27 +961,6 @@ PCAP_API struct pcap_samp *pcap_setsampling(pcap_t *p);
/* Maximum length of an host name (needed for the RPCAP active mode) */
#define RPCAP_HOSTLIST_SIZE 1024
/*
* Some minor differences between UN*X sockets and and Winsock sockets.
*/
#ifndef _WIN32
/*!
* \brief In Winsock, a socket handle is of type SOCKET; in UN*X, it's
* a file descriptor, and therefore a signed integer.
* We define SOCKET to be a signed integer on UN*X, so that it can
* be used on both platforms.
*/
#define SOCKET int
/*!
* \brief In Winsock, the error return if socket() fails is INVALID_SOCKET;
* in UN*X, it's -1.
* We define INVALID_SOCKET to be -1 on UN*X, so that it can be used on
* both platforms.
*/
#define INVALID_SOCKET -1
#endif
PCAP_API SOCKET pcap_remoteact_accept(const char *address, const char *port,
const char *hostlist, char *connectinghost,
struct pcap_rmtauth *auth, char *errbuf);

View File

@@ -74,27 +74,44 @@
#ifndef lib_pcap_sll_h
#define lib_pcap_sll_h
#include <pcap/pcap-inttypes.h>
/*
* A DLT_LINUX_SLL fake link-layer header.
*/
#define SLL_HDR_LEN 16 /* total header length */
#define SLL_ADDRLEN 8 /* length of address field */
#include <pcap/pcap-inttypes.h>
struct sll_header {
uint16_t sll_pkttype; /* packet type */
uint16_t sll_hatype; /* link-layer address type */
uint16_t sll_halen; /* link-layer address length */
uint8_t sll_addr[SLL_ADDRLEN]; /* link-layer address */
uint8_t sll_addr[SLL_ADDRLEN]; /* link-layer address */
uint16_t sll_protocol; /* protocol */
};
/*
* The LINUX_SLL_ values for "sll_pkttype"; these correspond to the
* PACKET_ values on Linux, but are defined here so that they're
* available even on systems other than Linux, and so that they
* don't change even if the PACKET_ values change.
* A DLT_LINUX_SLL2 fake link-layer header.
*/
#define SLL2_HDR_LEN 20 /* total header length */
struct sll2_header {
uint16_t sll2_protocol; /* protocol */
uint16_t sll2_reserved_mbz; /* reserved - must be zero */
uint32_t sll2_if_index; /* 1-based interface index */
uint16_t sll2_hatype; /* link-layer address type */
uint8_t sll2_pkttype; /* packet type */
uint8_t sll2_halen; /* link-layer address length */
uint8_t sll2_addr[SLL_ADDRLEN]; /* link-layer address */
};
/*
* The LINUX_SLL_ values for "sll_pkttype" and LINUX_SLL2_ values for
* "sll2_pkttype"; these correspond to the PACKET_ values on Linux,
* which are defined by a header under include/uapi in the current
* kernel source, and are thus not going to change on Linux. We
* define them here so that they're available even on systems other
* than Linux.
*/
#define LINUX_SLL_HOST 0
#define LINUX_SLL_BROADCAST 1
@@ -103,10 +120,11 @@ struct sll_header {
#define LINUX_SLL_OUTGOING 4
/*
* The LINUX_SLL_ values for "sll_protocol"; these correspond to the
* ETH_P_ values on Linux, but are defined here so that they're
* available even on systems other than Linux. We assume, for now,
* that the ETH_P_ values won't change in Linux; if they do, then:
* The LINUX_SLL_ values for "sll_protocol" and LINUX_SLL2_ values for
* "sll2_protocol"; these correspond to the ETH_P_ values on Linux, but
* are defined here so that they're available even on systems other than
* Linux. We assume, for now, that the ETH_P_ values won't change in
* Linux; if they do, then:
*
* if we don't translate them in "pcap-linux.c", capture files
* won't necessarily be readable if captured on a system that

93
libpcap/pcap/socket.h Normal file
View File

@@ -0,0 +1,93 @@
/* -*- Mode: c; tab-width: 8; indent-tabs-mode: 1; c-basic-offset: 8; -*- */
/*
* Copyright (c) 1993, 1994, 1995, 1996, 1997
* 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 Computer Systems
* Engineering Group at Lawrence Berkeley Laboratory.
* 4. Neither the name of the University nor of the Laboratory 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.
*/
#ifndef lib_pcap_socket_h
#define lib_pcap_socket_h
/*
* Some minor differences between sockets on various platforms.
* We include whatever sockets are needed for Internet-protocol
* socket access on UN*X and Windows.
*/
#ifdef _WIN32
/* Need windef.h for defines used in winsock2.h under MingW32 */
#ifdef __MINGW32__
#include <windef.h>
#endif
#include <winsock2.h>
#include <ws2tcpip.h>
/*
* Winsock doesn't have this UN*X type; it's used in the UN*X
* sockets API.
*
* XXX - do we need to worry about UN*Xes so old that *they*
* don't have it, either?
*/
typedef int socklen_t;
/*
* Winsock doesn't have this POSIX type; it's used for the
* tv_usec value of struct timeval.
*/
typedef long suseconds_t;
#else /* _WIN32 */
#include <sys/types.h>
#include <sys/socket.h>
#include <netdb.h> /* for struct addrinfo/getaddrinfo() */
#include <netinet/in.h> /* for sockaddr_in, in BSD at least */
#include <arpa/inet.h>
/*!
* \brief In Winsock, a socket handle is of type SOCKET; in UN*X, it's
* a file descriptor, and therefore a signed integer.
* We define SOCKET to be a signed integer on UN*X, so that it can
* be used on both platforms.
*/
#ifndef SOCKET
#define SOCKET int
#endif
/*!
* \brief In Winsock, the error return if socket() fails is INVALID_SOCKET;
* in UN*X, it's -1.
* We define INVALID_SOCKET to be -1 on UN*X, so that it can be used on
* both platforms.
*/
#ifndef INVALID_SOCKET
#define INVALID_SOCKET -1
#endif
#endif /* _WIN32 */
#endif /* lib_pcap_socket_h */

View File

@@ -50,15 +50,15 @@ promiscuous mode.
.TP
.B PCAP_WARNING_TSTAMP_TYPE_NOTSUP
The time stamp type specified in a previous
.B pcap_set_tstamp_type()
.B pcap_set_tstamp_type(3PCAP)
call isn't supported by the capture source (the time stamp type is
left as the default),
.TP
.B PCAP_WARNING
Another warning condition occurred;
.B pcap_geterr()
.B pcap_geterr(3PCAP)
or
.B pcap_perror()
.B pcap_perror(3PCAP)
may be called with
.I p
as an argument to fetch or display a message describing the warning
@@ -115,7 +115,7 @@ Additional warning and error codes may be added in the future; a program
should check for positive, negative, and zero return codes, and treat
all positive return codes as warnings and all negative return
codes as errors.
.B pcap_statustostr()
.B pcap_statustostr(3PCAP)
can be called, with a warning or error code as an argument, to fetch a
message describing the warning or error code.
.SH SEE ALSO

View File

@@ -17,7 +17,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP_BREAKLOOP 3PCAP "8 November 2017"
.TH PCAP_BREAKLOOP 3PCAP "25 July 2018"
.SH NAME
pcap_breakloop \- force a pcap_dispatch() or pcap_loop() call to return
.SH SYNOPSIS
@@ -33,12 +33,13 @@ void pcap_breakloop(pcap_t *);
.SH DESCRIPTION
.B pcap_breakloop()
sets a flag that will force
.B pcap_dispatch()
.B pcap_dispatch(3PCAP)
or
.B pcap_loop()
.B pcap_loop(3PCAP)
to return rather than looping; they will return the number of packets
that have been processed so far, or \-2 if no packets have been
processed so far.
that have been processed so far, or
.B PCAP_ERROR_BREAK
if no packets have been processed so far.
.PP
This routine is safe to use inside a signal handler on UNIX or a console
control handler on Windows, as it merely sets a flag that is checked
@@ -60,7 +61,7 @@ packets arrive and the call completes.
.PP
.ft B
Note also that, in a multi-threaded application, if one thread is
blocked in pcap_dispatch(), pcap_loop(), pcap_next(), or pcap_next_ex(),
blocked in pcap_dispatch(), pcap_loop(), pcap_next(3PCAP), or pcap_next_ex(3PCAP),
a call to pcap_breakloop() in a different thread will not unblock that
thread.
.ft R
@@ -99,12 +100,16 @@ or
.B pcap_loop()
after it is called; at most one more packet might be processed.
.PP
If \-2 is returned from
If
.B PCAP_ERROR_BREAK
is returned from
.B pcap_dispatch()
or
.BR pcap_loop() ,
the flag is cleared, so a subsequent call will resume reading packets.
If a positive number is returned, the flag is not cleared, so a
subsequent call will return \-2 and clear the flag.
subsequent call will return
.B PCAP_ERROR_BREAK
and clear the flag.
.SH SEE ALSO
pcap(3PCAP), pcap_loop(3PCAP), pcap_next_ex(3PCAP)
pcap(3PCAP)

View File

@@ -54,9 +54,9 @@ The capture handle has already been activated.
.TP
.B PCAP_ERROR
Another error occurred.
.B pcap_geterr()
.B pcap_geterr(3PCAP)
or
.B pcap_perror()
.B \%pcap_perror(3PCAP)
may be called with
.I p
as an argument to fetch or display a message describing the error.
@@ -64,7 +64,7 @@ as an argument to fetch or display a message describing the error.
Additional error codes may be added in the future; a program should
check for 0, 1, and negative, return codes, and treat all negative
return codes as errors.
.B pcap_statustostr()
.B pcap_statustostr(3PCAP)
can be called, with a warning or error code as an argument, to fetch a
message describing the warning or error code.
.SH SEE ALSO

View File

@@ -17,7 +17,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP_COMPILE 3PCAP "24 March 2017"
.TH PCAP_COMPILE 3PCAP "22 August 2018"
.SH NAME
pcap_compile \- compile a filter expression
.SH SYNOPSIS
@@ -52,7 +52,9 @@ captured; it is used only when checking for IPv4 broadcast addresses in
the filter program. If the netmask of the network on which packets are
being captured isn't known to the program, or if packets are being
captured on the Linux "any" pseudo-interface that can capture on more
than one network, a value of PCAP_NETMASK_UNKNOWN can be supplied; tests
than one network, a value of
.B PCAP_NETMASK_UNKNOWN
can be supplied; tests
for IPv4 broadcast addresses will fail to compile, but all other tests in
the filter program will be OK.
.LP
@@ -67,14 +69,21 @@ in multiple threads in a single process without some form of mutual
exclusion allowing only one thread to call it at any given time.
.SH RETURN VALUE
.B pcap_compile()
returns 0 on success and \-1 on failure.
If \-1 is returned,
.B pcap_geterr()
returns 0 on success and
.B PCAP_ERROR
on failure. If
.B PCAP_ERROR
is returned,
.B pcap_geterr(3PCAP)
or
.B pcap_perror()
.B pcap_perror(3PCAP)
may be called with
.I p
as an argument to fetch or display the error text.
.SH BACKWARD COMPATIBILITY
.PP
The
.B PCAP_NETMASK_UNKNOWN
constant became available in libpcap release 1.1.0.
.SH SEE ALSO
pcap(3PCAP), pcap_setfilter(3PCAP), pcap_freecode(3PCAP),
pcap_geterr(3PCAP), pcap-filter(@MAN_MISC_INFO@)

View File

@@ -48,7 +48,7 @@ argument of "any" or
can be used to capture packets from all interfaces.
.PP
The returned handle must be activated with
.B pcap_activate()
.B pcap_activate(3PCAP)
before packets can be captured
with it; options for the capture, such as promiscuous mode, can be set
on the handle before activating it.
@@ -69,4 +69,4 @@ is assumed to be able to hold at least
.B PCAP_ERRBUF_SIZE
chars.
.SH SEE ALSO
pcap(3PCAP), pcap_activate(3PCAP)
pcap(3PCAP)

View File

@@ -37,9 +37,9 @@ specified by
.IR p .
.PP
It must not be called on a pcap descriptor created by
.B pcap_create()
.B \%pcap_create(3PCAP)
that has not yet been activated by
.BR pcap_activate() .
.BR \%pcap_activate(3PCAP) .
.PP
.I https://www.tcpdump.org/linktypes.html
lists the values

View File

@@ -17,7 +17,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP_DATALINK_NAME_TO_VAL 3PCAP "12 October 2016"
.TH PCAP_DATALINK_NAME_TO_VAL 3PCAP "25 July 2018"
.SH NAME
pcap_datalink_name_to_val \- get the link-layer header type value
corresponding to a header type name
@@ -41,7 +41,9 @@ removed, to the corresponding link-layer header type value. The
translation is case-insensitive.
.SH RETURN VALUE
.B pcap_datalink_name_to_val()
returns the type value on success and \-1 if the name is not a known
returns the type value on success and
.B PCAP_ERROR
if the name is not a known
type name..
.SH SEE ALSO
pcap(3PCAP)

View File

@@ -19,7 +19,8 @@
.\"
.TH PCAP_DATALINK_VAL_TO_NAME 3PCAP "12 October 2016"
.SH NAME
pcap_datalink_val_to_name, pcap_datalink_val_to_description \- get a
pcap_datalink_val_to_name, pcap_datalink_val_to_description,
pcap_datalink_val_to_description_or_dlt \- get a
name or description for a link-layer header type value
.SH SYNOPSIS
.nf
@@ -30,6 +31,7 @@ name or description for a link-layer header type value
.ft B
const char *pcap_datalink_val_to_name(int dlt);
const char *pcap_datalink_val_to_description(int dlt);
const char *pcap_datalink_val_to_description_or_dlt(int dlt);
.ft
.fi
.SH DESCRIPTION
@@ -52,3 +54,13 @@ link-layer header type.
is returned if the type value does not correspond to a known
.B DLT_
value.
.PP
.B pcap_datalink_val_to_description_or_dlt()
translates a link-layer header type value to a short description of that
link-layer header type just like pcap_datalink_val_to_description.
If the type value does not correspond to a known
.B DLT_
value, the string "DLT n" is returned, where n is the value of
the dlt argument.
.SH SEE ALSO
pcap(3PCAP)

View File

@@ -35,11 +35,11 @@ u_char *sp);
.SH DESCRIPTION
.B pcap_dump()
outputs a packet to the ``savefile'' opened with
.BR pcap_dump_open() .
.BR pcap_dump_open(3PCAP) .
Note that its calling arguments are suitable for use with
.B pcap_dispatch()
.B pcap_dispatch(3PCAP)
or
.BR pcap_loop() .
.BR pcap_loop(3PCAP) .
If called directly, the
.I user
parameter is of type
@@ -47,5 +47,4 @@ parameter is of type
as returned by
.BR pcap_dump_open() .
.SH SEE ALSO
pcap(3PCAP), pcap_dump_open(3PCAP), pcap_dispatch(3PCAP),
pcap_loop(3PCAP)
pcap(3PCAP)

View File

@@ -33,6 +33,6 @@ FILE *pcap_dump_file(pcap_dumper_t *p);
.SH DESCRIPTION
.B pcap_dump_file()
returns the standard I/O stream of the ``savefile'' opened by
.BR pcap_dump_open() .
.BR pcap_dump_open(3PCAP) .
.SH SEE ALSO
pcap(3PCAP)

View File

@@ -17,7 +17,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP_DUMP_FLUSH 3PCAP "3 January 2014"
.TH PCAP_DUMP_FLUSH 3PCAP "25 July 2018"
.SH NAME
pcap_dump_flush \- flush to a savefile packets dumped
.SH SYNOPSIS
@@ -34,10 +34,12 @@ int pcap_dump_flush(pcap_dumper_t *p);
.B pcap_dump_flush()
flushes the output buffer to the ``savefile,'' so that any packets
written with
.B pcap_dump()
.B pcap_dump(3PCAP)
but not yet written to the ``savefile'' will be written.
.SH RETURN VALUE
.B pcap_dump_flush()
returns 0 on success and \-1 on failure.
returns 0 on success and
.B PCAP_ERROR
on failure.
.SH SEE ALSO
pcap(3PCAP), pcap_dump_open(3PCAP), pcap_dump(3PCAP)
pcap(3PCAP), pcap_dump_open(3PCAP)

View File

@@ -17,7 +17,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP_DUMP_FTELL 3PCAP "29 September 2017"
.TH PCAP_DUMP_FTELL 3PCAP "25 July 2018"
.SH NAME
pcap_dump_ftell, pcap_dump_ftell64 \- get the current file offset for a savefile being written
.SH SYNOPSIS
@@ -36,11 +36,11 @@ int64_t pcap_dump_ftell64(pcap_dumper_t *p);
.B pcap_dump_ftell()
returns the current file position for the ``savefile'', representing the
number of bytes written by
.B pcap_dump_open()
.B pcap_dump_open(3PCAP)
and
.BR pcap_dump() .
\-1 is returned on error.
If the current file position does not fit in a
.BR pcap_dump(3PCAP) .
.B PCAP_ERROR
is returned on error. If the current file position does not fit in a
.BR long ,
it will be truncated; this can happen on 32-bit UNIX-like systems with
large file support and on Windows.
@@ -52,6 +52,7 @@ so if file offsets that don't fit in a
but that fit in a
.B int64_t
are supported, this will return the file offset without truncation.
\-1 is returned on error.
.B PCAP_ERROR
is returned on error.
.SH SEE ALSO
pcap(3PCAP), pcap_dump_open(3PCAP), pcap_dump(3PCAP)
pcap(3PCAP)

View File

@@ -17,7 +17,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP_DUMP_OPEN 3PCAP "22 June 2018"
.TH PCAP_DUMP_OPEN 3PCAP "22 August 2018"
.SH NAME
pcap_dump_open, pcap_dump_fopen \- open a file to which to write packets
.SH SYNOPSIS
@@ -50,26 +50,26 @@ for
is called to write data to an existing open stream
.IR fp ;
this stream will be closed by a subsequent call to
.BR pcap_dump_close() .
.BR pcap_dump_close(3PCAP) .
Note that on Windows, that stream should be opened in binary mode.
.PP
.I p
is a capture or ``savefile'' handle returned by an earlier call to
.B pcap_create()
.B pcap_create(3PCAP)
and activated by an earlier call to
.BR pcap_activate() ,
.BR \%pcap_activate(3PCAP) ,
or returned by an earlier call to
.BR pcap_open_offline() ,
.BR pcap_open_live() ,
.BR \%pcap_open_offline(3PCAP) ,
.BR pcap_open_live(3PCAP) ,
or
.BR pcap_open_dead() .
.BR pcap_open_dead(3PCAP) .
The time stamp precision, link-layer type, and snapshot length from
.I p
are used as the link-layer type and snapshot length of the output file.
.PP
.B pcap_dump_open_append()
is like
.B pcap_dump_open
.B pcap_dump_open()
but does not create the file if it does not exist and, if it does
already exist, and is a pcap file with the same byte order as the host
opening the file, and has the same time stamp precision, link-layer
@@ -80,19 +80,24 @@ it will write new packets at the end of the file.
A pointer to a
.B pcap_dumper_t
structure to use in subsequent
.B pcap_dump()
.B pcap_dump(3PCAP)
and
.B pcap_dump_close()
.B pcap_dump_close(3PCAP)
calls is returned on success.
.B NULL
is returned on failure.
If
.B NULL
is returned,
.B pcap_geterr(\fIp\fB)
.B pcap_geterr(3PCAP)
can be used to get the error text.
.SH BACKWARD COMPATIBILITY
.PP
The
.B pcap_dump_open_append()
function became available in libpcap release 1.7.2. In previous
releases, there is no support for appending packets to an existing
savefile.
.SH SEE ALSO
pcap(3PCAP), pcap_create(3PCAP), pcap_activate(3PCAP),
\%pcap_open_offline(3PCAP), pcap_open_live(3PCAP), pcap_open_dead(3PCAP),
pcap_dump(3PCAP), pcap_dump_close(3PCAP), pcap_geterr(3PCAP),
pcap(3PCAP),
\%pcap-savefile(@MAN_FILE_FORMATS@)

View File

@@ -34,13 +34,15 @@ FILE *pcap_file(pcap_t *p);
.B pcap_file()
returns the standard I/O stream of the ``savefile,'' if a ``savefile''
was opened with
.BR pcap_open_offline() ,
or NULL, if a network device was opened with
.B pcap_create()
.BR pcap_open_offline(3PCAP) ,
or
.BR NULL ,
if a network device was opened with
.B pcap_create(3PCAP)
and
.BR pcap_activate() ,
.BR \%pcap_activate(3PCAP) ,
or with
.BR pcap_open_live() .
.BR pcap_open_live(3PCAP) .
.PP
Note that the Packet Capture library is usually built with large file
support, so the standard I/O stream of the ``savefile'' might refer to
@@ -50,8 +52,8 @@ should, if possible, use calls that support large files on the return
value of
.B pcap_file()
or the value returned by
.B fileno()
.B fileno(3)
when passed the return value of
.BR pcap_file() .
.SH SEE ALSO
pcap(3PCAP), pcap_open_offline(3PCAP)
pcap(3PCAP)

View File

@@ -17,7 +17,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP_FILENO 3PCAP "7 April 2014"
.TH PCAP_FILENO 3PCAP "25 July 2018"
.SH NAME
pcap_fileno \- get the file descriptor for a live capture
.SH SYNOPSIS
@@ -35,32 +35,31 @@ If
.I p
refers to a network device that was opened for a live capture using
a combination of
.B pcap_create()
.B pcap_create(3PCAP)
and
.BR pcap_activate() ,
.BR pcap_activate(3PCAP) ,
or using
.BR pcap_open_live() ,
.BR pcap_open_live(3PCAP) ,
.B pcap_fileno()
returns the file descriptor from which captured packets are read.
.LP
If
.I p
refers to a ``savefile'' that was opened using functions such as
.BR pcap_open_offline()
.BR pcap_open_offline(3PCAP)
or
.BR pcap_fopen_offline() ,
.BR pcap_fopen_offline(3PCAP) ,
a ``dead''
.B pcap_t
opened using
.BR pcap_open_dead() ,
.BR pcap_open_dead(3PCAP) ,
or a
.B pcap_t
that was created with
.B pcap_create()
but that has not yet been activated with
.BR pcap_activate() ,
it returns \-1.
it returns
.BR PCAP_ERROR .
.SH SEE ALSO
pcap(3PCAP), pcap_create(3PCAP), pcap_activate(3PCAP),
pcap_open_live(3PCAP), pcap_open_offline(3PCAP),
\%pcap_fopen_offline(3PCAP), pcap_open_dead(3PCAP)
pcap(3PCAP)

View File

@@ -17,7 +17,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP_FINDALLDEVS 3PCAP "29 April 2018"
.TH PCAP_FINDALLDEVS 3PCAP "22 August 2018"
.SH NAME
pcap_findalldevs, pcap_freealldevs \- get a list of capture devices, and
free that list
@@ -40,11 +40,11 @@ void pcap_freealldevs(pcap_if_t *alldevs);
.SH DESCRIPTION
.B pcap_findalldevs()
constructs a list of network devices that can be opened with
.B pcap_create()
.B pcap_create(3PCAP)
and
.B pcap_activate()
.B pcap_activate(3PCAP)
or with
.BR pcap_open_live() .
.BR pcap_open_live(3PCAP) .
(Note that there may be network devices that cannot be opened by the
process calling
.BR pcap_findalldevs() ,
@@ -194,21 +194,38 @@ for IPv6 addresses, it can be interpreted as if it pointed to a
.BR "struct sockaddr_in6".
.PP
The list of devices must be freed with
.BR pcap_freealldevs() ,
.BR pcap_freealldevs(3PCAP) ,
which frees the list pointed to by
.IR alldevs .
.SH RETURN VALUE
.B pcap_findalldevs()
returns 0 on success and \-1 on failure; as indicated, finding no
returns 0 on success and
.B PCAP_ERROR
on failure; as indicated, finding no
devices is considered success, rather than failure, so 0 will be
returned in that case.
If \-1 is returned,
returned in that case. If
.B PCAP_ERROR
is returned,
.I errbuf
is filled in with an appropriate error message.
.I errbuf
is assumed to be able to hold at least
.B PCAP_ERRBUF_SIZE
chars.
.SH BACKWARD COMPATIBILITY
.PP
The
.B PCAP_IF_UP
and
.B PCAP_IF_RUNNING
constants became available in libpcap release 1.6.1. The
.BR PCAP_IF_WIRELESS ,
.BR PCAP_IF_CONNECTION_STATUS ,
.BR PCAP_IF_CONNECTION_STATUS_UNKNOWN ,
.BR PCAP_IF_CONNECTION_STATUS_CONNECTED ,
.BR PCAP_IF_CONNECTION_STATUS_DISCONNECTED ,
and
.B PCAP_IF_CONNECTION_STATUS_NOT_APPLICABLE
constants became available in libpcap release 1.9.0.
.SH SEE ALSO
pcap(3PCAP), pcap_create(3PCAP), pcap_activate(3PCAP),
pcap_open_live(3PCAP)
pcap(3PCAP)

View File

@@ -35,9 +35,9 @@ void pcap_freecode(struct bpf_program *);
is used to free up allocated memory pointed to by a
.I bpf_program
struct generated by
.B pcap_compile()
.B pcap_compile(3PCAP)
when that BPF program is no longer needed, for example after it
has been made the filter program for a pcap structure by a call to
.BR pcap_setfilter() .
.BR pcap_setfilter(3PCAP) .
.SH SEE ALSO
pcap(3PCAP), pcap_compile(3PCAP), pcap_setfilter(3PCAP)
pcap(3PCAP)

View File

@@ -17,7 +17,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP_GET_SELECTABLE_FD 3PCAP "20 January 2018"
.TH PCAP_GET_SELECTABLE_FD 3PCAP "25 July 2018"
.SH NAME
pcap_get_selectable_fd \- get a file descriptor on which a select() can
be done for a live capture
@@ -36,32 +36,38 @@ int pcap_get_selectable_fd(pcap_t *p);
returns, on UNIX, a file descriptor number for a file descriptor on
which one can
do a
.BR select() ,
.BR poll() ,
.BR epoll_wait() ,
.BR select(2) ,
.BR poll(2) ,
.BR epoll_wait(2) ,
.BR kevent() ,
or other such call
to wait for it to be possible to read packets without blocking, if such
a descriptor exists, or \-1, if no such descriptor exists.
a descriptor exists, or
.BR PCAP_ERROR ,
if no such descriptor exists.
.PP
Some network devices opened with
.B pcap_create()
.B pcap_create(3PCAP)
and
.BR pcap_activate() ,
.BR pcap_activate(3PCAP) ,
or with
.BR pcap_open_live() ,
.BR pcap_open_live(3PCAP) ,
do not support those calls (for example, regular network devices on
FreeBSD 4.3 and 4.4, and Endace DAG devices), so \-1 is returned for
FreeBSD 4.3 and 4.4, and Endace DAG devices), so
.B PCAP_ERROR
is returned for
those devices. In that case, those calls must be given a timeout less
than or equal to the timeout returned by
.B pcap_get_required_select_timeout()
.B pcap_get_required_select_timeout(3PCAP)
for the device for which
.B pcap_get_selectable_fd()
returned \-1, the device must be put in non-blocking mode with a call to
.BR pcap_setnonblock() ,
returned
.BR PCAP_ERROR ,
the device must be put in non-blocking mode with a call to
.BR \%pcap_setnonblock(3PCAP) ,
and an attempt must always be made to read packets from the device
when the call returns. If
.B pcap_get_required_select_timeout()
.B \%pcap_get_required_select_timeout()
returns
.BR NULL ,
it is not possible to wait for packets to arrive on the device in an
@@ -70,9 +76,9 @@ event loop.
Note that a device on which a read can be done without blocking may,
on some platforms, not have any packets to read if the packet buffer
timeout has expired. A call to
.B pcap_dispatch()
.B pcap_dispatch(3PCAP)
or
.B pcap_next_ex()
.B pcap_next_ex(3PCAP)
will return 0 in this case, but will not block.
.PP
Note that in:
@@ -138,8 +144,8 @@ work on that descriptor in Mac OS X 10.6 and later.
.B pcap_get_selectable_fd()
is not available on Windows.
.SH RETURN VALUE
A selectable file descriptor is returned if one exists; otherwise, \-1
A selectable file descriptor is returned if one exists; otherwise,
.B PCAP_ERROR
is returned.
.SH SEE ALSO
pcap(3PCAP), pcap_get_required_select_timeout(3PCAP),
pcap_setnonblock(3PCAP), select(2), poll(2), epoll_wait(2), kqueue(2)
pcap(3PCAP), kqueue(2)

View File

@@ -46,6 +46,10 @@ or
which indicates
that pcap captures contains time stamps in microseconds or nanoseconds
respectively.
.SH BACKWARD COMPATIBILITY
This function became available in libpcap release 1.5.1. In previous
releases, time stamps from a capture device or savefile are always given
in seconds and microseconds.
.SH SEE ALSO
pcap(3PCAP),
pcap_set_tstamp_precision(3PCAP),

View File

@@ -17,7 +17,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP_INJECT 3PCAP "3 January 2014"
.TH PCAP_INJECT 3PCAP "25 July 2018"
.SH NAME
pcap_inject, pcap_sendpacket \- transmit a packet
.SH SYNOPSIS
@@ -42,7 +42,7 @@ is the number of bytes in the packet.
Note that, even if you successfully open the network interface, you
might not have permission to send packets on it, or it might not support
sending packets; as
.I pcap_open_live()
.B pcap_open_live(3PCAP)
doesn't have a flag to indicate whether to open for capturing, sending,
or capturing and sending, you cannot request an open that supports
sending and be notified at open time whether sending will be possible.
@@ -72,17 +72,23 @@ comes from OpenBSD;
comes from WinPcap. Both are provided for compatibility.)
.SH RETURN VALUE
.B pcap_inject()
returns the number of bytes written on success and \-1 on failure.
returns the number of bytes written on success and
.B PCAP_ERROR
on failure.
.PP
.B pcap_sendpacket()
returns 0 on success and \-1 on failure.
returns 0 on success and
.B PCAP_ERROR
on failure.
.PP
If \-1 is returned,
.B pcap_geterr()
If
.B PCAP_ERROR
is returned,
.B pcap_geterr(3PCAP)
or
.B pcap_perror()
.B pcap_perror(3PCAP)
may be called with
.I p
as an argument to fetch or display the error text.
.SH SEE ALSO
pcap(3PCAP), pcap_geterr(3PCAP)
pcap(3PCAP)

View File

@@ -39,9 +39,9 @@ than the current system. For a live capture, it always returns false
(0).
.PP
It must not be called on a pcap descriptor created by
.B pcap_create()
.B \%pcap_create(3PCAP)
that has not yet been activated by
.BR pcap_activate() .
.BR \%pcap_activate(3PCAP) .
.SH RETURN VALUE
.B pcap_is_swapped()
returns true (1) or false (0) on success and

View File

@@ -17,7 +17,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP_LIST_DATALINKS 3PCAP "8 March 2015"
.TH PCAP_LIST_DATALINKS 3PCAP "25 July 2018"
.SH NAME
pcap_list_datalinks, pcap_free_datalinks \- get a list of link-layer header
types supported by a capture device, and free that list
@@ -47,9 +47,9 @@ which frees the list of link-layer header types pointed to by
.IR dlt_list .
.LP
It must not be called on a pcap descriptor created by
.B pcap_create()
.B \%pcap_create(3PCAP)
that has not yet been activated by
.BR pcap_activate() .
.BR \%pcap_activate(3PCAP) .
.SH RETURN VALUE
.B pcap_list_datalinks()
returns the number of link-layer header types in the array on success,
@@ -57,17 +57,17 @@ returns the number of link-layer header types in the array on success,
if called on a capture handle that has been created but not activated,
and
.B PCAP_ERROR
(\-1) on other errors.
on other errors.
If
.B PCAP_ERROR
is returned,
.B pcap_geterr()
.B pcap_geterr(3PCAP)
or
.B pcap_perror()
.B \%pcap_perror(3PCAP)
may be called with
.I p
as an argument to fetch or display the error text.
.SH SEE ALSO
pcap(3PCAP), pcap_geterr(3PCAP),
pcap(3PCAP),
pcap_datalink_val_to_name(3PCAP),
pcap-linktype(@MAN_MISC_INFO@)

View File

@@ -18,7 +18,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP_LIST_TSTAMP_TYPES 3PCAP "22 August 2010"
.TH PCAP_LIST_TSTAMP_TYPES 3PCAP "22 August 2018"
.SH NAME
pcap_list_tstamp_types, pcap_free_tstamp_types \- get a list of time
stamp types supported by a capture device, and free that list
@@ -54,17 +54,28 @@ which frees the list pointed to by
returns the number of time stamp types in the array on success and
.B PCAP_ERROR
on failure.
A return value of zero means that you cannot specify a time stamp type;
you are limited to the capture device's default time stamp type.
A return value of one means that the only time stamp type supported is
the one in the list, which is the capture device's default time stamp
type. A return value of zero means that the only time stamp type
supported is
.BR PCAP_TSTAMP_HOST ,
which is the capture device's default time stamp type (only older
versions of libpcap will return that; newer versions will always return
one or more types).
If
.B PCAP_ERROR
is returned,
.B pcap_geterr()
.B pcap_geterr(3PCAP)
or
.B pcap_perror()
.B pcap_perror(3PCAP)
may be called with
.I p
as an argument to fetch or display the error text.
.SH BACKWARD COMPATIBILITY
.PP
These functions became available in libpcap release 1.2.1. In previous
releases, the time stamp type cannot be set; only the default time stamp
type offered by a capture source is available.
.SH SEE ALSO
pcap(3PCAP), pcap_geterr(3PCAP), pcap_tstamp_type_val_to_name(3PCAP),
pcap(3PCAP), pcap_tstamp_type_val_to_name(3PCAP),
pcap-tstamp(@MAN_MISC_INFO@)

View File

@@ -47,13 +47,13 @@ possible.)
.B pcap_lookupdev()
returns a pointer to a string giving the name of a network device
suitable for use with
.B pcap_create()
.B pcap_create(3PCAP)
and
.BR pcap_activate() ,
.BR \%pcap_activate(3PCAP) ,
or with
.BR pcap_open_live() ,
.BR pcap_open_live(3PCAP) ,
and with
.BR pcap_lookupnet() .
.BR pcap_lookupnet(3PCAP) .
If there is an error,
.B NULL
is returned and
@@ -64,8 +64,7 @@ is assumed to be able to hold at least
.B PCAP_ERRBUF_SIZE
chars.
.SH SEE ALSO
pcap(3PCAP), pcap_create(3PCAP), pcap_activate(3PCAP),
pcap_open_live(3PCAP), pcap_lookupnet(3PCAP)
pcap(3PCAP)
.SH BUGS
The pointer returned by
.B pcap_lookupdev()

View File

@@ -17,7 +17,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP_LOOKUPNET 3PCAP "3 January 2014"
.TH PCAP_LOOKUPNET 3PCAP "25 July 2018"
.SH NAME
pcap_lookupnet \- find the IPv4 network number and netmask for a device
.SH SYNOPSIS
@@ -51,8 +51,11 @@ are
pointers.
.SH RETURN VALUE
.B pcap_lookupnet()
returns 0 on success and \-1 on failure.
If \-1 is returned,
returns 0 on success and
.B PCAP_ERROR
on failure. If
.B PCAP_ERROR
is returned,
.I errbuf
is filled in with an appropriate error message.
.I errbuf

View File

@@ -17,7 +17,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP_LOOP 3PCAP "20 January 2017"
.TH PCAP_LOOP 3PCAP "25 July 2018"
.SH NAME
pcap_loop, pcap_dispatch \- process packets from a live capture or savefile
.SH SYNOPSIS
@@ -47,7 +47,7 @@ processes packets from a live capture or ``savefile'' until
.I cnt
packets are processed, the end of the ``savefile'' is
reached when reading from a ``savefile'',
.B pcap_breakloop()
.B pcap_breakloop(3PCAP)
is called, or an error occurs.
It does
.B not
@@ -123,7 +123,7 @@ them.
.PP
The bytes of data from the packet begin with a link-layer header. The
format of the link-layer header is indicated by the return value of the
.B pcap_datalink()
.B pcap_datalink(3PCAP)
routine when handed the
.B pcap_t
value also passed to
@@ -136,7 +136,7 @@ lists the values
can return and describes the packet formats that
correspond to those values. The value it returns will be valid for all
packets received unless and until
.B pcap_set_datalink()
.B pcap_set_datalink(3PCAP)
is called; after a successful call to
.BR pcap_set_datalink() ,
all subsequent packets will have a link-layer header of the type
@@ -160,8 +160,11 @@ for Ethernet.
returns 0 if
.I cnt
is exhausted or if, when reading from a ``savefile'', no more packets
are available. It returns \-1 if an error occurs or \-2 if the loop
terminated due to a call to
are available. It returns
.B PCAP_ERROR
if an error occurs or
.B PCAP_ERROR_BREAK
if the loop terminated due to a call to
.B pcap_breakloop()
before any packets were processed.
It does
@@ -177,23 +180,27 @@ platforms that support a packet buffer timeout that starts before any
packets arrive, the timeout expires before any packets arrive, or if the
file descriptor for the capture device is in non-blocking mode and no
packets were available to be read) or if no more packets are available
in a ``savefile.'' It returns \-1 if an error occurs or \-2 if the loop
terminated due to a call to
in a ``savefile.'' It returns
.B PCAP_ERROR
if an error occurs or
.B PCAP_ERROR_BREAK
if the loop terminated due to a call to
.B pcap_breakloop()
before any packets were processed.
.ft B
If your application uses pcap_breakloop(),
make sure that you explicitly check for \-1 and \-2, rather than just
checking for a return value < 0.
make sure that you explicitly check for PCAP_ERROR and PCAP_ERROR_BREAK,
rather than just checking for a return value < 0.
.ft R
.PP
If \-1 is returned,
.B pcap_geterr()
If
.B PCAP_ERROR
is returned,
.B pcap_geterr(3PCAP)
or
.B pcap_perror()
.B pcap_perror(3PCAP)
may be called with
.I p
as an argument to fetch or display the error text.
.SH SEE ALSO
pcap(3PCAP), pcap_geterr(3PCAP), pcap_breakloop(3PCAP),
pcap_datalink(3PCAP)
pcap(3PCAP)

View File

@@ -17,7 +17,7 @@
.\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
.\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
.\"
.TH PCAP_NEXT_EX 3PCAP "20 January 2017"
.TH PCAP_NEXT_EX 3PCAP "25 July 2018"
.SH NAME
pcap_next_ex, pcap_next \- read the next packet from a pcap_t
.SH SYNOPSIS
@@ -49,9 +49,9 @@ and the packet data are not to be freed by the caller, and are not
guaranteed to be valid after the next call to
.BR pcap_next_ex() ,
.BR pcap_next() ,
.BR pcap_loop() ,
.BR pcap_loop(3PCAP) ,
or
.BR pcap_dispatch() ;
.BR pcap_dispatch(3PCAP) ;
if the code needs them to remain valid, it must make a copy of them.
.PP
.B pcap_next()
@@ -78,7 +78,7 @@ is filled in with the appropriate values for the packet.
.PP
The bytes of data from the packet begin with a link-layer header. The
format of the link-layer header is indicated by the return value of the
.B pcap_datalink()
.B pcap_datalink(PCAP)
routine when handed the
.B pcap_t
value also passed to
@@ -91,7 +91,7 @@ lists the values
can return and describes the packet formats that
correspond to those values. The value it returns will be valid for all
packets received unless and until
.B pcap_set_datalink()
.B pcap_set_datalink(3PCAP)
is called; after a successful call to
.BR pcap_set_datalink() ,
all subsequent packets will have a link-layer header of the type
@@ -114,12 +114,17 @@ for Ethernet.
.B pcap_next_ex()
returns 1 if the packet was read without problems, 0 if packets are
being read from a live capture and the packet buffer timeout expired,
\-1 if an error occurred while reading the packet, and \-2 if packets
.B PCAP_ERROR
if an error occurred while reading the packet, and
.B PCAP_ERROR_BREAK
if packets
are being read from a ``savefile'' and there are no more packets to read
from the savefile. If \-1 is returned,
.B pcap_geterr()
from the savefile. If
.B PCAP_ERROR
is returned,
.B pcap_geterr(3PCAP)
or
.B pcap_perror()
.B pcap_perror(3PCAP)
may be called with
.I p
as an argument to fetch or display the error text.
@@ -136,5 +141,4 @@ non-blocking mode and no packets were available to be read), or if no
more packets are available in a ``savefile.'' Unfortunately, there is no
way to determine whether an error occurred or not.
.SH SEE ALSO
pcap(3PCAP), pcap_geterr(3PCAP), pcap_dispatch(3PCAP),
pcap_datalink(3PCAP)
pcap(3PCAP)

View File

@@ -39,7 +39,7 @@ checks whether a filter matches a packet.
is a pointer to a
.I bpf_program
struct, usually the result of a call to
.BR pcap_compile() .
.BR pcap_compile(3PCAP) .
.I h
points to the
.I pcap_pkthdr
@@ -52,4 +52,4 @@ returns the return value of the filter program. This will be zero if
the packet doesn't match the filter and non-zero if the packet matches
the filter.
.SH SEE ALSO
pcap(3PCAP), pcap_compile(3PCAP)
pcap(3PCAP)

View File

@@ -43,10 +43,10 @@ are used for creating a
structure to use when calling the other functions in libpcap. It is
typically used when just using libpcap for compiling BPF code; it can
also be used if using
.BR pcap_dump_open() ,
.BR pcap_dump() ,
.BR pcap_dump_open(3PCAP) ,
.BR pcap_dump(3PCAP) ,
and
.B pcap_dump_close()
.B pcap_dump_close(3PCAP)
to write a savefile if there is no
.B pcap_t
that supplies the packets to be written.
@@ -73,7 +73,6 @@ seconds and microseconds, and
.B PCAP_TSTAMP_PRECISION_NANO
should be specified if the packets to be written have time stamps in
seconds and nanoseconds. Its value does not affect
.BR pcap_compile() .
.BR pcap_compile(3PCAP) .
.SH SEE ALSO
pcap(3PCAP), pcap_compile(3PCAP), pcap_dump_open(3PCAP),
\%pcap-linktype(@MAN_MISC_INFO@)
pcap(3PCAP), \%pcap-linktype(@MAN_MISC_INFO@)

View File

@@ -87,4 +87,4 @@ is assumed to be able to hold at least
.B PCAP_ERRBUF_SIZE
chars.
.SH SEE ALSO
pcap(3PCAP), pcap_create(3PCAP), pcap_activate(3PCAP)
pcap_create(3PCAP), pcap_activate(3PCAP)

View File

@@ -81,7 +81,8 @@ or
.B pcap_fopen_offline_with_tstamp_precision()
to read dumped data from an existing open stream
.IR fp .
.B pcap_fopen_offline_with_tstamp_precision() takes an additional
.B pcap_fopen_offline_with_tstamp_precision()
takes an additional
.I precision
argument as described above.
Note that on Windows, that stream should be opened in binary mode.
@@ -105,5 +106,11 @@ is filled in with an appropriate error message.
is assumed to be able to hold at least
.B PCAP_ERRBUF_SIZE
chars.
.SH BACKWARD COMPATIBILITY
.B pcap_open_offline_with_tstamp_precision
and
.B pcap_fopen_offline_with_tstamp_precision
became available in libpcap release 1.5.1. In previous releases, time
stamps from a savefile are always given in seconds and microseconds.
.SH SEE ALSO
pcap(3PCAP), pcap-savefile(@MAN_FILE_FORMATS@)

Some files were not shown because too many files have changed in this diff Show More