From: Francois-Xavier Le Bail Date: Sun, 8 Dec 2024 22:08:52 +0000 (+0100) Subject: Fix two undefined behaviors for the pcap_loop() call X-Git-Url: https://git.tcpdump.org/tcpdump/commitdiff_plain/dc1b49b1f6864a0cbe58bb203634763fb26aa8d1 Fix two undefined behaviors for the pcap_loop() call Limit the --skip argument to INT_MAX. Limit the sum of -c and --skip arguments to INT_MAX. Fix the regression in 3eab64d3: The '--skip 0' option is allowed to get the first packet in some loop e.g. in a shell script. The errors were: tcpdump.c:2696:8: runtime error: implicit conversion from type 'int' of value -1 (32-bit, signed) to type 'u_int' (aka 'unsigned int') changed the value to 4294967295 (32-bit, unsigned) SUMMARY: UndefinedBehaviorSanitizer: undefined-behavior tcpdump.c:2696:8 tcpdump.c:2696:8: runtime error: implicit conversion from type 'u_int' (aka 'unsigned int') of value 4294967295 (32-bit, unsigned) to type 'int' changed the value to -1 (32-bit, signed) SUMMARY: UndefinedBehaviorSanitizer: undefined-behavior tcpdump.c:2696:8 --- diff --git a/tcpdump.c b/tcpdump.c index 3786b1da..31a81670 100644 --- a/tcpdump.c +++ b/tcpdump.c @@ -2056,7 +2056,7 @@ main(int argc, char **argv) case OPTION_SKIP: packets_skipped = parse_u_int("packet skip count", - optarg, NULL, 1, UINT_MAX, 0); + optarg, NULL, 0, INT_MAX, 0); break; #ifdef HAVE_PCAP_SET_TSTAMP_PRECISION @@ -2097,6 +2097,12 @@ main(int argc, char **argv) if (ndo->ndo_xflag && ndo->ndo_Xflag) warning("-x[x] and -X[X] are mutually exclusive. -x[x] ignored."); + if (cnt != -1) + if ((int)packets_skipped > (INT_MAX - cnt)) + // cnt + (int)packets_skipped used in pcap_loop() call + error("Overflow (-c count) %d + (--skip count) %d", cnt, + (int)packets_skipped); + if (Dflag) show_devices_and_exit(); #ifdef HAVE_PCAP_FINDALLDEVS_EX @@ -2693,7 +2699,7 @@ DIAG_ON_ASSIGN_ENUM do { status = pcap_loop(pd, - cnt + (cnt == -1 ? 0 : packets_skipped), + (cnt == -1 ? -1 : cnt + (int)packets_skipped), callback, pcap_userdata); if (WFileName == NULL) { /*