]> The Tcpdump Group git mirrors - tcpdump/commitdiff
Fix two undefined behaviors for the pcap_loop() call
authorFrancois-Xavier Le Bail <[email protected]>
Sun, 8 Dec 2024 22:08:52 +0000 (23:08 +0100)
committerfxlb <[email protected]>
Tue, 10 Dec 2024 03:58:04 +0000 (03:58 +0000)
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

tcpdump.c

index 3786b1da8d44bf79cd012e6e0a42d11c2c94d234..31a816707f1ef1c739ee123a4a153ba4d7bfbcf9 100644 (file)
--- 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) {
                        /*