From fae25ca2df204d5b61281cadd38b51b11ec59e4b Mon Sep 17 00:00:00 2001 From: Niels Dossche <7771979+nielsdos@users.noreply.github.com> Date: Sat, 4 May 2024 13:57:07 +0200 Subject: [PATCH] Move dom_attr_value() into ext/libxml --- ext/dom/attr.c | 32 +------------------------------- ext/dom/php_dom.c | 2 +- ext/dom/php_dom.h | 1 - ext/libxml/libxml.c | 30 ++++++++++++++++++++++++++++++ ext/libxml/php_libxml.h | 2 ++ 5 files changed, 34 insertions(+), 33 deletions(-) diff --git a/ext/dom/attr.c b/ext/dom/attr.c index 24c92e2a33a..9cefed6b747 100644 --- a/ext/dom/attr.c +++ b/ext/dom/attr.c @@ -199,40 +199,10 @@ PHP_METHOD(DOMAttr, isId) } /* }}} end dom_attr_is_id */ -xmlChar *dom_attr_value(const xmlAttr *attr, bool *free) -{ - /* For attributes we can have an optimized fast-path. - * This fast-path is only possible in the (common) case where the attribute - * has a single text child. Note that if the child or the content is NULL, this - * is equivalent to not having content (i.e. the attribute has the empty string as value). */ - - *free = false; - - if (attr->children == NULL) { - return BAD_CAST ""; - } - - if (attr->children->type == XML_TEXT_NODE && attr->children->next == NULL) { - if (attr->children->content == NULL) { - return BAD_CAST ""; - } else { - return attr->children->content; - } - } - - xmlChar *value = xmlNodeGetContent((const xmlNode *) attr); - if (UNEXPECTED(value == NULL)) { - return BAD_CAST ""; - } - - *free = true; - return value; -} - bool dom_compare_value(const xmlAttr *attr, const xmlChar *value) { bool free; - xmlChar *attr_value = dom_attr_value(attr, &free); + xmlChar *attr_value = php_libxml_attr_value(attr, &free); bool result = xmlStrEqual(attr_value, value); if (free) { xmlFree(attr_value); diff --git a/ext/dom/php_dom.c b/ext/dom/php_dom.c index 063c0aa1c6e..d85c0be56dc 100644 --- a/ext/dom/php_dom.c +++ b/ext/dom/php_dom.c @@ -2245,7 +2245,7 @@ void php_dom_get_content_into_zval(const xmlNode *nodep, zval *return_value, boo case XML_ATTRIBUTE_NODE: { bool free; - xmlChar *value = dom_attr_value((const xmlAttr *) nodep, &free); + xmlChar *value = php_libxml_attr_value((const xmlAttr *) nodep, &free); RETURN_STRING_FAST((const char *) value); if (free) { xmlFree(value); diff --git a/ext/dom/php_dom.h b/ext/dom/php_dom.h index 261354082d3..efc28ce79c8 100644 --- a/ext/dom/php_dom.h +++ b/ext/dom/php_dom.h @@ -175,7 +175,6 @@ dom_object *php_dom_instantiate_object_helper(zval *return_value, zend_class_ent xmlDocPtr php_dom_create_html_doc(void); xmlEntityPtr dom_entity_reference_fetch_and_sync_declaration(xmlNodePtr reference); -xmlChar *dom_attr_value(const xmlAttr *attr, bool *free); bool dom_compare_value(const xmlAttr *attr, const xmlChar *value); typedef enum { diff --git a/ext/libxml/libxml.c b/ext/libxml/libxml.c index e32e46a6480..35c88f05a06 100644 --- a/ext/libxml/libxml.c +++ b/ext/libxml/libxml.c @@ -1438,6 +1438,36 @@ PHP_LIBXML_API void php_libxml_node_decrement_resource(php_libxml_node_object *o } /* }}} */ +PHP_LIBXML_API xmlChar *php_libxml_attr_value(const xmlAttr *attr, bool *free) +{ + /* For attributes we can have an optimized fast-path. + * This fast-path is only possible in the (common) case where the attribute + * has a single text child. Note that if the child or the content is NULL, this + * is equivalent to not having content (i.e. the attribute has the empty string as value). */ + + *free = false; + + if (attr->children == NULL) { + return BAD_CAST ""; + } + + if (attr->children->type == XML_TEXT_NODE && attr->children->next == NULL) { + if (attr->children->content == NULL) { + return BAD_CAST ""; + } else { + return attr->children->content; + } + } + + xmlChar *value = xmlNodeGetContent((const xmlNode *) attr); + if (UNEXPECTED(value == NULL)) { + return BAD_CAST ""; + } + + *free = true; + return value; +} + #if defined(PHP_WIN32) && defined(COMPILE_DL_LIBXML) PHP_LIBXML_API BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved) { diff --git a/ext/libxml/php_libxml.h b/ext/libxml/php_libxml.h index b9262f5e969..5a8e02e8d8f 100644 --- a/ext/libxml/php_libxml.h +++ b/ext/libxml/php_libxml.h @@ -172,6 +172,8 @@ PHP_LIBXML_API void php_libxml_set_old_ns(xmlDocPtr doc, xmlNsPtr ns); PHP_LIBXML_API php_stream_context *php_libxml_get_stream_context(void); PHP_LIBXML_API bool php_libxml_uses_internal_errors(void); +PHP_LIBXML_API xmlChar *php_libxml_attr_value(const xmlAttr *attr, bool *free); + PHP_LIBXML_API zend_string *php_libxml_sniff_charset_from_string(const char *start, const char *end); PHP_LIBXML_API zend_string *php_libxml_sniff_charset_from_stream(const php_stream *s);