From 0ee79b2b17437f8401d280b3eea7858cf851d641 Mon Sep 17 00:00:00 2001 From: Niels Dossche <7771979+nielsdos@users.noreply.github.com> Date: Tue, 30 Apr 2024 20:50:30 +0200 Subject: [PATCH 1/2] Add test with wrong output --- ext/dom/tests/DOMNode_C14N_references.phpt | 45 ++++++++++++++++++++++ 1 file changed, 45 insertions(+) create mode 100644 ext/dom/tests/DOMNode_C14N_references.phpt diff --git a/ext/dom/tests/DOMNode_C14N_references.phpt b/ext/dom/tests/DOMNode_C14N_references.phpt new file mode 100644 index 000000000000..2bda9c708264 --- /dev/null +++ b/ext/dom/tests/DOMNode_C14N_references.phpt @@ -0,0 +1,45 @@ +--TEST-- +Test: Canonicalization - C14N() with references +--EXTENSIONS-- +dom +--FILE-- + + + + + + + + +EOXML; + +$dom = new DOMDocument(); +$dom->loadXML($xml); +$doc = $dom->documentElement->firstChild; + +$xpath = [ + 'query' => '(//a:contain | //a:bar | .//namespace::*)', + 'namespaces' => ['a' => 'http://www.example.com/ns/foo'], +]; +$prefixes = ['test']; + +foreach ($xpath['namespaces'] as $k => &$v); +unset($v); +foreach ($xpath as $k => &$v); +unset($v); +foreach ($prefixes as $k => &$v); +unset($v); + +echo $doc->C14N(true, false, $xpath, $prefixes); +?> +--EXPECTF-- +Fatal error: Uncaught TypeError: DOMNode::C14N(): Argument #3 ($xpath) "query" option must be a string, string given in %s:%d +Stack trace: +#0 %s(%d): DOMNode->C14N(true, false, Array, Array) +#1 {main} + thrown in %s on line %d From 52effd0fe9ad2f9d44561b0d30df27fda60ca1c9 Mon Sep 17 00:00:00 2001 From: Niels Dossche <7771979+nielsdos@users.noreply.github.com> Date: Tue, 30 Apr 2024 20:53:04 +0200 Subject: [PATCH 2/2] Fix references not handled correctly in C14N --- ext/dom/node.c | 5 +++-- ext/dom/tests/DOMNode_C14N_references.phpt | 8 ++------ 2 files changed, 5 insertions(+), 8 deletions(-) diff --git a/ext/dom/node.c b/ext/dom/node.c index 973505c5b01a..82f40860cfd3 100644 --- a/ext/dom/node.c +++ b/ext/dom/node.c @@ -1614,7 +1614,7 @@ static void dom_canonicalization(INTERNAL_FUNCTION_PARAMETERS, int mode) /* {{{ zval *tmp; char *xquery; - tmp = zend_hash_str_find(ht, "query", sizeof("query")-1); + tmp = zend_hash_str_find_deref(ht, "query", sizeof("query")-1); if (!tmp) { /* if mode == 0 then $xpath arg is 3, if mode == 1 then $xpath is 4 */ zend_argument_value_error(3 + mode, "must have a \"query\" key"); @@ -1630,12 +1630,13 @@ static void dom_canonicalization(INTERNAL_FUNCTION_PARAMETERS, int mode) /* {{{ ctxp = xmlXPathNewContext(docp); ctxp->node = nodep; - tmp = zend_hash_str_find(ht, "namespaces", sizeof("namespaces")-1); + tmp = zend_hash_str_find_deref(ht, "namespaces", sizeof("namespaces")-1); if (tmp && Z_TYPE_P(tmp) == IS_ARRAY && !HT_IS_PACKED(Z_ARRVAL_P(tmp))) { zval *tmpns; zend_string *prefix; ZEND_HASH_MAP_FOREACH_STR_KEY_VAL(Z_ARRVAL_P(tmp), prefix, tmpns) { + ZVAL_DEREF(tmpns); if (Z_TYPE_P(tmpns) == IS_STRING) { if (prefix) { xmlXPathRegisterNs(ctxp, (xmlChar *) ZSTR_VAL(prefix), (xmlChar *) Z_STRVAL_P(tmpns)); diff --git a/ext/dom/tests/DOMNode_C14N_references.phpt b/ext/dom/tests/DOMNode_C14N_references.phpt index 2bda9c708264..514e22be6365 100644 --- a/ext/dom/tests/DOMNode_C14N_references.phpt +++ b/ext/dom/tests/DOMNode_C14N_references.phpt @@ -37,9 +37,5 @@ unset($v); echo $doc->C14N(true, false, $xpath, $prefixes); ?> ---EXPECTF-- -Fatal error: Uncaught TypeError: DOMNode::C14N(): Argument #3 ($xpath) "query" option must be a string, string given in %s:%d -Stack trace: -#0 %s(%d): DOMNode->C14N(true, false, Array, Array) -#1 {main} - thrown in %s on line %d +--EXPECT-- +