]> The Tcpdump Group git mirrors - tcpdump/commitdiff
ICMP: Update the snapend for some nested IP packets
authorFrancois-Xavier Le Bail <[email protected]>
Sun, 24 Jan 2021 09:52:50 +0000 (10:52 +0100)
committerFrancois-Xavier Le Bail <[email protected]>
Tue, 23 Feb 2021 21:36:12 +0000 (22:36 +0100)
Update the snapend because extensions (MPLS, ...) may be present
after the IP packet. In this case the current (outer) packet's
snapend is not what ip_print() needs to decode an IP packet nested
in the middle of an ICMP payload.

This prevents that, in ip_print(), for the nested IP packet, the
remaining length < remaining caplen.

Moreover:
Reduce the scope of a variable.
Fix spaces

(cherry picked and updated from commit
 a29cd3e75e78bab784e906d6a4978d05510613c8)

CHANGES
print-icmp.c

diff --git a/CHANGES b/CHANGES
index 43b50419de8fbebd1133a5fe4b01cdfd44bf1cca..e010b12951d38927a2ae7354c017af1bfdb36b8b 100644 (file)
--- a/CHANGES
+++ b/CHANGES
@@ -3,6 +3,7 @@ Monthday, Month DD, YYYY by gharris
     Source code:
       Squelch some compiler warnings
       Rebuild configure script when building release
+      ICMP: Update the snapend for some nested IP packets.
     Solaris:
       Fix a compile error with Sun C
 
index eebb6e3fdf2e15240a0cfe7975e0da7c27043f32..e802de576d349d65106480541ac37e1cec023887 100644 (file)
@@ -305,7 +305,6 @@ icmp_print(netdissect_options *ndo, const u_char *bp, u_int plen, const u_char *
        const struct udphdr *ouh;
         const uint8_t *obj_tptr;
         uint32_t raw_label;
-        const u_char *snapend_save;
        const struct icmp_mpls_ext_object_header_t *icmp_mpls_ext_object_header;
        u_int hlen, mtu, obj_tlen, obj_class_num, obj_ctype;
        uint16_t dport;
@@ -651,12 +650,25 @@ icmp_print(netdissect_options *ndo, const u_char *bp, u_int plen, const u_char *
          * save the snaplength as this may get overridden in the IP printer.
          */
        if (ndo->ndo_vflag >= 1 && ICMP_ERRTYPE(icmp_type)) {
+               const u_char *snapend_save;
+
                bp += 8;
                ND_PRINT("\n\t");
                ip = (const struct ip *)bp;
-                snapend_save = ndo->ndo_snapend;
+               snapend_save = ndo->ndo_snapend;
+               /*
+                * Update the snapend because extensions (MPLS, ...) may be
+                * present after the IP packet. In this case the current
+                * (outer) packet's snapend is not what ip_print() needs to
+                * decode an IP packet nested in the middle of an ICMP payload.
+                *
+                * This prevents that, in ip_print(), for the nested IP packet,
+                * the remaining length < remaining caplen.
+                */
+               ndo->ndo_snapend = ND_MIN(bp + GET_BE_U_2(ip->ip_len),
+                                         ndo->ndo_snapend);
                ip_print(ndo, bp, GET_BE_U_2(ip->ip_len));
-                ndo->ndo_snapend = snapend_save;
+               ndo->ndo_snapend = snapend_save;
        }
 
        /* ndo_protocol reassignment after ip_print() call */