From 870eeabe8970db22c9c5f88d64b7b37bdd84bd49 Mon Sep 17 00:00:00 2001 From: Denis Ovsienko Date: Sat, 29 Aug 2020 02:48:07 +0100 Subject: [PATCH] Report periodic stats only when safe to do so. [skip ci] As explained in GH #155, when tcpdump is given -r, -w and -v and it takes long enough to read from the input file (because it is stdin connected through network or a pipe to stdout of another tcpdump doing a live capture), pcap_loop() will error before long. One of the ways to reproduce the fault is as follows: $ tcpdump -i eno1 -w - | tcpdump -r - -w /tmp/tmp.pcap -v tcpdump: listening on eno1, link-type EN10MB (Ethernet), snapshot length 262144 bytes reading from file -, link-type EN10MB (Ethernet), snapshot length 262144 tcpdump: pcap_loop: error reading dump file: Interrupted system call Skip the verbose_stats_dump() timer setup in this specific corner case for the time being and document it. --- tcpdump.1.in | 4 +++- tcpdump.c | 5 ++++- 2 files changed, 7 insertions(+), 2 deletions(-) diff --git a/tcpdump.1.in b/tcpdump.1.in index 7f716ab80..bf4d7b20b 100644 --- a/tcpdump.1.in +++ b/tcpdump.1.in @@ -20,7 +20,7 @@ .\" WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF .\" MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. .\" -.TH TCPDUMP 1 "10 Aug 2020" +.TH TCPDUMP 1 "29 Aug 2020" .SH NAME tcpdump \- dump traffic on a network .SH SYNOPSIS @@ -808,6 +808,8 @@ IP and ICMP header checksum. .IP When writing to a file with the .B \-w +option and at the same time not reading from a file with the +.B \-r option, report, once per second, the number of packets captured. .TP .B \-vv diff --git a/tcpdump.c b/tcpdump.c index 939df0b46..d5d35ffbf 100644 --- a/tcpdump.c +++ b/tcpdump.c @@ -2438,11 +2438,14 @@ DIAG_ON_CLANG(assign-enum) (void)setsignal(SIGNAL_FLUSH_PCAP, flushpcap); #endif - if (ndo->ndo_vflag > 0 && WFileName && !print) { + if (ndo->ndo_vflag > 0 && WFileName && RFileName == NULL && !print) { /* * When capturing to a file, if "--print" wasn't specified, *"-v" means tcpdump should, once per second, * "v"erbosely report the number of packets captured. + * Except when reading from a file, because -r, -w and -v + * together used to make a corner case, in which pcap_loop() + * errored due to EINTR (see GH #155 for details). */ #ifdef _WIN32 /*