@@ -820,25 +820,56 @@ int dom_node_text_content_write(dom_object *obj, zval *newval)
820
820
821
821
/* }}} */
822
822
823
- /* Returns true if the node was changed , false otherwise. */
824
- static bool dom_set_document_ref_obj_single (xmlNodePtr node , xmlDocPtr doc , php_libxml_ref_obj * document )
823
+ /* Returns true if the node had the same document reference , false otherwise. */
824
+ static bool dom_set_document_ref_obj_single (xmlNodePtr node , php_libxml_ref_obj * document )
825
825
{
826
826
dom_object * childobj = php_dom_object_get_data (node );
827
- if (childobj && !childobj -> document ) {
827
+ if (!childobj ) {
828
+ return true;
829
+ }
830
+ if (!childobj -> document ) {
828
831
childobj -> document = document ;
829
832
document -> refcount ++ ;
830
833
return true;
831
834
}
832
835
return false;
833
836
}
834
837
838
+ void dom_set_document_ref_pointers_attr (xmlAttrPtr attr , php_libxml_ref_obj * document )
839
+ {
840
+ ZEND_ASSERT (document != NULL );
841
+
842
+ dom_set_document_ref_obj_single ((xmlNodePtr ) attr , document );
843
+ for (xmlNodePtr attr_child = attr -> children ; attr_child ; attr_child = attr_child -> next ) {
844
+ dom_set_document_ref_obj_single (attr_child , document );
845
+ }
846
+ }
847
+
848
+ static bool dom_set_document_ref_pointers_node (xmlNodePtr node , php_libxml_ref_obj * document )
849
+ {
850
+ ZEND_ASSERT (document != NULL );
851
+
852
+ if (!dom_set_document_ref_obj_single (node , document )) {
853
+ return false;
854
+ }
855
+
856
+ if (node -> type == XML_ELEMENT_NODE ) {
857
+ for (xmlAttrPtr attr = node -> properties ; attr ; attr = attr -> next ) {
858
+ dom_set_document_ref_pointers_attr (attr , document );
859
+ }
860
+ }
861
+
862
+ return true;
863
+ }
864
+
835
865
/* TODO: on 8.4 replace the loop with the tree walk helper function. */
836
- static void dom_set_document_pointers (xmlNodePtr node , xmlDocPtr doc , php_libxml_ref_obj * document )
866
+ void dom_set_document_ref_pointers (xmlNodePtr node , php_libxml_ref_obj * document )
837
867
{
838
- /* Applies the document to the entire subtree. */
839
- xmlSetTreeDoc (node , doc );
868
+ if (!document ) {
869
+ return ;
870
+ }
840
871
841
- if (!dom_set_document_ref_obj_single (node , doc , document )) {
872
+ if (!dom_set_document_ref_pointers_node (node , document )) {
842
873
return ;
843
874
}
844
875
@@ -847,7 +878,7 @@ static void dom_set_document_pointers(xmlNodePtr node, xmlDocPtr doc, php_libxml
847
878
while (node != NULL ) {
848
879
ZEND_ASSERT (node != base );
849
880
850
- if (!dom_set_document_ref_obj_single (node , doc , document )) {
881
+ if (!dom_set_document_ref_pointers_node (node , document )) {
851
882
break ;
852
883
}
853
884
@@ -974,7 +1005,7 @@ PHP_METHOD(DOMNode, insertBefore)
974
1005
}
975
1006
976
1007
if (child -> doc == NULL && parentp -> doc != NULL ) {
977
- dom_set_document_pointers (child , parentp -> doc , intern -> document );
1008
+ dom_set_document_ref_pointers (child , intern -> document );
978
1009
}
979
1010
980
1011
php_libxml_invalidate_node_list_cache (intern -> document );
@@ -1137,7 +1168,7 @@ PHP_METHOD(DOMNode, replaceChild)
1137
1168
}
1138
1169
1139
1170
if (newchild -> doc == NULL && nodep -> doc != NULL ) {
1140
- dom_set_document_pointers (newchild , nodep -> doc , intern -> document );
1171
+ dom_set_document_ref_pointers (newchild , intern -> document );
1141
1172
}
1142
1173
1143
1174
if (newchild -> type == XML_DOCUMENT_FRAG_NODE ) {
@@ -1240,7 +1271,7 @@ PHP_METHOD(DOMNode, appendChild)
1240
1271
}
1241
1272
1242
1273
if (child -> doc == NULL && nodep -> doc != NULL ) {
1243
- dom_set_document_pointers (child , nodep -> doc , intern -> document );
1274
+ dom_set_document_ref_pointers (child , intern -> document );
1244
1275
}
1245
1276
1246
1277
if (child -> parent != NULL ){
0 commit comments