ยปCore Development>Code coverage>Modules/pyexpat.c

Python code coverage for Modules/pyexpat.c

#countcontent
1n/a#include "Python.h"
2n/a#include <ctype.h>
3n/a
4n/a#include "frameobject.h"
5n/a#include "expat.h"
6n/a
7n/a#include "pyexpat.h"
8n/a
9n/a/* Do not emit Clinic output to a file as that wreaks havoc with conditionally
10n/a included methods. */
11n/a/*[clinic input]
12n/amodule pyexpat
13n/a[clinic start generated code]*/
14n/a/*[clinic end generated code: output=da39a3ee5e6b4b0d input=b168d503a4490c15]*/
15n/a
16n/a#define XML_COMBINED_VERSION (10000*XML_MAJOR_VERSION+100*XML_MINOR_VERSION+XML_MICRO_VERSION)
17n/a
18n/astatic XML_Memory_Handling_Suite ExpatMemoryHandler = {
19n/a PyObject_Malloc, PyObject_Realloc, PyObject_Free};
20n/a
21n/aenum HandlerTypes {
22n/a StartElement,
23n/a EndElement,
24n/a ProcessingInstruction,
25n/a CharacterData,
26n/a UnparsedEntityDecl,
27n/a NotationDecl,
28n/a StartNamespaceDecl,
29n/a EndNamespaceDecl,
30n/a Comment,
31n/a StartCdataSection,
32n/a EndCdataSection,
33n/a Default,
34n/a DefaultHandlerExpand,
35n/a NotStandalone,
36n/a ExternalEntityRef,
37n/a StartDoctypeDecl,
38n/a EndDoctypeDecl,
39n/a EntityDecl,
40n/a XmlDecl,
41n/a ElementDecl,
42n/a AttlistDecl,
43n/a#if XML_COMBINED_VERSION >= 19504
44n/a SkippedEntity,
45n/a#endif
46n/a _DummyDecl
47n/a};
48n/a
49n/astatic PyObject *ErrorObject;
50n/a
51n/a/* ----------------------------------------------------- */
52n/a
53n/a/* Declarations for objects of type xmlparser */
54n/a
55n/atypedef struct {
56n/a PyObject_HEAD
57n/a
58n/a XML_Parser itself;
59n/a int ordered_attributes; /* Return attributes as a list. */
60n/a int specified_attributes; /* Report only specified attributes. */
61n/a int in_callback; /* Is a callback active? */
62n/a int ns_prefixes; /* Namespace-triplets mode? */
63n/a XML_Char *buffer; /* Buffer used when accumulating characters */
64n/a /* NULL if not enabled */
65n/a int buffer_size; /* Size of buffer, in XML_Char units */
66n/a int buffer_used; /* Buffer units in use */
67n/a PyObject *intern; /* Dictionary to intern strings */
68n/a PyObject **handlers;
69n/a} xmlparseobject;
70n/a
71n/a#include "clinic/pyexpat.c.h"
72n/a
73n/a#define CHARACTER_DATA_BUFFER_SIZE 8192
74n/a
75n/astatic PyTypeObject Xmlparsetype;
76n/a
77n/atypedef void (*xmlhandlersetter)(XML_Parser self, void *meth);
78n/atypedef void* xmlhandler;
79n/a
80n/astruct HandlerInfo {
81n/a const char *name;
82n/a xmlhandlersetter setter;
83n/a xmlhandler handler;
84n/a PyCodeObject *tb_code;
85n/a PyObject *nameobj;
86n/a};
87n/a
88n/astatic struct HandlerInfo handler_info[64];
89n/a
90n/a/* Set an integer attribute on the error object; return true on success,
91n/a * false on an exception.
92n/a */
93n/astatic int
94n/aset_error_attr(PyObject *err, const char *name, int value)
95n/a{
96n/a PyObject *v = PyLong_FromLong(value);
97n/a
98n/a if (v == NULL || PyObject_SetAttrString(err, name, v) == -1) {
99n/a Py_XDECREF(v);
100n/a return 0;
101n/a }
102n/a Py_DECREF(v);
103n/a return 1;
104n/a}
105n/a
106n/a/* Build and set an Expat exception, including positioning
107n/a * information. Always returns NULL.
108n/a */
109n/astatic PyObject *
110n/aset_error(xmlparseobject *self, enum XML_Error code)
111n/a{
112n/a PyObject *err;
113n/a PyObject *buffer;
114n/a XML_Parser parser = self->itself;
115n/a int lineno = XML_GetErrorLineNumber(parser);
116n/a int column = XML_GetErrorColumnNumber(parser);
117n/a
118n/a buffer = PyUnicode_FromFormat("%s: line %i, column %i",
119n/a XML_ErrorString(code), lineno, column);
120n/a if (buffer == NULL)
121n/a return NULL;
122n/a err = PyObject_CallFunctionObjArgs(ErrorObject, buffer, NULL);
123n/a Py_DECREF(buffer);
124n/a if ( err != NULL
125n/a && set_error_attr(err, "code", code)
126n/a && set_error_attr(err, "offset", column)
127n/a && set_error_attr(err, "lineno", lineno)) {
128n/a PyErr_SetObject(ErrorObject, err);
129n/a }
130n/a Py_XDECREF(err);
131n/a return NULL;
132n/a}
133n/a
134n/astatic int
135n/ahave_handler(xmlparseobject *self, int type)
136n/a{
137n/a PyObject *handler = self->handlers[type];
138n/a return handler != NULL;
139n/a}
140n/a
141n/astatic PyObject *
142n/aget_handler_name(struct HandlerInfo *hinfo)
143n/a{
144n/a PyObject *name = hinfo->nameobj;
145n/a if (name == NULL) {
146n/a name = PyUnicode_FromString(hinfo->name);
147n/a hinfo->nameobj = name;
148n/a }
149n/a Py_XINCREF(name);
150n/a return name;
151n/a}
152n/a
153n/a
154n/a/* Convert a string of XML_Chars into a Unicode string.
155n/a Returns None if str is a null pointer. */
156n/a
157n/astatic PyObject *
158n/aconv_string_to_unicode(const XML_Char *str)
159n/a{
160n/a /* XXX currently this code assumes that XML_Char is 8-bit,
161n/a and hence in UTF-8. */
162n/a /* UTF-8 from Expat, Unicode desired */
163n/a if (str == NULL) {
164n/a Py_RETURN_NONE;
165n/a }
166n/a return PyUnicode_DecodeUTF8(str, strlen(str), "strict");
167n/a}
168n/a
169n/astatic PyObject *
170n/aconv_string_len_to_unicode(const XML_Char *str, int len)
171n/a{
172n/a /* XXX currently this code assumes that XML_Char is 8-bit,
173n/a and hence in UTF-8. */
174n/a /* UTF-8 from Expat, Unicode desired */
175n/a if (str == NULL) {
176n/a Py_RETURN_NONE;
177n/a }
178n/a return PyUnicode_DecodeUTF8((const char *)str, len, "strict");
179n/a}
180n/a
181n/a/* Callback routines */
182n/a
183n/astatic void clear_handlers(xmlparseobject *self, int initial);
184n/a
185n/a/* This handler is used when an error has been detected, in the hope
186n/a that actual parsing can be terminated early. This will only help
187n/a if an external entity reference is encountered. */
188n/astatic int
189n/aerror_external_entity_ref_handler(XML_Parser parser,
190n/a const XML_Char *context,
191n/a const XML_Char *base,
192n/a const XML_Char *systemId,
193n/a const XML_Char *publicId)
194n/a{
195n/a return 0;
196n/a}
197n/a
198n/a/* Dummy character data handler used when an error (exception) has
199n/a been detected, and the actual parsing can be terminated early.
200n/a This is needed since character data handler can't be safely removed
201n/a from within the character data handler, but can be replaced. It is
202n/a used only from the character data handler trampoline, and must be
203n/a used right after `flag_error()` is called. */
204n/astatic void
205n/anoop_character_data_handler(void *userData, const XML_Char *data, int len)
206n/a{
207n/a /* Do nothing. */
208n/a}
209n/a
210n/astatic void
211n/aflag_error(xmlparseobject *self)
212n/a{
213n/a clear_handlers(self, 0);
214n/a XML_SetExternalEntityRefHandler(self->itself,
215n/a error_external_entity_ref_handler);
216n/a}
217n/a
218n/astatic PyObject*
219n/acall_with_frame(const char *funcname, int lineno, PyObject* func, PyObject* args,
220n/a xmlparseobject *self)
221n/a{
222n/a PyObject *res;
223n/a
224n/a res = PyEval_CallObject(func, args);
225n/a if (res == NULL) {
226n/a _PyTraceback_Add(funcname, __FILE__, lineno);
227n/a XML_StopParser(self->itself, XML_FALSE);
228n/a }
229n/a return res;
230n/a}
231n/a
232n/astatic PyObject*
233n/astring_intern(xmlparseobject *self, const char* str)
234n/a{
235n/a PyObject *result = conv_string_to_unicode(str);
236n/a PyObject *value;
237n/a /* result can be NULL if the unicode conversion failed. */
238n/a if (!result)
239n/a return result;
240n/a if (!self->intern)
241n/a return result;
242n/a value = PyDict_GetItem(self->intern, result);
243n/a if (!value) {
244n/a if (PyDict_SetItem(self->intern, result, result) == 0)
245n/a return result;
246n/a else
247n/a return NULL;
248n/a }
249n/a Py_INCREF(value);
250n/a Py_DECREF(result);
251n/a return value;
252n/a}
253n/a
254n/a/* Return 0 on success, -1 on exception.
255n/a * flag_error() will be called before return if needed.
256n/a */
257n/astatic int
258n/acall_character_handler(xmlparseobject *self, const XML_Char *buffer, int len)
259n/a{
260n/a PyObject *args;
261n/a PyObject *temp;
262n/a
263n/a if (!have_handler(self, CharacterData))
264n/a return -1;
265n/a
266n/a args = PyTuple_New(1);
267n/a if (args == NULL)
268n/a return -1;
269n/a temp = (conv_string_len_to_unicode(buffer, len));
270n/a if (temp == NULL) {
271n/a Py_DECREF(args);
272n/a flag_error(self);
273n/a XML_SetCharacterDataHandler(self->itself,
274n/a noop_character_data_handler);
275n/a return -1;
276n/a }
277n/a PyTuple_SET_ITEM(args, 0, temp);
278n/a /* temp is now a borrowed reference; consider it unused. */
279n/a self->in_callback = 1;
280n/a temp = call_with_frame("CharacterData", __LINE__,
281n/a self->handlers[CharacterData], args, self);
282n/a /* temp is an owned reference again, or NULL */
283n/a self->in_callback = 0;
284n/a Py_DECREF(args);
285n/a if (temp == NULL) {
286n/a flag_error(self);
287n/a XML_SetCharacterDataHandler(self->itself,
288n/a noop_character_data_handler);
289n/a return -1;
290n/a }
291n/a Py_DECREF(temp);
292n/a return 0;
293n/a}
294n/a
295n/astatic int
296n/aflush_character_buffer(xmlparseobject *self)
297n/a{
298n/a int rc;
299n/a if (self->buffer == NULL || self->buffer_used == 0)
300n/a return 0;
301n/a rc = call_character_handler(self, self->buffer, self->buffer_used);
302n/a self->buffer_used = 0;
303n/a return rc;
304n/a}
305n/a
306n/astatic void
307n/amy_CharacterDataHandler(void *userData, const XML_Char *data, int len)
308n/a{
309n/a xmlparseobject *self = (xmlparseobject *) userData;
310n/a
311n/a if (PyErr_Occurred())
312n/a return;
313n/a
314n/a if (self->buffer == NULL)
315n/a call_character_handler(self, data, len);
316n/a else {
317n/a if ((self->buffer_used + len) > self->buffer_size) {
318n/a if (flush_character_buffer(self) < 0)
319n/a return;
320n/a /* handler might have changed; drop the rest on the floor
321n/a * if there isn't a handler anymore
322n/a */
323n/a if (!have_handler(self, CharacterData))
324n/a return;
325n/a }
326n/a if (len > self->buffer_size) {
327n/a call_character_handler(self, data, len);
328n/a self->buffer_used = 0;
329n/a }
330n/a else {
331n/a memcpy(self->buffer + self->buffer_used,
332n/a data, len * sizeof(XML_Char));
333n/a self->buffer_used += len;
334n/a }
335n/a }
336n/a}
337n/a
338n/astatic void
339n/amy_StartElementHandler(void *userData,
340n/a const XML_Char *name, const XML_Char *atts[])
341n/a{
342n/a xmlparseobject *self = (xmlparseobject *)userData;
343n/a
344n/a if (have_handler(self, StartElement)) {
345n/a PyObject *container, *rv, *args;
346n/a int i, max;
347n/a
348n/a if (PyErr_Occurred())
349n/a return;
350n/a
351n/a if (flush_character_buffer(self) < 0)
352n/a return;
353n/a /* Set max to the number of slots filled in atts[]; max/2 is
354n/a * the number of attributes we need to process.
355n/a */
356n/a if (self->specified_attributes) {
357n/a max = XML_GetSpecifiedAttributeCount(self->itself);
358n/a }
359n/a else {
360n/a max = 0;
361n/a while (atts[max] != NULL)
362n/a max += 2;
363n/a }
364n/a /* Build the container. */
365n/a if (self->ordered_attributes)
366n/a container = PyList_New(max);
367n/a else
368n/a container = PyDict_New();
369n/a if (container == NULL) {
370n/a flag_error(self);
371n/a return;
372n/a }
373n/a for (i = 0; i < max; i += 2) {
374n/a PyObject *n = string_intern(self, (XML_Char *) atts[i]);
375n/a PyObject *v;
376n/a if (n == NULL) {
377n/a flag_error(self);
378n/a Py_DECREF(container);
379n/a return;
380n/a }
381n/a v = conv_string_to_unicode((XML_Char *) atts[i+1]);
382n/a if (v == NULL) {
383n/a flag_error(self);
384n/a Py_DECREF(container);
385n/a Py_DECREF(n);
386n/a return;
387n/a }
388n/a if (self->ordered_attributes) {
389n/a PyList_SET_ITEM(container, i, n);
390n/a PyList_SET_ITEM(container, i+1, v);
391n/a }
392n/a else if (PyDict_SetItem(container, n, v)) {
393n/a flag_error(self);
394n/a Py_DECREF(n);
395n/a Py_DECREF(v);
396n/a return;
397n/a }
398n/a else {
399n/a Py_DECREF(n);
400n/a Py_DECREF(v);
401n/a }
402n/a }
403n/a args = string_intern(self, name);
404n/a if (args != NULL)
405n/a args = Py_BuildValue("(NN)", args, container);
406n/a if (args == NULL) {
407n/a Py_DECREF(container);
408n/a return;
409n/a }
410n/a /* Container is now a borrowed reference; ignore it. */
411n/a self->in_callback = 1;
412n/a rv = call_with_frame("StartElement", __LINE__,
413n/a self->handlers[StartElement], args, self);
414n/a self->in_callback = 0;
415n/a Py_DECREF(args);
416n/a if (rv == NULL) {
417n/a flag_error(self);
418n/a return;
419n/a }
420n/a Py_DECREF(rv);
421n/a }
422n/a}
423n/a
424n/a#define RC_HANDLER(RC, NAME, PARAMS, INIT, PARAM_FORMAT, CONVERSION, \
425n/a RETURN, GETUSERDATA) \
426n/astatic RC \
427n/amy_##NAME##Handler PARAMS {\
428n/a xmlparseobject *self = GETUSERDATA ; \
429n/a PyObject *args = NULL; \
430n/a PyObject *rv = NULL; \
431n/a INIT \
432n/a\
433n/a if (have_handler(self, NAME)) { \
434n/a if (PyErr_Occurred()) \
435n/a return RETURN; \
436n/a if (flush_character_buffer(self) < 0) \
437n/a return RETURN; \
438n/a args = Py_BuildValue PARAM_FORMAT ;\
439n/a if (!args) { flag_error(self); return RETURN;} \
440n/a self->in_callback = 1; \
441n/a rv = call_with_frame(#NAME,__LINE__, \
442n/a self->handlers[NAME], args, self); \
443n/a self->in_callback = 0; \
444n/a Py_DECREF(args); \
445n/a if (rv == NULL) { \
446n/a flag_error(self); \
447n/a return RETURN; \
448n/a } \
449n/a CONVERSION \
450n/a Py_DECREF(rv); \
451n/a } \
452n/a return RETURN; \
453n/a}
454n/a
455n/a#define VOID_HANDLER(NAME, PARAMS, PARAM_FORMAT) \
456n/a RC_HANDLER(void, NAME, PARAMS, ;, PARAM_FORMAT, ;, ;,\
457n/a (xmlparseobject *)userData)
458n/a
459n/a#define INT_HANDLER(NAME, PARAMS, PARAM_FORMAT)\
460n/a RC_HANDLER(int, NAME, PARAMS, int rc=0;, PARAM_FORMAT, \
461n/a rc = PyLong_AsLong(rv);, rc, \
462n/a (xmlparseobject *)userData)
463n/a
464n/aVOID_HANDLER(EndElement,
465n/a (void *userData, const XML_Char *name),
466n/a ("(N)", string_intern(self, name)))
467n/a
468n/aVOID_HANDLER(ProcessingInstruction,
469n/a (void *userData,
470n/a const XML_Char *target,
471n/a const XML_Char *data),
472n/a ("(NO&)", string_intern(self, target), conv_string_to_unicode ,data))
473n/a
474n/aVOID_HANDLER(UnparsedEntityDecl,
475n/a (void *userData,
476n/a const XML_Char *entityName,
477n/a const XML_Char *base,
478n/a const XML_Char *systemId,
479n/a const XML_Char *publicId,
480n/a const XML_Char *notationName),
481n/a ("(NNNNN)",
482n/a string_intern(self, entityName), string_intern(self, base),
483n/a string_intern(self, systemId), string_intern(self, publicId),
484n/a string_intern(self, notationName)))
485n/a
486n/aVOID_HANDLER(EntityDecl,
487n/a (void *userData,
488n/a const XML_Char *entityName,
489n/a int is_parameter_entity,
490n/a const XML_Char *value,
491n/a int value_length,
492n/a const XML_Char *base,
493n/a const XML_Char *systemId,
494n/a const XML_Char *publicId,
495n/a const XML_Char *notationName),
496n/a ("NiNNNNN",
497n/a string_intern(self, entityName), is_parameter_entity,
498n/a (conv_string_len_to_unicode(value, value_length)),
499n/a string_intern(self, base), string_intern(self, systemId),
500n/a string_intern(self, publicId),
501n/a string_intern(self, notationName)))
502n/a
503n/aVOID_HANDLER(XmlDecl,
504n/a (void *userData,
505n/a const XML_Char *version,
506n/a const XML_Char *encoding,
507n/a int standalone),
508n/a ("(O&O&i)",
509n/a conv_string_to_unicode ,version, conv_string_to_unicode ,encoding,
510n/a standalone))
511n/a
512n/astatic PyObject *
513n/aconv_content_model(XML_Content * const model,
514n/a PyObject *(*conv_string)(const XML_Char *))
515n/a{
516n/a PyObject *result = NULL;
517n/a PyObject *children = PyTuple_New(model->numchildren);
518n/a int i;
519n/a
520n/a if (children != NULL) {
521n/a assert(model->numchildren < INT_MAX);
522n/a for (i = 0; i < (int)model->numchildren; ++i) {
523n/a PyObject *child = conv_content_model(&model->children[i],
524n/a conv_string);
525n/a if (child == NULL) {
526n/a Py_XDECREF(children);
527n/a return NULL;
528n/a }
529n/a PyTuple_SET_ITEM(children, i, child);
530n/a }
531n/a result = Py_BuildValue("(iiO&N)",
532n/a model->type, model->quant,
533n/a conv_string,model->name, children);
534n/a }
535n/a return result;
536n/a}
537n/a
538n/astatic void
539n/amy_ElementDeclHandler(void *userData,
540n/a const XML_Char *name,
541n/a XML_Content *model)
542n/a{
543n/a xmlparseobject *self = (xmlparseobject *)userData;
544n/a PyObject *args = NULL;
545n/a
546n/a if (have_handler(self, ElementDecl)) {
547n/a PyObject *rv = NULL;
548n/a PyObject *modelobj, *nameobj;
549n/a
550n/a if (PyErr_Occurred())
551n/a return;
552n/a
553n/a if (flush_character_buffer(self) < 0)
554n/a goto finally;
555n/a modelobj = conv_content_model(model, (conv_string_to_unicode));
556n/a if (modelobj == NULL) {
557n/a flag_error(self);
558n/a goto finally;
559n/a }
560n/a nameobj = string_intern(self, name);
561n/a if (nameobj == NULL) {
562n/a Py_DECREF(modelobj);
563n/a flag_error(self);
564n/a goto finally;
565n/a }
566n/a args = Py_BuildValue("NN", nameobj, modelobj);
567n/a if (args == NULL) {
568n/a Py_DECREF(modelobj);
569n/a flag_error(self);
570n/a goto finally;
571n/a }
572n/a self->in_callback = 1;
573n/a rv = call_with_frame("ElementDecl", __LINE__,
574n/a self->handlers[ElementDecl], args, self);
575n/a self->in_callback = 0;
576n/a if (rv == NULL) {
577n/a flag_error(self);
578n/a goto finally;
579n/a }
580n/a Py_DECREF(rv);
581n/a }
582n/a finally:
583n/a Py_XDECREF(args);
584n/a XML_FreeContentModel(self->itself, model);
585n/a return;
586n/a}
587n/a
588n/aVOID_HANDLER(AttlistDecl,
589n/a (void *userData,
590n/a const XML_Char *elname,
591n/a const XML_Char *attname,
592n/a const XML_Char *att_type,
593n/a const XML_Char *dflt,
594n/a int isrequired),
595n/a ("(NNO&O&i)",
596n/a string_intern(self, elname), string_intern(self, attname),
597n/a conv_string_to_unicode ,att_type, conv_string_to_unicode ,dflt,
598n/a isrequired))
599n/a
600n/a#if XML_COMBINED_VERSION >= 19504
601n/aVOID_HANDLER(SkippedEntity,
602n/a (void *userData,
603n/a const XML_Char *entityName,
604n/a int is_parameter_entity),
605n/a ("Ni",
606n/a string_intern(self, entityName), is_parameter_entity))
607n/a#endif
608n/a
609n/aVOID_HANDLER(NotationDecl,
610n/a (void *userData,
611n/a const XML_Char *notationName,
612n/a const XML_Char *base,
613n/a const XML_Char *systemId,
614n/a const XML_Char *publicId),
615n/a ("(NNNN)",
616n/a string_intern(self, notationName), string_intern(self, base),
617n/a string_intern(self, systemId), string_intern(self, publicId)))
618n/a
619n/aVOID_HANDLER(StartNamespaceDecl,
620n/a (void *userData,
621n/a const XML_Char *prefix,
622n/a const XML_Char *uri),
623n/a ("(NN)",
624n/a string_intern(self, prefix), string_intern(self, uri)))
625n/a
626n/aVOID_HANDLER(EndNamespaceDecl,
627n/a (void *userData,
628n/a const XML_Char *prefix),
629n/a ("(N)", string_intern(self, prefix)))
630n/a
631n/aVOID_HANDLER(Comment,
632n/a (void *userData, const XML_Char *data),
633n/a ("(O&)", conv_string_to_unicode ,data))
634n/a
635n/aVOID_HANDLER(StartCdataSection,
636n/a (void *userData),
637n/a ("()"))
638n/a
639n/aVOID_HANDLER(EndCdataSection,
640n/a (void *userData),
641n/a ("()"))
642n/a
643n/aVOID_HANDLER(Default,
644n/a (void *userData, const XML_Char *s, int len),
645n/a ("(N)", (conv_string_len_to_unicode(s,len))))
646n/a
647n/aVOID_HANDLER(DefaultHandlerExpand,
648n/a (void *userData, const XML_Char *s, int len),
649n/a ("(N)", (conv_string_len_to_unicode(s,len))))
650n/a
651n/aINT_HANDLER(NotStandalone,
652n/a (void *userData),
653n/a ("()"))
654n/a
655n/aRC_HANDLER(int, ExternalEntityRef,
656n/a (XML_Parser parser,
657n/a const XML_Char *context,
658n/a const XML_Char *base,
659n/a const XML_Char *systemId,
660n/a const XML_Char *publicId),
661n/a int rc=0;,
662n/a ("(O&NNN)",
663n/a conv_string_to_unicode ,context, string_intern(self, base),
664n/a string_intern(self, systemId), string_intern(self, publicId)),
665n/a rc = PyLong_AsLong(rv);, rc,
666n/a XML_GetUserData(parser))
667n/a
668n/a/* XXX UnknownEncodingHandler */
669n/a
670n/aVOID_HANDLER(StartDoctypeDecl,
671n/a (void *userData, const XML_Char *doctypeName,
672n/a const XML_Char *sysid, const XML_Char *pubid,
673n/a int has_internal_subset),
674n/a ("(NNNi)", string_intern(self, doctypeName),
675n/a string_intern(self, sysid), string_intern(self, pubid),
676n/a has_internal_subset))
677n/a
678n/aVOID_HANDLER(EndDoctypeDecl, (void *userData), ("()"))
679n/a
680n/a/* ---------------------------------------------------------------- */
681n/a/*[clinic input]
682n/aclass pyexpat.xmlparser "xmlparseobject *" "&Xmlparsetype"
683n/a[clinic start generated code]*/
684n/a/*[clinic end generated code: output=da39a3ee5e6b4b0d input=2393162385232e1c]*/
685n/a
686n/a
687n/astatic PyObject *
688n/aget_parse_result(xmlparseobject *self, int rv)
689n/a{
690n/a if (PyErr_Occurred()) {
691n/a return NULL;
692n/a }
693n/a if (rv == 0) {
694n/a return set_error(self, XML_GetErrorCode(self->itself));
695n/a }
696n/a if (flush_character_buffer(self) < 0) {
697n/a return NULL;
698n/a }
699n/a return PyLong_FromLong(rv);
700n/a}
701n/a
702n/a#define MAX_CHUNK_SIZE (1 << 20)
703n/a
704n/a/*[clinic input]
705n/apyexpat.xmlparser.Parse
706n/a
707n/a data: object
708n/a isfinal: int(c_default="0") = False
709n/a /
710n/a
711n/aParse XML data.
712n/a
713n/a`isfinal' should be true at end of input.
714n/a[clinic start generated code]*/
715n/a
716n/astatic PyObject *
717n/apyexpat_xmlparser_Parse_impl(xmlparseobject *self, PyObject *data,
718n/a int isfinal)
719n/a/*[clinic end generated code: output=f4db843dd1f4ed4b input=199d9e8e92ebbb4b]*/
720n/a{
721n/a const char *s;
722n/a Py_ssize_t slen;
723n/a Py_buffer view;
724n/a int rc;
725n/a
726n/a if (PyUnicode_Check(data)) {
727n/a view.buf = NULL;
728n/a s = PyUnicode_AsUTF8AndSize(data, &slen);
729n/a if (s == NULL)
730n/a return NULL;
731n/a /* Explicitly set UTF-8 encoding. Return code ignored. */
732n/a (void)XML_SetEncoding(self->itself, "utf-8");
733n/a }
734n/a else {
735n/a if (PyObject_GetBuffer(data, &view, PyBUF_SIMPLE) < 0)
736n/a return NULL;
737n/a s = view.buf;
738n/a slen = view.len;
739n/a }
740n/a
741n/a while (slen > MAX_CHUNK_SIZE) {
742n/a rc = XML_Parse(self->itself, s, MAX_CHUNK_SIZE, 0);
743n/a if (!rc)
744n/a goto done;
745n/a s += MAX_CHUNK_SIZE;
746n/a slen -= MAX_CHUNK_SIZE;
747n/a }
748n/a Py_BUILD_ASSERT(MAX_CHUNK_SIZE <= INT_MAX);
749n/a assert(slen <= INT_MAX);
750n/a rc = XML_Parse(self->itself, s, (int)slen, isfinal);
751n/a
752n/adone:
753n/a if (view.buf != NULL)
754n/a PyBuffer_Release(&view);
755n/a return get_parse_result(self, rc);
756n/a}
757n/a
758n/a/* File reading copied from cPickle */
759n/a
760n/a#define BUF_SIZE 2048
761n/a
762n/astatic int
763n/areadinst(char *buf, int buf_size, PyObject *meth)
764n/a{
765n/a PyObject *str;
766n/a Py_ssize_t len;
767n/a const char *ptr;
768n/a
769n/a str = PyObject_CallFunction(meth, "n", buf_size);
770n/a if (str == NULL)
771n/a goto error;
772n/a
773n/a if (PyBytes_Check(str))
774n/a ptr = PyBytes_AS_STRING(str);
775n/a else if (PyByteArray_Check(str))
776n/a ptr = PyByteArray_AS_STRING(str);
777n/a else {
778n/a PyErr_Format(PyExc_TypeError,
779n/a "read() did not return a bytes object (type=%.400s)",
780n/a Py_TYPE(str)->tp_name);
781n/a goto error;
782n/a }
783n/a len = Py_SIZE(str);
784n/a if (len > buf_size) {
785n/a PyErr_Format(PyExc_ValueError,
786n/a "read() returned too much data: "
787n/a "%i bytes requested, %zd returned",
788n/a buf_size, len);
789n/a goto error;
790n/a }
791n/a memcpy(buf, ptr, len);
792n/a Py_DECREF(str);
793n/a /* len <= buf_size <= INT_MAX */
794n/a return (int)len;
795n/a
796n/aerror:
797n/a Py_XDECREF(str);
798n/a return -1;
799n/a}
800n/a
801n/a/*[clinic input]
802n/apyexpat.xmlparser.ParseFile
803n/a
804n/a file: object
805n/a /
806n/a
807n/aParse XML data from file-like object.
808n/a[clinic start generated code]*/
809n/a
810n/astatic PyObject *
811n/apyexpat_xmlparser_ParseFile(xmlparseobject *self, PyObject *file)
812n/a/*[clinic end generated code: output=2adc6a13100cc42b input=fbb5a12b6038d735]*/
813n/a{
814n/a int rv = 1;
815n/a PyObject *readmethod = NULL;
816n/a _Py_IDENTIFIER(read);
817n/a
818n/a readmethod = _PyObject_GetAttrId(file, &PyId_read);
819n/a if (readmethod == NULL) {
820n/a PyErr_SetString(PyExc_TypeError,
821n/a "argument must have 'read' attribute");
822n/a return NULL;
823n/a }
824n/a for (;;) {
825n/a int bytes_read;
826n/a void *buf = XML_GetBuffer(self->itself, BUF_SIZE);
827n/a if (buf == NULL) {
828n/a Py_XDECREF(readmethod);
829n/a return get_parse_result(self, 0);
830n/a }
831n/a
832n/a bytes_read = readinst(buf, BUF_SIZE, readmethod);
833n/a if (bytes_read < 0) {
834n/a Py_DECREF(readmethod);
835n/a return NULL;
836n/a }
837n/a rv = XML_ParseBuffer(self->itself, bytes_read, bytes_read == 0);
838n/a if (PyErr_Occurred()) {
839n/a Py_XDECREF(readmethod);
840n/a return NULL;
841n/a }
842n/a
843n/a if (!rv || bytes_read == 0)
844n/a break;
845n/a }
846n/a Py_XDECREF(readmethod);
847n/a return get_parse_result(self, rv);
848n/a}
849n/a
850n/a/*[clinic input]
851n/apyexpat.xmlparser.SetBase
852n/a
853n/a base: str
854n/a /
855n/a
856n/aSet the base URL for the parser.
857n/a[clinic start generated code]*/
858n/a
859n/astatic PyObject *
860n/apyexpat_xmlparser_SetBase_impl(xmlparseobject *self, const char *base)
861n/a/*[clinic end generated code: output=c212ddceb607b539 input=c684e5de895ee1a8]*/
862n/a{
863n/a if (!XML_SetBase(self->itself, base)) {
864n/a return PyErr_NoMemory();
865n/a }
866n/a Py_RETURN_NONE;
867n/a}
868n/a
869n/a/*[clinic input]
870n/apyexpat.xmlparser.GetBase
871n/a
872n/aReturn base URL string for the parser.
873n/a[clinic start generated code]*/
874n/a
875n/astatic PyObject *
876n/apyexpat_xmlparser_GetBase_impl(xmlparseobject *self)
877n/a/*[clinic end generated code: output=2886cb21f9a8739a input=918d71c38009620e]*/
878n/a{
879n/a return Py_BuildValue("z", XML_GetBase(self->itself));
880n/a}
881n/a
882n/a/*[clinic input]
883n/apyexpat.xmlparser.GetInputContext
884n/a
885n/aReturn the untranslated text of the input that caused the current event.
886n/a
887n/aIf the event was generated by a large amount of text (such as a start tag
888n/afor an element with many attributes), not all of the text may be available.
889n/a[clinic start generated code]*/
890n/a
891n/astatic PyObject *
892n/apyexpat_xmlparser_GetInputContext_impl(xmlparseobject *self)
893n/a/*[clinic end generated code: output=a88026d683fc22cc input=034df8712db68379]*/
894n/a{
895n/a if (self->in_callback) {
896n/a int offset, size;
897n/a const char *buffer
898n/a = XML_GetInputContext(self->itself, &offset, &size);
899n/a
900n/a if (buffer != NULL)
901n/a return PyBytes_FromStringAndSize(buffer + offset,
902n/a size - offset);
903n/a else
904n/a Py_RETURN_NONE;
905n/a }
906n/a else
907n/a Py_RETURN_NONE;
908n/a}
909n/a
910n/a/*[clinic input]
911n/apyexpat.xmlparser.ExternalEntityParserCreate
912n/a
913n/a context: str(accept={str, NoneType})
914n/a encoding: str = NULL
915n/a /
916n/a
917n/aCreate a parser for parsing an external entity based on the information passed to the ExternalEntityRefHandler.
918n/a[clinic start generated code]*/
919n/a
920n/astatic PyObject *
921n/apyexpat_xmlparser_ExternalEntityParserCreate_impl(xmlparseobject *self,
922n/a const char *context,
923n/a const char *encoding)
924n/a/*[clinic end generated code: output=535cda9d7a0fbcd6 input=b906714cc122c322]*/
925n/a{
926n/a xmlparseobject *new_parser;
927n/a int i;
928n/a
929n/a new_parser = PyObject_GC_New(xmlparseobject, &Xmlparsetype);
930n/a if (new_parser == NULL)
931n/a return NULL;
932n/a new_parser->buffer_size = self->buffer_size;
933n/a new_parser->buffer_used = 0;
934n/a new_parser->buffer = NULL;
935n/a new_parser->ordered_attributes = self->ordered_attributes;
936n/a new_parser->specified_attributes = self->specified_attributes;
937n/a new_parser->in_callback = 0;
938n/a new_parser->ns_prefixes = self->ns_prefixes;
939n/a new_parser->itself = XML_ExternalEntityParserCreate(self->itself, context,
940n/a encoding);
941n/a new_parser->handlers = 0;
942n/a new_parser->intern = self->intern;
943n/a Py_XINCREF(new_parser->intern);
944n/a PyObject_GC_Track(new_parser);
945n/a
946n/a if (self->buffer != NULL) {
947n/a new_parser->buffer = PyMem_Malloc(new_parser->buffer_size);
948n/a if (new_parser->buffer == NULL) {
949n/a Py_DECREF(new_parser);
950n/a return PyErr_NoMemory();
951n/a }
952n/a }
953n/a if (!new_parser->itself) {
954n/a Py_DECREF(new_parser);
955n/a return PyErr_NoMemory();
956n/a }
957n/a
958n/a XML_SetUserData(new_parser->itself, (void *)new_parser);
959n/a
960n/a /* allocate and clear handlers first */
961n/a for (i = 0; handler_info[i].name != NULL; i++)
962n/a /* do nothing */;
963n/a
964n/a new_parser->handlers = PyMem_New(PyObject *, i);
965n/a if (!new_parser->handlers) {
966n/a Py_DECREF(new_parser);
967n/a return PyErr_NoMemory();
968n/a }
969n/a clear_handlers(new_parser, 1);
970n/a
971n/a /* then copy handlers from self */
972n/a for (i = 0; handler_info[i].name != NULL; i++) {
973n/a PyObject *handler = self->handlers[i];
974n/a if (handler != NULL) {
975n/a Py_INCREF(handler);
976n/a new_parser->handlers[i] = handler;
977n/a handler_info[i].setter(new_parser->itself,
978n/a handler_info[i].handler);
979n/a }
980n/a }
981n/a return (PyObject *)new_parser;
982n/a}
983n/a
984n/a/*[clinic input]
985n/apyexpat.xmlparser.SetParamEntityParsing
986n/a
987n/a flag: int
988n/a /
989n/a
990n/aControls parsing of parameter entities (including the external DTD subset).
991n/a
992n/aPossible flag values are XML_PARAM_ENTITY_PARSING_NEVER,
993n/aXML_PARAM_ENTITY_PARSING_UNLESS_STANDALONE and
994n/aXML_PARAM_ENTITY_PARSING_ALWAYS. Returns true if setting the flag
995n/awas successful.
996n/a[clinic start generated code]*/
997n/a
998n/astatic PyObject *
999n/apyexpat_xmlparser_SetParamEntityParsing_impl(xmlparseobject *self, int flag)
1000n/a/*[clinic end generated code: output=18668ee8e760d64c input=8aea19b4b15e9af1]*/
1001n/a{
1002n/a flag = XML_SetParamEntityParsing(self->itself, flag);
1003n/a return PyLong_FromLong(flag);
1004n/a}
1005n/a
1006n/a
1007n/a#if XML_COMBINED_VERSION >= 19505
1008n/a/*[clinic input]
1009n/apyexpat.xmlparser.UseForeignDTD
1010n/a
1011n/a flag: bool = True
1012n/a /
1013n/a
1014n/aAllows the application to provide an artificial external subset if one is not specified as part of the document instance.
1015n/a
1016n/aThis readily allows the use of a 'default' document type controlled by the
1017n/aapplication, while still getting the advantage of providing document type
1018n/ainformation to the parser. 'flag' defaults to True if not provided.
1019n/a[clinic start generated code]*/
1020n/a
1021n/astatic PyObject *
1022n/apyexpat_xmlparser_UseForeignDTD_impl(xmlparseobject *self, int flag)
1023n/a/*[clinic end generated code: output=cfaa9aa50bb0f65c input=78144c519d116a6e]*/
1024n/a{
1025n/a enum XML_Error rc;
1026n/a
1027n/a rc = XML_UseForeignDTD(self->itself, flag ? XML_TRUE : XML_FALSE);
1028n/a if (rc != XML_ERROR_NONE) {
1029n/a return set_error(self, rc);
1030n/a }
1031n/a Py_RETURN_NONE;
1032n/a}
1033n/a#endif
1034n/a
1035n/a/*[clinic input]
1036n/apyexpat.xmlparser.__dir__
1037n/a[clinic start generated code]*/
1038n/a
1039n/astatic PyObject *
1040n/apyexpat_xmlparser___dir___impl(xmlparseobject *self)
1041n/a/*[clinic end generated code: output=bc22451efb9e4d17 input=76aa455f2a661384]*/
1042n/a{
1043n/a#define APPEND(list, str) \
1044n/a do { \
1045n/a PyObject *o = PyUnicode_FromString(str); \
1046n/a if (o != NULL) \
1047n/a PyList_Append(list, o); \
1048n/a Py_XDECREF(o); \
1049n/a } while (0)
1050n/a
1051n/a int i;
1052n/a PyObject *rc = PyList_New(0);
1053n/a if (!rc)
1054n/a return NULL;
1055n/a for (i = 0; handler_info[i].name != NULL; i++) {
1056n/a PyObject *o = get_handler_name(&handler_info[i]);
1057n/a if (o != NULL)
1058n/a PyList_Append(rc, o);
1059n/a Py_XDECREF(o);
1060n/a }
1061n/a APPEND(rc, "ErrorCode");
1062n/a APPEND(rc, "ErrorLineNumber");
1063n/a APPEND(rc, "ErrorColumnNumber");
1064n/a APPEND(rc, "ErrorByteIndex");
1065n/a APPEND(rc, "CurrentLineNumber");
1066n/a APPEND(rc, "CurrentColumnNumber");
1067n/a APPEND(rc, "CurrentByteIndex");
1068n/a APPEND(rc, "buffer_size");
1069n/a APPEND(rc, "buffer_text");
1070n/a APPEND(rc, "buffer_used");
1071n/a APPEND(rc, "namespace_prefixes");
1072n/a APPEND(rc, "ordered_attributes");
1073n/a APPEND(rc, "specified_attributes");
1074n/a APPEND(rc, "intern");
1075n/a
1076n/a#undef APPEND
1077n/a
1078n/a if (PyErr_Occurred()) {
1079n/a Py_DECREF(rc);
1080n/a rc = NULL;
1081n/a }
1082n/a
1083n/a return rc;
1084n/a}
1085n/a
1086n/astatic struct PyMethodDef xmlparse_methods[] = {
1087n/a PYEXPAT_XMLPARSER_PARSE_METHODDEF
1088n/a PYEXPAT_XMLPARSER_PARSEFILE_METHODDEF
1089n/a PYEXPAT_XMLPARSER_SETBASE_METHODDEF
1090n/a PYEXPAT_XMLPARSER_GETBASE_METHODDEF
1091n/a PYEXPAT_XMLPARSER_GETINPUTCONTEXT_METHODDEF
1092n/a PYEXPAT_XMLPARSER_EXTERNALENTITYPARSERCREATE_METHODDEF
1093n/a PYEXPAT_XMLPARSER_SETPARAMENTITYPARSING_METHODDEF
1094n/a#if XML_COMBINED_VERSION >= 19505
1095n/a PYEXPAT_XMLPARSER_USEFOREIGNDTD_METHODDEF
1096n/a#endif
1097n/a PYEXPAT_XMLPARSER___DIR___METHODDEF
1098n/a {NULL, NULL} /* sentinel */
1099n/a};
1100n/a
1101n/a/* ---------- */
1102n/a
1103n/a
1104n/a
1105n/a/* pyexpat international encoding support.
1106n/a Make it as simple as possible.
1107n/a*/
1108n/a
1109n/astatic int
1110n/aPyUnknownEncodingHandler(void *encodingHandlerData,
1111n/a const XML_Char *name,
1112n/a XML_Encoding *info)
1113n/a{
1114n/a static unsigned char template_buffer[256] = {0};
1115n/a PyObject* u;
1116n/a int i;
1117n/a void *data;
1118n/a unsigned int kind;
1119n/a
1120n/a if (PyErr_Occurred())
1121n/a return XML_STATUS_ERROR;
1122n/a
1123n/a if (template_buffer[1] == 0) {
1124n/a for (i = 0; i < 256; i++)
1125n/a template_buffer[i] = i;
1126n/a }
1127n/a
1128n/a u = PyUnicode_Decode((char*) template_buffer, 256, name, "replace");
1129n/a if (u == NULL || PyUnicode_READY(u)) {
1130n/a Py_XDECREF(u);
1131n/a return XML_STATUS_ERROR;
1132n/a }
1133n/a
1134n/a if (PyUnicode_GET_LENGTH(u) != 256) {
1135n/a Py_DECREF(u);
1136n/a PyErr_SetString(PyExc_ValueError,
1137n/a "multi-byte encodings are not supported");
1138n/a return XML_STATUS_ERROR;
1139n/a }
1140n/a
1141n/a kind = PyUnicode_KIND(u);
1142n/a data = PyUnicode_DATA(u);
1143n/a for (i = 0; i < 256; i++) {
1144n/a Py_UCS4 ch = PyUnicode_READ(kind, data, i);
1145n/a if (ch != Py_UNICODE_REPLACEMENT_CHARACTER)
1146n/a info->map[i] = ch;
1147n/a else
1148n/a info->map[i] = -1;
1149n/a }
1150n/a
1151n/a info->data = NULL;
1152n/a info->convert = NULL;
1153n/a info->release = NULL;
1154n/a Py_DECREF(u);
1155n/a
1156n/a return XML_STATUS_OK;
1157n/a}
1158n/a
1159n/a
1160n/astatic PyObject *
1161n/anewxmlparseobject(const char *encoding, const char *namespace_separator, PyObject *intern)
1162n/a{
1163n/a int i;
1164n/a xmlparseobject *self;
1165n/a
1166n/a self = PyObject_GC_New(xmlparseobject, &Xmlparsetype);
1167n/a if (self == NULL)
1168n/a return NULL;
1169n/a
1170n/a self->buffer = NULL;
1171n/a self->buffer_size = CHARACTER_DATA_BUFFER_SIZE;
1172n/a self->buffer_used = 0;
1173n/a self->ordered_attributes = 0;
1174n/a self->specified_attributes = 0;
1175n/a self->in_callback = 0;
1176n/a self->ns_prefixes = 0;
1177n/a self->handlers = NULL;
1178n/a self->intern = intern;
1179n/a Py_XINCREF(self->intern);
1180n/a PyObject_GC_Track(self);
1181n/a
1182n/a /* namespace_separator is either NULL or contains one char + \0 */
1183n/a self->itself = XML_ParserCreate_MM(encoding, &ExpatMemoryHandler,
1184n/a namespace_separator);
1185n/a if (self->itself == NULL) {
1186n/a PyErr_SetString(PyExc_RuntimeError,
1187n/a "XML_ParserCreate failed");
1188n/a Py_DECREF(self);
1189n/a return NULL;
1190n/a }
1191n/a#if ((XML_MAJOR_VERSION >= 2) && (XML_MINOR_VERSION >= 1)) || defined(XML_HAS_SET_HASH_SALT)
1192n/a /* This feature was added upstream in libexpat 2.1.0. Our expat copy
1193n/a * has a backport of this feature where we also define XML_HAS_SET_HASH_SALT
1194n/a * to indicate that we can still use it. */
1195n/a XML_SetHashSalt(self->itself,
1196n/a (unsigned long)_Py_HashSecret.expat.hashsalt);
1197n/a#endif
1198n/a XML_SetUserData(self->itself, (void *)self);
1199n/a XML_SetUnknownEncodingHandler(self->itself,
1200n/a (XML_UnknownEncodingHandler) PyUnknownEncodingHandler, NULL);
1201n/a
1202n/a for (i = 0; handler_info[i].name != NULL; i++)
1203n/a /* do nothing */;
1204n/a
1205n/a self->handlers = PyMem_New(PyObject *, i);
1206n/a if (!self->handlers) {
1207n/a Py_DECREF(self);
1208n/a return PyErr_NoMemory();
1209n/a }
1210n/a clear_handlers(self, 1);
1211n/a
1212n/a return (PyObject*)self;
1213n/a}
1214n/a
1215n/a
1216n/astatic void
1217n/axmlparse_dealloc(xmlparseobject *self)
1218n/a{
1219n/a int i;
1220n/a PyObject_GC_UnTrack(self);
1221n/a if (self->itself != NULL)
1222n/a XML_ParserFree(self->itself);
1223n/a self->itself = NULL;
1224n/a
1225n/a if (self->handlers != NULL) {
1226n/a for (i = 0; handler_info[i].name != NULL; i++)
1227n/a Py_CLEAR(self->handlers[i]);
1228n/a PyMem_Free(self->handlers);
1229n/a self->handlers = NULL;
1230n/a }
1231n/a if (self->buffer != NULL) {
1232n/a PyMem_Free(self->buffer);
1233n/a self->buffer = NULL;
1234n/a }
1235n/a Py_XDECREF(self->intern);
1236n/a PyObject_GC_Del(self);
1237n/a}
1238n/a
1239n/astatic int
1240n/ahandlername2int(PyObject *name)
1241n/a{
1242n/a int i;
1243n/a for (i = 0; handler_info[i].name != NULL; i++) {
1244n/a if (_PyUnicode_EqualToASCIIString(name, handler_info[i].name)) {
1245n/a return i;
1246n/a }
1247n/a }
1248n/a return -1;
1249n/a}
1250n/a
1251n/astatic PyObject *
1252n/aget_pybool(int istrue)
1253n/a{
1254n/a PyObject *result = istrue ? Py_True : Py_False;
1255n/a Py_INCREF(result);
1256n/a return result;
1257n/a}
1258n/a
1259n/astatic PyObject *
1260n/axmlparse_getattro(xmlparseobject *self, PyObject *nameobj)
1261n/a{
1262n/a Py_UCS4 first_char;
1263n/a int handlernum = -1;
1264n/a
1265n/a if (!PyUnicode_Check(nameobj))
1266n/a goto generic;
1267n/a if (PyUnicode_READY(nameobj))
1268n/a return NULL;
1269n/a
1270n/a handlernum = handlername2int(nameobj);
1271n/a
1272n/a if (handlernum != -1) {
1273n/a PyObject *result = self->handlers[handlernum];
1274n/a if (result == NULL)
1275n/a result = Py_None;
1276n/a Py_INCREF(result);
1277n/a return result;
1278n/a }
1279n/a
1280n/a first_char = PyUnicode_READ_CHAR(nameobj, 0);
1281n/a if (first_char == 'E') {
1282n/a if (_PyUnicode_EqualToASCIIString(nameobj, "ErrorCode"))
1283n/a return PyLong_FromLong((long)
1284n/a XML_GetErrorCode(self->itself));
1285n/a if (_PyUnicode_EqualToASCIIString(nameobj, "ErrorLineNumber"))
1286n/a return PyLong_FromLong((long)
1287n/a XML_GetErrorLineNumber(self->itself));
1288n/a if (_PyUnicode_EqualToASCIIString(nameobj, "ErrorColumnNumber"))
1289n/a return PyLong_FromLong((long)
1290n/a XML_GetErrorColumnNumber(self->itself));
1291n/a if (_PyUnicode_EqualToASCIIString(nameobj, "ErrorByteIndex"))
1292n/a return PyLong_FromLong((long)
1293n/a XML_GetErrorByteIndex(self->itself));
1294n/a }
1295n/a if (first_char == 'C') {
1296n/a if (_PyUnicode_EqualToASCIIString(nameobj, "CurrentLineNumber"))
1297n/a return PyLong_FromLong((long)
1298n/a XML_GetCurrentLineNumber(self->itself));
1299n/a if (_PyUnicode_EqualToASCIIString(nameobj, "CurrentColumnNumber"))
1300n/a return PyLong_FromLong((long)
1301n/a XML_GetCurrentColumnNumber(self->itself));
1302n/a if (_PyUnicode_EqualToASCIIString(nameobj, "CurrentByteIndex"))
1303n/a return PyLong_FromLong((long)
1304n/a XML_GetCurrentByteIndex(self->itself));
1305n/a }
1306n/a if (first_char == 'b') {
1307n/a if (_PyUnicode_EqualToASCIIString(nameobj, "buffer_size"))
1308n/a return PyLong_FromLong((long) self->buffer_size);
1309n/a if (_PyUnicode_EqualToASCIIString(nameobj, "buffer_text"))
1310n/a return get_pybool(self->buffer != NULL);
1311n/a if (_PyUnicode_EqualToASCIIString(nameobj, "buffer_used"))
1312n/a return PyLong_FromLong((long) self->buffer_used);
1313n/a }
1314n/a if (_PyUnicode_EqualToASCIIString(nameobj, "namespace_prefixes"))
1315n/a return get_pybool(self->ns_prefixes);
1316n/a if (_PyUnicode_EqualToASCIIString(nameobj, "ordered_attributes"))
1317n/a return get_pybool(self->ordered_attributes);
1318n/a if (_PyUnicode_EqualToASCIIString(nameobj, "specified_attributes"))
1319n/a return get_pybool((long) self->specified_attributes);
1320n/a if (_PyUnicode_EqualToASCIIString(nameobj, "intern")) {
1321n/a if (self->intern == NULL) {
1322n/a Py_RETURN_NONE;
1323n/a }
1324n/a else {
1325n/a Py_INCREF(self->intern);
1326n/a return self->intern;
1327n/a }
1328n/a }
1329n/a generic:
1330n/a return PyObject_GenericGetAttr((PyObject*)self, nameobj);
1331n/a}
1332n/a
1333n/astatic int
1334n/asethandler(xmlparseobject *self, PyObject *name, PyObject* v)
1335n/a{
1336n/a int handlernum = handlername2int(name);
1337n/a if (handlernum >= 0) {
1338n/a xmlhandler c_handler = NULL;
1339n/a
1340n/a if (v == Py_None) {
1341n/a /* If this is the character data handler, and a character
1342n/a data handler is already active, we need to be more
1343n/a careful. What we can safely do is replace the existing
1344n/a character data handler callback function with a no-op
1345n/a function that will refuse to call Python. The downside
1346n/a is that this doesn't completely remove the character
1347n/a data handler from the C layer if there's any callback
1348n/a active, so Expat does a little more work than it
1349n/a otherwise would, but that's really an odd case. A more
1350n/a elaborate system of handlers and state could remove the
1351n/a C handler more effectively. */
1352n/a if (handlernum == CharacterData && self->in_callback)
1353n/a c_handler = noop_character_data_handler;
1354n/a v = NULL;
1355n/a }
1356n/a else if (v != NULL) {
1357n/a Py_INCREF(v);
1358n/a c_handler = handler_info[handlernum].handler;
1359n/a }
1360n/a Py_XSETREF(self->handlers[handlernum], v);
1361n/a handler_info[handlernum].setter(self->itself, c_handler);
1362n/a return 1;
1363n/a }
1364n/a return 0;
1365n/a}
1366n/a
1367n/astatic int
1368n/axmlparse_setattro(xmlparseobject *self, PyObject *name, PyObject *v)
1369n/a{
1370n/a /* Set attribute 'name' to value 'v'. v==NULL means delete */
1371n/a if (!PyUnicode_Check(name)) {
1372n/a PyErr_Format(PyExc_TypeError,
1373n/a "attribute name must be string, not '%.200s'",
1374n/a name->ob_type->tp_name);
1375n/a return -1;
1376n/a }
1377n/a if (v == NULL) {
1378n/a PyErr_SetString(PyExc_RuntimeError, "Cannot delete attribute");
1379n/a return -1;
1380n/a }
1381n/a if (_PyUnicode_EqualToASCIIString(name, "buffer_text")) {
1382n/a int b = PyObject_IsTrue(v);
1383n/a if (b < 0)
1384n/a return -1;
1385n/a if (b) {
1386n/a if (self->buffer == NULL) {
1387n/a self->buffer = PyMem_Malloc(self->buffer_size);
1388n/a if (self->buffer == NULL) {
1389n/a PyErr_NoMemory();
1390n/a return -1;
1391n/a }
1392n/a self->buffer_used = 0;
1393n/a }
1394n/a }
1395n/a else if (self->buffer != NULL) {
1396n/a if (flush_character_buffer(self) < 0)
1397n/a return -1;
1398n/a PyMem_Free(self->buffer);
1399n/a self->buffer = NULL;
1400n/a }
1401n/a return 0;
1402n/a }
1403n/a if (_PyUnicode_EqualToASCIIString(name, "namespace_prefixes")) {
1404n/a int b = PyObject_IsTrue(v);
1405n/a if (b < 0)
1406n/a return -1;
1407n/a self->ns_prefixes = b;
1408n/a XML_SetReturnNSTriplet(self->itself, self->ns_prefixes);
1409n/a return 0;
1410n/a }
1411n/a if (_PyUnicode_EqualToASCIIString(name, "ordered_attributes")) {
1412n/a int b = PyObject_IsTrue(v);
1413n/a if (b < 0)
1414n/a return -1;
1415n/a self->ordered_attributes = b;
1416n/a return 0;
1417n/a }
1418n/a if (_PyUnicode_EqualToASCIIString(name, "specified_attributes")) {
1419n/a int b = PyObject_IsTrue(v);
1420n/a if (b < 0)
1421n/a return -1;
1422n/a self->specified_attributes = b;
1423n/a return 0;
1424n/a }
1425n/a
1426n/a if (_PyUnicode_EqualToASCIIString(name, "buffer_size")) {
1427n/a long new_buffer_size;
1428n/a if (!PyLong_Check(v)) {
1429n/a PyErr_SetString(PyExc_TypeError, "buffer_size must be an integer");
1430n/a return -1;
1431n/a }
1432n/a
1433n/a new_buffer_size = PyLong_AsLong(v);
1434n/a if (new_buffer_size <= 0) {
1435n/a if (!PyErr_Occurred())
1436n/a PyErr_SetString(PyExc_ValueError, "buffer_size must be greater than zero");
1437n/a return -1;
1438n/a }
1439n/a
1440n/a /* trivial case -- no change */
1441n/a if (new_buffer_size == self->buffer_size) {
1442n/a return 0;
1443n/a }
1444n/a
1445n/a /* check maximum */
1446n/a if (new_buffer_size > INT_MAX) {
1447n/a char errmsg[100];
1448n/a sprintf(errmsg, "buffer_size must not be greater than %i", INT_MAX);
1449n/a PyErr_SetString(PyExc_ValueError, errmsg);
1450n/a return -1;
1451n/a }
1452n/a
1453n/a if (self->buffer != NULL) {
1454n/a /* there is already a buffer */
1455n/a if (self->buffer_used != 0) {
1456n/a if (flush_character_buffer(self) < 0) {
1457n/a return -1;
1458n/a }
1459n/a }
1460n/a /* free existing buffer */
1461n/a PyMem_Free(self->buffer);
1462n/a }
1463n/a self->buffer = PyMem_Malloc(new_buffer_size);
1464n/a if (self->buffer == NULL) {
1465n/a PyErr_NoMemory();
1466n/a return -1;
1467n/a }
1468n/a self->buffer_size = new_buffer_size;
1469n/a return 0;
1470n/a }
1471n/a
1472n/a if (_PyUnicode_EqualToASCIIString(name, "CharacterDataHandler")) {
1473n/a /* If we're changing the character data handler, flush all
1474n/a * cached data with the old handler. Not sure there's a
1475n/a * "right" thing to do, though, but this probably won't
1476n/a * happen.
1477n/a */
1478n/a if (flush_character_buffer(self) < 0)
1479n/a return -1;
1480n/a }
1481n/a if (sethandler(self, name, v)) {
1482n/a return 0;
1483n/a }
1484n/a PyErr_SetObject(PyExc_AttributeError, name);
1485n/a return -1;
1486n/a}
1487n/a
1488n/astatic int
1489n/axmlparse_traverse(xmlparseobject *op, visitproc visit, void *arg)
1490n/a{
1491n/a int i;
1492n/a for (i = 0; handler_info[i].name != NULL; i++)
1493n/a Py_VISIT(op->handlers[i]);
1494n/a return 0;
1495n/a}
1496n/a
1497n/astatic int
1498n/axmlparse_clear(xmlparseobject *op)
1499n/a{
1500n/a clear_handlers(op, 0);
1501n/a Py_CLEAR(op->intern);
1502n/a return 0;
1503n/a}
1504n/a
1505n/aPyDoc_STRVAR(Xmlparsetype__doc__, "XML parser");
1506n/a
1507n/astatic PyTypeObject Xmlparsetype = {
1508n/a PyVarObject_HEAD_INIT(NULL, 0)
1509n/a "pyexpat.xmlparser", /*tp_name*/
1510n/a sizeof(xmlparseobject), /*tp_basicsize*/
1511n/a 0, /*tp_itemsize*/
1512n/a /* methods */
1513n/a (destructor)xmlparse_dealloc, /*tp_dealloc*/
1514n/a (printfunc)0, /*tp_print*/
1515n/a 0, /*tp_getattr*/
1516n/a 0, /*tp_setattr*/
1517n/a 0, /*tp_reserved*/
1518n/a (reprfunc)0, /*tp_repr*/
1519n/a 0, /*tp_as_number*/
1520n/a 0, /*tp_as_sequence*/
1521n/a 0, /*tp_as_mapping*/
1522n/a (hashfunc)0, /*tp_hash*/
1523n/a (ternaryfunc)0, /*tp_call*/
1524n/a (reprfunc)0, /*tp_str*/
1525n/a (getattrofunc)xmlparse_getattro, /* tp_getattro */
1526n/a (setattrofunc)xmlparse_setattro, /* tp_setattro */
1527n/a 0, /* tp_as_buffer */
1528n/a Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC, /*tp_flags*/
1529n/a Xmlparsetype__doc__, /* tp_doc - Documentation string */
1530n/a (traverseproc)xmlparse_traverse, /* tp_traverse */
1531n/a (inquiry)xmlparse_clear, /* tp_clear */
1532n/a 0, /* tp_richcompare */
1533n/a 0, /* tp_weaklistoffset */
1534n/a 0, /* tp_iter */
1535n/a 0, /* tp_iternext */
1536n/a xmlparse_methods, /* tp_methods */
1537n/a};
1538n/a
1539n/a/* End of code for xmlparser objects */
1540n/a/* -------------------------------------------------------- */
1541n/a
1542n/a/*[clinic input]
1543n/apyexpat.ParserCreate
1544n/a
1545n/a encoding: str(accept={str, NoneType}) = NULL
1546n/a namespace_separator: str(accept={str, NoneType}) = NULL
1547n/a intern: object = NULL
1548n/a
1549n/aReturn a new XML parser object.
1550n/a[clinic start generated code]*/
1551n/a
1552n/astatic PyObject *
1553n/apyexpat_ParserCreate_impl(PyObject *module, const char *encoding,
1554n/a const char *namespace_separator, PyObject *intern)
1555n/a/*[clinic end generated code: output=295c0cf01ab1146c input=23d29704acad385d]*/
1556n/a{
1557n/a PyObject *result;
1558n/a int intern_decref = 0;
1559n/a
1560n/a if (namespace_separator != NULL
1561n/a && strlen(namespace_separator) > 1) {
1562n/a PyErr_SetString(PyExc_ValueError,
1563n/a "namespace_separator must be at most one"
1564n/a " character, omitted, or None");
1565n/a return NULL;
1566n/a }
1567n/a /* Explicitly passing None means no interning is desired.
1568n/a Not passing anything means that a new dictionary is used. */
1569n/a if (intern == Py_None)
1570n/a intern = NULL;
1571n/a else if (intern == NULL) {
1572n/a intern = PyDict_New();
1573n/a if (!intern)
1574n/a return NULL;
1575n/a intern_decref = 1;
1576n/a }
1577n/a else if (!PyDict_Check(intern)) {
1578n/a PyErr_SetString(PyExc_TypeError, "intern must be a dictionary");
1579n/a return NULL;
1580n/a }
1581n/a
1582n/a result = newxmlparseobject(encoding, namespace_separator, intern);
1583n/a if (intern_decref) {
1584n/a Py_DECREF(intern);
1585n/a }
1586n/a return result;
1587n/a}
1588n/a
1589n/a/*[clinic input]
1590n/apyexpat.ErrorString
1591n/a
1592n/a code: long
1593n/a /
1594n/a
1595n/aReturns string error for given number.
1596n/a[clinic start generated code]*/
1597n/a
1598n/astatic PyObject *
1599n/apyexpat_ErrorString_impl(PyObject *module, long code)
1600n/a/*[clinic end generated code: output=2feae50d166f2174 input=cc67de010d9e62b3]*/
1601n/a{
1602n/a return Py_BuildValue("z", XML_ErrorString((int)code));
1603n/a}
1604n/a
1605n/a/* List of methods defined in the module */
1606n/a
1607n/astatic struct PyMethodDef pyexpat_methods[] = {
1608n/a PYEXPAT_PARSERCREATE_METHODDEF
1609n/a PYEXPAT_ERRORSTRING_METHODDEF
1610n/a {NULL, NULL} /* sentinel */
1611n/a};
1612n/a
1613n/a/* Module docstring */
1614n/a
1615n/aPyDoc_STRVAR(pyexpat_module_documentation,
1616n/a"Python wrapper for Expat parser.");
1617n/a
1618n/a/* Initialization function for the module */
1619n/a
1620n/a#ifndef MODULE_NAME
1621n/a#define MODULE_NAME "pyexpat"
1622n/a#endif
1623n/a
1624n/a#ifndef MODULE_INITFUNC
1625n/a#define MODULE_INITFUNC PyInit_pyexpat
1626n/a#endif
1627n/a
1628n/astatic struct PyModuleDef pyexpatmodule = {
1629n/a PyModuleDef_HEAD_INIT,
1630n/a MODULE_NAME,
1631n/a pyexpat_module_documentation,
1632n/a -1,
1633n/a pyexpat_methods,
1634n/a NULL,
1635n/a NULL,
1636n/a NULL,
1637n/a NULL
1638n/a};
1639n/a
1640n/aPyMODINIT_FUNC
1641n/aMODULE_INITFUNC(void)
1642n/a{
1643n/a PyObject *m, *d;
1644n/a PyObject *errmod_name = PyUnicode_FromString(MODULE_NAME ".errors");
1645n/a PyObject *errors_module;
1646n/a PyObject *modelmod_name;
1647n/a PyObject *model_module;
1648n/a PyObject *sys_modules;
1649n/a PyObject *tmpnum, *tmpstr;
1650n/a PyObject *codes_dict;
1651n/a PyObject *rev_codes_dict;
1652n/a int res;
1653n/a static struct PyExpat_CAPI capi;
1654n/a PyObject *capi_object;
1655n/a
1656n/a if (errmod_name == NULL)
1657n/a return NULL;
1658n/a modelmod_name = PyUnicode_FromString(MODULE_NAME ".model");
1659n/a if (modelmod_name == NULL)
1660n/a return NULL;
1661n/a
1662n/a if (PyType_Ready(&Xmlparsetype) < 0)
1663n/a return NULL;
1664n/a
1665n/a /* Create the module and add the functions */
1666n/a m = PyModule_Create(&pyexpatmodule);
1667n/a if (m == NULL)
1668n/a return NULL;
1669n/a
1670n/a /* Add some symbolic constants to the module */
1671n/a if (ErrorObject == NULL) {
1672n/a ErrorObject = PyErr_NewException("xml.parsers.expat.ExpatError",
1673n/a NULL, NULL);
1674n/a if (ErrorObject == NULL)
1675n/a return NULL;
1676n/a }
1677n/a Py_INCREF(ErrorObject);
1678n/a PyModule_AddObject(m, "error", ErrorObject);
1679n/a Py_INCREF(ErrorObject);
1680n/a PyModule_AddObject(m, "ExpatError", ErrorObject);
1681n/a Py_INCREF(&Xmlparsetype);
1682n/a PyModule_AddObject(m, "XMLParserType", (PyObject *) &Xmlparsetype);
1683n/a
1684n/a PyModule_AddStringConstant(m, "EXPAT_VERSION",
1685n/a XML_ExpatVersion());
1686n/a {
1687n/a XML_Expat_Version info = XML_ExpatVersionInfo();
1688n/a PyModule_AddObject(m, "version_info",
1689n/a Py_BuildValue("(iii)", info.major,
1690n/a info.minor, info.micro));
1691n/a }
1692n/a /* XXX When Expat supports some way of figuring out how it was
1693n/a compiled, this should check and set native_encoding
1694n/a appropriately.
1695n/a */
1696n/a PyModule_AddStringConstant(m, "native_encoding", "UTF-8");
1697n/a
1698n/a sys_modules = PySys_GetObject("modules");
1699n/a if (sys_modules == NULL) {
1700n/a Py_DECREF(m);
1701n/a return NULL;
1702n/a }
1703n/a d = PyModule_GetDict(m);
1704n/a if (d == NULL) {
1705n/a Py_DECREF(m);
1706n/a return NULL;
1707n/a }
1708n/a errors_module = PyDict_GetItem(d, errmod_name);
1709n/a if (errors_module == NULL) {
1710n/a errors_module = PyModule_New(MODULE_NAME ".errors");
1711n/a if (errors_module != NULL) {
1712n/a PyDict_SetItem(sys_modules, errmod_name, errors_module);
1713n/a /* gives away the reference to errors_module */
1714n/a PyModule_AddObject(m, "errors", errors_module);
1715n/a }
1716n/a }
1717n/a Py_DECREF(errmod_name);
1718n/a model_module = PyDict_GetItem(d, modelmod_name);
1719n/a if (model_module == NULL) {
1720n/a model_module = PyModule_New(MODULE_NAME ".model");
1721n/a if (model_module != NULL) {
1722n/a PyDict_SetItem(sys_modules, modelmod_name, model_module);
1723n/a /* gives away the reference to model_module */
1724n/a PyModule_AddObject(m, "model", model_module);
1725n/a }
1726n/a }
1727n/a Py_DECREF(modelmod_name);
1728n/a if (errors_module == NULL || model_module == NULL) {
1729n/a /* Don't core dump later! */
1730n/a Py_DECREF(m);
1731n/a return NULL;
1732n/a }
1733n/a
1734n/a#if XML_COMBINED_VERSION > 19505
1735n/a {
1736n/a const XML_Feature *features = XML_GetFeatureList();
1737n/a PyObject *list = PyList_New(0);
1738n/a if (list == NULL)
1739n/a /* just ignore it */
1740n/a PyErr_Clear();
1741n/a else {
1742n/a int i = 0;
1743n/a for (; features[i].feature != XML_FEATURE_END; ++i) {
1744n/a int ok;
1745n/a PyObject *item = Py_BuildValue("si", features[i].name,
1746n/a features[i].value);
1747n/a if (item == NULL) {
1748n/a Py_DECREF(list);
1749n/a list = NULL;
1750n/a break;
1751n/a }
1752n/a ok = PyList_Append(list, item);
1753n/a Py_DECREF(item);
1754n/a if (ok < 0) {
1755n/a PyErr_Clear();
1756n/a break;
1757n/a }
1758n/a }
1759n/a if (list != NULL)
1760n/a PyModule_AddObject(m, "features", list);
1761n/a }
1762n/a }
1763n/a#endif
1764n/a
1765n/a codes_dict = PyDict_New();
1766n/a rev_codes_dict = PyDict_New();
1767n/a if (codes_dict == NULL || rev_codes_dict == NULL) {
1768n/a Py_XDECREF(codes_dict);
1769n/a Py_XDECREF(rev_codes_dict);
1770n/a return NULL;
1771n/a }
1772n/a
1773n/a#define MYCONST(name) \
1774n/a if (PyModule_AddStringConstant(errors_module, #name, \
1775n/a XML_ErrorString(name)) < 0) \
1776n/a return NULL; \
1777n/a tmpnum = PyLong_FromLong(name); \
1778n/a if (tmpnum == NULL) return NULL; \
1779n/a res = PyDict_SetItemString(codes_dict, \
1780n/a XML_ErrorString(name), tmpnum); \
1781n/a if (res < 0) return NULL; \
1782n/a tmpstr = PyUnicode_FromString(XML_ErrorString(name)); \
1783n/a if (tmpstr == NULL) return NULL; \
1784n/a res = PyDict_SetItem(rev_codes_dict, tmpnum, tmpstr); \
1785n/a Py_DECREF(tmpstr); \
1786n/a Py_DECREF(tmpnum); \
1787n/a if (res < 0) return NULL; \
1788n/a
1789n/a MYCONST(XML_ERROR_NO_MEMORY);
1790n/a MYCONST(XML_ERROR_SYNTAX);
1791n/a MYCONST(XML_ERROR_NO_ELEMENTS);
1792n/a MYCONST(XML_ERROR_INVALID_TOKEN);
1793n/a MYCONST(XML_ERROR_UNCLOSED_TOKEN);
1794n/a MYCONST(XML_ERROR_PARTIAL_CHAR);
1795n/a MYCONST(XML_ERROR_TAG_MISMATCH);
1796n/a MYCONST(XML_ERROR_DUPLICATE_ATTRIBUTE);
1797n/a MYCONST(XML_ERROR_JUNK_AFTER_DOC_ELEMENT);
1798n/a MYCONST(XML_ERROR_PARAM_ENTITY_REF);
1799n/a MYCONST(XML_ERROR_UNDEFINED_ENTITY);
1800n/a MYCONST(XML_ERROR_RECURSIVE_ENTITY_REF);
1801n/a MYCONST(XML_ERROR_ASYNC_ENTITY);
1802n/a MYCONST(XML_ERROR_BAD_CHAR_REF);
1803n/a MYCONST(XML_ERROR_BINARY_ENTITY_REF);
1804n/a MYCONST(XML_ERROR_ATTRIBUTE_EXTERNAL_ENTITY_REF);
1805n/a MYCONST(XML_ERROR_MISPLACED_XML_PI);
1806n/a MYCONST(XML_ERROR_UNKNOWN_ENCODING);
1807n/a MYCONST(XML_ERROR_INCORRECT_ENCODING);
1808n/a MYCONST(XML_ERROR_UNCLOSED_CDATA_SECTION);
1809n/a MYCONST(XML_ERROR_EXTERNAL_ENTITY_HANDLING);
1810n/a MYCONST(XML_ERROR_NOT_STANDALONE);
1811n/a MYCONST(XML_ERROR_UNEXPECTED_STATE);
1812n/a MYCONST(XML_ERROR_ENTITY_DECLARED_IN_PE);
1813n/a MYCONST(XML_ERROR_FEATURE_REQUIRES_XML_DTD);
1814n/a MYCONST(XML_ERROR_CANT_CHANGE_FEATURE_ONCE_PARSING);
1815n/a /* Added in Expat 1.95.7. */
1816n/a MYCONST(XML_ERROR_UNBOUND_PREFIX);
1817n/a /* Added in Expat 1.95.8. */
1818n/a MYCONST(XML_ERROR_UNDECLARING_PREFIX);
1819n/a MYCONST(XML_ERROR_INCOMPLETE_PE);
1820n/a MYCONST(XML_ERROR_XML_DECL);
1821n/a MYCONST(XML_ERROR_TEXT_DECL);
1822n/a MYCONST(XML_ERROR_PUBLICID);
1823n/a MYCONST(XML_ERROR_SUSPENDED);
1824n/a MYCONST(XML_ERROR_NOT_SUSPENDED);
1825n/a MYCONST(XML_ERROR_ABORTED);
1826n/a MYCONST(XML_ERROR_FINISHED);
1827n/a MYCONST(XML_ERROR_SUSPEND_PE);
1828n/a
1829n/a if (PyModule_AddStringConstant(errors_module, "__doc__",
1830n/a "Constants used to describe "
1831n/a "error conditions.") < 0)
1832n/a return NULL;
1833n/a
1834n/a if (PyModule_AddObject(errors_module, "codes", codes_dict) < 0)
1835n/a return NULL;
1836n/a if (PyModule_AddObject(errors_module, "messages", rev_codes_dict) < 0)
1837n/a return NULL;
1838n/a
1839n/a#undef MYCONST
1840n/a
1841n/a#define MYCONST(c) PyModule_AddIntConstant(m, #c, c)
1842n/a MYCONST(XML_PARAM_ENTITY_PARSING_NEVER);
1843n/a MYCONST(XML_PARAM_ENTITY_PARSING_UNLESS_STANDALONE);
1844n/a MYCONST(XML_PARAM_ENTITY_PARSING_ALWAYS);
1845n/a#undef MYCONST
1846n/a
1847n/a#define MYCONST(c) PyModule_AddIntConstant(model_module, #c, c)
1848n/a PyModule_AddStringConstant(model_module, "__doc__",
1849n/a "Constants used to interpret content model information.");
1850n/a
1851n/a MYCONST(XML_CTYPE_EMPTY);
1852n/a MYCONST(XML_CTYPE_ANY);
1853n/a MYCONST(XML_CTYPE_MIXED);
1854n/a MYCONST(XML_CTYPE_NAME);
1855n/a MYCONST(XML_CTYPE_CHOICE);
1856n/a MYCONST(XML_CTYPE_SEQ);
1857n/a
1858n/a MYCONST(XML_CQUANT_NONE);
1859n/a MYCONST(XML_CQUANT_OPT);
1860n/a MYCONST(XML_CQUANT_REP);
1861n/a MYCONST(XML_CQUANT_PLUS);
1862n/a#undef MYCONST
1863n/a
1864n/a /* initialize pyexpat dispatch table */
1865n/a capi.size = sizeof(capi);
1866n/a capi.magic = PyExpat_CAPI_MAGIC;
1867n/a capi.MAJOR_VERSION = XML_MAJOR_VERSION;
1868n/a capi.MINOR_VERSION = XML_MINOR_VERSION;
1869n/a capi.MICRO_VERSION = XML_MICRO_VERSION;
1870n/a capi.ErrorString = XML_ErrorString;
1871n/a capi.GetErrorCode = XML_GetErrorCode;
1872n/a capi.GetErrorColumnNumber = XML_GetErrorColumnNumber;
1873n/a capi.GetErrorLineNumber = XML_GetErrorLineNumber;
1874n/a capi.Parse = XML_Parse;
1875n/a capi.ParserCreate_MM = XML_ParserCreate_MM;
1876n/a capi.ParserFree = XML_ParserFree;
1877n/a capi.SetCharacterDataHandler = XML_SetCharacterDataHandler;
1878n/a capi.SetCommentHandler = XML_SetCommentHandler;
1879n/a capi.SetDefaultHandlerExpand = XML_SetDefaultHandlerExpand;
1880n/a capi.SetElementHandler = XML_SetElementHandler;
1881n/a capi.SetNamespaceDeclHandler = XML_SetNamespaceDeclHandler;
1882n/a capi.SetProcessingInstructionHandler = XML_SetProcessingInstructionHandler;
1883n/a capi.SetUnknownEncodingHandler = XML_SetUnknownEncodingHandler;
1884n/a capi.SetUserData = XML_SetUserData;
1885n/a capi.SetStartDoctypeDeclHandler = XML_SetStartDoctypeDeclHandler;
1886n/a capi.SetEncoding = XML_SetEncoding;
1887n/a capi.DefaultUnknownEncodingHandler = PyUnknownEncodingHandler;
1888n/a
1889n/a /* export using capsule */
1890n/a capi_object = PyCapsule_New(&capi, PyExpat_CAPSULE_NAME, NULL);
1891n/a if (capi_object)
1892n/a PyModule_AddObject(m, "expat_CAPI", capi_object);
1893n/a return m;
1894n/a}
1895n/a
1896n/astatic void
1897n/aclear_handlers(xmlparseobject *self, int initial)
1898n/a{
1899n/a int i = 0;
1900n/a
1901n/a for (; handler_info[i].name != NULL; i++) {
1902n/a if (initial)
1903n/a self->handlers[i] = NULL;
1904n/a else {
1905n/a Py_CLEAR(self->handlers[i]);
1906n/a handler_info[i].setter(self->itself, NULL);
1907n/a }
1908n/a }
1909n/a}
1910n/a
1911n/astatic struct HandlerInfo handler_info[] = {
1912n/a {"StartElementHandler",
1913n/a (xmlhandlersetter)XML_SetStartElementHandler,
1914n/a (xmlhandler)my_StartElementHandler},
1915n/a {"EndElementHandler",
1916n/a (xmlhandlersetter)XML_SetEndElementHandler,
1917n/a (xmlhandler)my_EndElementHandler},
1918n/a {"ProcessingInstructionHandler",
1919n/a (xmlhandlersetter)XML_SetProcessingInstructionHandler,
1920n/a (xmlhandler)my_ProcessingInstructionHandler},
1921n/a {"CharacterDataHandler",
1922n/a (xmlhandlersetter)XML_SetCharacterDataHandler,
1923n/a (xmlhandler)my_CharacterDataHandler},
1924n/a {"UnparsedEntityDeclHandler",
1925n/a (xmlhandlersetter)XML_SetUnparsedEntityDeclHandler,
1926n/a (xmlhandler)my_UnparsedEntityDeclHandler},
1927n/a {"NotationDeclHandler",
1928n/a (xmlhandlersetter)XML_SetNotationDeclHandler,
1929n/a (xmlhandler)my_NotationDeclHandler},
1930n/a {"StartNamespaceDeclHandler",
1931n/a (xmlhandlersetter)XML_SetStartNamespaceDeclHandler,
1932n/a (xmlhandler)my_StartNamespaceDeclHandler},
1933n/a {"EndNamespaceDeclHandler",
1934n/a (xmlhandlersetter)XML_SetEndNamespaceDeclHandler,
1935n/a (xmlhandler)my_EndNamespaceDeclHandler},
1936n/a {"CommentHandler",
1937n/a (xmlhandlersetter)XML_SetCommentHandler,
1938n/a (xmlhandler)my_CommentHandler},
1939n/a {"StartCdataSectionHandler",
1940n/a (xmlhandlersetter)XML_SetStartCdataSectionHandler,
1941n/a (xmlhandler)my_StartCdataSectionHandler},
1942n/a {"EndCdataSectionHandler",
1943n/a (xmlhandlersetter)XML_SetEndCdataSectionHandler,
1944n/a (xmlhandler)my_EndCdataSectionHandler},
1945n/a {"DefaultHandler",
1946n/a (xmlhandlersetter)XML_SetDefaultHandler,
1947n/a (xmlhandler)my_DefaultHandler},
1948n/a {"DefaultHandlerExpand",
1949n/a (xmlhandlersetter)XML_SetDefaultHandlerExpand,
1950n/a (xmlhandler)my_DefaultHandlerExpandHandler},
1951n/a {"NotStandaloneHandler",
1952n/a (xmlhandlersetter)XML_SetNotStandaloneHandler,
1953n/a (xmlhandler)my_NotStandaloneHandler},
1954n/a {"ExternalEntityRefHandler",
1955n/a (xmlhandlersetter)XML_SetExternalEntityRefHandler,
1956n/a (xmlhandler)my_ExternalEntityRefHandler},
1957n/a {"StartDoctypeDeclHandler",
1958n/a (xmlhandlersetter)XML_SetStartDoctypeDeclHandler,
1959n/a (xmlhandler)my_StartDoctypeDeclHandler},
1960n/a {"EndDoctypeDeclHandler",
1961n/a (xmlhandlersetter)XML_SetEndDoctypeDeclHandler,
1962n/a (xmlhandler)my_EndDoctypeDeclHandler},
1963n/a {"EntityDeclHandler",
1964n/a (xmlhandlersetter)XML_SetEntityDeclHandler,
1965n/a (xmlhandler)my_EntityDeclHandler},
1966n/a {"XmlDeclHandler",
1967n/a (xmlhandlersetter)XML_SetXmlDeclHandler,
1968n/a (xmlhandler)my_XmlDeclHandler},
1969n/a {"ElementDeclHandler",
1970n/a (xmlhandlersetter)XML_SetElementDeclHandler,
1971n/a (xmlhandler)my_ElementDeclHandler},
1972n/a {"AttlistDeclHandler",
1973n/a (xmlhandlersetter)XML_SetAttlistDeclHandler,
1974n/a (xmlhandler)my_AttlistDeclHandler},
1975n/a#if XML_COMBINED_VERSION >= 19504
1976n/a {"SkippedEntityHandler",
1977n/a (xmlhandlersetter)XML_SetSkippedEntityHandler,
1978n/a (xmlhandler)my_SkippedEntityHandler},
1979n/a#endif
1980n/a
1981n/a {NULL, NULL, NULL} /* sentinel */
1982n/a};