diff options
Diffstat (limited to 'savefile.c')
-rw-r--r-- | savefile.c | 179 |
1 files changed, 151 insertions, 28 deletions
diff --git a/savefile.c b/savefile.c index 0ab2fdefb201..247338c5b879 100644 --- a/savefile.c +++ b/savefile.c @@ -32,9 +32,9 @@ #include "config.h" #endif -#ifdef WIN32 +#ifdef _WIN32 #include <pcap-stdinc.h> -#else /* WIN32 */ +#else /* _WIN32 */ #if HAVE_INTTYPES_H #include <inttypes.h> #elif HAVE_STDINT_H @@ -44,7 +44,7 @@ #include <sys/bitypes.h> #endif #include <sys/types.h> -#endif /* WIN32 */ +#endif /* _WIN32 */ #include <errno.h> #include <memory.h> @@ -53,7 +53,6 @@ #include <string.h> #include "pcap-int.h" -#include "pcap/usb.h" #ifdef HAVE_OS_PROTO_H #include "os-proto.h" @@ -62,10 +61,27 @@ #include "sf-pcap.h" #include "sf-pcap-ng.h" +#ifdef _WIN32 +/* + * These aren't exported on Windows, because they would only work if both + * WinPcap and the code using it were to use the Universal CRT; otherwise, + * a FILE structure in WinPcap and a FILE structure in the code using it + * could be different if they're using different versions of the C runtime. + * + * Instead, pcap/pcap.h defines them as macros that wrap the hopen versions, + * with the wrappers calling _fileno() and _get_osfhandle() themselves, + * so that they convert the appropriate CRT version's FILE structure to + * a HANDLE (which is OS-defined, not CRT-defined, and is part of the Win32 + * and Win64 ABIs). + */ +static pcap_t *pcap_fopen_offline_with_tstamp_precision(FILE *, u_int, char *); +static pcap_t *pcap_fopen_offline(FILE *, char *); +#endif + /* * Setting O_BINARY on DOS/Windows is a bit tricky */ -#if defined(WIN32) +#if defined(_WIN32) #define SET_BINMODE(f) _setmode(_fileno(f), _O_BINARY) #elif defined(MSDOS) #if defined(__HIGHC__) @@ -96,7 +112,7 @@ sf_setnonblock(pcap_t *p, int nonblock, char *errbuf) * as it would have to handle reading partial packets and * keeping the state of the read.) */ - snprintf(p->errbuf, PCAP_ERRBUF_SIZE, + pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE, "Savefiles cannot be put into non-blocking mode"); return (-1); } @@ -104,16 +120,24 @@ sf_setnonblock(pcap_t *p, int nonblock, char *errbuf) static int sf_stats(pcap_t *p, struct pcap_stat *ps) { - snprintf(p->errbuf, PCAP_ERRBUF_SIZE, + pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE, "Statistics aren't available from savefiles"); return (-1); } -#ifdef WIN32 +#ifdef _WIN32 +static struct pcap_stat * +sf_stats_ex(pcap_t *p, int *size) +{ + pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE, + "Statistics aren't available from savefiles"); + return (NULL); +} + static int sf_setbuff(pcap_t *p, int dim) { - snprintf(p->errbuf, PCAP_ERRBUF_SIZE, + pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE, "The kernel buffer size cannot be set while reading from a file"); return (-1); } @@ -121,7 +145,7 @@ sf_setbuff(pcap_t *p, int dim) static int sf_setmode(pcap_t *p, int mode) { - snprintf(p->errbuf, PCAP_ERRBUF_SIZE, + pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE, "impossible to set mode while reading from a file"); return (-1); } @@ -129,10 +153,74 @@ sf_setmode(pcap_t *p, int mode) static int sf_setmintocopy(pcap_t *p, int size) { - snprintf(p->errbuf, PCAP_ERRBUF_SIZE, + pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE, "The mintocopy parameter cannot be set while reading from a file"); return (-1); } + +static HANDLE +sf_getevent(pcap_t *pcap) +{ + (void)pcap_snprintf(pcap->errbuf, sizeof(pcap->errbuf), + "The read event cannot be retrieved while reading from a file"); + return (INVALID_HANDLE_VALUE); +} + +static int +sf_oid_get_request(pcap_t *p, bpf_u_int32 oid _U_, void *data _U_, + size_t *lenp _U_) +{ + pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE, + "An OID get request cannot be performed on a file"); + return (PCAP_ERROR); +} + +static int +sf_oid_set_request(pcap_t *p, bpf_u_int32 oid _U_, const void *data _U_, + size_t *lenp _U_) +{ + pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE, + "An OID set request cannot be performed on a file"); + return (PCAP_ERROR); +} + +static u_int +sf_sendqueue_transmit(pcap_t *p, pcap_send_queue *queue, int sync) +{ + strlcpy(p->errbuf, "Sending packets isn't supported on savefiles", + PCAP_ERRBUF_SIZE); + return (0); +} + +static int +sf_setuserbuffer(pcap_t *p, int size) +{ + pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE, + "The user buffer cannot be set when reading from a file"); + return (-1); +} + +static int +sf_live_dump(pcap_t *p, char *filename, int maxsize, int maxpacks) +{ + pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE, + "Live packet dumping cannot be performed when reading from a file"); + return (-1); +} + +static int +sf_live_dump_ended(pcap_t *p, int sync) +{ + pcap_snprintf(p->errbuf, PCAP_ERRBUF_SIZE, + "Live packet dumping cannot be performed on a pcap_open_dead pcap_t"); + return (-1); +} + +static PAirpcapHandle +sf_get_airpcap_handle(pcap_t *pcap) +{ + return (NULL); +} #endif static int @@ -150,7 +238,7 @@ sf_inject(pcap_t *p, const void *buf _U_, size_t size _U_) static int sf_setdirection(pcap_t *p, pcap_direction_t d) { - snprintf(p->errbuf, sizeof(p->errbuf), + pcap_snprintf(p->errbuf, sizeof(p->errbuf), "Setting direction is not supported on savefiles"); return (-1); } @@ -165,17 +253,38 @@ sf_cleanup(pcap_t *p) pcap_freecode(&p->fcode); } +/* +* fopen's safe version on Windows. +*/ +#ifdef _MSC_VER +FILE *fopen_safe(const char *filename, const char* mode) +{ + FILE *fp = NULL; + errno_t errno; + errno = fopen_s(&fp, filename, mode); + if (errno == 0) + return fp; + else + return NULL; +} +#endif + pcap_t * pcap_open_offline_with_tstamp_precision(const char *fname, u_int precision, - char *errbuf) + char *errbuf) { FILE *fp; pcap_t *p; + if (fname == NULL) { + pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, + "A null pointer was supplied as the file name"); + return (NULL); + } if (fname[0] == '-' && fname[1] == '\0') { fp = stdin; -#if defined(WIN32) || defined(MSDOS) +#if defined(_WIN32) || defined(MSDOS) /* * We're reading from the standard input, so put it in binary * mode, as savefiles are binary files. @@ -184,13 +293,13 @@ pcap_open_offline_with_tstamp_precision(const char *fname, u_int precision, #endif } else { -#if !defined(WIN32) && !defined(MSDOS) +#if !defined(_WIN32) && !defined(MSDOS) fp = fopen(fname, "r"); #else fp = fopen(fname, "rb"); #endif if (fp == NULL) { - snprintf(errbuf, PCAP_ERRBUF_SIZE, "%s: %s", fname, + pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "%s: %s", fname, pcap_strerror(errno)); return (NULL); } @@ -210,7 +319,7 @@ pcap_open_offline(const char *fname, char *errbuf) PCAP_TSTAMP_PRECISION_MICRO, errbuf)); } -#ifdef WIN32 +#ifdef _WIN32 pcap_t* pcap_hopen_offline_with_tstamp_precision(intptr_t osfd, u_int precision, char *errbuf) { @@ -218,16 +327,16 @@ pcap_t* pcap_hopen_offline_with_tstamp_precision(intptr_t osfd, u_int precision, FILE *file; fd = _open_osfhandle(osfd, _O_RDONLY); - if ( fd < 0 ) + if ( fd < 0 ) { - snprintf(errbuf, PCAP_ERRBUF_SIZE, pcap_strerror(errno)); + pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, pcap_strerror(errno)); return NULL; } file = _fdopen(fd, "rb"); - if ( file == NULL ) + if ( file == NULL ) { - snprintf(errbuf, PCAP_ERRBUF_SIZE, pcap_strerror(errno)); + pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, pcap_strerror(errno)); return NULL; } @@ -249,7 +358,7 @@ static pcap_t *(*check_headers[])(bpf_u_int32, FILE *, u_int, char *, int *) = { #define N_FILE_TYPES (sizeof check_headers / sizeof check_headers[0]) -#ifdef WIN32 +#ifdef _WIN32 static #endif pcap_t * @@ -272,11 +381,11 @@ pcap_fopen_offline_with_tstamp_precision(FILE *fp, u_int precision, amt_read = fread((char *)&magic, 1, sizeof(magic), fp); if (amt_read != sizeof(magic)) { if (ferror(fp)) { - snprintf(errbuf, PCAP_ERRBUF_SIZE, + pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "error reading dump file: %s", pcap_strerror(errno)); } else { - snprintf(errbuf, PCAP_ERRBUF_SIZE, + pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "truncated dump file; tried to read %lu file header bytes, only got %lu", (unsigned long)sizeof(magic), (unsigned long)amt_read); @@ -304,7 +413,7 @@ pcap_fopen_offline_with_tstamp_precision(FILE *fp, u_int precision, /* * Well, who knows what this mess is.... */ - snprintf(errbuf, PCAP_ERRBUF_SIZE, "unknown file format"); + pcap_snprintf(errbuf, PCAP_ERRBUF_SIZE, "unknown file format"); return (NULL); found: @@ -313,7 +422,7 @@ found: /* Padding only needed for live capture fcode */ p->fddipad = 0; -#if !defined(WIN32) && !defined(MSDOS) +#if !defined(_WIN32) && !defined(MSDOS) /* * You can do "select()" and "poll()" on plain files on most * platforms, and should be able to do so on pipes. @@ -332,10 +441,19 @@ found: p->getnonblock_op = sf_getnonblock; p->setnonblock_op = sf_setnonblock; p->stats_op = sf_stats; -#ifdef WIN32 +#ifdef _WIN32 + p->stats_ex_op = sf_stats_ex; p->setbuff_op = sf_setbuff; p->setmode_op = sf_setmode; p->setmintocopy_op = sf_setmintocopy; + p->getevent_op = sf_getevent; + p->oid_get_request_op = sf_oid_get_request; + p->oid_set_request_op = sf_oid_set_request; + p->sendqueue_transmit_op = sf_sendqueue_transmit; + p->setuserbuffer_op = sf_setuserbuffer; + p->live_dump_op = sf_live_dump; + p->live_dump_ended_op = sf_live_dump_ended; + p->get_airpcap_handle_op = sf_get_airpcap_handle; #endif /* @@ -344,12 +462,17 @@ found: */ p->oneshot_callback = pcap_oneshot; + /* + * Savefiles never require special BPF code generation. + */ + p->bpf_codegen_flags = 0; + p->activated = 1; return (p); } -#ifdef WIN32 +#ifdef _WIN32 static #endif pcap_t * |