CVE-2017-13045 (published 2017-09-14T06:29Z)

The VQP parser in tcpdump before 4.9.2 has a buffer over-read in print-vqp.c:vqp_print().

Severity: HIGH
CVSS v2 base score: 7.5 (AV:N/AC:L/Au:N/C:P/I:P/A:P)
CVSS v3 base score: 9.8, CRITICAL (CVSS:3.0/AV:N/AC:L/PR:N/UI:N/S:U/C:H/I:H/A:H)

Weakness information:
cwe_id: CWE-125
cwe_name: Out-of-bounds Read
description: The product reads data past the end, or before the beginning, of the intended buffer.
extended_description: 
            
            
             
			 
         
         

Fix information:
repo_url: https://github.com/the-tcpdump-group/tcpdump
commit_details: repo_url: https://github.com/the-tcpdump-group/tcpdump
author: Denis Ovsienko
author_date: 2017-07-29 23:21:00+01:00
msg: CVE-2017-13045/VQP: add some bounds checks

This fixes a buffer over-read discovered by Bhargava Shastry,
SecT/TU Berlin.

Add a test using the capture file supplied by the reporter(s).
repository: repo_url: https://github.com/the-tcpdump-group/tcpdump
repo_name: the-tcpdump-group/tcpdump
description: the TCPdump network dissector
repo_language: C
owner: the-tcpdump-group
file_changes: filename: print-vqp.c
change_type: ModificationType.MODIFY
diff: @@ -26,6 +26,7 @@
 #include "netdissect.h"
 #include "extract.h"
 #include "addrtoname.h"
+#include "ether.h"
 
 #define VQP_VERSION            		1
 #define VQP_EXTRACT_VERSION(x) ((x)&0xFF)
@@ -105,13 +106,15 @@ vqp_print(netdissect_options *ndo, register const u_char *pptr, register u_int l
     const u_char *tptr;
     uint16_t vqp_obj_len;
     uint32_t vqp_obj_type;
-    int tlen;
+    u_int tlen;
     uint8_t nitems;
 
     tptr=pptr;
     tlen = len;
     vqp_common_header = (const struct vqp_common_header_t *)pptr;
     ND_TCHECK(*vqp_common_header);
+    if (sizeof(struct vqp_common_header_t) > tlen)
+        goto trunc;
 
     /*
      * Sanity checking of the header.
@@ -151,6 +154,9 @@ vqp_print(netdissect_options *ndo, register const u_char *pptr, register u_int l
     while (nitems > 0 && tlen > 0) {
 
         vqp_obj_tlv = (const struct vqp_obj_tlv_t *)tptr;
+        ND_TCHECK(*vqp_obj_tlv);
+        if (sizeof(struct vqp_obj_tlv_t) > tlen)
+            goto trunc;
         vqp_obj_type = EXTRACT_32BITS(vqp_obj_tlv->obj_type);
         vqp_obj_len = EXTRACT_16BITS(vqp_obj_tlv->obj_length);
         tptr+=sizeof(struct vqp_obj_tlv_t);
@@ -167,9 +173,13 @@ vqp_print(netdissect_options *ndo, register const u_char *pptr, register u_int l
 
         /* did we capture enough for fully decoding the object ? */
         ND_TCHECK2(*tptr, vqp_obj_len);
+        if (vqp_obj_len > tlen)
+            goto trunc;
 
         switch(vqp_obj_type) {
 	case VQP_OBJ_IP_ADDRESS:
+            if (vqp_obj_len != 4)
+                goto trunc;
             ND_PRINT((ndo, "%s (0x%08x)", ipaddr_string(ndo, tptr), EXTRACT_32BITS(tptr)));
             break;
             /* those objects have similar semantics - fall through */
@@ -182,6 +192,8 @@ vqp_print(netdissect_options *ndo, register const u_char *pptr, register u_int l
             /* those objects have similar semantics - fall through */
 	case VQP_OBJ_MAC_ADDRESS:
 	case VQP_OBJ_MAC_NULL:
+            if (vqp_obj_len != ETHER_ADDR_LEN)
+                goto trunc;
 	      ND_PRINT((ndo, "%s", etheraddr_string(ndo, tptr)));
               break;
         default:

programming_language: C
filename: TESTLIST
change_type: ModificationType.MODIFY
diff: @@ -562,6 +562,7 @@ isakmpv1-attr-oobr	isakmpv1-attr-oobr.pcap		isakmpv1-attr-oobr.out	-v
 hncp_dhcpv6data-oobr	hncp_dhcpv6data-oobr.pcap	hncp_dhcpv6data-oobr.out -v -c1
 # Same comments apply to the case below.
 hncp_dhcpv4data-oobr	hncp_dhcpv4data-oobr.pcap	hncp_dhcpv4data-oobr.out -v -c1
+vqp-oobr		vqp-oobr.pcap			vqp-oobr.out		-v -c1
 
 # bad packets from Katie Holly
 mlppp-oobr		mlppp-oobr.pcap			mlppp-oobr.out

programming_language: Shell
filename: vqp-oobr.out
change_type: ModificationType.ADD
diff: @@ -0,0 +1,4 @@
+IP (tos 0x0, ttl 17, id 40207, offset 0, flags [+, DF, rsvd], proto UDP (17), length 46, bad cksum 8f04 (->f897)!)
+    0.0.128.20.1589 > 12.251.167.8.62720: 
+	VQPv1, unknown (127) Message, error-code unknown (31) (31), seq 0x80f90000, items 27, length 18
+	[|VQP]

programming_language: Markdown