diff options
author | Gerald Combs <gerald@wireshark.org> | 2018-10-17 17:59:07 +0000 |
---|---|---|
committer | Michael Mann <mmann78@netscape.net> | 2018-10-21 11:58:14 +0000 |
commit | aea4e4b42ac3856b26d729dde7387bad37f261fc (patch) | |
tree | 3d87a0eef7610b7d351268851010f75396d79c47 /dumpcap.c | |
parent | 1957673703fb5e5865bfc4412393e20302569392 (diff) |
Dumpcap: Swap bytes only for pcap sources.
Instead of trying to byte swap all of pcapng's block types, refuse
to handle pcapng sources that have a different byte order.
Rename cap_pipe_adjust_header to cap_pipe_adjust_pcap_header.
Change-Id: I2615da57ba9d3fc365c631dc191f7767a284d460
Reviewed-on: https://code.wireshark.org/review/30235
Reviewed-by: Gerald Combs <gerald@wireshark.org>
Petri-Dish: Gerald Combs <gerald@wireshark.org>
Tested-by: Petri Dish Buildbot
Reviewed-by: James Ko <jim.list@hotmail.com>
Reviewed-by: Michael Mann <mmann78@netscape.net>
Diffstat (limited to 'dumpcap.c')
-rw-r--r-- | dumpcap.c | 74 |
1 files changed, 30 insertions, 44 deletions
@@ -223,8 +223,9 @@ typedef enum { } cap_pipe_err_t; typedef struct _pcap_pipe_info { - struct pcap_hdr hdr; /**< Pcap header when capturing from a pipe */ - struct pcaprec_modified_hdr rechdr; /**< Pcap record header when capturing from a pipe */ + gboolean byte_swapped; /**< TRUE if data in the pipe is byte swapped. */ + struct pcap_hdr hdr; /**< Pcap header when capturing from a pipe */ + struct pcaprec_modified_hdr rechdr; /**< Pcap record header when capturing from a pipe */ } pcap_pipe_info_t; typedef struct _pcapng_pipe_info { @@ -265,7 +266,6 @@ typedef struct _capture_src { #endif int cap_pipe_fd; /**< the file descriptor of the capture pipe */ gboolean cap_pipe_modified; /**< TRUE if data in the pipe uses modified pcap headers */ - gboolean cap_pipe_byte_swapped; /**< TRUE if data in the pipe is byte swapped */ char * cap_pipe_databuf; /**< Pointer to the data buffer we've allocated */ size_t cap_pipe_databuf_size; /**< Current size of the data buffer */ guint cap_pipe_max_pkt_size; /**< Maximum packet size allowed */ @@ -1198,7 +1198,7 @@ relinquish_privs_except_capture(void) /* Take care of byte order in the libpcap headers read from pipes. * (function taken from wiretap/libpcap.c) */ static void -cap_pipe_adjust_header(gboolean byte_swapped, struct pcap_hdr *hdr, struct pcaprec_hdr *rechdr) +cap_pipe_adjust_pcap_header(gboolean byte_swapped, struct pcap_hdr *hdr, struct pcaprec_hdr *rechdr) { if (byte_swapped) { /* Byte-swap the record header fields. */ @@ -1802,14 +1802,14 @@ cap_pipe_open_live(char *pipename, case PCAP_NSEC_MAGIC: /* Host that wrote it has our byte order, and was running a program using either standard or ss990417 libpcap. */ - pcap_src->cap_pipe_byte_swapped = FALSE; + pcap_src->cap_pipe_info.pcap.byte_swapped = FALSE; pcap_src->cap_pipe_modified = FALSE; pcap_src->ts_nsec = magic == PCAP_NSEC_MAGIC; break; case PCAP_MODIFIED_MAGIC: /* Host that wrote it has our byte order, but was running a program using either ss990915 or ss991029 libpcap. */ - pcap_src->cap_pipe_byte_swapped = FALSE; + pcap_src->cap_pipe_info.pcap.byte_swapped = FALSE; pcap_src->cap_pipe_modified = TRUE; break; case PCAP_SWAPPED_MAGIC: @@ -1817,7 +1817,7 @@ cap_pipe_open_live(char *pipename, /* Host that wrote it has a byte order opposite to ours, and was running a program using either standard or ss990417 libpcap. */ - pcap_src->cap_pipe_byte_swapped = TRUE; + pcap_src->cap_pipe_info.pcap.byte_swapped = TRUE; pcap_src->cap_pipe_modified = FALSE; pcap_src->ts_nsec = magic == PCAP_SWAPPED_NSEC_MAGIC; break; @@ -1825,7 +1825,7 @@ cap_pipe_open_live(char *pipename, /* Host that wrote it out has a byte order opposite to ours, and was running a program using either ss990915 or ss991029 libpcap. */ - pcap_src->cap_pipe_byte_swapped = TRUE; + pcap_src->cap_pipe_info.pcap.byte_swapped = TRUE; pcap_src->cap_pipe_modified = TRUE; break; case BLOCK_TYPE_SHB: @@ -1909,7 +1909,7 @@ pcap_pipe_open_live(int fd, } #endif - if (pcap_src->cap_pipe_byte_swapped) { + if (pcap_src->cap_pipe_info.pcap.byte_swapped) { /* Byte-swap the header fields about which we care. */ hdr->version_major = GUINT16_SWAP_LE_BE(hdr->version_major); hdr->version_minor = GUINT16_SWAP_LE_BE(hdr->version_minor); @@ -1955,7 +1955,6 @@ pcapng_read_shb(capture_src *pcap_src, char *errmsg, int errmsgl) { - struct pcapng_block_header_s *bh = &pcap_src->cap_pipe_info.pcapng.bh; struct pcapng_section_header_block_s *shb = &pcap_src->cap_pipe_info.pcapng.shb; #ifdef _WIN32 @@ -1991,26 +1990,30 @@ pcapng_read_shb(capture_src *pcap_src, { case PCAPNG_MAGIC: g_log(LOG_DOMAIN_CAPTURE_CHILD, G_LOG_LEVEL_DEBUG, "pcapng SHB MAGIC"); - pcap_src->cap_pipe_byte_swapped = FALSE; break; case PCAPNG_SWAPPED_MAGIC: g_log(LOG_DOMAIN_CAPTURE_CHILD, G_LOG_LEVEL_DEBUG, "pcapng SHB SWAPPED MAGIC"); - pcap_src->cap_pipe_byte_swapped = TRUE; - break; + /* + * pcapng sources can contain all sorts of block types. Rather than add a bunch of + * complexity to this code (which is often privileged), punt and tell the user to + * swap bytes elsewhere. + */ +#if G_BYTE_ORDER == G_BIG_ENDIAN +#define OUR_ENDIAN "big" +#define IFACE_ENDIAN "little" +#else +#define OUR_ENDIAN "little" +#define IFACE_ENDIAN "big" +#endif + g_snprintf(errmsg, errmsgl, "Interface %u is " IFACE_ENDIAN " endian but we're " OUR_ENDIAN " endian.", + pcap_src->interface_id); + return -1; default: /* Not a pcapng type we know about, or not pcapng at all. */ g_snprintf(errmsg, errmsgl, "Unrecognized pcapng format or not pcapng data."); return -1; } - if (pcap_src->cap_pipe_byte_swapped) { - /* Byte-swap the header fields about which we care. */ - shb->version_major = GUINT16_SWAP_LE_BE(shb->version_major); - shb->version_minor = GUINT16_SWAP_LE_BE(shb->version_minor); - shb->section_length = GUINT64_SWAP_LE_BE(shb->section_length); - bh->block_total_length = GUINT32_SWAP_LE_BE(bh->block_total_length); - } - pcap_src->cap_pipe_max_pkt_size = WTAP_MAX_PACKET_SIZE_STANDARD; /* Setup state to capture any options following the section header block */ @@ -2019,21 +2022,6 @@ pcapng_read_shb(capture_src *pcap_src, return 0; } -static int -pcapng_write_saved_block(capture_src *pcap_src, struct pcapng_block_header_s *bh) -{ - guint32 length = bh->block_total_length; - - if (pcap_src->cap_pipe_byte_swapped) { - length = GUINT32_SWAP_LE_BE(length); - } - - return pcapng_write_block(global_ld.pdh, - (const guint8 *) bh, - length, - &global_ld.bytes_written, &global_ld.err); -} - /* Save SHB and IDB blocks to playback whenever we change output files. */ /* The list is saved in reverse order of blocks added */ static gboolean @@ -2272,7 +2260,7 @@ pcap_pipe_dispatch(loop_data *ld, capture_src *pcap_src, char *errmsg, int errms case PD_REC_HDR_READ: /* We've read the header. Take care of byte order. */ - cap_pipe_adjust_header(pcap_src->cap_pipe_byte_swapped, &pcap_info->hdr, + cap_pipe_adjust_pcap_header(pcap_src->cap_pipe_info.pcap.byte_swapped, &pcap_info->hdr, &pcap_info->rechdr.hdr); if (pcap_info->rechdr.hdr.incl_len > pcap_src->cap_pipe_max_pkt_size) { /* @@ -2504,12 +2492,6 @@ pcapng_pipe_dispatch(loop_data *ld, capture_src *pcap_src, char *errmsg, int err return 1; } - /* We've read the header. Take care of byte order. */ - if (pcap_src->cap_pipe_byte_swapped) { - /* Byte-swap the record header fields. */ - bh->block_type = GUINT32_SWAP_LE_BE(bh->block_type); - bh->block_total_length = GUINT32_SWAP_LE_BE(bh->block_total_length); - } if (bh->block_total_length > pcap_src->cap_pipe_max_pkt_size) { /* * The record contains more data than the advertised/allowed in the @@ -3502,7 +3484,11 @@ do_file_switch_or_stop(capture_options *capture_opts, GList *list = rlist; successful = TRUE; while (list && successful) { - successful = pcapng_write_saved_block(pcap_src, (struct pcapng_block_header_s *) list->data); + struct pcapng_block_header_s *bh = (struct pcapng_block_header_s *) list->data; + successful = pcapng_write_block(global_ld.pdh, + (const guint8 *) bh, + bh->block_total_length, + &global_ld.bytes_written, &global_ld.err); list = g_list_next(list); } pcap_src->cap_pipe_info.pcapng.saved_blocks = g_list_reverse(rlist); |