From e41032ae9f94d0db2d1074eb68ac7d69bd9e0992 Mon Sep 17 00:00:00 2001
From: mohammadmseet-hue <mohammadmseet@gmail.com>
Date: Thu, 16 Apr 2026 02:54:24 +0200
Subject: [PATCH] fix: add overflow checks to xmlDictAddQString in dict.c

xmlDictAddString has overflow guards for pool size calculations, but its
sibling xmlDictAddQString lacks these entirely. The namelen + plen + 1
addition can overflow unsigned int, and 4 * (overflowed_value) produces
a small allocation, leading to heap buffer overflow when memcpy writes
the prefix and name.

Add the same SIZE_MAX-based overflow guards and safe size_t cast.
---
 dict.c | 19 +++++++++++++++----
 1 file changed, 15 insertions(+), 4 deletions(-)

diff --git a/dict.c b/dict.c
index fed3a0ac4..b87221481 100644
--- a/dict.c
+++ b/dict.c
@@ -218,10 +218,21 @@ xmlDictAddQString(xmlDictPtr dict, const xmlChar *prefix, unsigned int plen,
             return(NULL);
         }
 
-        if (size == 0) size = 1000;
-	else size *= 4; /* exponential growth */
-        if (size < 4 * (namelen + plen + 1))
-	    size = 4 * (namelen + plen + 1); /* just in case ! */
+        if (size == 0) {
+            size = 1000;
+        } else {
+            if (size < (SIZE_MAX - sizeof(xmlDictStrings)) / 4)
+                size *= 4; /* exponential growth */
+            else
+                size = SIZE_MAX - sizeof(xmlDictStrings);
+        }
+        if (size / 4 < namelen + plen + 1) {
+            if ((size_t) namelen + plen + 1 <
+                    (SIZE_MAX - sizeof(xmlDictStrings)) / 4)
+                size = 4 * ((size_t) namelen + plen + 1); /* just in case ! */
+            else
+                return(NULL);
+        }
 	pool = (xmlDictStringsPtr) xmlMalloc(sizeof(xmlDictStrings) + size);
 	if (pool == NULL)
 	    return(NULL);
-- 
GitLab

