2 * Copyright (c) 1988, 1989, 1990, 1991, 1992, 1993, 1994, 1995, 1996, 1997, 2000
3 * The Regents of the University of California. All rights reserved.
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that: (1) source code distributions
7 * retain the above copyright notice and this paragraph in its entirety, (2)
8 * distributions including binary code include the above copyright notice and
9 * this paragraph in its entirety in the documentation or other materials
10 * provided with the distribution, and (3) all advertising materials mentioning
11 * features or use of this software display the following acknowledgement:
12 * ``This product includes software developed by the University of California,
13 * Lawrence Berkeley Laboratory and its contributors.'' Neither the name of
14 * the University nor the names of its contributors may be used to endorse
15 * or promote products derived from this software without specific prior
17 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
18 * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
19 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
21 * Support for splitting captures into multiple files with a maximum
25 * Seth Webster <swebster@sst.ll.mit.edu>
36 #include "netdissect-stdinc.h"
38 #include "netdissect.h"
39 #include "addrtoname.h"
41 #include "netdissect-alloc.h"
43 #include "pcap-missing.h"
55 static const struct uint_printer uint_printers
[] = {
56 #ifdef DLT_IEEE802_15_4
57 { ieee802_15_4_if_print
, DLT_IEEE802_15_4
},
59 #ifdef DLT_IEEE802_15_4_NOFCS
60 { ieee802_15_4_if_print
, DLT_IEEE802_15_4_NOFCS
},
62 #ifdef DLT_IEEE802_15_4_TAP
63 { ieee802_15_4_tap_if_print
, DLT_IEEE802_15_4_TAP
},
66 { cip_if_print
, DLT_CIP
},
69 { cip_if_print
, DLT_ATM_CLIP
},
72 { ipfc_if_print
, DLT_IP_OVER_FC
},
75 { lane_if_print
, DLT_LANE8023
},
78 { chdlc_if_print
, DLT_C_HDLC
},
81 { chdlc_if_print
, DLT_HDLC
},
83 #if defined(DLT_PFLOG) && defined(HAVE_NET_IF_PFLOG_H)
84 { pflog_if_print
, DLT_PFLOG
},
86 { token_if_print
, DLT_IEEE802
},
87 { fddi_if_print
, DLT_FDDI
},
89 { sll_if_print
, DLT_LINUX_SLL
},
92 { sll2_if_print
, DLT_LINUX_SLL2
},
95 { fr_if_print
, DLT_FR
},
98 { fr_if_print
, DLT_FRELAY
},
101 { mfr_if_print
, DLT_MFR
},
103 { atm_if_print
, DLT_ATM_RFC1483
},
105 { ltalk_if_print
, DLT_LTALK
},
107 #ifdef DLT_IEEE802_11_RADIO
108 { ieee802_11_radio_if_print
, DLT_IEEE802_11_RADIO
},
110 #ifdef DLT_IEEE802_11
111 { ieee802_11_if_print
, DLT_IEEE802_11
},
113 #ifdef DLT_IEEE802_11_RADIO_AVS
114 { ieee802_11_radio_avs_if_print
, DLT_IEEE802_11_RADIO_AVS
},
116 #ifdef DLT_PRISM_HEADER
117 { prism_if_print
, DLT_PRISM_HEADER
},
119 { ppp_if_print
, DLT_PPP
},
120 #ifdef DLT_PPP_WITHDIRECTION
121 { ppp_if_print
, DLT_PPP_WITHDIRECTION
},
124 { ppp_bsdos_if_print
, DLT_PPP_BSDOS
},
126 #ifdef DLT_PPP_SERIAL
127 { ppp_hdlc_if_print
, DLT_PPP_SERIAL
},
132 static const struct void_printer void_printers
[] = {
133 #ifdef DLT_APPLE_IP_OVER_IEEE1394
134 { ap1394_if_print
, DLT_APPLE_IP_OVER_IEEE1394
},
136 { arcnet_if_print
, DLT_ARCNET
},
137 #ifdef DLT_ARCNET_LINUX
138 { arcnet_linux_if_print
, DLT_ARCNET_LINUX
},
140 #ifdef DLT_DSA_TAG_BRCM
141 { brcm_tag_if_print
, DLT_DSA_TAG_BRCM
},
143 #ifdef DLT_DSA_TAG_BRCM_PREPEND
144 { brcm_tag_prepend_if_print
, DLT_DSA_TAG_BRCM_PREPEND
},
146 #ifdef DLT_BLUETOOTH_HCI_H4_WITH_PHDR
147 { bt_if_print
, DLT_BLUETOOTH_HCI_H4_WITH_PHDR
},
149 #ifdef DLT_DSA_TAG_DSA
150 { dsa_if_print
, DLT_DSA_TAG_DSA
},
152 #ifdef DLT_DSA_TAG_EDSA
153 { edsa_if_print
, DLT_DSA_TAG_EDSA
},
156 { enc_if_print
, DLT_ENC
},
158 { ether_if_print
, DLT_EN10MB
},
160 { ipnet_if_print
, DLT_IPNET
},
163 { ipoib_if_print
, DLT_IPOIB
},
165 #ifdef DLT_JUNIPER_ATM1
166 { juniper_atm1_if_print
, DLT_JUNIPER_ATM1
},
168 #ifdef DLT_JUNIPER_ATM2
169 { juniper_atm2_if_print
, DLT_JUNIPER_ATM2
},
171 #ifdef DLT_JUNIPER_CHDLC
172 { juniper_chdlc_if_print
, DLT_JUNIPER_CHDLC
},
174 #ifdef DLT_JUNIPER_ES
175 { juniper_es_if_print
, DLT_JUNIPER_ES
},
177 #ifdef DLT_JUNIPER_ETHER
178 { juniper_ether_if_print
, DLT_JUNIPER_ETHER
},
180 #ifdef DLT_JUNIPER_FRELAY
181 { juniper_frelay_if_print
, DLT_JUNIPER_FRELAY
},
183 #ifdef DLT_JUNIPER_GGSN
184 { juniper_ggsn_if_print
, DLT_JUNIPER_GGSN
},
186 #ifdef DLT_JUNIPER_MFR
187 { juniper_mfr_if_print
, DLT_JUNIPER_MFR
},
189 #ifdef DLT_JUNIPER_MLFR
190 { juniper_mlfr_if_print
, DLT_JUNIPER_MLFR
},
192 #ifdef DLT_JUNIPER_MLPPP
193 { juniper_mlppp_if_print
, DLT_JUNIPER_MLPPP
},
195 #ifdef DLT_JUNIPER_MONITOR
196 { juniper_monitor_if_print
, DLT_JUNIPER_MONITOR
},
198 #ifdef DLT_JUNIPER_PPP
199 { juniper_ppp_if_print
, DLT_JUNIPER_PPP
},
201 #ifdef DLT_JUNIPER_PPPOE_ATM
202 { juniper_pppoe_atm_if_print
, DLT_JUNIPER_PPPOE_ATM
},
204 #ifdef DLT_JUNIPER_PPPOE
205 { juniper_pppoe_if_print
, DLT_JUNIPER_PPPOE
},
207 #ifdef DLT_JUNIPER_SERVICES
208 { juniper_services_if_print
, DLT_JUNIPER_SERVICES
},
210 #ifdef DLT_NETANALYZER
211 { netanalyzer_if_print
, DLT_NETANALYZER
},
213 #ifdef DLT_NETANALYZER_TRANSPARENT
214 { netanalyzer_transparent_if_print
, DLT_NETANALYZER_TRANSPARENT
},
217 { nflog_if_print
, DLT_NFLOG
},
219 { null_if_print
, DLT_NULL
},
221 { null_if_print
, DLT_LOOP
},
224 { pktap_if_print
, DLT_PKTAP
},
227 { ppi_if_print
, DLT_PPI
},
230 { pppoe_if_print
, DLT_PPP_ETHER
},
232 { raw_if_print
, DLT_RAW
},
234 { raw_if_print
, DLT_IPV4
},
237 { raw_if_print
, DLT_IPV6
},
239 #ifdef DLT_SLIP_BSDOS
240 { sl_bsdos_if_print
, DLT_SLIP_BSDOS
},
242 { sl_if_print
, DLT_SLIP
},
244 { sunatm_if_print
, DLT_SUNATM
},
246 #ifdef DLT_SYMANTEC_FIREWALL
247 { symantec_if_print
, DLT_SYMANTEC_FIREWALL
},
250 { usb_linux_48_byte_if_print
, DLT_USB_LINUX
},
251 #endif /* DLT_USB_LINUX */
252 #ifdef DLT_USB_LINUX_MMAPPED
253 { usb_linux_64_byte_if_print
, DLT_USB_LINUX_MMAPPED
},
254 #endif /* DLT_USB_LINUX_MMAPPED */
256 { vsock_if_print
, DLT_VSOCK
},
261 static void ndo_default_print(netdissect_options
*ndo
, const u_char
*bp
,
264 static void NORETURN
ndo_error(netdissect_options
*ndo
,
265 status_exit_codes_t status
,
266 FORMAT_STRING(const char *fmt
), ...)
268 static void ndo_warning(netdissect_options
*ndo
,
269 FORMAT_STRING(const char *fmt
), ...)
272 static int ndo_printf(netdissect_options
*ndo
,
273 FORMAT_STRING(const char *fmt
), ...)
277 init_print(netdissect_options
*ndo
, uint32_t localnet
, uint32_t mask
)
280 init_addrtoname(ndo
, localnet
, mask
);
285 lookup_uint_printer(int type
)
287 const struct uint_printer
*p
;
289 for (p
= uint_printers
; p
->f
; ++p
)
293 #if defined(DLT_USER2) && defined(DLT_PKTAP)
295 * Apple incorrectly chose to use DLT_USER2 for their PKTAP
298 * We map DLT_PKTAP, whether it's DLT_USER2 as it is on Darwin-
299 * based OSes or the same value as LINKTYPE_PKTAP as it is on
300 * other OSes, to LINKTYPE_PKTAP, so files written with
301 * this version of libpcap for a DLT_PKTAP capture have a link-
302 * layer header type of LINKTYPE_PKTAP.
304 * However, files written on OS X Mavericks for a DLT_PKTAP
305 * capture have a link-layer header type of LINKTYPE_USER2.
306 * If we don't have a printer for DLT_USER2, and type is
307 * DLT_USER2, we look up the printer for DLT_PKTAP and use
310 if (type
== DLT_USER2
) {
311 for (p
= uint_printers
; p
->f
; ++p
)
312 if (DLT_PKTAP
== p
->type
)
322 lookup_void_printer(int type
)
324 const struct void_printer
*p
;
326 for (p
= void_printers
; p
->f
; ++p
)
330 #if defined(DLT_USER2) && defined(DLT_PKTAP)
332 * Apple incorrectly chose to use DLT_USER2 for their PKTAP
335 * We map DLT_PKTAP, whether it's DLT_USER2 as it is on Darwin-
336 * based OSes or the same value as LINKTYPE_PKTAP as it is on
337 * other OSes, to LINKTYPE_PKTAP, so files written with
338 * this version of libpcap for a DLT_PKTAP capture have a link-
339 * layer header type of LINKTYPE_PKTAP.
341 * However, files written on OS X Mavericks for a DLT_PKTAP
342 * capture have a link-layer header type of LINKTYPE_USER2.
343 * If we don't have a printer for DLT_USER2, and type is
344 * DLT_USER2, we look up the printer for DLT_PKTAP and use
347 if (type
== DLT_USER2
) {
348 for (p
= void_printers
; p
->f
; ++p
)
349 if (DLT_PKTAP
== p
->type
)
359 lookup_printer(netdissect_options
*ndo
, int type
)
361 if_printer_t printer
;
363 printer
.void_printer
= lookup_void_printer(type
);
364 ndo
->ndo_void_printer
= TRUE
;
365 if (printer
.void_printer
== NULL
) {
366 printer
.uint_printer
= lookup_uint_printer(type
);
367 ndo
->ndo_void_printer
= FALSE
;
373 has_printer(int type
)
375 return (lookup_void_printer(type
) != NULL
||
376 lookup_uint_printer(type
) != NULL
);
380 get_if_printer(netdissect_options
*ndo
, int type
)
382 if_printer_t printer
;
384 printer
= lookup_printer(ndo
, type
);
385 if (printer
.printer
== NULL
)
386 printer
.void_printer
= unsupported_if_print
;
391 pretty_print_packet(netdissect_options
*ndo
, const struct pcap_pkthdr
*h
,
392 const u_char
*sp
, u_int packets_captured
)
395 int invalid_header
= 0;
397 if (ndo
->ndo_packet_number
)
398 ND_PRINT("%5u ", packets_captured
);
400 /* Sanity checks on packet length / capture length */
401 if (h
->caplen
== 0) {
403 ND_PRINT("[Invalid header: caplen==0");
406 if (!invalid_header
) {
408 ND_PRINT("[Invalid header:");
412 } else if (h
->len
< h
->caplen
) {
413 if (!invalid_header
) {
415 ND_PRINT("[Invalid header:");
418 ND_PRINT(" len(%u) < caplen(%u)", h
->len
, h
->caplen
);
420 if (h
->caplen
> MAXIMUM_SNAPLEN
) {
421 if (!invalid_header
) {
423 ND_PRINT("[Invalid header:");
426 ND_PRINT(" caplen(%u) > %u", h
->caplen
, MAXIMUM_SNAPLEN
);
428 if (h
->len
> MAXIMUM_SNAPLEN
) {
429 if (!invalid_header
) {
431 ND_PRINT("[Invalid header:");
434 ND_PRINT(" len(%u) > %u", h
->len
, MAXIMUM_SNAPLEN
);
436 if (invalid_header
) {
443 * capture length != 0,
444 * packet length != 0,
445 * capture length <= MAXIMUM_SNAPLEN,
446 * packet length <= MAXIMUM_SNAPLEN,
447 * packet length >= capture length.
449 * Currently, there is no D-Bus printer, thus no need for
453 ts_print(ndo
, &h
->ts
);
456 * Printers must check that they're not walking off the end of
458 * Rather than pass it all the way down, we set this member
459 * of the netdissect_options structure.
461 ndo
->ndo_snapend
= sp
+ h
->caplen
;
463 ndo
->ndo_protocol
= "";
464 ndo
->ndo_ll_hdr_len
= 0;
465 if (setjmp(ndo
->ndo_truncated
) == 0) {
466 /* Print the packet. */
467 if (ndo
->ndo_void_printer
== TRUE
) {
468 (ndo
->ndo_if_printer
.void_printer
)(ndo
, h
, sp
);
469 hdrlen
= ndo
->ndo_ll_hdr_len
;
471 hdrlen
= (ndo
->ndo_if_printer
.uint_printer
)(ndo
, h
, sp
);
473 /* A printer quit because the packet was truncated; report it */
474 ND_PRINT(" [|%s]", ndo
->ndo_protocol
);
475 hdrlen
= ndo
->ndo_ll_hdr_len
;
479 * Empty the stack of packet information, freeing all pushed buffers;
480 * if we got here by a printer quitting, we need to release anything
481 * that didn't get released because we longjmped out of the code
482 * before it popped the packet information.
484 nd_pop_all_packet_info(ndo
);
487 * Restore the original snapend, as a printer might have
490 ndo
->ndo_snapend
= sp
+ h
->caplen
;
491 if (ndo
->ndo_Xflag
) {
493 * Print the raw packet data in hex and ASCII.
495 if (ndo
->ndo_Xflag
> 1) {
497 * Include the link-layer header.
499 hex_and_ascii_print(ndo
, "\n\t", sp
, h
->caplen
);
502 * Don't include the link-layer header - and if
503 * we have nothing past the link-layer header,
506 if (h
->caplen
> hdrlen
)
507 hex_and_ascii_print(ndo
, "\n\t", sp
+ hdrlen
,
510 } else if (ndo
->ndo_xflag
) {
512 * Print the raw packet data in hex.
514 if (ndo
->ndo_xflag
> 1) {
516 * Include the link-layer header.
518 hex_print(ndo
, "\n\t", sp
, h
->caplen
);
521 * Don't include the link-layer header - and if
522 * we have nothing past the link-layer header,
525 if (h
->caplen
> hdrlen
)
526 hex_print(ndo
, "\n\t", sp
+ hdrlen
,
529 } else if (ndo
->ndo_Aflag
) {
531 * Print the raw packet data in ASCII.
533 if (ndo
->ndo_Aflag
> 1) {
535 * Include the link-layer header.
537 ascii_print(ndo
, sp
, h
->caplen
);
540 * Don't include the link-layer header - and if
541 * we have nothing past the link-layer header,
544 if (h
->caplen
> hdrlen
)
545 ascii_print(ndo
, sp
+ hdrlen
, h
->caplen
- hdrlen
);
554 * By default, print the specified data out in hex and ASCII.
557 ndo_default_print(netdissect_options
*ndo
, const u_char
*bp
, u_int length
)
559 hex_and_ascii_print(ndo
, "\n\t", bp
, length
); /* pass on lf and indentation string */
564 ndo_error(netdissect_options
*ndo
, status_exit_codes_t status
,
565 const char *fmt
, ...)
569 if (ndo
->program_name
)
570 (void)fprintf(stderr
, "%s: ", ndo
->program_name
);
572 (void)vfprintf(stderr
, fmt
, ap
);
577 (void)fputc('\n', stderr
);
586 ndo_warning(netdissect_options
*ndo
, const char *fmt
, ...)
590 if (ndo
->program_name
)
591 (void)fprintf(stderr
, "%s: ", ndo
->program_name
);
592 (void)fprintf(stderr
, "WARNING: ");
594 (void)vfprintf(stderr
, fmt
, ap
);
599 (void)fputc('\n', stderr
);
604 ndo_printf(netdissect_options
*ndo
, const char *fmt
, ...)
610 ret
= vfprintf(stdout
, fmt
, args
);
614 ndo_error(ndo
, S_ERR_ND_WRITE_FILE
,
615 "Unable to write output: %s", pcap_strerror(errno
));
620 ndo_set_function_pointers(netdissect_options
*ndo
)
622 ndo
->ndo_default_print
=ndo_default_print
;
623 ndo
->ndo_printf
=ndo_printf
;
624 ndo
->ndo_error
=ndo_error
;
625 ndo
->ndo_warning
=ndo_warning
;