GNOME Bugzilla – Bug 659564
properties field is not initialized in a DTD xmlNode
Last modified: 2014-03-07 21:58:49 UTC
The following C program crashes on x86-64 Linux (Mageia Linux 2). I build it using «gcc -g -Wall `xml2-config --cflags --libs` test-xml-2.c» . The problem appears to be that the ->properties field is junk in the nbsp entity of the DTD. This was reported here earlier: https://rt.cpan.org/Ticket/Display.html?id=71076 I'll attach the C file soon. Regards, -- Shlomi Fish [CODE] #include <stdio.h> #include <string.h> #include <libxml/tree.h> #include <libxml/parser.h> #include <libxml/parserInternals.h> void dump_xml(xmlNodePtr root, int depth) { printf ("Depth = %d\n", depth); printf ("Name = %s\n", root->name); printf ("AttrPtr = %p\n", root->properties); if (root->properties) { xmlAttrPtr attr = root->properties; while (attr) { printf ("Attr = %p ; Name = %s\n", attr, attr->name); attr = attr->next; } } { xmlNodePtr child; child = root->children; while (child) { dump_xml(child, depth+1); child = child->next; } } } const char * xml_s = "<?xml version=\"1.0\"?><!DOCTYPE doc [ <!ENTITY nbsp \" \"> ]><doc></doc>"; int main(int argc, char * argv[]) { xmlParserCtxtPtr ctxt; xmlDocPtr doc; ctxt = xmlCreateMemoryParserCtxt(xml_s, strlen(xml_s)); xmlParseDocument(ctxt); doc = ctxt->myDoc; #if 0 dump_xml (xmlDocGetRootElement(doc), 1); #else dump_xml ((xmlNodePtr)doc, 1); #endif return 0; } [/CODE]
Created attachment 197027 [details] The C source of the program that segfaults. This is the C source of the program that segfaults.
The "properties" slot isn't valid for DTD nodes. From include/libxml/tree.h: struct _xmlNode { void *_private; /* application data */ xmlElementType type; /* type number, must be second ! */ const xmlChar *name; /* the name of the node, or the entity */ struct _xmlNode *children; /* parent->childs link */ struct _xmlNode *last; /* last child link */ struct _xmlNode *parent; /* child->parent link */ struct _xmlNode *next; /* next sibling link */ struct _xmlNode *prev; /* previous sibling link */ struct _xmlDoc *doc; /* the containing document */ /* End of common part */ xmlNs *ns; /* pointer to the associated namespace */ xmlChar *content; /* the content */ struct _xmlAttr *properties;/* properties list */ xmlNs *nsDef; /* namespace definitions on this node */ void *psvi; /* for type/PSVI informations */ unsigned short line; /* line number */ unsigned short extra; /* extra data for XPath/XSLT */ }; struct _xmlDtd { void *_private; /* application data */ xmlElementType type; /* XML_DTD_NODE, must be second ! */ const xmlChar *name; /* Name of the DTD */ struct _xmlNode *children; /* the value of the property link */ struct _xmlNode *last; /* last child link */ struct _xmlDoc *parent; /* child->parent link */ struct _xmlNode *next; /* next sibling link */ struct _xmlNode *prev; /* previous sibling link */ struct _xmlDoc *doc; /* the containing document */ /* End of common part */ void *notations; /* Hash table for notations if any */ void *elements; /* Hash table for elements if any */ void *attributes; /* Hash table for attributes if any */ void *entities; /* Hash table for entities if any */ const xmlChar *ExternalID; /* External identifier for PUBLIC DTD */ const xmlChar *SystemID; /* URI for a SYSTEM or PUBLIC DTD */ void *pentities; /* Hash table for param entities if any */ }; You should never access the slots after "End of common part" unless you have verified the node type.