]> git.ipfire.org Git - thirdparty/snort3.git/commitdiff
dce_rpc: underflow memory leak fix
authorJITHENDIRAN EASWARAMURTHY KOUSALYA <jieaswar@cisco.com>
Fri, 10 Apr 2026 11:11:12 +0000 (16:41 +0530)
committerGitHub <noreply@github.com>
Fri, 10 Apr 2026 11:11:12 +0000 (16:41 +0530)
src/service_inspectors/dce_rpc/dce_co.cc

index 7f72f76c895baaf7dd38a044c7481477437cb9f6..e8495ea3113ce787b1908657c21a1d1be26a0914 100644 (file)
@@ -1312,24 +1312,30 @@ static Packet* DCE2_CoGetRpkt(DCE2_SsnData* sd, DCE2_CoTracker* cot,
     if ((frag_data != nullptr) && (seg_data != nullptr))
     {
         uint16_t hdr_size = sizeof(DceRpcCoHdr) + sizeof(DceRpcCoRequest);
-
-        /* Need to just extract the stub data from the seg buffer
-         * if there is enough data there */
-        // FIXIT-L PORT_IF_NEEDED seg len check
-        const DceRpcCoHdr* co_hdr = (const DceRpcCoHdr*)seg_data;
-
-        /* Don't use it if it's not a request and therefore doesn't
-         * belong with the frag data.  This is an insanity check -
-         * shouldn't have seg data that's not a request if there are
-         * frags queued up */
-        if (DceRpcCoPduType(co_hdr) != DCERPC_PDU_TYPE__REQUEST)
+        if (seg_len >= hdr_size)
         {
-            seg_data = nullptr;
-            seg_len = 0;
+            /* Need to just extract the stub data from the seg buffer
+             * if there is enough data there */
+            const DceRpcCoHdr* co_hdr = (const DceRpcCoHdr*)seg_data;
+
+            /* Don't use it if it's not a request and therefore doesn't
+             * belong with the frag data.  This is an insanity check -
+             * shouldn't have seg data that's not a request if there are
+             * frags queued up */
+            if (DceRpcCoPduType(co_hdr) != DCERPC_PDU_TYPE__REQUEST)
+            {
+                seg_data = nullptr;
+                seg_len = 0;
+            }
+            else
+            {
+                dce2_move(seg_data, seg_len, hdr_size);
+            }
         }
         else
         {
-            dce2_move(seg_data, seg_len, hdr_size);
+            seg_data = nullptr;
+            seg_len = 0;
         }
     }
 
@@ -2182,17 +2188,19 @@ static void DCE2_CoEarlyReassemble(DCE2_SsnData* sd, DCE2_CoTracker* cot)
         {
             uint16_t hdr_size = sizeof(DceRpcCoHdr) + sizeof(DceRpcCoRequest);
 
-            // FIXIT-L PORT_IF_NEEDED header size check
-            DceRpcCoHdr* co_hdr = (DceRpcCoHdr*)DCE2_BufferData(cot->cli_seg.buf);
-
-            if (DceRpcCoPduType(co_hdr) == DCERPC_PDU_TYPE__REQUEST)
+            if (DCE2_BufferLength(cot->cli_seg.buf) >= hdr_size)
             {
-                seg_bytes = DCE2_BufferLength(cot->cli_seg.buf) - hdr_size;
+                DceRpcCoHdr* co_hdr = (DceRpcCoHdr*)DCE2_BufferData(cot->cli_seg.buf);
 
-                if ((UINT32_MAX - bytes) < seg_bytes)
-                    seg_bytes = UINT32_MAX - bytes;
+                if (DceRpcCoPduType(co_hdr) == DCERPC_PDU_TYPE__REQUEST)
+                {
+                    seg_bytes = DCE2_BufferLength(cot->cli_seg.buf) - hdr_size;
+
+                    if ((UINT32_MAX - bytes) < seg_bytes)
+                        seg_bytes = UINT32_MAX - bytes;
 
-                bytes += seg_bytes;
+                    bytes += seg_bytes;
+                }
             }
         }