mirror of
https://github.com/php/php-src.git
synced 2025-08-16 05:58:45 +02:00
Fix GH-18597: Heap-buffer-overflow in zend_alloc.c when assigning string with UTF-8 bytes
xmlSave() also can flush in some cases. When the encoding is not available this can fail for short inputs, resulting in an empty string which is interned but then wrongly tagged by RETURN_NEW_STR. Fix this by checking the error condition and switching to RETURN_STR for defense-in-depth. This issue also exists on 8.3, but does not crash; however, due to the different API usage internally I cannot easily fix it on 8.3. There it gives a partial output. Closes GH-18606.
This commit is contained in:
parent
3e0a4259a8
commit
40e667280b
6 changed files with 26 additions and 5 deletions
3
NEWS
3
NEWS
|
@ -2,6 +2,9 @@ PHP NEWS
|
|||
|||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||
?? ??? ????, PHP 8.4.9
|
||||
|
||||
- SimpleXML:
|
||||
. Fixed bug GH-18597 (Heap-buffer-overflow in zend_alloc.c when assigning
|
||||
string with UTF-8 bytes). (nielsdos)
|
||||
|
||||
06 Jun 2025, PHP 8.4.8
|
||||
|
||||
|
|
|
@ -98,7 +98,7 @@ zend_result dom_element_inner_html_read(dom_object *obj, zval *retval)
|
|||
status |= xmlOutputBufferFlush(out);
|
||||
status |= xmlOutputBufferClose(out);
|
||||
}
|
||||
(void) xmlSaveClose(ctxt);
|
||||
status |= xmlSaveClose(ctxt);
|
||||
xmlCharEncCloseFunc(handler);
|
||||
}
|
||||
if (UNEXPECTED(status < 0)) {
|
||||
|
|
|
@ -282,7 +282,7 @@ static zend_string *php_new_dom_dump_node_to_str_ex(xmlNodePtr node, int options
|
|||
} else {
|
||||
xmlCharEncCloseFunc(handler);
|
||||
}
|
||||
(void) xmlSaveClose(ctxt);
|
||||
status |= xmlSaveClose(ctxt);
|
||||
}
|
||||
|
||||
if (UNEXPECTED(status < 0)) {
|
||||
|
@ -319,7 +319,7 @@ zend_long php_new_dom_dump_node_to_file(const char *filename, xmlDocPtr doc, xml
|
|||
if (EXPECTED(ctxt != NULL)) {
|
||||
status = dom_xml_serialize(ctxt, out, node, format, false, get_private_data_from_node(node));
|
||||
status |= xmlOutputBufferFlush(out);
|
||||
(void) xmlSaveClose(ctxt);
|
||||
status |= xmlSaveClose(ctxt);
|
||||
}
|
||||
|
||||
size_t offset = php_stream_tell(stream);
|
||||
|
|
|
@ -1519,7 +1519,7 @@ static zend_string *php_libxml_default_dump_doc_to_str(xmlDocPtr doc, int option
|
|||
}
|
||||
|
||||
long status = xmlSaveDoc(ctxt, doc);
|
||||
(void) xmlSaveClose(ctxt);
|
||||
status |= xmlSaveClose(ctxt);
|
||||
if (status < 0) {
|
||||
smart_str_free_ex(&str, false);
|
||||
return NULL;
|
||||
|
|
|
@ -1404,7 +1404,8 @@ PHP_METHOD(SimpleXMLElement, asXML)
|
|||
if (!result) {
|
||||
RETURN_FALSE;
|
||||
} else {
|
||||
RETURN_NEW_STR(result);
|
||||
/* Defense-in-depth: don't use the NEW variant in case somehow an empty string gets returned */
|
||||
RETURN_STR(result);
|
||||
}
|
||||
}
|
||||
/* }}} */
|
||||
|
|
17
ext/simplexml/tests/gh18597.phpt
Normal file
17
ext/simplexml/tests/gh18597.phpt
Normal file
|
@ -0,0 +1,17 @@
|
|||
--TEST--
|
||||
GH-18597 (Heap-buffer-overflow in zend_alloc.c when assigning string with UTF-8 bytes)
|
||||
--EXTENSIONS--
|
||||
simplexml
|
||||
--FILE--
|
||||
<?php
|
||||
$sx1 = new SimpleXMLElement("<root />");
|
||||
$sx1->node[0] = 'node1';
|
||||
$node = $sx1->node[0];
|
||||
|
||||
$node[0] = '<27><>c';
|
||||
|
||||
$sx1->asXML(); // Depends on the available system encodings whether this fails or not, point is, it should not crash
|
||||
echo "Done\n";
|
||||
?>
|
||||
--EXPECT--
|
||||
Done
|
Loading…
Add table
Add a link
Reference in a new issue