2 * Our own private code for writing libpcap files when capturing.
4 * We have these because we want a way to open a stream for output given
5 * only a file descriptor. libpcap 0.9[.x] has "pcap_dump_fopen()", which
8 * 1) earlier versions of libpcap doesn't have it
12 * 2) WinPcap doesn't have it, because a file descriptor opened
13 * by code built for one version of the MSVC++ C library
14 * can't be used by library routines built for another version
15 * (e.g., threaded vs. unthreaded).
17 * Libpcap's pcap_dump() also doesn't return any error indications.
21 * Wireshark - Network traffic analyzer
22 * By Gerald Combs <gerald@wireshark.org>
23 * Copyright 1998 Gerald Combs
25 * Derived from code in the Wiretap Library
26 * Copyright (c) 1998 by Gilbert Ramirez <gram@alumni.rice.edu>
28 * This program is free software; you can redistribute it and/or
29 * modify it under the terms of the GNU General Public License
30 * as published by the Free Software Foundation; either version 2
31 * of the License, or (at your option) any later version.
33 * This program is distributed in the hope that it will be useful,
34 * but WITHOUT ANY WARRANTY; without even the implied warranty of
35 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
36 * GNU General Public License for more details.
38 * You should have received a copy of the GNU General Public License
39 * along with this program; if not, write to the Free Software
40 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
49 #ifdef HAVE_SYS_TIME_H
60 /* Magic numbers in "libpcap" files.
62 "libpcap" file records are written in the byte order of the host that
63 writes them, and the reader is expected to fix this up.
65 PCAP_MAGIC is the magic number, in host byte order; PCAP_SWAPPED_MAGIC
66 is a byte-swapped version of that.
68 PCAP_NSEC_MAGIC is for Ulf Lamping's modified "libpcap" format,
69 which uses the same common file format as PCAP_MAGIC, but the
70 timestamps are saved in nanosecond resolution instead of microseconds.
71 PCAP_SWAPPED_NSEC_MAGIC is a byte-swapped version of that. */
72 #define PCAP_MAGIC 0xa1b2c3d4
73 #define PCAP_SWAPPED_MAGIC 0xd4c3b2a1
74 #define PCAP_NSEC_MAGIC 0xa1b23c4d
75 #define PCAP_SWAPPED_NSEC_MAGIC 0x4d3cb2a1
77 /* "libpcap" file header. */
79 guint32 magic
; /* magic number */
80 guint16 version_major
; /* major version number */
81 guint16 version_minor
; /* minor version number */
82 gint32 thiszone
; /* GMT to local correction */
83 guint32 sigfigs
; /* accuracy of timestamps */
84 guint32 snaplen
; /* max length of captured packets, in octets */
85 guint32 network
; /* data link type */
88 /* "libpcap" record header. */
90 guint32 ts_sec
; /* timestamp seconds */
91 guint32 ts_usec
; /* timestamp microseconds (nsecs for PCAP_NSEC_MAGIC) */
92 guint32 incl_len
; /* number of octets of packet saved in file */
93 guint32 orig_len
; /* actual length of packet */
96 /* Magic numbers in ".pcapng" files.
98 * .pcapng file records are written in the byte order of the host that
99 * writes them, and the reader is expected to fix this up.
100 * PCAPNG_MAGIC is the magic number, in host byte order;
101 * PCAPNG_SWAPPED_MAGIC is a byte-swapped version of that.
103 #define PCAPNG_MAGIC 0x1A2B3C4D
104 #define PCAPNG_SWAPPED_MAGIC 0xD4C3B2A1
106 /* Currently we are only supporting the initial version of
108 #define PCAPNG_MAJOR_VERSION 1
109 #define PCAPNG_MINOR_VERSION 0
111 /* Section Header Block without options and trailing Block Total Length */
114 guint32 block_total_length
;
115 guint32 byte_order_magic
;
116 guint16 major_version
;
117 guint16 minor_version
;
118 guint64 section_length
;
120 #define SECTION_HEADER_BLOCK_TYPE 0x0A0D0D0A
122 /* Interface Decription Block without options and trailing Block Total Length */
125 guint32 block_total_length
;
130 #define INTERFACE_DESCRIPTION_BLOCK_TYPE 0x00000001
132 /* Interface Statistics Block without actual packet, options, and trailing
133 Block Total Length */
136 guint32 block_total_length
;
137 guint32 interface_id
;
138 guint32 timestamp_high
;
139 guint32 timestamp_low
;
141 #define INTERFACE_STATISTICS_BLOCK_TYPE 0x00000005
143 /* Enhanced Packet Block without actual packet, options, and trailing
144 Block Total Length */
147 guint32 block_total_length
;
148 guint32 interface_id
;
149 guint32 timestamp_high
;
150 guint32 timestamp_low
;
151 guint32 captured_len
;
154 #define ENHANCED_PACKET_BLOCK_TYPE 0x00000006
158 guint16 value_length
;
160 #define OPT_ENDOFOPT 0
161 #define OPT_COMMENT 1
163 #define SHB_HARDWARE 2 /* currently not used */
165 #define SHB_USERAPPL 4
167 #define IDB_DESCRIPTION 3
168 #define IDB_IF_SPEED 8
169 #define IDB_TSRESOL 9
170 #define IDB_FILTER 11
172 #define ISB_STARTTIME 2
173 #define ISB_ENDTIME 3
176 #define ISB_FILTERACCEPT 6
178 #define ISB_USRDELIV 8
179 #define ADD_PADDING(x) ((((x) + 3) >> 2) << 2)
181 /* Write to capture file */
183 write_to_file(FILE* pfile
, const guint8
* data
, size_t data_length
,
184 guint64
*bytes_written
, int *err
)
188 nwritten
= fwrite(data
, data_length
, 1, pfile
);
198 (*bytes_written
) += data_length
;
202 /* Writing pcap files */
204 /* Write the file header to a dump file.
205 Returns TRUE on success, FALSE on failure.
206 Sets "*err" to an error code, or 0 for a short write, on failure*/
208 libpcap_write_file_header(FILE* pfile
, int linktype
, int snaplen
, gboolean ts_nsecs
, guint64
*bytes_written
, int *err
)
210 struct pcap_hdr file_hdr
;
212 file_hdr
.magic
= ts_nsecs
? PCAP_NSEC_MAGIC
: PCAP_MAGIC
;
213 /* current "libpcap" format is 2.4 */
214 file_hdr
.version_major
= 2;
215 file_hdr
.version_minor
= 4;
216 file_hdr
.thiszone
= 0; /* XXX - current offset? */
217 file_hdr
.sigfigs
= 0; /* unknown, but also apparently unused */
218 file_hdr
.snaplen
= snaplen
;
219 file_hdr
.network
= linktype
;
221 return write_to_file(pfile
, (const guint8
*)&file_hdr
, sizeof(file_hdr
), bytes_written
, err
);
224 /* Write a record for a packet to a dump file.
225 Returns TRUE on success, FALSE on failure. */
227 libpcap_write_packet(FILE* pfile
,
228 time_t sec
, guint32 usec
,
229 guint32 caplen
, guint32 len
,
231 guint64
*bytes_written
, int *err
)
233 struct pcaprec_hdr rec_hdr
;
235 rec_hdr
.ts_sec
= (guint32
)sec
; /* Y2.038K issue in pcap format.... */
236 rec_hdr
.ts_usec
= usec
;
237 rec_hdr
.incl_len
= caplen
;
238 rec_hdr
.orig_len
= len
;
239 if (!write_to_file(pfile
, (const guint8
*)&rec_hdr
, sizeof(rec_hdr
), bytes_written
, err
))
242 return write_to_file(pfile
, pd
, caplen
, bytes_written
, err
);
245 /* Writing pcap-ng files */
248 pcapng_count_string_option(const char *option_value
)
250 if ((option_value
!= NULL
) && (strlen(option_value
) > 0) && (strlen(option_value
) < G_MAXUINT16
)) {
251 /* There's a value to write; get its length */
252 return (guint32
)(sizeof(struct option
) +
253 (guint16
)ADD_PADDING(strlen(option_value
)));
255 return 0; /* nothing to write */
259 pcapng_write_string_option(FILE* pfile
,
260 guint16 option_type
, const char *option_value
,
261 guint64
*bytes_written
, int *err
)
263 size_t option_value_length
;
264 struct option option
;
265 const guint32 padding
= 0;
267 if (option_value
== NULL
)
268 return TRUE
; /* nothing to write */
269 option_value_length
= strlen(option_value
);
270 if ((option_value_length
> 0) && (option_value_length
< G_MAXUINT16
)) {
271 /* something to write */
272 option
.type
= option_type
;
273 option
.value_length
= (guint16
)option_value_length
;
275 if (!write_to_file(pfile
, (const guint8
*)&option
, sizeof(struct option
), bytes_written
, err
))
278 if (!write_to_file(pfile
, (const guint8
*)option_value
, (int) option_value_length
, bytes_written
, err
))
281 if (option_value_length
% 4) {
282 if (!write_to_file(pfile
, (const guint8
*)&padding
, 4 - option_value_length
% 4, bytes_written
, err
))
290 pcapng_write_session_header_block(FILE* pfile
,
295 guint64 section_length
,
296 guint64
*bytes_written
,
300 struct option option
;
301 guint32 block_total_length
;
302 guint32 options_length
;
304 /* Size of base header */
305 block_total_length
= sizeof(struct shb
) +
308 options_length
+= pcapng_count_string_option(comment
);
309 options_length
+= pcapng_count_string_option(hw
);
310 options_length
+= pcapng_count_string_option(os
);
311 options_length
+= pcapng_count_string_option(appname
);
312 /* If we have options add size of end-of-options */
313 if (options_length
!= 0) {
314 options_length
+= (guint32
)sizeof(struct option
);
316 block_total_length
+= options_length
;
318 /* write shb header */
319 shb
.block_type
= SECTION_HEADER_BLOCK_TYPE
;
320 shb
.block_total_length
= block_total_length
;
321 shb
.byte_order_magic
= PCAPNG_MAGIC
;
322 shb
.major_version
= PCAPNG_MAJOR_VERSION
;
323 shb
.minor_version
= PCAPNG_MINOR_VERSION
;
324 shb
.section_length
= section_length
;
326 if (!write_to_file(pfile
, (const guint8
*)&shb
, sizeof(struct shb
), bytes_written
, err
))
329 if (!pcapng_write_string_option(pfile
, OPT_COMMENT
, comment
,
332 if (!pcapng_write_string_option(pfile
, SHB_HARDWARE
, hw
,
335 if (!pcapng_write_string_option(pfile
, SHB_OS
, os
,
338 if (!pcapng_write_string_option(pfile
, SHB_USERAPPL
, appname
,
341 if (options_length
!= 0) {
342 /* write end of options */
343 option
.type
= OPT_ENDOFOPT
;
344 option
.value_length
= 0;
345 if (!write_to_file(pfile
, (const guint8
*)&option
, sizeof(struct option
), bytes_written
, err
))
349 /* write the trailing block total length */
350 return write_to_file(pfile
, (const guint8
*)&block_total_length
, sizeof(guint32
), bytes_written
, err
);
354 pcapng_write_interface_description_block(FILE* pfile
,
355 const char *comment
, /* OPT_COMMENT 1 */
356 const char *name
, /* IDB_NAME 2 */
357 const char *descr
, /* IDB_DESCRIPTION 3 */
358 const char *filter
, /* IDB_FILTER 11 */
359 const char *os
, /* IDB_OS 12 */
362 guint64
*bytes_written
,
363 guint64 if_speed
, /* IDB_IF_SPEED 8 */
364 guint8 tsresol
, /* IDB_TSRESOL 9 */
368 struct option option
;
369 guint32 block_total_length
;
370 guint32 options_length
;
371 const guint32 padding
= 0;
373 block_total_length
= (guint32
)(sizeof(struct idb
) + sizeof(guint32
));
375 /* 01 - OPT_COMMENT */
376 options_length
+= pcapng_count_string_option(comment
);
379 options_length
+= pcapng_count_string_option(name
);
381 /* 03 - IDB_DESCRIPTION */
382 options_length
+= pcapng_count_string_option(descr
);
384 /* 08 - IDB_IF_SPEED */
386 options_length
+= (guint32
)(sizeof(struct option
) +
390 /* 09 - IDB_TSRESOL */
392 options_length
+= (guint32
)(sizeof(struct option
) +
393 sizeof(struct option
));
396 /* 11 - IDB_FILTER */
397 if ((filter
!= NULL
) && (strlen(filter
) > 0) && (strlen(filter
) < G_MAXUINT16
)) {
398 /* No, this isn't a string, it has an extra type byte */
399 options_length
+= (guint32
)(sizeof(struct option
) +
400 (guint16
)(ADD_PADDING(strlen(filter
)+ 1)));
404 options_length
+= pcapng_count_string_option(os
);
406 /* If we have options add size of end-of-options */
407 if (options_length
!= 0) {
408 options_length
+= (guint32
)sizeof(struct option
);
410 block_total_length
+= options_length
;
412 /* write block header */
413 idb
.block_type
= INTERFACE_DESCRIPTION_BLOCK_TYPE
;
414 idb
.block_total_length
= block_total_length
;
415 idb
.link_type
= link_type
;
417 idb
.snap_len
= snap_len
;
418 if (!write_to_file(pfile
, (const guint8
*)&idb
, sizeof(struct idb
), bytes_written
, err
))
421 /* 01 - OPT_COMMENT - write comment string if applicable */
422 if (!pcapng_write_string_option(pfile
, OPT_COMMENT
, comment
,
426 /* 02 - IDB_NAME - write interface name string if applicable */
427 if (!pcapng_write_string_option(pfile
, IDB_NAME
, name
,
431 /* 03 - IDB_DESCRIPTION */
432 /* write interface description string if applicable */
433 if (!pcapng_write_string_option(pfile
, IDB_DESCRIPTION
, descr
,
437 /* 08 - IDB_IF_SPEED */
439 option
.type
= IDB_IF_SPEED
;
440 option
.value_length
= sizeof(guint64
);
442 if (!write_to_file(pfile
, (const guint8
*)&option
, sizeof(struct option
), bytes_written
, err
))
445 if (!write_to_file(pfile
, (const guint8
*)&if_speed
, sizeof(guint64
), bytes_written
, err
))
449 /* 09 - IDB_TSRESOL */
451 option
.type
= IDB_TSRESOL
;
452 option
.value_length
= sizeof(guint8
);
454 if (!write_to_file(pfile
, (const guint8
*)&option
, sizeof(struct option
), bytes_written
, err
))
457 if (!write_to_file(pfile
, (const guint8
*)&tsresol
, sizeof(guint8
), bytes_written
, err
))
460 if (!write_to_file(pfile
, (const guint8
*)&padding
, 3, bytes_written
, err
))
464 /* 11 - IDB_FILTER - write filter string if applicable
465 * We only write version 1 of the filter, pcapng string
467 if ((filter
!= NULL
) && (strlen(filter
) > 0) && (strlen(filter
) < G_MAXUINT16
- 1)) {
468 option
.type
= IDB_FILTER
;
469 option
.value_length
= (guint16
)(strlen(filter
) + 1 );
470 if (!write_to_file(pfile
, (const guint8
*)&option
, sizeof(struct option
), bytes_written
, err
))
473 /* The first byte of the Option Data keeps a code of the filter used, 0 = lipbpcap filter string */
474 if (!write_to_file(pfile
, (const guint8
*)&padding
, 1, bytes_written
, err
))
476 if (!write_to_file(pfile
, (const guint8
*)filter
, (int) strlen(filter
), bytes_written
, err
))
478 if ((strlen(filter
) + 1) % 4) {
479 if (!write_to_file(pfile
, (const guint8
*)&padding
, 4 - (strlen(filter
) + 1) % 4, bytes_written
, err
))
484 /* 12 - IDB_OS - write os string if applicable */
485 if (!pcapng_write_string_option(pfile
, IDB_OS
, os
,
489 if (options_length
!= 0) {
490 /* write end of options */
491 option
.type
= OPT_ENDOFOPT
;
492 option
.value_length
= 0;
493 if (!write_to_file(pfile
, (const guint8
*)&option
, sizeof(struct option
), bytes_written
, err
))
497 /* write the trailing Block Total Length */
498 return write_to_file(pfile
, (const guint8
*)&block_total_length
, sizeof(guint32
), bytes_written
, err
);
501 /* Write a record for a packet to a dump file.
502 Returns TRUE on success, FALSE on failure. */
504 pcapng_write_enhanced_packet_block(FILE* pfile
,
506 time_t sec
, guint32 usec
,
507 guint32 caplen
, guint32 len
,
508 guint32 interface_id
,
512 guint64
*bytes_written
,
516 struct option option
;
517 guint32 block_total_length
;
519 guint32 options_length
;
520 const guint32 padding
= 0;
522 block_total_length
= (guint32
)(sizeof(struct epb
) +
523 ADD_PADDING(caplen
) +
526 options_length
+= pcapng_count_string_option(comment
);
528 options_length
+= (guint32
)(sizeof(struct option
) +
531 /* If we have options add size of end-of-options */
532 if (options_length
!= 0) {
533 options_length
+= (guint32
)sizeof(struct option
);
535 block_total_length
+= options_length
;
536 timestamp
= (guint64
)sec
* ts_mul
+ (guint64
)usec
;
537 epb
.block_type
= ENHANCED_PACKET_BLOCK_TYPE
;
538 epb
.block_total_length
= block_total_length
;
539 epb
.interface_id
= interface_id
;
540 epb
.timestamp_high
= (guint32
)((timestamp
>>32) & 0xffffffff);
541 epb
.timestamp_low
= (guint32
)(timestamp
& 0xffffffff);
542 epb
.captured_len
= caplen
;
543 epb
.packet_len
= len
;
544 if (!write_to_file(pfile
, (const guint8
*)&epb
, sizeof(struct epb
), bytes_written
, err
))
546 if (!write_to_file(pfile
, pd
, caplen
, bytes_written
, err
))
549 if (!write_to_file(pfile
, (const guint8
*)&padding
, 4 - caplen
% 4, bytes_written
, err
))
552 if (!pcapng_write_string_option(pfile
, OPT_COMMENT
, comment
,
556 option
.type
= EPB_FLAGS
;
557 option
.value_length
= sizeof(guint32
);
558 if (!write_to_file(pfile
, (const guint8
*)&option
, sizeof(struct option
), bytes_written
, err
))
560 if (!write_to_file(pfile
, (const guint8
*)&flags
, sizeof(guint32
), bytes_written
, err
))
563 if (options_length
!= 0) {
564 /* write end of options */
565 option
.type
= OPT_ENDOFOPT
;
566 option
.value_length
= 0;
567 if (!write_to_file(pfile
, (const guint8
*)&option
, sizeof(struct option
), bytes_written
, err
))
571 return write_to_file(pfile
, (const guint8
*)&block_total_length
, sizeof(guint32
), bytes_written
, err
);
575 pcapng_write_interface_statistics_block(FILE* pfile
,
576 guint32 interface_id
,
577 guint64
*bytes_written
,
578 const char *comment
, /* OPT_COMMENT 1 */
579 guint64 isb_starttime
, /* ISB_STARTTIME 2 */
580 guint64 isb_endtime
, /* ISB_ENDTIME 3 */
581 guint64 isb_ifrecv
, /* ISB_IFRECV 4 */
582 guint64 isb_ifdrop
, /* ISB_IFDROP 5 */
591 struct option option
;
592 guint32 block_total_length
;
593 guint32 options_length
;
598 * Current time, represented as 100-nanosecond intervals since
599 * January 1, 1601, 00:00:00 UTC.
601 * I think DWORD might be signed, so cast both parts of "now"
602 * to guint32 so that the sign bit doesn't get treated specially.
604 * Windows 8 provides GetSystemTimePreciseAsFileTime which we
605 * might want to use instead.
607 GetSystemTimeAsFileTime(&now
);
608 timestamp
= (((guint64
)(guint32
)now
.dwHighDateTime
) << 32) +
609 (guint32
)now
.dwLowDateTime
;
612 * Convert to same thing but as 1-microsecond, i.e. 1000-nanosecond,
618 * Subtract difference, in microseconds, between January 1, 1601
619 * 00:00:00 UTC and January 1, 1970, 00:00:00 UTC.
621 timestamp
-= G_GINT64_CONSTANT(11644473600000000U);
624 * Current time, represented as seconds and microseconds since
625 * January 1, 1970, 00:00:00 UTC.
627 gettimeofday(&now
, NULL
);
630 * Convert to delta in microseconds.
632 timestamp
= (guint64
)(now
.tv_sec
) * 1000000 +
633 (guint64
)(now
.tv_usec
);
635 block_total_length
= (guint32
)(sizeof(struct isb
) + sizeof(guint32
));
637 if (isb_ifrecv
!= G_MAXUINT64
) {
638 options_length
+= (guint32
)(sizeof(struct option
) +
641 if (isb_ifdrop
!= G_MAXUINT64
) {
642 options_length
+= (guint32
)(sizeof(struct option
) +
646 options_length
+= pcapng_count_string_option(comment
);
647 if (isb_starttime
!=0) {
648 options_length
+= (guint32
)(sizeof(struct option
) +
649 sizeof(guint64
)); /* ISB_STARTTIME */
651 if (isb_endtime
!=0) {
652 options_length
+= (guint32
)(sizeof(struct option
) +
653 sizeof(guint64
)); /* ISB_ENDTIME */
655 /* If we have options add size of end-of-options */
656 if (options_length
!= 0) {
657 options_length
+= (guint32
)sizeof(struct option
);
659 block_total_length
+= options_length
;
661 isb
.block_type
= INTERFACE_STATISTICS_BLOCK_TYPE
;
662 isb
.block_total_length
= block_total_length
;
663 isb
.interface_id
= interface_id
;
664 isb
.timestamp_high
= (guint32
)((timestamp
>>32) & 0xffffffff);
665 isb
.timestamp_low
= (guint32
)(timestamp
& 0xffffffff);
666 if (!write_to_file(pfile
, (const guint8
*)&isb
, sizeof(struct isb
), bytes_written
, err
))
669 /* write comment string if applicable */
670 if (!pcapng_write_string_option(pfile
, OPT_COMMENT
, comment
,
674 if (isb_starttime
!=0) {
677 option
.type
= ISB_STARTTIME
;
678 option
.value_length
= sizeof(guint64
);
679 high
= (guint32
)((isb_starttime
>>32) & 0xffffffff);
680 low
= (guint32
)(isb_starttime
& 0xffffffff);
681 if (!write_to_file(pfile
, (const guint8
*)&option
, sizeof(struct option
), bytes_written
, err
))
684 if (!write_to_file(pfile
, (const guint8
*)&high
, sizeof(guint32
), bytes_written
, err
))
687 if (!write_to_file(pfile
, (const guint8
*)&low
, sizeof(guint32
), bytes_written
, err
))
690 if (isb_endtime
!=0) {
693 option
.type
= ISB_ENDTIME
;
694 option
.value_length
= sizeof(guint64
);
695 high
= (guint32
)((isb_endtime
>>32) & 0xffffffff);
696 low
= (guint32
)(isb_endtime
& 0xffffffff);
697 if (!write_to_file(pfile
, (const guint8
*)&option
, sizeof(struct option
), bytes_written
, err
))
700 if (!write_to_file(pfile
, (const guint8
*)&high
, sizeof(guint32
), bytes_written
, err
))
703 if (!write_to_file(pfile
, (const guint8
*)&low
, sizeof(guint32
), bytes_written
, err
))
706 if (isb_ifrecv
!= G_MAXUINT64
) {
707 option
.type
= ISB_IFRECV
;
708 option
.value_length
= sizeof(guint64
);
709 if (!write_to_file(pfile
, (const guint8
*)&option
, sizeof(struct option
), bytes_written
, err
))
712 if (!write_to_file(pfile
, (const guint8
*)&isb_ifrecv
, sizeof(guint64
), bytes_written
, err
))
715 if (isb_ifdrop
!= G_MAXUINT64
) {
716 option
.type
= ISB_IFDROP
;
717 option
.value_length
= sizeof(guint64
);
718 if (!write_to_file(pfile
, (const guint8
*)&option
, sizeof(struct option
), bytes_written
, err
))
721 if (!write_to_file(pfile
, (const guint8
*)&isb_ifdrop
, sizeof(guint64
), bytes_written
, err
))
724 if (options_length
!= 0) {
725 /* write end of options */
726 option
.type
= OPT_ENDOFOPT
;
727 option
.value_length
= 0;
728 if (!write_to_file(pfile
, (const guint8
*)&option
, sizeof(struct option
), bytes_written
, err
))
732 return write_to_file(pfile
, (const guint8
*)&block_total_length
, sizeof(guint32
), bytes_written
, err
);
736 * Editor modelines - http://www.wireshark.org/tools/modelines.html
741 * indent-tabs-mode: nil
744 * vi: set shiftwidth=4 tabstop=8 expandtab:
745 * :indentSize=4:tabSize=8:noTabs=true: