src/server/webdav/xml.c

branch
webdav
changeset 224
0de1ec82628e
parent 223
bbaec8415c10
child 225
e4f3e1433098
--- a/src/server/webdav/xml.c	Tue Jan 14 22:05:34 2020 +0100
+++ b/src/server/webdav/xml.c	Thu Jan 16 19:14:53 2020 +0100
@@ -30,12 +30,12 @@
 #include <stdlib.h>
 #include <string.h>
 
-
 #include "xml.h"
 
 typedef struct StackElm {
     WSXmlNode *node; // list of nodes
-    WSXmlNode *parent; // if not NULL, call endcb after node->next is NULL
+    //WSXmlNode *parent; // if not NULL, call endcb after node->next is NULL
+    int endonly;
     struct StackElm *next;
 } StackElm;
 
@@ -58,7 +58,8 @@
     }
     stack->next = NULL;
     stack->node = node;
-    stack->parent = NULL;
+    stack->endonly = 0;
+    //stack->parent = NULL;
     
     int ret = 0;
     int br = 0;
@@ -68,7 +69,7 @@
         stack = cur->next;              // and remove it
         cur->next = NULL;
         
-        while(xmlnode) {
+        while(xmlnode && !cur->endonly) {
             // element begin callback
             if(begincb(xmlnode, udata)) {
                 br = 1;
@@ -88,20 +89,37 @@
                 newelm->node = xmlnode->children;
                 // setting the parent will make sure endcb will be called
                 // for the current xmlnode after all children are processed
-                newelm->parent = xmlnode;
+                //newelm->parent = xmlnode;
+                newelm->endonly = 0;
                 
                 // if xmlnode->next is not NULL, there are still nodes at
                 // this level, therefore we have to put these also on the
                 // stack
                 // this way, the remaining nodes are processed after all
-                // children of the current node are processed
+                // children and the end tag are processed
                 if(xmlnode->next) {
-                    // reuse current StackElm
-                    cur->node = xmlnode->next;
-                    STACK_PUSH(stack, cur);
-                    cur = NULL;
+                    StackElm *nextelm = pool_malloc(pool, sizeof(StackElm));
+                    if(!nextelm) {
+                        ret = 1;
+                        br = 1;
+                        break;
+                    }
+                    nextelm->node = xmlnode->next;
+                    nextelm->next = NULL;
+                    nextelm->endonly = 0;
+                    STACK_PUSH(stack, nextelm);
                 }
                 
+                // we have to put the end tag of the current element
+                // on the stack to ensure endcb is called for the current
+                // element, after all children are processed
+                // reuse cur
+                cur->node = xmlnode;
+                cur->endonly = 1;
+                STACK_PUSH(stack, cur);
+                
+                cur = NULL;
+                
                 // now we can put the children on the stack
                 STACK_PUSH(stack, newelm);
                 // break, because we don't want to process xmlnode->next now
@@ -109,6 +127,7 @@
             } else {
                 // no children means, the end callback can be called directly
                 // after the begin callback (no intermediate nodes)
+                cur->node = NULL;
                 if(endcb(xmlnode, udata)) {
                     br = 1;
                     break;
@@ -122,11 +141,11 @@
             break; // break because of an error
         }
         
-        if(cur) {
-            if(cur->parent) {
-                if(endcb(cur->parent, udata)) {
-                    break;
-                }
+        if(cur && cur->node) {
+            //xmlNode *endNode = cur->parent ? cur->parent : cur->node;
+            xmlNode *endNode = cur->node;
+            if(endcb(endNode, udata)) {
+                break;
             }
             pool_free(pool, cur);
         }

mercurial