]> git.proxmox.com Git - mirror_edk2.git/blobdiff - AppPkg/Applications/Python/Python-2.7.2/Modules/_elementtree.c
edk2: Remove AppPkg, StdLib, StdLibPrivateInternalFiles
[mirror_edk2.git] / AppPkg / Applications / Python / Python-2.7.2 / Modules / _elementtree.c
diff --git a/AppPkg/Applications/Python/Python-2.7.2/Modules/_elementtree.c b/AppPkg/Applications/Python/Python-2.7.2/Modules/_elementtree.c
deleted file mode 100644 (file)
index f465321..0000000
+++ /dev/null
@@ -1,3079 +0,0 @@
-/*\r
- * ElementTree\r
- * $Id: _elementtree.c 3473 2009-01-11 22:53:55Z fredrik $\r
- *\r
- * elementtree accelerator\r
- *\r
- * History:\r
- * 1999-06-20 fl  created (as part of sgmlop)\r
- * 2001-05-29 fl  effdom edition\r
- * 2003-02-27 fl  elementtree edition (alpha)\r
- * 2004-06-03 fl  updates for elementtree 1.2\r
- * 2005-01-05 fl  major optimization effort\r
- * 2005-01-11 fl  first public release (cElementTree 0.8)\r
- * 2005-01-12 fl  split element object into base and extras\r
- * 2005-01-13 fl  use tagged pointers for tail/text (cElementTree 0.9)\r
- * 2005-01-17 fl  added treebuilder close method\r
- * 2005-01-17 fl  fixed crash in getchildren\r
- * 2005-01-18 fl  removed observer api, added iterparse (cElementTree 0.9.3)\r
- * 2005-01-23 fl  revised iterparse api; added namespace event support (0.9.8)\r
- * 2005-01-26 fl  added VERSION module property (cElementTree 1.0)\r
- * 2005-01-28 fl  added remove method (1.0.1)\r
- * 2005-03-01 fl  added iselement function; fixed makeelement aliasing (1.0.2)\r
- * 2005-03-13 fl  export Comment and ProcessingInstruction/PI helpers\r
- * 2005-03-26 fl  added Comment and PI support to XMLParser\r
- * 2005-03-27 fl  event optimizations; complain about bogus events\r
- * 2005-08-08 fl  fixed read error handling in parse\r
- * 2005-08-11 fl  added runtime test for copy workaround (1.0.3)\r
- * 2005-12-13 fl  added expat_capi support (for xml.etree) (1.0.4)\r
- * 2005-12-16 fl  added support for non-standard encodings\r
- * 2006-03-08 fl  fixed a couple of potential null-refs and leaks\r
- * 2006-03-12 fl  merge in 2.5 ssize_t changes\r
- * 2007-08-25 fl  call custom builder's close method from XMLParser\r
- * 2007-08-31 fl  added iter, extend from ET 1.3\r
- * 2007-09-01 fl  fixed ParseError exception, setslice source type, etc\r
- * 2007-09-03 fl  fixed handling of negative insert indexes\r
- * 2007-09-04 fl  added itertext from ET 1.3\r
- * 2007-09-06 fl  added position attribute to ParseError exception\r
- * 2008-06-06 fl  delay error reporting in iterparse (from Hrvoje Niksic)\r
- *\r
- * Copyright (c) 1999-2009 by Secret Labs AB.  All rights reserved.\r
- * Copyright (c) 1999-2009 by Fredrik Lundh.\r
- *\r
- * info@pythonware.com\r
- * http://www.pythonware.com\r
- */\r
-\r
-/* Licensed to PSF under a Contributor Agreement. */\r
-/* See http://www.python.org/psf/license for licensing details. */\r
-\r
-#include "Python.h"\r
-\r
-#define VERSION "1.0.6"\r
-\r
-/* -------------------------------------------------------------------- */\r
-/* configuration */\r
-\r
-/* Leave defined to include the expat-based XMLParser type */\r
-#define USE_EXPAT\r
-\r
-/* Define to do all expat calls via pyexpat's embedded expat library */\r
-/* #define USE_PYEXPAT_CAPI */\r
-\r
-/* An element can hold this many children without extra memory\r
-   allocations. */\r
-#define STATIC_CHILDREN 4\r
-\r
-/* For best performance, chose a value so that 80-90% of all nodes\r
-   have no more than the given number of children.  Set this to zero\r
-   to minimize the size of the element structure itself (this only\r
-   helps if you have lots of leaf nodes with attributes). */\r
-\r
-/* Also note that pymalloc always allocates blocks in multiples of\r
-   eight bytes.  For the current version of cElementTree, this means\r
-   that the number of children should be an even number, at least on\r
-   32-bit platforms. */\r
-\r
-/* -------------------------------------------------------------------- */\r
-\r
-#if 0\r
-static int memory = 0;\r
-#define ALLOC(size, comment)\\r
-do { memory += size; printf("%8d - %s\n", memory, comment); } while (0)\r
-#define RELEASE(size, comment)\\r
-do { memory -= size; printf("%8d - %s\n", memory, comment); } while (0)\r
-#else\r
-#define ALLOC(size, comment)\r
-#define RELEASE(size, comment)\r
-#endif\r
-\r
-/* compiler tweaks */\r
-#if defined(_MSC_VER)\r
-#define LOCAL(type) static __inline type __fastcall\r
-#else\r
-#define LOCAL(type) static type\r
-#endif\r
-\r
-/* compatibility macros */\r
-#if (PY_VERSION_HEX < 0x02060000)\r
-#define Py_REFCNT(ob) (((PyObject*)(ob))->ob_refcnt)\r
-#define Py_TYPE(ob) (((PyObject*)(ob))->ob_type)\r
-#endif\r
-\r
-#if (PY_VERSION_HEX < 0x02050000)\r
-typedef int Py_ssize_t;\r
-#define lenfunc inquiry\r
-#endif\r
-\r
-#if (PY_VERSION_HEX < 0x02040000)\r
-#define PyDict_CheckExact PyDict_Check\r
-\r
-#if !defined(Py_RETURN_NONE)\r
-#define Py_RETURN_NONE return Py_INCREF(Py_None), Py_None\r
-#endif\r
-#endif\r
-\r
-/* macros used to store 'join' flags in string object pointers.  note\r
-   that all use of text and tail as object pointers must be wrapped in\r
-   JOIN_OBJ.  see comments in the ElementObject definition for more\r
-   info. */\r
-#define JOIN_GET(p) ((Py_uintptr_t) (p) & 1)\r
-#define JOIN_SET(p, flag) ((void*) ((Py_uintptr_t) (JOIN_OBJ(p)) | (flag)))\r
-#define JOIN_OBJ(p) ((PyObject*) ((Py_uintptr_t) (p) & ~1))\r
-\r
-/* glue functions (see the init function for details) */\r
-static PyObject* elementtree_parseerror_obj;\r
-static PyObject* elementtree_copyelement_obj;\r
-static PyObject* elementtree_deepcopy_obj;\r
-static PyObject* elementtree_iter_obj;\r
-static PyObject* elementtree_itertext_obj;\r
-static PyObject* elementpath_obj;\r
-\r
-/* helpers */\r
-\r
-LOCAL(PyObject*)\r
-deepcopy(PyObject* object, PyObject* memo)\r
-{\r
-    /* do a deep copy of the given object */\r
-\r
-    PyObject* args;\r
-    PyObject* result;\r
-\r
-    if (!elementtree_deepcopy_obj) {\r
-        PyErr_SetString(\r
-            PyExc_RuntimeError,\r
-            "deepcopy helper not found"\r
-            );\r
-        return NULL;\r
-    }\r
-\r
-    args = PyTuple_New(2);\r
-    if (!args)\r
-        return NULL;\r
-\r
-    Py_INCREF(object); PyTuple_SET_ITEM(args, 0, (PyObject*) object);\r
-    Py_INCREF(memo);   PyTuple_SET_ITEM(args, 1, (PyObject*) memo);\r
-\r
-    result = PyObject_CallObject(elementtree_deepcopy_obj, args);\r
-\r
-    Py_DECREF(args);\r
-\r
-    return result;\r
-}\r
-\r
-LOCAL(PyObject*)\r
-list_join(PyObject* list)\r
-{\r
-    /* join list elements (destroying the list in the process) */\r
-\r
-    PyObject* joiner;\r
-    PyObject* function;\r
-    PyObject* args;\r
-    PyObject* result;\r
-\r
-    switch (PyList_GET_SIZE(list)) {\r
-    case 0:\r
-        Py_DECREF(list);\r
-        return PyString_FromString("");\r
-    case 1:\r
-        result = PyList_GET_ITEM(list, 0);\r
-        Py_INCREF(result);\r
-        Py_DECREF(list);\r
-        return result;\r
-    }\r
-\r
-    /* two or more elements: slice out a suitable separator from the\r
-       first member, and use that to join the entire list */\r
-\r
-    joiner = PySequence_GetSlice(PyList_GET_ITEM(list, 0), 0, 0);\r
-    if (!joiner)\r
-        return NULL;\r
-\r
-    function = PyObject_GetAttrString(joiner, "join");\r
-    if (!function) {\r
-        Py_DECREF(joiner);\r
-        return NULL;\r
-    }\r
-\r
-    args = PyTuple_New(1);\r
-    if (!args)\r
-        return NULL;\r
-\r
-    PyTuple_SET_ITEM(args, 0, list);\r
-\r
-    result = PyObject_CallObject(function, args);\r
-\r
-    Py_DECREF(args); /* also removes list */\r
-    Py_DECREF(function);\r
-    Py_DECREF(joiner);\r
-\r
-    return result;\r
-}\r
-\r
-/* -------------------------------------------------------------------- */\r
-/* the element type */\r
-\r
-typedef struct {\r
-\r
-    /* attributes (a dictionary object), or None if no attributes */\r
-    PyObject* attrib;\r
-\r
-    /* child elements */\r
-    int length; /* actual number of items */\r
-    int allocated; /* allocated items */\r
-\r
-    /* this either points to _children or to a malloced buffer */\r
-    PyObject* *children;\r
-\r
-    PyObject* _children[STATIC_CHILDREN];\r
-    \r
-} ElementObjectExtra;\r
-\r
-typedef struct {\r
-    PyObject_HEAD\r
-\r
-    /* element tag (a string). */\r
-    PyObject* tag;\r
-\r
-    /* text before first child.  note that this is a tagged pointer;\r
-       use JOIN_OBJ to get the object pointer.  the join flag is used\r
-       to distinguish lists created by the tree builder from lists\r
-       assigned to the attribute by application code; the former\r
-       should be joined before being returned to the user, the latter\r
-       should be left intact. */\r
-    PyObject* text;\r
-\r
-    /* text after this element, in parent.  note that this is a tagged\r
-       pointer; use JOIN_OBJ to get the object pointer. */\r
-    PyObject* tail;\r
-\r
-    ElementObjectExtra* extra;\r
-\r
-} ElementObject;\r
-\r
-staticforward PyTypeObject Element_Type;\r
-\r
-#define Element_CheckExact(op) (Py_TYPE(op) == &Element_Type)\r
-\r
-/* -------------------------------------------------------------------- */\r
-/* element constructor and destructor */\r
-\r
-LOCAL(int)\r
-element_new_extra(ElementObject* self, PyObject* attrib)\r
-{\r
-    self->extra = PyObject_Malloc(sizeof(ElementObjectExtra));\r
-    if (!self->extra)\r
-        return -1;\r
-\r
-    if (!attrib)\r
-        attrib = Py_None;\r
-\r
-    Py_INCREF(attrib);\r
-    self->extra->attrib = attrib;\r
-\r
-    self->extra->length = 0;\r
-    self->extra->allocated = STATIC_CHILDREN;\r
-    self->extra->children = self->extra->_children;\r
-\r
-    return 0;\r
-}\r
-\r
-LOCAL(void)\r
-element_dealloc_extra(ElementObject* self)\r
-{\r
-    int i;\r
-\r
-    Py_DECREF(self->extra->attrib);\r
-\r
-    for (i = 0; i < self->extra->length; i++)\r
-        Py_DECREF(self->extra->children[i]);\r
-\r
-    if (self->extra->children != self->extra->_children)\r
-        PyObject_Free(self->extra->children);\r
-\r
-    PyObject_Free(self->extra);\r
-}\r
-\r
-LOCAL(PyObject*)\r
-element_new(PyObject* tag, PyObject* attrib)\r
-{\r
-    ElementObject* self;\r
-\r
-    self = PyObject_New(ElementObject, &Element_Type);\r
-    if (self == NULL)\r
-        return NULL;\r
-\r
-    /* use None for empty dictionaries */\r
-    if (PyDict_CheckExact(attrib) && !PyDict_Size(attrib))\r
-        attrib = Py_None;\r
-\r
-    self->extra = NULL;\r
-\r
-    if (attrib != Py_None) {\r
-\r
-        if (element_new_extra(self, attrib) < 0) {\r
-            PyObject_Del(self);\r
-            return NULL;\r
-        }\r
-\r
-        self->extra->length = 0;\r
-        self->extra->allocated = STATIC_CHILDREN;\r
-        self->extra->children = self->extra->_children;\r
-\r
-    }\r
-\r
-    Py_INCREF(tag);\r
-    self->tag = tag;\r
-\r
-    Py_INCREF(Py_None);\r
-    self->text = Py_None;\r
-\r
-    Py_INCREF(Py_None);\r
-    self->tail = Py_None;\r
-\r
-    ALLOC(sizeof(ElementObject), "create element");\r
-\r
-    return (PyObject*) self;\r
-}\r
-\r
-LOCAL(int)\r
-element_resize(ElementObject* self, int extra)\r
-{\r
-    int size;\r
-    PyObject* *children;\r
-\r
-    /* make sure self->children can hold the given number of extra\r
-       elements.  set an exception and return -1 if allocation failed */\r
-\r
-    if (!self->extra)\r
-        element_new_extra(self, NULL);\r
-\r
-    size = self->extra->length + extra;\r
-\r
-    if (size > self->extra->allocated) {\r
-        /* use Python 2.4's list growth strategy */\r
-        size = (size >> 3) + (size < 9 ? 3 : 6) + size;\r
-        /* Coverity CID #182 size_error: Allocating 1 bytes to pointer "children"\r
-         * which needs at least 4 bytes. \r
-         * Although it's a false alarm always assume at least one child to \r
-         * be safe.\r
-         */\r
-        size = size ? size : 1;\r
-        if (self->extra->children != self->extra->_children) {\r
-            /* Coverity CID #182 size_error: Allocating 1 bytes to pointer\r
-             * "children", which needs at least 4 bytes. Although it's a \r
-             * false alarm always assume at least one child to be safe.\r
-             */\r
-            children = PyObject_Realloc(self->extra->children,\r
-                                        size * sizeof(PyObject*));\r
-            if (!children)\r
-                goto nomemory;\r
-        } else {\r
-            children = PyObject_Malloc(size * sizeof(PyObject*));\r
-            if (!children)\r
-                goto nomemory;\r
-            /* copy existing children from static area to malloc buffer */\r
-            memcpy(children, self->extra->children,\r
-                   self->extra->length * sizeof(PyObject*));\r
-        }\r
-        self->extra->children = children;\r
-        self->extra->allocated = size;\r
-    }\r
-\r
-    return 0;\r
-\r
-  nomemory:\r
-    PyErr_NoMemory();\r
-    return -1;\r
-}\r
-\r
-LOCAL(int)\r
-element_add_subelement(ElementObject* self, PyObject* element)\r
-{\r
-    /* add a child element to a parent */\r
-\r
-    if (element_resize(self, 1) < 0)\r
-        return -1;\r
-\r
-    Py_INCREF(element);\r
-    self->extra->children[self->extra->length] = element;\r
-\r
-    self->extra->length++;\r
-\r
-    return 0;\r
-}\r
-\r
-LOCAL(PyObject*)\r
-element_get_attrib(ElementObject* self)\r
-{\r
-    /* return borrowed reference to attrib dictionary */\r
-    /* note: this function assumes that the extra section exists */\r
-\r
-    PyObject* res = self->extra->attrib;\r
-\r
-    if (res == Py_None) {\r
-        Py_DECREF(res);\r
-        /* create missing dictionary */\r
-        res = PyDict_New();\r
-        if (!res)\r
-            return NULL;\r
-        self->extra->attrib = res;\r
-    }\r
-\r
-    return res;\r
-}\r
-\r
-LOCAL(PyObject*)\r
-element_get_text(ElementObject* self)\r
-{\r
-    /* return borrowed reference to text attribute */\r
-\r
-    PyObject* res = self->text;\r
-\r
-    if (JOIN_GET(res)) {\r
-        res = JOIN_OBJ(res);\r
-        if (PyList_CheckExact(res)) {\r
-            res = list_join(res);\r
-            if (!res)\r
-                return NULL;\r
-            self->text = res;\r
-        }\r
-    }\r
-\r
-    return res;\r
-}\r
-\r
-LOCAL(PyObject*)\r
-element_get_tail(ElementObject* self)\r
-{\r
-    /* return borrowed reference to text attribute */\r
-\r
-    PyObject* res = self->tail;\r
-\r
-    if (JOIN_GET(res)) {\r
-        res = JOIN_OBJ(res);\r
-        if (PyList_CheckExact(res)) {\r
-            res = list_join(res);\r
-            if (!res)\r
-                return NULL;\r
-            self->tail = res;\r
-        }\r
-    }\r
-\r
-    return res;\r
-}\r
-\r
-static PyObject*\r
-element(PyObject* self, PyObject* args, PyObject* kw)\r
-{\r
-    PyObject* elem;\r
-\r
-    PyObject* tag;\r
-    PyObject* attrib = NULL;\r
-    if (!PyArg_ParseTuple(args, "O|O!:Element", &tag,\r
-                          &PyDict_Type, &attrib))\r
-        return NULL;\r
-\r
-    if (attrib || kw) {\r
-        attrib = (attrib) ? PyDict_Copy(attrib) : PyDict_New();\r
-        if (!attrib)\r
-            return NULL;\r
-        if (kw)\r
-            PyDict_Update(attrib, kw);\r
-    } else {\r
-        Py_INCREF(Py_None);\r
-        attrib = Py_None;\r
-    }\r
-\r
-    elem = element_new(tag, attrib);\r
-\r
-    Py_DECREF(attrib);\r
-\r
-    return elem;\r
-}\r
-\r
-static PyObject*\r
-subelement(PyObject* self, PyObject* args, PyObject* kw)\r
-{\r
-    PyObject* elem;\r
-\r
-    ElementObject* parent;\r
-    PyObject* tag;\r
-    PyObject* attrib = NULL;\r
-    if (!PyArg_ParseTuple(args, "O!O|O!:SubElement",\r
-                          &Element_Type, &parent, &tag,\r
-                          &PyDict_Type, &attrib))\r
-        return NULL;\r
-\r
-    if (attrib || kw) {\r
-        attrib = (attrib) ? PyDict_Copy(attrib) : PyDict_New();\r
-        if (!attrib)\r
-            return NULL;\r
-        if (kw)\r
-            PyDict_Update(attrib, kw);\r
-    } else {\r
-        Py_INCREF(Py_None);\r
-        attrib = Py_None;\r
-    }\r
-\r
-    elem = element_new(tag, attrib);\r
-\r
-    Py_DECREF(attrib);\r
-\r
-    if (element_add_subelement(parent, elem) < 0) {\r
-        Py_DECREF(elem);\r
-        return NULL;\r
-    }\r
-\r
-    return elem;\r
-}\r
-\r
-static void\r
-element_dealloc(ElementObject* self)\r
-{\r
-    if (self->extra)\r
-        element_dealloc_extra(self);\r
-\r
-    /* discard attributes */\r
-    Py_DECREF(self->tag);\r
-    Py_DECREF(JOIN_OBJ(self->text));\r
-    Py_DECREF(JOIN_OBJ(self->tail));\r
-\r
-    RELEASE(sizeof(ElementObject), "destroy element");\r
-\r
-    PyObject_Del(self);\r
-}\r
-\r
-/* -------------------------------------------------------------------- */\r
-/* methods (in alphabetical order) */\r
-\r
-static PyObject*\r
-element_append(ElementObject* self, PyObject* args)\r
-{\r
-    PyObject* element;\r
-    if (!PyArg_ParseTuple(args, "O!:append", &Element_Type, &element))\r
-        return NULL;\r
-\r
-    if (element_add_subelement(self, element) < 0)\r
-        return NULL;\r
-\r
-    Py_RETURN_NONE;\r
-}\r
-\r
-static PyObject*\r
-element_clear(ElementObject* self, PyObject* args)\r
-{\r
-    if (!PyArg_ParseTuple(args, ":clear"))\r
-        return NULL;\r
-\r
-    if (self->extra) {\r
-        element_dealloc_extra(self);\r
-        self->extra = NULL;\r
-    }\r
-\r
-    Py_INCREF(Py_None);\r
-    Py_DECREF(JOIN_OBJ(self->text));\r
-    self->text = Py_None;\r
-\r
-    Py_INCREF(Py_None);\r
-    Py_DECREF(JOIN_OBJ(self->tail));\r
-    self->tail = Py_None;\r
-\r
-    Py_RETURN_NONE;\r
-}\r
-\r
-static PyObject*\r
-element_copy(ElementObject* self, PyObject* args)\r
-{\r
-    int i;\r
-    ElementObject* element;\r
-\r
-    if (!PyArg_ParseTuple(args, ":__copy__"))\r
-        return NULL;\r
-\r
-    element = (ElementObject*) element_new(\r
-        self->tag, (self->extra) ? self->extra->attrib : Py_None\r
-        );\r
-    if (!element)\r
-        return NULL;\r
-\r
-    Py_DECREF(JOIN_OBJ(element->text));\r
-    element->text = self->text;\r
-    Py_INCREF(JOIN_OBJ(element->text));\r
-\r
-    Py_DECREF(JOIN_OBJ(element->tail));\r
-    element->tail = self->tail;\r
-    Py_INCREF(JOIN_OBJ(element->tail));\r
-\r
-    if (self->extra) {\r
-        \r
-        if (element_resize(element, self->extra->length) < 0) {\r
-            Py_DECREF(element);\r
-            return NULL;\r
-        }\r
-\r
-        for (i = 0; i < self->extra->length; i++) {\r
-            Py_INCREF(self->extra->children[i]);\r
-            element->extra->children[i] = self->extra->children[i];\r
-        }\r
-\r
-        element->extra->length = self->extra->length;\r
-        \r
-    }\r
-\r
-    return (PyObject*) element;\r
-}\r
-\r
-static PyObject*\r
-element_deepcopy(ElementObject* self, PyObject* args)\r
-{\r
-    int i;\r
-    ElementObject* element;\r
-    PyObject* tag;\r
-    PyObject* attrib;\r
-    PyObject* text;\r
-    PyObject* tail;\r
-    PyObject* id;\r
-\r
-    PyObject* memo;\r
-    if (!PyArg_ParseTuple(args, "O:__deepcopy__", &memo))\r
-        return NULL;\r
-\r
-    tag = deepcopy(self->tag, memo);\r
-    if (!tag)\r
-        return NULL;\r
-\r
-    if (self->extra) {\r
-        attrib = deepcopy(self->extra->attrib, memo);\r
-        if (!attrib) {\r
-            Py_DECREF(tag);\r
-            return NULL;\r
-        }\r
-    } else {\r
-        Py_INCREF(Py_None);\r
-        attrib = Py_None;\r
-    }\r
-\r
-    element = (ElementObject*) element_new(tag, attrib);\r
-\r
-    Py_DECREF(tag);\r
-    Py_DECREF(attrib);\r
-\r
-    if (!element)\r
-        return NULL;\r
-    \r
-    text = deepcopy(JOIN_OBJ(self->text), memo);\r
-    if (!text)\r
-        goto error;\r
-    Py_DECREF(element->text);\r
-    element->text = JOIN_SET(text, JOIN_GET(self->text));\r
-\r
-    tail = deepcopy(JOIN_OBJ(self->tail), memo);\r
-    if (!tail)\r
-        goto error;\r
-    Py_DECREF(element->tail);\r
-    element->tail = JOIN_SET(tail, JOIN_GET(self->tail));\r
-\r
-    if (self->extra) {\r
-        \r
-        if (element_resize(element, self->extra->length) < 0)\r
-            goto error;\r
-\r
-        for (i = 0; i < self->extra->length; i++) {\r
-            PyObject* child = deepcopy(self->extra->children[i], memo);\r
-            if (!child) {\r
-                element->extra->length = i;\r
-                goto error;\r
-            }\r
-            element->extra->children[i] = child;\r
-        }\r
-\r
-        element->extra->length = self->extra->length;\r
-        \r
-    }\r
-\r
-    /* add object to memo dictionary (so deepcopy won't visit it again) */\r
-    id = PyInt_FromLong((Py_uintptr_t) self);\r
-    if (!id)\r
-        goto error;\r
-\r
-    i = PyDict_SetItem(memo, id, (PyObject*) element);\r
-\r
-    Py_DECREF(id);\r
-\r
-    if (i < 0)\r
-        goto error;\r
-\r
-    return (PyObject*) element;\r
-\r
-  error:\r
-    Py_DECREF(element);\r
-    return NULL;\r
-}\r
-\r
-LOCAL(int)\r
-checkpath(PyObject* tag)\r
-{\r
-    Py_ssize_t i;\r
-    int check = 1;\r
-\r
-    /* check if a tag contains an xpath character */\r
-\r
-#define PATHCHAR(ch) \\r
-    (ch == '/' || ch == '*' || ch == '[' || ch == '@' || ch == '.')\r
-\r
-#if defined(Py_USING_UNICODE)\r
-    if (PyUnicode_Check(tag)) {\r
-        Py_UNICODE *p = PyUnicode_AS_UNICODE(tag);\r
-        for (i = 0; i < PyUnicode_GET_SIZE(tag); i++) {\r
-            if (p[i] == '{')\r
-                check = 0;\r
-            else if (p[i] == '}')\r
-                check = 1;\r
-            else if (check && PATHCHAR(p[i]))\r
-                return 1;\r
-        }\r
-        return 0;\r
-    }\r
-#endif\r
-    if (PyString_Check(tag)) {\r
-        char *p = PyString_AS_STRING(tag);\r
-        for (i = 0; i < PyString_GET_SIZE(tag); i++) {\r
-            if (p[i] == '{')\r
-                check = 0;\r
-            else if (p[i] == '}')\r
-                check = 1;\r
-            else if (check && PATHCHAR(p[i]))\r
-                return 1;\r
-        }\r
-        return 0;\r
-    }\r
-\r
-    return 1; /* unknown type; might be path expression */\r
-}\r
-\r
-static PyObject*\r
-element_extend(ElementObject* self, PyObject* args)\r
-{\r
-    PyObject* seq;\r
-    Py_ssize_t i, seqlen = 0;\r
-\r
-    PyObject* seq_in;\r
-    if (!PyArg_ParseTuple(args, "O:extend", &seq_in))\r
-        return NULL;\r
-\r
-    seq = PySequence_Fast(seq_in, "");\r
-    if (!seq) {\r
-        PyErr_Format(\r
-            PyExc_TypeError,\r
-            "expected sequence, not \"%.200s\"", Py_TYPE(seq_in)->tp_name\r
-            );\r
-        return NULL;\r
-    }\r
-\r
-    seqlen = PySequence_Size(seq);\r
-    for (i = 0; i < seqlen; i++) {\r
-        PyObject* element = PySequence_Fast_GET_ITEM(seq, i);\r
-        if (element_add_subelement(self, element) < 0) {\r
-            Py_DECREF(seq);\r
-            return NULL;\r
-        }\r
-    }\r
-\r
-    Py_DECREF(seq);\r
-\r
-    Py_RETURN_NONE;\r
-}\r
-\r
-static PyObject*\r
-element_find(ElementObject* self, PyObject* args)\r
-{\r
-    int i;\r
-\r
-    PyObject* tag;\r
-    PyObject* namespaces = Py_None;\r
-    if (!PyArg_ParseTuple(args, "O|O:find", &tag, &namespaces))\r
-        return NULL;\r
-\r
-    if (checkpath(tag) || namespaces != Py_None)\r
-        return PyObject_CallMethod(\r
-            elementpath_obj, "find", "OOO", self, tag, namespaces\r
-            );\r
-\r
-    if (!self->extra)\r
-        Py_RETURN_NONE;\r
-        \r
-    for (i = 0; i < self->extra->length; i++) {\r
-        PyObject* item = self->extra->children[i];\r
-        if (Element_CheckExact(item) &&\r
-            PyObject_Compare(((ElementObject*)item)->tag, tag) == 0) {\r
-            Py_INCREF(item);\r
-            return item;\r
-        }\r
-    }\r
-\r
-    Py_RETURN_NONE;\r
-}\r
-\r
-static PyObject*\r
-element_findtext(ElementObject* self, PyObject* args)\r
-{\r
-    int i;\r
-\r
-    PyObject* tag;\r
-    PyObject* default_value = Py_None;\r
-    PyObject* namespaces = Py_None;\r
-    if (!PyArg_ParseTuple(args, "O|OO:findtext", &tag, &default_value, &namespaces))\r
-        return NULL;\r
-\r
-    if (checkpath(tag) || namespaces != Py_None)\r
-        return PyObject_CallMethod(\r
-            elementpath_obj, "findtext", "OOOO", self, tag, default_value, namespaces\r
-            );\r
-\r
-    if (!self->extra) {\r
-        Py_INCREF(default_value);\r
-        return default_value;\r
-    }\r
-\r
-    for (i = 0; i < self->extra->length; i++) {\r
-        ElementObject* item = (ElementObject*) self->extra->children[i];\r
-        if (Element_CheckExact(item) && !PyObject_Compare(item->tag, tag)) {\r
-            PyObject* text = element_get_text(item);\r
-            if (text == Py_None)\r
-                return PyString_FromString("");\r
-            Py_XINCREF(text);\r
-            return text;\r
-        }\r
-    }\r
-\r
-    Py_INCREF(default_value);\r
-    return default_value;\r
-}\r
-\r
-static PyObject*\r
-element_findall(ElementObject* self, PyObject* args)\r
-{\r
-    int i;\r
-    PyObject* out;\r
-\r
-    PyObject* tag;\r
-    PyObject* namespaces = Py_None;\r
-    if (!PyArg_ParseTuple(args, "O|O:findall", &tag, &namespaces))\r
-        return NULL;\r
-\r
-    if (checkpath(tag) || namespaces != Py_None)\r
-        return PyObject_CallMethod(\r
-            elementpath_obj, "findall", "OOO", self, tag, namespaces\r
-            );\r
-\r
-    out = PyList_New(0);\r
-    if (!out)\r
-        return NULL;\r
-\r
-    if (!self->extra)\r
-        return out;\r
-\r
-    for (i = 0; i < self->extra->length; i++) {\r
-        PyObject* item = self->extra->children[i];\r
-        if (Element_CheckExact(item) &&\r
-            PyObject_Compare(((ElementObject*)item)->tag, tag) == 0) {\r
-            if (PyList_Append(out, item) < 0) {\r
-                Py_DECREF(out);\r
-                return NULL;\r
-            }\r
-        }\r
-    }\r
-\r
-    return out;\r
-}\r
-\r
-static PyObject*\r
-element_iterfind(ElementObject* self, PyObject* args)\r
-{\r
-    PyObject* tag;\r
-    PyObject* namespaces = Py_None;\r
-    if (!PyArg_ParseTuple(args, "O|O:iterfind", &tag, &namespaces))\r
-        return NULL;\r
-\r
-    return PyObject_CallMethod(\r
-        elementpath_obj, "iterfind", "OOO", self, tag, namespaces\r
-        );\r
-}\r
-\r
-static PyObject*\r
-element_get(ElementObject* self, PyObject* args)\r
-{\r
-    PyObject* value;\r
-\r
-    PyObject* key;\r
-    PyObject* default_value = Py_None;\r
-    if (!PyArg_ParseTuple(args, "O|O:get", &key, &default_value))\r
-        return NULL;\r
-\r
-    if (!self->extra || self->extra->attrib == Py_None)\r
-        value = default_value;\r
-    else {\r
-        value = PyDict_GetItem(self->extra->attrib, key);\r
-        if (!value)\r
-            value = default_value;\r
-    }\r
-\r
-    Py_INCREF(value);\r
-    return value;\r
-}\r
-\r
-static PyObject*\r
-element_getchildren(ElementObject* self, PyObject* args)\r
-{\r
-    int i;\r
-    PyObject* list;\r
-\r
-    /* FIXME: report as deprecated? */\r
-\r
-    if (!PyArg_ParseTuple(args, ":getchildren"))\r
-        return NULL;\r
-\r
-    if (!self->extra)\r
-        return PyList_New(0);\r
-\r
-    list = PyList_New(self->extra->length);\r
-    if (!list)\r
-        return NULL;\r
-\r
-    for (i = 0; i < self->extra->length; i++) {\r
-        PyObject* item = self->extra->children[i];\r
-        Py_INCREF(item);\r
-        PyList_SET_ITEM(list, i, item);\r
-    }\r
-\r
-    return list;\r
-}\r
-\r
-static PyObject*\r
-element_iter(ElementObject* self, PyObject* args)\r
-{\r
-    PyObject* result;\r
-    \r
-    PyObject* tag = Py_None;\r
-    if (!PyArg_ParseTuple(args, "|O:iter", &tag))\r
-        return NULL;\r
-\r
-    if (!elementtree_iter_obj) {\r
-        PyErr_SetString(\r
-            PyExc_RuntimeError,\r
-            "iter helper not found"\r
-            );\r
-        return NULL;\r
-    }\r
-\r
-    args = PyTuple_New(2);\r
-    if (!args)\r
-        return NULL;\r
-\r
-    Py_INCREF(self); PyTuple_SET_ITEM(args, 0, (PyObject*) self);\r
-    Py_INCREF(tag);  PyTuple_SET_ITEM(args, 1, (PyObject*) tag);\r
-\r
-    result = PyObject_CallObject(elementtree_iter_obj, args);\r
-\r
-    Py_DECREF(args);\r
-\r
-    return result;\r
-}\r
-\r
-\r
-static PyObject*\r
-element_itertext(ElementObject* self, PyObject* args)\r
-{\r
-    PyObject* result;\r
-    \r
-    if (!PyArg_ParseTuple(args, ":itertext"))\r
-        return NULL;\r
-\r
-    if (!elementtree_itertext_obj) {\r
-        PyErr_SetString(\r
-            PyExc_RuntimeError,\r
-            "itertext helper not found"\r
-            );\r
-        return NULL;\r
-    }\r
-\r
-    args = PyTuple_New(1);\r
-    if (!args)\r
-        return NULL;\r
-\r
-    Py_INCREF(self); PyTuple_SET_ITEM(args, 0, (PyObject*) self);\r
-\r
-    result = PyObject_CallObject(elementtree_itertext_obj, args);\r
-\r
-    Py_DECREF(args);\r
-\r
-    return result;\r
-}\r
-\r
-static PyObject*\r
-element_getitem(PyObject* self_, Py_ssize_t index)\r
-{\r
-    ElementObject* self = (ElementObject*) self_;\r
-\r
-    if (!self->extra || index < 0 || index >= self->extra->length) {\r
-        PyErr_SetString(\r
-            PyExc_IndexError,\r
-            "child index out of range"\r
-            );\r
-        return NULL;\r
-    }\r
-\r
-    Py_INCREF(self->extra->children[index]);\r
-    return self->extra->children[index];\r
-}\r
-\r
-static PyObject*\r
-element_insert(ElementObject* self, PyObject* args)\r
-{\r
-    int i;\r
-\r
-    int index;\r
-    PyObject* element;\r
-    if (!PyArg_ParseTuple(args, "iO!:insert", &index,\r
-                          &Element_Type, &element))\r
-        return NULL;\r
-\r
-    if (!self->extra)\r
-        element_new_extra(self, NULL);\r
-\r
-    if (index < 0) {\r
-        index += self->extra->length;\r
-        if (index < 0)\r
-            index = 0;\r
-    }\r
-    if (index > self->extra->length)\r
-        index = self->extra->length;\r
-\r
-    if (element_resize(self, 1) < 0)\r
-        return NULL;\r
-\r
-    for (i = self->extra->length; i > index; i--)\r
-        self->extra->children[i] = self->extra->children[i-1];\r
-\r
-    Py_INCREF(element);\r
-    self->extra->children[index] = element;\r
-\r
-    self->extra->length++;\r
-\r
-    Py_RETURN_NONE;\r
-}\r
-\r
-static PyObject*\r
-element_items(ElementObject* self, PyObject* args)\r
-{\r
-    if (!PyArg_ParseTuple(args, ":items"))\r
-        return NULL;\r
-\r
-    if (!self->extra || self->extra->attrib == Py_None)\r
-        return PyList_New(0);\r
-\r
-    return PyDict_Items(self->extra->attrib);\r
-}\r
-\r
-static PyObject*\r
-element_keys(ElementObject* self, PyObject* args)\r
-{\r
-    if (!PyArg_ParseTuple(args, ":keys"))\r
-        return NULL;\r
-\r
-    if (!self->extra || self->extra->attrib == Py_None)\r
-        return PyList_New(0);\r
-\r
-    return PyDict_Keys(self->extra->attrib);\r
-}\r
-\r
-static Py_ssize_t\r
-element_length(ElementObject* self)\r
-{\r
-    if (!self->extra)\r
-        return 0;\r
-\r
-    return self->extra->length;\r
-}\r
-\r
-static PyObject*\r
-element_makeelement(PyObject* self, PyObject* args, PyObject* kw)\r
-{\r
-    PyObject* elem;\r
-\r
-    PyObject* tag;\r
-    PyObject* attrib;\r
-    if (!PyArg_ParseTuple(args, "OO:makeelement", &tag, &attrib))\r
-        return NULL;\r
-\r
-    attrib = PyDict_Copy(attrib);\r
-    if (!attrib)\r
-        return NULL;\r
-\r
-    elem = element_new(tag, attrib);\r
-\r
-    Py_DECREF(attrib);\r
-\r
-    return elem;\r
-}\r
-\r
-static PyObject*\r
-element_reduce(ElementObject* self, PyObject* args)\r
-{\r
-    if (!PyArg_ParseTuple(args, ":__reduce__"))\r
-        return NULL;\r
-\r
-    /* Hack alert: This method is used to work around a __copy__\r
-       problem on certain 2.3 and 2.4 versions.  To save time and\r
-       simplify the code, we create the copy in here, and use a dummy\r
-       copyelement helper to trick the copy module into doing the\r
-       right thing. */\r
-\r
-    if (!elementtree_copyelement_obj) {\r
-        PyErr_SetString(\r
-            PyExc_RuntimeError,\r
-            "copyelement helper not found"\r
-            );\r
-        return NULL;\r
-    }\r
-\r
-    return Py_BuildValue(\r
-        "O(N)", elementtree_copyelement_obj, element_copy(self, args)\r
-        );\r
-}\r
-\r
-static PyObject*\r
-element_remove(ElementObject* self, PyObject* args)\r
-{\r
-    int i;\r
-\r
-    PyObject* element;\r
-    if (!PyArg_ParseTuple(args, "O!:remove", &Element_Type, &element))\r
-        return NULL;\r
-\r
-    if (!self->extra) {\r
-        /* element has no children, so raise exception */\r
-        PyErr_SetString(\r
-            PyExc_ValueError,\r
-            "list.remove(x): x not in list"\r
-            );\r
-        return NULL;\r
-    }\r
-\r
-    for (i = 0; i < self->extra->length; i++) {\r
-        if (self->extra->children[i] == element)\r
-            break;\r
-        if (PyObject_Compare(self->extra->children[i], element) == 0)\r
-            break;\r
-    }\r
-\r
-    if (i == self->extra->length) {\r
-        /* element is not in children, so raise exception */\r
-        PyErr_SetString(\r
-            PyExc_ValueError,\r
-            "list.remove(x): x not in list"\r
-            );\r
-        return NULL;\r
-    }\r
-\r
-    Py_DECREF(self->extra->children[i]);\r
-\r
-    self->extra->length--;\r
-\r
-    for (; i < self->extra->length; i++)\r
-        self->extra->children[i] = self->extra->children[i+1];\r
-\r
-    Py_RETURN_NONE;\r
-}\r
-\r
-static PyObject*\r
-element_repr(ElementObject* self)\r
-{\r
-    PyObject *repr, *tag;\r
-\r
-    tag = PyObject_Repr(self->tag);\r
-    if (!tag)\r
-        return NULL;\r
-\r
-    repr = PyString_FromFormat("<Element %s at %p>",\r
-                               PyString_AS_STRING(tag), self);\r
-\r
-    Py_DECREF(tag);\r
-\r
-    return repr;\r
-}\r
-\r
-static PyObject*\r
-element_set(ElementObject* self, PyObject* args)\r
-{\r
-    PyObject* attrib;\r
-\r
-    PyObject* key;\r
-    PyObject* value;\r
-    if (!PyArg_ParseTuple(args, "OO:set", &key, &value))\r
-        return NULL;\r
-\r
-    if (!self->extra)\r
-        element_new_extra(self, NULL);\r
-\r
-    attrib = element_get_attrib(self);\r
-    if (!attrib)\r
-        return NULL;\r
-\r
-    if (PyDict_SetItem(attrib, key, value) < 0)\r
-        return NULL;\r
-\r
-    Py_RETURN_NONE;\r
-}\r
-\r
-static int\r
-element_setitem(PyObject* self_, Py_ssize_t index, PyObject* item)\r
-{\r
-    ElementObject* self = (ElementObject*) self_;\r
-    int i;\r
-    PyObject* old;\r
-\r
-    if (!self->extra || index < 0 || index >= self->extra->length) {\r
-        PyErr_SetString(\r
-            PyExc_IndexError,\r
-            "child assignment index out of range");\r
-        return -1;\r
-    }\r
-\r
-    old = self->extra->children[index];\r
-\r
-    if (item) {\r
-        Py_INCREF(item);\r
-        self->extra->children[index] = item;\r
-    } else {\r
-        self->extra->length--;\r
-        for (i = index; i < self->extra->length; i++)\r
-            self->extra->children[i] = self->extra->children[i+1];\r
-    }\r
-\r
-    Py_DECREF(old);\r
-\r
-    return 0;\r
-}\r
-\r
-static PyObject*\r
-element_subscr(PyObject* self_, PyObject* item)\r
-{\r
-    ElementObject* self = (ElementObject*) self_;\r
-\r
-#if (PY_VERSION_HEX < 0x02050000)\r
-    if (PyInt_Check(item) || PyLong_Check(item)) {\r
-        long i = PyInt_AsLong(item);\r
-#else\r
-    if (PyIndex_Check(item)) {\r
-        Py_ssize_t i = PyNumber_AsSsize_t(item, PyExc_IndexError);\r
-#endif\r
-\r
-        if (i == -1 && PyErr_Occurred()) {\r
-            return NULL;\r
-        }\r
-        if (i < 0 && self->extra)\r
-            i += self->extra->length;\r
-        return element_getitem(self_, i);\r
-    }\r
-    else if (PySlice_Check(item)) {\r
-        Py_ssize_t start, stop, step, slicelen, cur, i;\r
-        PyObject* list;\r
-\r
-        if (!self->extra)\r
-            return PyList_New(0);\r
-\r
-        if (PySlice_GetIndicesEx((PySliceObject *)item,\r
-                self->extra->length,\r
-                &start, &stop, &step, &slicelen) < 0) {\r
-            return NULL;\r
-        }\r
-\r
-        if (slicelen <= 0)\r
-            return PyList_New(0);\r
-        else {\r
-            list = PyList_New(slicelen);\r
-            if (!list)\r
-                return NULL;\r
-\r
-            for (cur = start, i = 0; i < slicelen;\r
-                 cur += step, i++) {\r
-                PyObject* item = self->extra->children[cur];\r
-                Py_INCREF(item);\r
-                PyList_SET_ITEM(list, i, item);\r
-            }\r
-\r
-            return list;\r
-        }\r
-    }\r
-    else {\r
-        PyErr_SetString(PyExc_TypeError,\r
-                "element indices must be integers");\r
-        return NULL;\r
-    }\r
-}\r
-\r
-static int\r
-element_ass_subscr(PyObject* self_, PyObject* item, PyObject* value)\r
-{\r
-    ElementObject* self = (ElementObject*) self_;\r
-\r
-#if (PY_VERSION_HEX < 0x02050000)\r
-    if (PyInt_Check(item) || PyLong_Check(item)) {\r
-        long i = PyInt_AsLong(item);\r
-#else\r
-    if (PyIndex_Check(item)) {\r
-        Py_ssize_t i = PyNumber_AsSsize_t(item, PyExc_IndexError);\r
-#endif\r
-\r
-        if (i == -1 && PyErr_Occurred()) {\r
-            return -1;\r
-        }\r
-        if (i < 0 && self->extra)\r
-            i += self->extra->length;\r
-        return element_setitem(self_, i, value);\r
-    }\r
-    else if (PySlice_Check(item)) {\r
-        Py_ssize_t start, stop, step, slicelen, newlen, cur, i;\r
-\r
-        PyObject* recycle = NULL;\r
-        PyObject* seq = NULL;\r
-\r
-        if (!self->extra)\r
-            element_new_extra(self, NULL);\r
-\r
-        if (PySlice_GetIndicesEx((PySliceObject *)item,\r
-                self->extra->length,\r
-                &start, &stop, &step, &slicelen) < 0) {\r
-            return -1;\r
-        }\r
-\r
-        if (value == NULL)\r
-            newlen = 0;\r
-        else {\r
-            seq = PySequence_Fast(value, "");\r
-            if (!seq) {\r
-                PyErr_Format(\r
-                    PyExc_TypeError,\r
-                    "expected sequence, not \"%.200s\"", Py_TYPE(value)->tp_name\r
-                    );\r
-                return -1;\r
-            }\r
-            newlen = PySequence_Size(seq);\r
-        }\r
-\r
-        if (step !=  1 && newlen != slicelen)\r
-        {\r
-            PyErr_Format(PyExc_ValueError,\r
-#if (PY_VERSION_HEX < 0x02050000)\r
-                "attempt to assign sequence of size %d "\r
-                "to extended slice of size %d",\r
-#else\r
-                "attempt to assign sequence of size %zd "\r
-                "to extended slice of size %zd",\r
-#endif\r
-                newlen, slicelen\r
-                );\r
-            return -1;\r
-        }\r
-\r
-\r
-        /* Resize before creating the recycle bin, to prevent refleaks. */\r
-        if (newlen > slicelen) {\r
-            if (element_resize(self, newlen - slicelen) < 0) {\r
-                if (seq) {\r
-                    Py_DECREF(seq);\r
-                }\r
-                return -1;\r
-            }\r
-        }\r
-\r
-        if (slicelen > 0) {\r
-            /* to avoid recursive calls to this method (via decref), move\r
-               old items to the recycle bin here, and get rid of them when\r
-               we're done modifying the element */\r
-            recycle = PyList_New(slicelen);\r
-            if (!recycle) {\r
-                if (seq) {\r
-                    Py_DECREF(seq);\r
-                }\r
-                return -1;\r
-            }\r
-            for (cur = start, i = 0; i < slicelen;\r
-                 cur += step, i++)\r
-                PyList_SET_ITEM(recycle, i, self->extra->children[cur]);\r
-        }\r
-\r
-        if (newlen < slicelen) {\r
-            /* delete slice */\r
-            for (i = stop; i < self->extra->length; i++)\r
-                self->extra->children[i + newlen - slicelen] = self->extra->children[i];\r
-        } else if (newlen > slicelen) {\r
-            /* insert slice */\r
-            for (i = self->extra->length-1; i >= stop; i--)\r
-                self->extra->children[i + newlen - slicelen] = self->extra->children[i];\r
-        }\r
-\r
-        /* replace the slice */\r
-        for (cur = start, i = 0; i < newlen;\r
-             cur += step, i++) {\r
-            PyObject* element = PySequence_Fast_GET_ITEM(seq, i);\r
-            Py_INCREF(element);\r
-            self->extra->children[cur] = element;\r
-        }\r
-\r
-        self->extra->length += newlen - slicelen;\r
-\r
-        if (seq) {\r
-            Py_DECREF(seq);\r
-        }\r
-\r
-        /* discard the recycle bin, and everything in it */\r
-        Py_XDECREF(recycle);\r
-\r
-        return 0;\r
-    }\r
-    else {\r
-        PyErr_SetString(PyExc_TypeError,\r
-                "element indices must be integers");\r
-        return -1;\r
-    }\r
-}\r
-\r
-static PyMethodDef element_methods[] = {\r
-\r
-    {"clear", (PyCFunction) element_clear, METH_VARARGS},\r
-\r
-    {"get", (PyCFunction) element_get, METH_VARARGS},\r
-    {"set", (PyCFunction) element_set, METH_VARARGS},\r
-\r
-    {"find", (PyCFunction) element_find, METH_VARARGS},\r
-    {"findtext", (PyCFunction) element_findtext, METH_VARARGS},\r
-    {"findall", (PyCFunction) element_findall, METH_VARARGS},\r
-\r
-    {"append", (PyCFunction) element_append, METH_VARARGS},\r
-    {"extend", (PyCFunction) element_extend, METH_VARARGS},\r
-    {"insert", (PyCFunction) element_insert, METH_VARARGS},\r
-    {"remove", (PyCFunction) element_remove, METH_VARARGS},\r
-\r
-    {"iter", (PyCFunction) element_iter, METH_VARARGS},\r
-    {"itertext", (PyCFunction) element_itertext, METH_VARARGS},\r
-    {"iterfind", (PyCFunction) element_iterfind, METH_VARARGS},\r
-\r
-    {"getiterator", (PyCFunction) element_iter, METH_VARARGS},\r
-    {"getchildren", (PyCFunction) element_getchildren, METH_VARARGS},\r
-\r
-    {"items", (PyCFunction) element_items, METH_VARARGS},\r
-    {"keys", (PyCFunction) element_keys, METH_VARARGS},\r
-\r
-    {"makeelement", (PyCFunction) element_makeelement, METH_VARARGS},\r
-\r
-    {"__copy__", (PyCFunction) element_copy, METH_VARARGS},\r
-    {"__deepcopy__", (PyCFunction) element_deepcopy, METH_VARARGS},\r
-\r
-    /* Some 2.3 and 2.4 versions do not handle the __copy__ method on\r
-       C objects correctly, so we have to fake it using a __reduce__-\r
-       based hack (see the element_reduce implementation above for\r
-       details). */\r
-\r
-    /* The behaviour has been changed in 2.3.5 and 2.4.1, so we're\r
-       using a runtime test to figure out if we need to fake things\r
-       or now (see the init code below).  The following entry is\r
-       enabled only if the hack is needed. */\r
-\r
-    {"!__reduce__", (PyCFunction) element_reduce, METH_VARARGS},\r
-\r
-    {NULL, NULL}\r
-};\r
-\r
-static PyObject*  \r
-element_getattr(ElementObject* self, char* name)\r
-{\r
-    PyObject* res;\r
-\r
-    /* handle common attributes first */\r
-    if (strcmp(name, "tag") == 0) {\r
-        res = self->tag;\r
-        Py_INCREF(res);\r
-        return res;\r
-    } else if (strcmp(name, "text") == 0) {\r
-        res = element_get_text(self);\r
-        Py_INCREF(res);\r
-        return res;\r
-    }\r
-\r
-    /* methods */\r
-    res = Py_FindMethod(element_methods, (PyObject*) self, name);\r
-    if (res)\r
-        return res;\r
-\r
-    PyErr_Clear();\r
-\r
-    /* less common attributes */\r
-    if (strcmp(name, "tail") == 0) {\r
-        res = element_get_tail(self);\r
-    } else if (strcmp(name, "attrib") == 0) {\r
-        if (!self->extra)\r
-            element_new_extra(self, NULL);\r
-        res = element_get_attrib(self);\r
-    } else {\r
-        PyErr_SetString(PyExc_AttributeError, name);\r
-        return NULL;\r
-    }\r
-\r
-    if (!res)\r
-        return NULL;\r
-\r
-    Py_INCREF(res);\r
-    return res;\r
-}\r
-\r
-static int\r
-element_setattr(ElementObject* self, const char* name, PyObject* value)\r
-{\r
-    if (value == NULL) {\r
-        PyErr_SetString(\r
-            PyExc_AttributeError,\r
-            "can't delete element attributes"\r
-            );\r
-        return -1;\r
-    }\r
-\r
-    if (strcmp(name, "tag") == 0) {\r
-        Py_DECREF(self->tag);\r
-        self->tag = value;\r
-        Py_INCREF(self->tag);\r
-    } else if (strcmp(name, "text") == 0) {\r
-        Py_DECREF(JOIN_OBJ(self->text));\r
-        self->text = value;\r
-        Py_INCREF(self->text);\r
-    } else if (strcmp(name, "tail") == 0) {\r
-        Py_DECREF(JOIN_OBJ(self->tail));\r
-        self->tail = value;\r
-        Py_INCREF(self->tail);\r
-    } else if (strcmp(name, "attrib") == 0) {\r
-        if (!self->extra)\r
-            element_new_extra(self, NULL);\r
-        Py_DECREF(self->extra->attrib);\r
-        self->extra->attrib = value;\r
-        Py_INCREF(self->extra->attrib);\r
-    } else {\r
-        PyErr_SetString(PyExc_AttributeError, name);\r
-        return -1;\r
-    }\r
-\r
-    return 0;\r
-}\r
-\r
-static PySequenceMethods element_as_sequence = {\r
-    (lenfunc) element_length,\r
-    0, /* sq_concat */\r
-    0, /* sq_repeat */\r
-    element_getitem,\r
-    0,\r
-    element_setitem,\r
-    0,\r
-};\r
-\r
-static PyMappingMethods element_as_mapping = {\r
-    (lenfunc) element_length,\r
-    (binaryfunc) element_subscr,\r
-    (objobjargproc) element_ass_subscr,\r
-};\r
-\r
-statichere PyTypeObject Element_Type = {\r
-    PyObject_HEAD_INIT(NULL)\r
-    0, "Element", sizeof(ElementObject), 0,\r
-    /* methods */\r
-    (destructor)element_dealloc, /* tp_dealloc */\r
-    0, /* tp_print */\r
-    (getattrfunc)element_getattr, /* tp_getattr */\r
-    (setattrfunc)element_setattr, /* tp_setattr */\r
-    0, /* tp_compare */\r
-    (reprfunc)element_repr, /* tp_repr */\r
-    0, /* tp_as_number */\r
-    &element_as_sequence, /* tp_as_sequence */\r
-    &element_as_mapping, /* tp_as_mapping */\r
-};\r
-\r
-/* ==================================================================== */\r
-/* the tree builder type */\r
-\r
-typedef struct {\r
-    PyObject_HEAD\r
-\r
-    PyObject* root; /* root node (first created node) */\r
-\r
-    ElementObject* this; /* current node */\r
-    ElementObject* last; /* most recently created node */\r
-\r
-    PyObject* data; /* data collector (string or list), or NULL */\r
-\r
-    PyObject* stack; /* element stack */\r
-    Py_ssize_t index; /* current stack size (0=empty) */\r
-\r
-    /* element tracing */\r
-    PyObject* events; /* list of events, or NULL if not collecting */\r
-    PyObject* start_event_obj; /* event objects (NULL to ignore) */\r
-    PyObject* end_event_obj;\r
-    PyObject* start_ns_event_obj;\r
-    PyObject* end_ns_event_obj;\r
-\r
-} TreeBuilderObject;\r
-\r
-staticforward PyTypeObject TreeBuilder_Type;\r
-\r
-#define TreeBuilder_CheckExact(op) (Py_TYPE(op) == &TreeBuilder_Type)\r
-\r
-/* -------------------------------------------------------------------- */\r
-/* constructor and destructor */\r
-\r
-LOCAL(PyObject*)\r
-treebuilder_new(void)\r
-{\r
-    TreeBuilderObject* self;\r
-\r
-    self = PyObject_New(TreeBuilderObject, &TreeBuilder_Type);\r
-    if (self == NULL)\r
-        return NULL;\r
-\r
-    self->root = NULL;\r
-\r
-    Py_INCREF(Py_None);\r
-    self->this = (ElementObject*) Py_None;\r
-\r
-    Py_INCREF(Py_None);\r
-    self->last = (ElementObject*) Py_None;\r
-\r
-    self->data = NULL;\r
-\r
-    self->stack = PyList_New(20);\r
-    self->index = 0;\r
-\r
-    self->events = NULL;\r
-    self->start_event_obj = self->end_event_obj = NULL;\r
-    self->start_ns_event_obj = self->end_ns_event_obj = NULL;\r
-\r
-    ALLOC(sizeof(TreeBuilderObject), "create treebuilder");\r
-\r
-    return (PyObject*) self;\r
-}\r
-\r
-static PyObject*\r
-treebuilder(PyObject* self_, PyObject* args)\r
-{\r
-    if (!PyArg_ParseTuple(args, ":TreeBuilder"))\r
-        return NULL;\r
-\r
-    return treebuilder_new();\r
-}\r
-\r
-static void\r
-treebuilder_dealloc(TreeBuilderObject* self)\r
-{\r
-    Py_XDECREF(self->end_ns_event_obj);\r
-    Py_XDECREF(self->start_ns_event_obj);\r
-    Py_XDECREF(self->end_event_obj);\r
-    Py_XDECREF(self->start_event_obj);\r
-    Py_XDECREF(self->events);\r
-    Py_DECREF(self->stack);\r
-    Py_XDECREF(self->data);\r
-    Py_DECREF(self->last);\r
-    Py_DECREF(self->this);\r
-    Py_XDECREF(self->root);\r
-\r
-    RELEASE(sizeof(TreeBuilderObject), "destroy treebuilder");\r
-\r
-    PyObject_Del(self);\r
-}\r
-\r
-/* -------------------------------------------------------------------- */\r
-/* handlers */\r
-\r
-LOCAL(PyObject*)\r
-treebuilder_handle_xml(TreeBuilderObject* self, PyObject* encoding,\r
-                       PyObject* standalone)\r
-{\r
-    Py_RETURN_NONE;\r
-}\r
-\r
-LOCAL(PyObject*)\r
-treebuilder_handle_start(TreeBuilderObject* self, PyObject* tag,\r
-                         PyObject* attrib)\r
-{\r
-    PyObject* node;\r
-    PyObject* this;\r
-\r
-    if (self->data) {\r
-        if (self->this == self->last) {\r
-            Py_DECREF(JOIN_OBJ(self->last->text));\r
-            self->last->text = JOIN_SET(\r
-                self->data, PyList_CheckExact(self->data)\r
-                );\r
-        } else {\r
-            Py_DECREF(JOIN_OBJ(self->last->tail));\r
-            self->last->tail = JOIN_SET(\r
-                self->data, PyList_CheckExact(self->data)\r
-                );\r
-        }\r
-        self->data = NULL;\r
-    }\r
-\r
-    node = element_new(tag, attrib);\r
-    if (!node)\r
-        return NULL;\r
-\r
-    this = (PyObject*) self->this;\r
-\r
-    if (this != Py_None) {\r
-        if (element_add_subelement((ElementObject*) this, node) < 0)\r
-            goto error;\r
-    } else {\r
-        if (self->root) {\r
-            PyErr_SetString(\r
-                elementtree_parseerror_obj,\r
-                "multiple elements on top level"\r
-                );\r
-            goto error;\r
-        }\r
-        Py_INCREF(node);\r
-        self->root = node;\r
-    }\r
-\r
-    if (self->index < PyList_GET_SIZE(self->stack)) {\r
-        if (PyList_SetItem(self->stack, self->index, this) < 0)\r
-            goto error;\r
-        Py_INCREF(this);\r
-    } else {\r
-        if (PyList_Append(self->stack, this) < 0)\r
-            goto error;\r
-    }\r
-    self->index++;\r
-\r
-    Py_DECREF(this);\r
-    Py_INCREF(node);\r
-    self->this = (ElementObject*) node;\r
-\r
-    Py_DECREF(self->last);\r
-    Py_INCREF(node);\r
-    self->last = (ElementObject*) node;\r
-\r
-    if (self->start_event_obj) {\r
-        PyObject* res;\r
-        PyObject* action = self->start_event_obj;\r
-        res = PyTuple_New(2);\r
-        if (res) {\r
-            Py_INCREF(action); PyTuple_SET_ITEM(res, 0, (PyObject*) action);\r
-            Py_INCREF(node);   PyTuple_SET_ITEM(res, 1, (PyObject*) node);\r
-            PyList_Append(self->events, res);\r
-            Py_DECREF(res);\r
-        } else\r
-            PyErr_Clear(); /* FIXME: propagate error */\r
-    }\r
-\r
-    return node;\r
-\r
-  error:\r
-    Py_DECREF(node);\r
-    return NULL;\r
-}\r
-\r
-LOCAL(PyObject*)\r
-treebuilder_handle_data(TreeBuilderObject* self, PyObject* data)\r
-{\r
-    if (!self->data) {\r
-        if (self->last == (ElementObject*) Py_None) {\r
-            /* ignore calls to data before the first call to start */\r
-            Py_RETURN_NONE;\r
-        }\r
-        /* store the first item as is */\r
-        Py_INCREF(data); self->data = data;\r
-    } else {\r
-        /* more than one item; use a list to collect items */\r
-        if (PyString_CheckExact(self->data) && Py_REFCNT(self->data) == 1 &&\r
-            PyString_CheckExact(data) && PyString_GET_SIZE(data) == 1) {\r
-            /* expat often generates single character data sections; handle\r
-               the most common case by resizing the existing string... */\r
-            Py_ssize_t size = PyString_GET_SIZE(self->data);\r
-            if (_PyString_Resize(&self->data, size + 1) < 0)\r
-                return NULL;\r
-            PyString_AS_STRING(self->data)[size] = PyString_AS_STRING(data)[0];\r
-        } else if (PyList_CheckExact(self->data)) {\r
-            if (PyList_Append(self->data, data) < 0)\r
-                return NULL;\r
-        } else {\r
-            PyObject* list = PyList_New(2);\r
-            if (!list)\r
-                return NULL;\r
-            PyList_SET_ITEM(list, 0, self->data);\r
-            Py_INCREF(data); PyList_SET_ITEM(list, 1, data);\r
-            self->data = list;\r
-        }\r
-    }\r
-\r
-    Py_RETURN_NONE;\r
-}\r
-\r
-LOCAL(PyObject*)\r
-treebuilder_handle_end(TreeBuilderObject* self, PyObject* tag)\r
-{\r
-    PyObject* item;\r
-\r
-    if (self->data) {\r
-        if (self->this == self->last) {\r
-            Py_DECREF(JOIN_OBJ(self->last->text));\r
-            self->last->text = JOIN_SET(\r
-                self->data, PyList_CheckExact(self->data)\r
-                );\r
-        } else {\r
-            Py_DECREF(JOIN_OBJ(self->last->tail));\r
-            self->last->tail = JOIN_SET(\r
-                self->data, PyList_CheckExact(self->data)\r
-                );\r
-        }\r
-        self->data = NULL;\r
-    }\r
-\r
-    if (self->index == 0) {\r
-        PyErr_SetString(\r
-            PyExc_IndexError,\r
-            "pop from empty stack"\r
-            );\r
-        return NULL;\r
-    }\r
-\r
-    self->index--;\r
-\r
-    item = PyList_GET_ITEM(self->stack, self->index);\r
-    Py_INCREF(item);\r
-\r
-    Py_DECREF(self->last);\r
-\r
-    self->last = (ElementObject*) self->this;\r
-    self->this = (ElementObject*) item;\r
-\r
-    if (self->end_event_obj) {\r
-        PyObject* res;\r
-        PyObject* action = self->end_event_obj;\r
-        PyObject* node = (PyObject*) self->last;\r
-        res = PyTuple_New(2);\r
-        if (res) {\r
-            Py_INCREF(action); PyTuple_SET_ITEM(res, 0, (PyObject*) action);\r
-            Py_INCREF(node);   PyTuple_SET_ITEM(res, 1, (PyObject*) node);\r
-            PyList_Append(self->events, res);\r
-            Py_DECREF(res);\r
-        } else\r
-            PyErr_Clear(); /* FIXME: propagate error */\r
-    }\r
-\r
-    Py_INCREF(self->last);\r
-    return (PyObject*) self->last;\r
-}\r
-\r
-LOCAL(void)\r
-treebuilder_handle_namespace(TreeBuilderObject* self, int start,\r
-                             PyObject *prefix, PyObject *uri)\r
-{\r
-    PyObject* res;\r
-    PyObject* action;\r
-    PyObject* parcel;\r
-\r
-    if (!self->events)\r
-        return;\r
-\r
-    if (start) {\r
-        if (!self->start_ns_event_obj)\r
-            return;\r
-        action = self->start_ns_event_obj;\r
-        parcel = Py_BuildValue("OO", prefix, uri);\r
-        if (!parcel)\r
-            return;\r
-        Py_INCREF(action);\r
-    } else {\r
-        if (!self->end_ns_event_obj)\r
-            return;\r
-        action = self->end_ns_event_obj;\r
-        Py_INCREF(action);\r
-        parcel = Py_None;\r
-        Py_INCREF(parcel);\r
-    }\r
-\r
-    res = PyTuple_New(2);\r
-\r
-    if (res) {\r
-        PyTuple_SET_ITEM(res, 0, action);\r
-        PyTuple_SET_ITEM(res, 1, parcel);\r
-        PyList_Append(self->events, res);\r
-        Py_DECREF(res);\r
-    } else\r
-        PyErr_Clear(); /* FIXME: propagate error */\r
-}\r
-\r
-/* -------------------------------------------------------------------- */\r
-/* methods (in alphabetical order) */\r
-\r
-static PyObject*\r
-treebuilder_data(TreeBuilderObject* self, PyObject* args)\r
-{\r
-    PyObject* data;\r
-    if (!PyArg_ParseTuple(args, "O:data", &data))\r
-        return NULL;\r
-\r
-    return treebuilder_handle_data(self, data);\r
-}\r
-\r
-static PyObject*\r
-treebuilder_end(TreeBuilderObject* self, PyObject* args)\r
-{\r
-    PyObject* tag;\r
-    if (!PyArg_ParseTuple(args, "O:end", &tag))\r
-        return NULL;\r
-\r
-    return treebuilder_handle_end(self, tag);\r
-}\r
-\r
-LOCAL(PyObject*)\r
-treebuilder_done(TreeBuilderObject* self)\r
-{\r
-    PyObject* res;\r
-\r
-    /* FIXME: check stack size? */\r
-\r
-    if (self->root)\r
-        res = self->root;\r
-    else\r
-        res = Py_None;\r
-\r
-    Py_INCREF(res);\r
-    return res;\r
-}\r
-\r
-static PyObject*\r
-treebuilder_close(TreeBuilderObject* self, PyObject* args)\r
-{\r
-    if (!PyArg_ParseTuple(args, ":close"))\r
-        return NULL;\r
-\r
-    return treebuilder_done(self);\r
-}\r
-\r
-static PyObject*\r
-treebuilder_start(TreeBuilderObject* self, PyObject* args)\r
-{\r
-    PyObject* tag;\r
-    PyObject* attrib = Py_None;\r
-    if (!PyArg_ParseTuple(args, "O|O:start", &tag, &attrib))\r
-        return NULL;\r
-\r
-    return treebuilder_handle_start(self, tag, attrib);\r
-}\r
-\r
-static PyObject*\r
-treebuilder_xml(TreeBuilderObject* self, PyObject* args)\r
-{\r
-    PyObject* encoding;\r
-    PyObject* standalone;\r
-    if (!PyArg_ParseTuple(args, "OO:xml", &encoding, &standalone))\r
-        return NULL;\r
-\r
-    return treebuilder_handle_xml(self, encoding, standalone);\r
-}\r
-\r
-static PyMethodDef treebuilder_methods[] = {\r
-    {"data", (PyCFunction) treebuilder_data, METH_VARARGS},\r
-    {"start", (PyCFunction) treebuilder_start, METH_VARARGS},\r
-    {"end", (PyCFunction) treebuilder_end, METH_VARARGS},\r
-    {"xml", (PyCFunction) treebuilder_xml, METH_VARARGS},\r
-    {"close", (PyCFunction) treebuilder_close, METH_VARARGS},\r
-    {NULL, NULL}\r
-};\r
-\r
-static PyObject*  \r
-treebuilder_getattr(TreeBuilderObject* self, char* name)\r
-{\r
-    return Py_FindMethod(treebuilder_methods, (PyObject*) self, name);\r
-}\r
-\r
-statichere PyTypeObject TreeBuilder_Type = {\r
-    PyObject_HEAD_INIT(NULL)\r
-    0, "TreeBuilder", sizeof(TreeBuilderObject), 0,\r
-    /* methods */\r
-    (destructor)treebuilder_dealloc, /* tp_dealloc */\r
-    0, /* tp_print */\r
-    (getattrfunc)treebuilder_getattr, /* tp_getattr */\r
-};\r
-\r
-/* ==================================================================== */\r
-/* the expat interface */\r
-\r
-#if defined(USE_EXPAT)\r
-\r
-#include "expat.h"\r
-\r
-#if defined(USE_PYEXPAT_CAPI)\r
-#include "pyexpat.h"\r
-static struct PyExpat_CAPI* expat_capi;\r
-#define EXPAT(func) (expat_capi->func)\r
-#else\r
-#define EXPAT(func) (XML_##func)\r
-#endif\r
-\r
-typedef struct {\r
-    PyObject_HEAD\r
-\r
-    XML_Parser parser;\r
-\r
-    PyObject* target;\r
-    PyObject* entity;\r
-\r
-    PyObject* names;\r
-\r
-    PyObject* handle_xml;\r
-\r
-    PyObject* handle_start;\r
-    PyObject* handle_data;\r
-    PyObject* handle_end;\r
-\r
-    PyObject* handle_comment;\r
-    PyObject* handle_pi;\r
-\r
-    PyObject* handle_close;\r
-\r
-} XMLParserObject;\r
-\r
-staticforward PyTypeObject XMLParser_Type;\r
-\r
-/* helpers */\r
-\r
-#if defined(Py_USING_UNICODE)\r
-LOCAL(int)\r
-checkstring(const char* string, int size)\r
-{\r
-    int i;\r
-\r
-    /* check if an 8-bit string contains UTF-8 characters */\r
-    for (i = 0; i < size; i++)\r
-        if (string[i] & 0x80)\r
-            return 1;\r
-\r
-    return 0;\r
-}\r
-#endif\r
-\r
-LOCAL(PyObject*)\r
-makestring(const char* string, int size)\r
-{\r
-    /* convert a UTF-8 string to either a 7-bit ascii string or a\r
-       Unicode string */\r
-\r
-#if defined(Py_USING_UNICODE)\r
-    if (checkstring(string, size))\r
-        return PyUnicode_DecodeUTF8(string, size, "strict");\r
-#endif\r
-\r
-    return PyString_FromStringAndSize(string, size);\r
-}\r
-\r
-LOCAL(PyObject*)\r
-makeuniversal(XMLParserObject* self, const char* string)\r
-{\r
-    /* convert a UTF-8 tag/attribute name from the expat parser\r
-       to a universal name string */\r
-\r
-    int size = strlen(string);\r
-    PyObject* key;\r
-    PyObject* value;\r
-\r
-    /* look the 'raw' name up in the names dictionary */\r
-    key = PyString_FromStringAndSize(string, size);\r
-    if (!key)\r
-        return NULL;\r
-\r
-    value = PyDict_GetItem(self->names, key);\r
-\r
-    if (value) {\r
-        Py_INCREF(value);\r
-    } else {\r
-        /* new name.  convert to universal name, and decode as\r
-           necessary */\r
-\r
-        PyObject* tag;\r
-        char* p;\r
-        int i;\r
-\r
-        /* look for namespace separator */\r
-        for (i = 0; i < size; i++)\r
-            if (string[i] == '}')\r
-                break;\r
-        if (i != size) {\r
-            /* convert to universal name */\r
-            tag = PyString_FromStringAndSize(NULL, size+1);\r
-            p = PyString_AS_STRING(tag);\r
-            p[0] = '{';\r
-            memcpy(p+1, string, size);\r
-            size++;\r
-        } else {\r
-            /* plain name; use key as tag */\r
-            Py_INCREF(key);\r
-            tag = key;\r
-        }\r
-        \r
-        /* decode universal name */\r
-#if defined(Py_USING_UNICODE)\r
-        /* inline makestring, to avoid duplicating the source string if\r
-           it's not an utf-8 string */\r
-        p = PyString_AS_STRING(tag);\r
-        if (checkstring(p, size)) {\r
-            value = PyUnicode_DecodeUTF8(p, size, "strict");\r
-            Py_DECREF(tag);\r
-            if (!value) {\r
-                Py_DECREF(key);\r
-                return NULL;\r
-            }\r
-        } else\r
-#endif\r
-            value = tag; /* use tag as is */\r
-\r
-        /* add to names dictionary */\r
-        if (PyDict_SetItem(self->names, key, value) < 0) {\r
-            Py_DECREF(key);\r
-            Py_DECREF(value);\r
-            return NULL;\r
-        }\r
-    }\r
-\r
-    Py_DECREF(key);\r
-    return value;\r
-}\r
-\r
-static void\r
-expat_set_error(const char* message, int line, int column)\r
-{\r
-    PyObject *error;\r
-    PyObject *position;\r
-    char buffer[256];\r
-\r
-    sprintf(buffer, "%s: line %d, column %d", message, line, column);\r
-\r
-    error = PyObject_CallFunction(elementtree_parseerror_obj, "s", buffer);\r
-    if (!error)\r
-        return;\r
-\r
-    /* add position attribute */\r
-    position = Py_BuildValue("(ii)", line, column);\r
-    if (!position) {\r
-        Py_DECREF(error);\r
-        return;\r
-    }\r
-    if (PyObject_SetAttrString(error, "position", position) == -1) {\r
-        Py_DECREF(error);\r
-        Py_DECREF(position);\r
-        return;\r
-    }\r
-    Py_DECREF(position);\r
-\r
-    PyErr_SetObject(elementtree_parseerror_obj, error);\r
-    Py_DECREF(error);\r
-}\r
-\r
-/* -------------------------------------------------------------------- */\r
-/* handlers */\r
-\r
-static void\r
-expat_default_handler(XMLParserObject* self, const XML_Char* data_in,\r
-                      int data_len)\r
-{\r
-    PyObject* key;\r
-    PyObject* value;\r
-    PyObject* res;\r
-\r
-    if (data_len < 2 || data_in[0] != '&')\r
-        return;\r
-\r
-    key = makestring(data_in + 1, data_len - 2);\r
-    if (!key)\r
-        return;\r
-\r
-    value = PyDict_GetItem(self->entity, key);\r
-\r
-    if (value) {\r
-        if (TreeBuilder_CheckExact(self->target))\r
-            res = treebuilder_handle_data(\r
-                (TreeBuilderObject*) self->target, value\r
-                );\r
-        else if (self->handle_data)\r
-            res = PyObject_CallFunction(self->handle_data, "O", value);\r
-        else\r
-            res = NULL;\r
-        Py_XDECREF(res);\r
-    } else if (!PyErr_Occurred()) {\r
-        /* Report the first error, not the last */\r
-        char message[128];\r
-        sprintf(message, "undefined entity &%.100s;", PyString_AS_STRING(key));\r
-        expat_set_error(\r
-            message,\r
-            EXPAT(GetErrorLineNumber)(self->parser),\r
-            EXPAT(GetErrorColumnNumber)(self->parser)\r
-            );\r
-    }\r
-\r
-    Py_DECREF(key);\r
-}\r
-\r
-static void\r
-expat_start_handler(XMLParserObject* self, const XML_Char* tag_in,\r
-                    const XML_Char **attrib_in)\r
-{\r
-    PyObject* res;\r
-    PyObject* tag;\r
-    PyObject* attrib;\r
-    int ok;\r
-\r
-    /* tag name */\r
-    tag = makeuniversal(self, tag_in);\r
-    if (!tag)\r
-        return; /* parser will look for errors */\r
-\r
-    /* attributes */\r
-    if (attrib_in[0]) {\r
-        attrib = PyDict_New();\r
-        if (!attrib)\r
-            return;\r
-        while (attrib_in[0] && attrib_in[1]) {\r
-            PyObject* key = makeuniversal(self, attrib_in[0]);\r
-            PyObject* value = makestring(attrib_in[1], strlen(attrib_in[1]));\r
-            if (!key || !value) {\r
-                Py_XDECREF(value);\r
-                Py_XDECREF(key);\r
-                Py_DECREF(attrib);\r
-                return;\r
-            }\r
-            ok = PyDict_SetItem(attrib, key, value);\r
-            Py_DECREF(value);\r
-            Py_DECREF(key);\r
-            if (ok < 0) {\r
-                Py_DECREF(attrib);\r
-                return;\r
-            }\r
-            attrib_in += 2;\r
-        }\r
-    } else {\r
-        Py_INCREF(Py_None);\r
-        attrib = Py_None;\r
-    }\r
-\r
-    if (TreeBuilder_CheckExact(self->target))\r
-        /* shortcut */\r
-        res = treebuilder_handle_start((TreeBuilderObject*) self->target,\r
-                                       tag, attrib);\r
-    else if (self->handle_start) {\r
-        if (attrib == Py_None) {\r
-            Py_DECREF(attrib);\r
-            attrib = PyDict_New();\r
-            if (!attrib)\r
-                return;\r
-        }\r
-        res = PyObject_CallFunction(self->handle_start, "OO", tag, attrib);\r
-    } else\r
-        res = NULL;\r
-\r
-    Py_DECREF(tag);\r
-    Py_DECREF(attrib);\r
-\r
-    Py_XDECREF(res);\r
-}\r
-\r
-static void\r
-expat_data_handler(XMLParserObject* self, const XML_Char* data_in,\r
-                   int data_len)\r
-{\r
-    PyObject* data;\r
-    PyObject* res;\r
-\r
-    data = makestring(data_in, data_len);\r
-    if (!data)\r
-        return; /* parser will look for errors */\r
-\r
-    if (TreeBuilder_CheckExact(self->target))\r
-        /* shortcut */\r
-        res = treebuilder_handle_data((TreeBuilderObject*) self->target, data);\r
-    else if (self->handle_data)\r
-        res = PyObject_CallFunction(self->handle_data, "O", data);\r
-    else\r
-        res = NULL;\r
-\r
-    Py_DECREF(data);\r
-\r
-    Py_XDECREF(res);\r
-}\r
-\r
-static void\r
-expat_end_handler(XMLParserObject* self, const XML_Char* tag_in)\r
-{\r
-    PyObject* tag;\r
-    PyObject* res = NULL;\r
-\r
-    if (TreeBuilder_CheckExact(self->target))\r
-        /* shortcut */\r
-        /* the standard tree builder doesn't look at the end tag */\r
-        res = treebuilder_handle_end(\r
-            (TreeBuilderObject*) self->target, Py_None\r
-            );\r
-    else if (self->handle_end) {\r
-        tag = makeuniversal(self, tag_in);\r
-        if (tag) {\r
-            res = PyObject_CallFunction(self->handle_end, "O", tag);\r
-            Py_DECREF(tag);\r
-        }\r
-    }\r
-\r
-    Py_XDECREF(res);\r
-}\r
-\r
-static void\r
-expat_start_ns_handler(XMLParserObject* self, const XML_Char* prefix,\r
-                       const XML_Char *uri)\r
-{\r
-    PyObject* sprefix = NULL;\r
-    PyObject* suri = NULL;\r
-\r
-    suri = makestring(uri, strlen(uri));\r
-    if (!suri)\r
-        return;\r
-\r
-    if (prefix)\r
-        sprefix = makestring(prefix, strlen(prefix));\r
-    else\r
-        sprefix = PyString_FromStringAndSize("", 0);\r
-    if (!sprefix) {\r
-        Py_DECREF(suri);\r
-        return;\r
-    }\r
-\r
-    treebuilder_handle_namespace(\r
-        (TreeBuilderObject*) self->target, 1, sprefix, suri\r
-        );\r
-\r
-    Py_DECREF(sprefix);\r
-    Py_DECREF(suri);\r
-}\r
-\r
-static void\r
-expat_end_ns_handler(XMLParserObject* self, const XML_Char* prefix_in)\r
-{\r
-    treebuilder_handle_namespace(\r
-        (TreeBuilderObject*) self->target, 0, NULL, NULL\r
-        );\r
-}\r
-\r
-static void\r
-expat_comment_handler(XMLParserObject* self, const XML_Char* comment_in)\r
-{\r
-    PyObject* comment;\r
-    PyObject* res;\r
-\r
-    if (self->handle_comment) {\r
-        comment = makestring(comment_in, strlen(comment_in));\r
-        if (comment) {\r
-            res = PyObject_CallFunction(self->handle_comment, "O", comment);\r
-            Py_XDECREF(res);\r
-            Py_DECREF(comment);\r
-        }\r
-    }\r
-}\r
-\r
-static void\r
-expat_pi_handler(XMLParserObject* self, const XML_Char* target_in,\r
-                 const XML_Char* data_in)\r
-{\r
-    PyObject* target;\r
-    PyObject* data;\r
-    PyObject* res;\r
-\r
-    if (self->handle_pi) {\r
-        target = makestring(target_in, strlen(target_in));\r
-        data = makestring(data_in, strlen(data_in));\r
-        if (target && data) {\r
-            res = PyObject_CallFunction(self->handle_pi, "OO", target, data);\r
-            Py_XDECREF(res);\r
-            Py_DECREF(data);\r
-            Py_DECREF(target);\r
-        } else {\r
-            Py_XDECREF(data);\r
-            Py_XDECREF(target);\r
-        }\r
-    }\r
-}\r
-\r
-#if defined(Py_USING_UNICODE)\r
-static int\r
-expat_unknown_encoding_handler(XMLParserObject *self, const XML_Char *name,\r
-                               XML_Encoding *info)\r
-{\r
-    PyObject* u;\r
-    Py_UNICODE* p;\r
-    unsigned char s[256];\r
-    int i;\r
-\r
-    memset(info, 0, sizeof(XML_Encoding));\r
-\r
-    for (i = 0; i < 256; i++)\r
-        s[i] = i;\r
-    \r
-    u = PyUnicode_Decode((char*) s, 256, name, "replace");\r
-    if (!u)\r
-        return XML_STATUS_ERROR;\r
-\r
-    if (PyUnicode_GET_SIZE(u) != 256) {\r
-        Py_DECREF(u);\r
-        return XML_STATUS_ERROR;\r
-    }\r
-\r
-    p = PyUnicode_AS_UNICODE(u);\r
-\r
-    for (i = 0; i < 256; i++) {\r
-        if (p[i] != Py_UNICODE_REPLACEMENT_CHARACTER)\r
-            info->map[i] = p[i];\r
-        else\r
-            info->map[i] = -1;\r
-    }\r
-\r
-    Py_DECREF(u);\r
-\r
-    return XML_STATUS_OK;\r
-}\r
-#endif\r
-\r
-/* -------------------------------------------------------------------- */\r
-/* constructor and destructor */\r
-\r
-static PyObject*\r
-xmlparser(PyObject* self_, PyObject* args, PyObject* kw)\r
-{\r
-    XMLParserObject* self;\r
-    /* FIXME: does this need to be static? */\r
-    static XML_Memory_Handling_Suite memory_handler;\r
-\r
-    PyObject* target = NULL;\r
-    char* encoding = NULL;\r
-    static char* kwlist[] = { "target", "encoding", NULL };\r
-    if (!PyArg_ParseTupleAndKeywords(args, kw, "|Oz:XMLParser", kwlist,\r
-                                     &target, &encoding))\r
-        return NULL;\r
-\r
-#if defined(USE_PYEXPAT_CAPI)\r
-    if (!expat_capi) {\r
-        PyErr_SetString(\r
-            PyExc_RuntimeError, "cannot load dispatch table from pyexpat"\r
-            );\r
-        return NULL;\r
-    }\r
-#endif\r
-\r
-    self = PyObject_New(XMLParserObject, &XMLParser_Type);\r
-    if (self == NULL)\r
-        return NULL;\r
-\r
-    self->entity = PyDict_New();\r
-    if (!self->entity) {\r
-        PyObject_Del(self);\r
-        return NULL;\r
-    }\r
-     \r
-    self->names = PyDict_New();\r
-    if (!self->names) {\r
-        PyObject_Del(self->entity);\r
-        PyObject_Del(self);\r
-        return NULL;\r
-    }\r
-\r
-    memory_handler.malloc_fcn = PyObject_Malloc;\r
-    memory_handler.realloc_fcn = PyObject_Realloc;\r
-    memory_handler.free_fcn = PyObject_Free;\r
-\r
-    self->parser = EXPAT(ParserCreate_MM)(encoding, &memory_handler, "}");\r
-    if (!self->parser) {\r
-        PyObject_Del(self->names);\r
-        PyObject_Del(self->entity);\r
-        PyObject_Del(self);\r
-        PyErr_NoMemory();\r
-        return NULL;\r
-    }\r
-\r
-    /* setup target handlers */\r
-    if (!target) {\r
-        target = treebuilder_new();\r
-        if (!target) {\r
-            EXPAT(ParserFree)(self->parser);\r
-            PyObject_Del(self->names);\r
-            PyObject_Del(self->entity);\r
-            PyObject_Del(self);\r
-            return NULL;\r
-        }\r
-    } else\r
-        Py_INCREF(target);\r
-    self->target = target;\r
-\r
-    self->handle_xml = PyObject_GetAttrString(target, "xml");\r
-    self->handle_start = PyObject_GetAttrString(target, "start");\r
-    self->handle_data = PyObject_GetAttrString(target, "data");\r
-    self->handle_end = PyObject_GetAttrString(target, "end");\r
-    self->handle_comment = PyObject_GetAttrString(target, "comment");\r
-    self->handle_pi = PyObject_GetAttrString(target, "pi");\r
-    self->handle_close = PyObject_GetAttrString(target, "close");\r
-\r
-    PyErr_Clear();\r
-\r
-    /* configure parser */\r
-    EXPAT(SetUserData)(self->parser, self);\r
-    EXPAT(SetElementHandler)(\r
-        self->parser,\r
-        (XML_StartElementHandler) expat_start_handler,\r
-        (XML_EndElementHandler) expat_end_handler\r
-        );\r
-    EXPAT(SetDefaultHandlerExpand)(\r
-        self->parser,\r
-        (XML_DefaultHandler) expat_default_handler\r
-        );\r
-    EXPAT(SetCharacterDataHandler)(\r
-        self->parser,\r
-        (XML_CharacterDataHandler) expat_data_handler\r
-        );\r
-    if (self->handle_comment)\r
-        EXPAT(SetCommentHandler)(\r
-            self->parser,\r
-            (XML_CommentHandler) expat_comment_handler\r
-            );\r
-    if (self->handle_pi)\r
-        EXPAT(SetProcessingInstructionHandler)(\r
-            self->parser,\r
-            (XML_ProcessingInstructionHandler) expat_pi_handler\r
-            );\r
-#if defined(Py_USING_UNICODE)\r
-    EXPAT(SetUnknownEncodingHandler)(\r
-        self->parser,\r
-        (XML_UnknownEncodingHandler) expat_unknown_encoding_handler, NULL\r
-        );\r
-#endif\r
-\r
-    ALLOC(sizeof(XMLParserObject), "create expatparser");\r
-\r
-    return (PyObject*) self;\r
-}\r
-\r
-static void\r
-xmlparser_dealloc(XMLParserObject* self)\r
-{\r
-    EXPAT(ParserFree)(self->parser);\r
-\r
-    Py_XDECREF(self->handle_close);\r
-    Py_XDECREF(self->handle_pi);\r
-    Py_XDECREF(self->handle_comment);\r
-    Py_XDECREF(self->handle_end);\r
-    Py_XDECREF(self->handle_data);\r
-    Py_XDECREF(self->handle_start);\r
-    Py_XDECREF(self->handle_xml);\r
-\r
-    Py_DECREF(self->target);\r
-    Py_DECREF(self->entity);\r
-    Py_DECREF(self->names);\r
-\r
-    RELEASE(sizeof(XMLParserObject), "destroy expatparser");\r
-\r
-    PyObject_Del(self);\r
-}\r
-\r
-/* -------------------------------------------------------------------- */\r
-/* methods (in alphabetical order) */\r
-\r
-LOCAL(PyObject*)\r
-expat_parse(XMLParserObject* self, char* data, int data_len, int final)\r
-{\r
-    int ok;\r
-\r
-    ok = EXPAT(Parse)(self->parser, data, data_len, final);\r
-\r
-    if (PyErr_Occurred())\r
-        return NULL;\r
-\r
-    if (!ok) {\r
-        expat_set_error(\r
-            EXPAT(ErrorString)(EXPAT(GetErrorCode)(self->parser)),\r
-            EXPAT(GetErrorLineNumber)(self->parser),\r
-            EXPAT(GetErrorColumnNumber)(self->parser)\r
-            );\r
-        return NULL;\r
-    }\r
-\r
-    Py_RETURN_NONE;\r
-}\r
-\r
-static PyObject*\r
-xmlparser_close(XMLParserObject* self, PyObject* args)\r
-{\r
-    /* end feeding data to parser */\r
-\r
-    PyObject* res;\r
-    if (!PyArg_ParseTuple(args, ":close"))\r
-        return NULL;\r
-\r
-    res = expat_parse(self, "", 0, 1);\r
-    if (!res)\r
-        return NULL;\r
-\r
-    if (TreeBuilder_CheckExact(self->target)) {\r
-        Py_DECREF(res);\r
-        return treebuilder_done((TreeBuilderObject*) self->target);\r
-    } if (self->handle_close) {\r
-        Py_DECREF(res);\r
-        return PyObject_CallFunction(self->handle_close, "");\r
-    } else\r
-        return res;\r
-}\r
-\r
-static PyObject*\r
-xmlparser_feed(XMLParserObject* self, PyObject* args)\r
-{\r
-    /* feed data to parser */\r
-\r
-    char* data;\r
-    int data_len;\r
-    if (!PyArg_ParseTuple(args, "s#:feed", &data, &data_len))\r
-        return NULL;\r
-\r
-    return expat_parse(self, data, data_len, 0);\r
-}\r
-\r
-static PyObject*\r
-xmlparser_parse(XMLParserObject* self, PyObject* args)\r
-{\r
-    /* (internal) parse until end of input stream */\r
-\r
-    PyObject* reader;\r
-    PyObject* buffer;\r
-    PyObject* res;\r
-\r
-    PyObject* fileobj;\r
-    if (!PyArg_ParseTuple(args, "O:_parse", &fileobj))\r
-        return NULL;\r
-\r
-    reader = PyObject_GetAttrString(fileobj, "read");\r
-    if (!reader)\r
-        return NULL;\r
-    \r
-    /* read from open file object */\r
-    for (;;) {\r
-\r
-        buffer = PyObject_CallFunction(reader, "i", 64*1024);\r
-\r
-        if (!buffer) {\r
-            /* read failed (e.g. due to KeyboardInterrupt) */\r
-            Py_DECREF(reader);\r
-            return NULL;\r
-        }\r
-\r
-        if (!PyString_CheckExact(buffer) || PyString_GET_SIZE(buffer) == 0) {\r
-            Py_DECREF(buffer);\r
-            break;\r
-        }\r
-\r
-        res = expat_parse(\r
-            self, PyString_AS_STRING(buffer), PyString_GET_SIZE(buffer), 0\r
-            );\r
-\r
-        Py_DECREF(buffer);\r
-\r
-        if (!res) {\r
-            Py_DECREF(reader);\r
-            return NULL;\r
-        }\r
-        Py_DECREF(res);\r
-\r
-    }\r
-\r
-    Py_DECREF(reader);\r
-\r
-    res = expat_parse(self, "", 0, 1);\r
-\r
-    if (res && TreeBuilder_CheckExact(self->target)) {\r
-        Py_DECREF(res);\r
-        return treebuilder_done((TreeBuilderObject*) self->target);\r
-    }\r
-\r
-    return res;\r
-}\r
-\r
-static PyObject*\r
-xmlparser_setevents(XMLParserObject* self, PyObject* args)\r
-{\r
-    /* activate element event reporting */\r
-\r
-    Py_ssize_t i;\r
-    TreeBuilderObject* target;\r
-\r
-    PyObject* events; /* event collector */\r
-    PyObject* event_set = Py_None;\r
-    if (!PyArg_ParseTuple(args, "O!|O:_setevents",  &PyList_Type, &events,\r
-                          &event_set))\r
-        return NULL;\r
-\r
-    if (!TreeBuilder_CheckExact(self->target)) {\r
-        PyErr_SetString(\r
-            PyExc_TypeError,\r
-            "event handling only supported for cElementTree.Treebuilder "\r
-            "targets"\r
-            );\r
-        return NULL;\r
-    }\r
-\r
-    target = (TreeBuilderObject*) self->target;\r
-\r
-    Py_INCREF(events);\r
-    Py_XDECREF(target->events);\r
-    target->events = events;\r
-\r
-    /* clear out existing events */\r
-    Py_XDECREF(target->start_event_obj); target->start_event_obj = NULL;\r
-    Py_XDECREF(target->end_event_obj); target->end_event_obj = NULL;\r
-    Py_XDECREF(target->start_ns_event_obj); target->start_ns_event_obj = NULL;\r
-    Py_XDECREF(target->end_ns_event_obj); target->end_ns_event_obj = NULL;\r
-\r
-    if (event_set == Py_None) {\r
-        /* default is "end" only */\r
-        target->end_event_obj = PyString_FromString("end");\r
-        Py_RETURN_NONE;\r
-    }\r
-\r
-    if (!PyTuple_Check(event_set)) /* FIXME: handle arbitrary sequences */\r
-        goto error;\r
-\r
-    for (i = 0; i < PyTuple_GET_SIZE(event_set); i++) {\r
-        PyObject* item = PyTuple_GET_ITEM(event_set, i);\r
-        char* event;\r
-        if (!PyString_Check(item))\r
-            goto error;\r
-        event = PyString_AS_STRING(item);\r
-        if (strcmp(event, "start") == 0) {\r
-            Py_INCREF(item);\r
-            target->start_event_obj = item;\r
-        } else if (strcmp(event, "end") == 0) {\r
-            Py_INCREF(item);\r
-            Py_XDECREF(target->end_event_obj);\r
-            target->end_event_obj = item;\r
-        } else if (strcmp(event, "start-ns") == 0) {\r
-            Py_INCREF(item);\r
-            Py_XDECREF(target->start_ns_event_obj);\r
-            target->start_ns_event_obj = item;\r
-            EXPAT(SetNamespaceDeclHandler)(\r
-                self->parser,\r
-                (XML_StartNamespaceDeclHandler) expat_start_ns_handler,\r
-                (XML_EndNamespaceDeclHandler) expat_end_ns_handler\r
-                );\r
-        } else if (strcmp(event, "end-ns") == 0) {\r
-            Py_INCREF(item);\r
-            Py_XDECREF(target->end_ns_event_obj);\r
-            target->end_ns_event_obj = item;\r
-            EXPAT(SetNamespaceDeclHandler)(\r
-                self->parser,\r
-                (XML_StartNamespaceDeclHandler) expat_start_ns_handler,\r
-                (XML_EndNamespaceDeclHandler) expat_end_ns_handler\r
-                );\r
-        } else {\r
-            PyErr_Format(\r
-                PyExc_ValueError,\r
-                "unknown event '%s'", event\r
-                );\r
-            return NULL;\r
-        }\r
-    }\r
-\r
-    Py_RETURN_NONE;\r
-\r
-  error:\r
-    PyErr_SetString(\r
-        PyExc_TypeError,\r
-        "invalid event tuple"\r
-        );\r
-    return NULL;\r
-}\r
-\r
-static PyMethodDef xmlparser_methods[] = {\r
-    {"feed", (PyCFunction) xmlparser_feed, METH_VARARGS},\r
-    {"close", (PyCFunction) xmlparser_close, METH_VARARGS},\r
-    {"_parse", (PyCFunction) xmlparser_parse, METH_VARARGS},\r
-    {"_setevents", (PyCFunction) xmlparser_setevents, METH_VARARGS},\r
-    {NULL, NULL}\r
-};\r
-\r
-static PyObject*  \r
-xmlparser_getattr(XMLParserObject* self, char* name)\r
-{\r
-    PyObject* res;\r
-\r
-    res = Py_FindMethod(xmlparser_methods, (PyObject*) self, name);\r
-    if (res)\r
-        return res;\r
-\r
-    PyErr_Clear();\r
-\r
-    if (strcmp(name, "entity") == 0)\r
-        res = self->entity;\r
-    else if (strcmp(name, "target") == 0)\r
-        res = self->target;\r
-    else if (strcmp(name, "version") == 0) {\r
-        char buffer[100];\r
-        sprintf(buffer, "Expat %d.%d.%d", XML_MAJOR_VERSION,\r
-                XML_MINOR_VERSION, XML_MICRO_VERSION);\r
-        return PyString_FromString(buffer);\r
-    } else {\r
-        PyErr_SetString(PyExc_AttributeError, name);\r
-        return NULL;\r
-    }\r
-\r
-    Py_INCREF(res);\r
-    return res;\r
-}\r
-\r
-statichere PyTypeObject XMLParser_Type = {\r
-    PyObject_HEAD_INIT(NULL)\r
-    0, "XMLParser", sizeof(XMLParserObject), 0,\r
-    /* methods */\r
-    (destructor)xmlparser_dealloc, /* tp_dealloc */\r
-    0, /* tp_print */\r
-    (getattrfunc)xmlparser_getattr, /* tp_getattr */\r
-};\r
-\r
-#endif\r
-\r
-/* ==================================================================== */\r
-/* python module interface */\r
-\r
-static PyMethodDef _functions[] = {\r
-    {"Element", (PyCFunction) element, METH_VARARGS|METH_KEYWORDS},\r
-    {"SubElement", (PyCFunction) subelement, METH_VARARGS|METH_KEYWORDS},\r
-    {"TreeBuilder", (PyCFunction) treebuilder, METH_VARARGS},\r
-#if defined(USE_EXPAT)\r
-    {"XMLParser", (PyCFunction) xmlparser, METH_VARARGS|METH_KEYWORDS},\r
-    {"XMLTreeBuilder", (PyCFunction) xmlparser, METH_VARARGS|METH_KEYWORDS},\r
-#endif\r
-    {NULL, NULL}\r
-};\r
-\r
-DL_EXPORT(void)\r
-init_elementtree(void)\r
-{\r
-    PyObject* m;\r
-    PyObject* g;\r
-    char* bootstrap;\r
-\r
-    /* Patch object type */\r
-    Py_TYPE(&Element_Type) = Py_TYPE(&TreeBuilder_Type) = &PyType_Type;\r
-#if defined(USE_EXPAT)\r
-    Py_TYPE(&XMLParser_Type) = &PyType_Type;\r
-#endif\r
-\r
-    m = Py_InitModule("_elementtree", _functions);\r
-    if (!m)\r
-        return;\r
-\r
-    /* python glue code */\r
-\r
-    g = PyDict_New();\r
-    if (!g)\r
-        return;\r
-\r
-    PyDict_SetItemString(g, "__builtins__", PyEval_GetBuiltins());\r
-\r
-    bootstrap = (\r
-\r
-        "from copy import copy, deepcopy\n"\r
-\r
-        "try:\n"\r
-        "  from xml.etree import ElementTree\n"\r
-        "except ImportError:\n"\r
-        "  import ElementTree\n"\r
-        "ET = ElementTree\n"\r
-        "del ElementTree\n"\r
-\r
-        "import _elementtree as cElementTree\n"\r
-\r
-        "try:\n" /* check if copy works as is */\r
-        "  copy(cElementTree.Element('x'))\n"\r
-        "except:\n"\r
-        "  def copyelement(elem):\n"\r
-        "    return elem\n"\r
-\r
-        "class CommentProxy:\n"\r
-        " def __call__(self, text=None):\n"\r
-        "  element = cElementTree.Element(ET.Comment)\n"\r
-        "  element.text = text\n"\r
-        "  return element\n"\r
-        " def __cmp__(self, other):\n"\r
-        "  return cmp(ET.Comment, other)\n"\r
-        "cElementTree.Comment = CommentProxy()\n"\r
-\r
-        "class ElementTree(ET.ElementTree):\n" /* public */\r
-        "  def parse(self, source, parser=None):\n"\r
-        "    if not hasattr(source, 'read'):\n"\r
-        "      source = open(source, 'rb')\n"\r
-        "    if parser is not None:\n"\r
-        "      while 1:\n"\r
-        "        data = source.read(65536)\n"\r
-        "        if not data:\n"\r
-        "          break\n"\r
-        "        parser.feed(data)\n"\r
-        "      self._root = parser.close()\n"\r
-        "    else:\n" \r
-        "      parser = cElementTree.XMLParser()\n"\r
-        "      self._root = parser._parse(source)\n"\r
-        "    return self._root\n"\r
-        "cElementTree.ElementTree = ElementTree\n"\r
-\r
-        "def iter(node, tag=None):\n" /* helper */\r
-        "  if tag == '*':\n"\r
-        "    tag = None\n"\r
-        "  if tag is None or node.tag == tag:\n"\r
-        "    yield node\n"\r
-        "  for node in node:\n"\r
-        "    for node in iter(node, tag):\n"\r
-        "      yield node\n"\r
-\r
-        "def itertext(node):\n" /* helper */\r
-        "  if node.text:\n"\r
-        "    yield node.text\n"\r
-        "  for e in node:\n"\r
-        "    for s in e.itertext():\n"\r
-        "      yield s\n"\r
-        "    if e.tail:\n"\r
-        "      yield e.tail\n"\r
-\r
-        "def parse(source, parser=None):\n" /* public */\r
-        "  tree = ElementTree()\n"\r
-        "  tree.parse(source, parser)\n"\r
-        "  return tree\n"\r
-        "cElementTree.parse = parse\n"\r
-\r
-        "class iterparse(object):\n"\r
-        " root = None\n"\r
-        " def __init__(self, file, events=None):\n"\r
-        "  if not hasattr(file, 'read'):\n"\r
-        "    file = open(file, 'rb')\n"\r
-        "  self._file = file\n"\r
-        "  self._events = []\n"\r
-        "  self._index = 0\n"\r
-        "  self.root = self._root = None\n"\r
-        "  b = cElementTree.TreeBuilder()\n"\r
-        "  self._parser = cElementTree.XMLParser(b)\n"\r
-        "  self._parser._setevents(self._events, events)\n"\r
-        " def next(self):\n"\r
-        "  while 1:\n"\r
-        "    try:\n"\r
-        "      item = self._events[self._index]\n"\r
-        "    except IndexError:\n"\r
-        "      if self._parser is None:\n"\r
-        "        self.root = self._root\n"\r
-        "        raise StopIteration\n"\r
-        "      # load event buffer\n"\r
-        "      del self._events[:]\n"\r
-        "      self._index = 0\n"\r
-        "      data = self._file.read(16384)\n"\r
-        "      if data:\n"\r
-        "        self._parser.feed(data)\n"\r
-        "      else:\n"\r
-        "        self._root = self._parser.close()\n"\r
-        "        self._parser = None\n"\r
-        "    else:\n"\r
-        "      self._index = self._index + 1\n"\r
-        "      return item\n"\r
-        " def __iter__(self):\n"\r
-        "  return self\n"\r
-        "cElementTree.iterparse = iterparse\n"\r
-\r
-        "class PIProxy:\n"\r
-        " def __call__(self, target, text=None):\n"\r
-        "  element = cElementTree.Element(ET.PI)\n"\r
-        "  element.text = target\n"\r
-        "  if text:\n"\r
-        "    element.text = element.text + ' ' + text\n"\r
-        "  return element\n"\r
-        " def __cmp__(self, other):\n"\r
-        "  return cmp(ET.PI, other)\n"\r
-        "cElementTree.PI = cElementTree.ProcessingInstruction = PIProxy()\n"\r
-\r
-        "def XML(text):\n" /* public */\r
-        "  parser = cElementTree.XMLParser()\n"\r
-        "  parser.feed(text)\n"\r
-        "  return parser.close()\n"\r
-        "cElementTree.XML = cElementTree.fromstring = XML\n"\r
-\r
-        "def XMLID(text):\n" /* public */\r
-        "  tree = XML(text)\n"\r
-        "  ids = {}\n"\r
-        "  for elem in tree.iter():\n"\r
-        "    id = elem.get('id')\n"\r
-        "    if id:\n"\r
-        "      ids[id] = elem\n"\r
-        "  return tree, ids\n"\r
-        "cElementTree.XMLID = XMLID\n"\r
-\r
-        "try:\n"\r
-        " register_namespace = ET.register_namespace\n"\r
-        "except AttributeError:\n"\r
-        " def register_namespace(prefix, uri):\n"\r
-        "  ET._namespace_map[uri] = prefix\n"\r
-        "cElementTree.register_namespace = register_namespace\n"\r
-\r
-        "cElementTree.dump = ET.dump\n"\r
-        "cElementTree.ElementPath = ElementPath = ET.ElementPath\n"\r
-        "cElementTree.iselement = ET.iselement\n"\r
-        "cElementTree.QName = ET.QName\n"\r
-        "cElementTree.tostring = ET.tostring\n"\r
-        "cElementTree.fromstringlist = ET.fromstringlist\n"\r
-        "cElementTree.tostringlist = ET.tostringlist\n"\r
-        "cElementTree.VERSION = '" VERSION "'\n"\r
-        "cElementTree.__version__ = '" VERSION "'\n"\r
-\r
-       );\r
-\r
-    if (!PyRun_String(bootstrap, Py_file_input, g, NULL))\r
-        return;\r
-\r
-    elementpath_obj = PyDict_GetItemString(g, "ElementPath");\r
-\r
-    elementtree_copyelement_obj = PyDict_GetItemString(g, "copyelement");\r
-    if (elementtree_copyelement_obj) {\r
-        /* reduce hack needed; enable reduce method */\r
-        PyMethodDef* mp;\r
-        for (mp = element_methods; mp->ml_name; mp++)\r
-            if (mp->ml_meth == (PyCFunction) element_reduce) {\r
-                mp->ml_name = "__reduce__";\r
-                break;\r
-            }\r
-    } else\r
-        PyErr_Clear();\r
-\r
-    elementtree_deepcopy_obj = PyDict_GetItemString(g, "deepcopy");\r
-    elementtree_iter_obj = PyDict_GetItemString(g, "iter");\r
-    elementtree_itertext_obj = PyDict_GetItemString(g, "itertext");\r
-\r
-#if defined(USE_PYEXPAT_CAPI)\r
-    /* link against pyexpat, if possible */\r
-    expat_capi = PyCapsule_Import(PyExpat_CAPSULE_NAME, 0);\r
-    if (expat_capi) {\r
-        /* check that it's usable */\r
-        if (strcmp(expat_capi->magic, PyExpat_CAPI_MAGIC) != 0 ||\r
-            expat_capi->size < sizeof(struct PyExpat_CAPI) ||\r
-            expat_capi->MAJOR_VERSION != XML_MAJOR_VERSION ||\r
-            expat_capi->MINOR_VERSION != XML_MINOR_VERSION ||\r
-            expat_capi->MICRO_VERSION != XML_MICRO_VERSION)\r
-            expat_capi = NULL;\r
-    }\r
-#endif\r
-\r
-    elementtree_parseerror_obj = PyErr_NewException(\r
-        "cElementTree.ParseError", PyExc_SyntaxError, NULL\r
-        );\r
-    Py_INCREF(elementtree_parseerror_obj);\r
-    PyModule_AddObject(m, "ParseError", elementtree_parseerror_obj);\r
-}\r