blob: ae98ef721a7e8f1b8dff619043313a4b41e37e27 [file] [log] [blame]
Martin v. Löwis7090ed12001-09-19 10:37:50 +00001#include "Python.h"
Fred Drake4113b132001-03-24 19:58:26 +00002#include <ctype.h>
3
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00004#include "frameobject.h"
Fred Drakea77254a2000-09-29 19:23:29 +00005#include "expat.h"
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00006
Fredrik Lundhc3345042005-12-13 19:49:55 +00007#include "pyexpat.h"
8
Martin v. Löwisc847f402003-01-21 11:09:21 +00009#define XML_COMBINED_VERSION (10000*XML_MAJOR_VERSION+100*XML_MINOR_VERSION+XML_MICRO_VERSION)
10
Jeremy Hylton9263f572003-06-27 16:13:17 +000011#define FIX_TRACE
Martin v. Löwis339d0f72001-08-17 18:39:25 +000012
Fred Drake0582df92000-07-12 04:49:00 +000013enum HandlerTypes {
14 StartElement,
15 EndElement,
16 ProcessingInstruction,
17 CharacterData,
18 UnparsedEntityDecl,
19 NotationDecl,
20 StartNamespaceDecl,
21 EndNamespaceDecl,
22 Comment,
23 StartCdataSection,
24 EndCdataSection,
25 Default,
26 DefaultHandlerExpand,
27 NotStandalone,
Martin v. Löwis0078f6c2001-01-21 10:18:10 +000028 ExternalEntityRef,
29 StartDoctypeDecl,
30 EndDoctypeDecl,
Fred Drake85d835f2001-02-08 15:39:08 +000031 EntityDecl,
32 XmlDecl,
33 ElementDecl,
34 AttlistDecl,
Martin v. Löwisc847f402003-01-21 11:09:21 +000035#if XML_COMBINED_VERSION >= 19504
Martin v. Löwis069dde22003-01-21 10:58:18 +000036 SkippedEntity,
Martin v. Löwisc847f402003-01-21 11:09:21 +000037#endif
Fred Drake85d835f2001-02-08 15:39:08 +000038 _DummyDecl
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +000039};
40
41static PyObject *ErrorObject;
42
43/* ----------------------------------------------------- */
44
45/* Declarations for objects of type xmlparser */
46
47typedef struct {
Fred Drake0582df92000-07-12 04:49:00 +000048 PyObject_HEAD
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +000049
Fred Drake0582df92000-07-12 04:49:00 +000050 XML_Parser itself;
Fred Drake85d835f2001-02-08 15:39:08 +000051 int ordered_attributes; /* Return attributes as a list. */
52 int specified_attributes; /* Report only specified attributes. */
Fred Drakebd6101c2001-02-14 18:29:45 +000053 int in_callback; /* Is a callback active? */
Martin v. Löwis069dde22003-01-21 10:58:18 +000054 int ns_prefixes; /* Namespace-triplets mode? */
Fred Drake2a3d7db2002-06-28 22:56:48 +000055 XML_Char *buffer; /* Buffer used when accumulating characters */
56 /* NULL if not enabled */
57 int buffer_size; /* Size of buffer, in XML_Char units */
58 int buffer_used; /* Buffer units in use */
Fred Drakeb91a36b2002-06-27 19:40:48 +000059 PyObject *intern; /* Dictionary to intern strings */
Fred Drake0582df92000-07-12 04:49:00 +000060 PyObject **handlers;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +000061} xmlparseobject;
62
Fred Drake2a3d7db2002-06-28 22:56:48 +000063#define CHARACTER_DATA_BUFFER_SIZE 8192
64
Jeremy Hylton938ace62002-07-17 16:30:39 +000065static PyTypeObject Xmlparsetype;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +000066
Fred Drake117ac852002-09-24 16:24:54 +000067typedef void (*xmlhandlersetter)(XML_Parser self, void *meth);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +000068typedef void* xmlhandler;
69
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +000070struct HandlerInfo {
Fred Drake0582df92000-07-12 04:49:00 +000071 const char *name;
72 xmlhandlersetter setter;
73 xmlhandler handler;
Martin v. Löwis0078f6c2001-01-21 10:18:10 +000074 PyCodeObject *tb_code;
Fred Drake71b63ff2002-06-28 22:29:01 +000075 PyObject *nameobj;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +000076};
77
Jeremy Hylton938ace62002-07-17 16:30:39 +000078static struct HandlerInfo handler_info[64];
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +000079
Fred Drakebd6101c2001-02-14 18:29:45 +000080/* Set an integer attribute on the error object; return true on success,
81 * false on an exception.
82 */
83static int
84set_error_attr(PyObject *err, char *name, int value)
85{
Christian Heimes217cfd12007-12-02 14:31:20 +000086 PyObject *v = PyLong_FromLong(value);
Fred Drake85d835f2001-02-08 15:39:08 +000087
Neal Norwitz2f5e9902006-03-08 06:36:45 +000088 if (v == NULL || PyObject_SetAttrString(err, name, v) == -1) {
89 Py_XDECREF(v);
Fred Drakebd6101c2001-02-14 18:29:45 +000090 return 0;
91 }
Michael W. Hudson0bb84542004-08-03 11:31:31 +000092 Py_DECREF(v);
Fred Drakebd6101c2001-02-14 18:29:45 +000093 return 1;
94}
95
96/* Build and set an Expat exception, including positioning
97 * information. Always returns NULL.
98 */
Fred Drake85d835f2001-02-08 15:39:08 +000099static PyObject *
Martin v. Löwis069dde22003-01-21 10:58:18 +0000100set_error(xmlparseobject *self, enum XML_Error code)
Fred Drake85d835f2001-02-08 15:39:08 +0000101{
102 PyObject *err;
103 char buffer[256];
104 XML_Parser parser = self->itself;
Fred Drakebd6101c2001-02-14 18:29:45 +0000105 int lineno = XML_GetErrorLineNumber(parser);
106 int column = XML_GetErrorColumnNumber(parser);
Fred Drake85d835f2001-02-08 15:39:08 +0000107
Martin v. Löwis6b2cf0e2002-06-30 06:03:35 +0000108 /* There is no risk of overflowing this buffer, since
109 even for 64-bit integers, there is sufficient space. */
110 sprintf(buffer, "%.200s: line %i, column %i",
Fred Drakebd6101c2001-02-14 18:29:45 +0000111 XML_ErrorString(code), lineno, column);
Fred Drake85d835f2001-02-08 15:39:08 +0000112 err = PyObject_CallFunction(ErrorObject, "s", buffer);
Fred Drakebd6101c2001-02-14 18:29:45 +0000113 if ( err != NULL
114 && set_error_attr(err, "code", code)
115 && set_error_attr(err, "offset", column)
116 && set_error_attr(err, "lineno", lineno)) {
117 PyErr_SetObject(ErrorObject, err);
Fred Drake85d835f2001-02-08 15:39:08 +0000118 }
Neal Norwitz2f5e9902006-03-08 06:36:45 +0000119 Py_XDECREF(err);
Fred Drake85d835f2001-02-08 15:39:08 +0000120 return NULL;
121}
122
Fred Drake71b63ff2002-06-28 22:29:01 +0000123static int
124have_handler(xmlparseobject *self, int type)
125{
126 PyObject *handler = self->handlers[type];
127 return handler != NULL;
128}
129
130static PyObject *
131get_handler_name(struct HandlerInfo *hinfo)
132{
133 PyObject *name = hinfo->nameobj;
134 if (name == NULL) {
Neal Norwitz392c5be2007-08-25 17:20:32 +0000135 name = PyUnicode_FromString(hinfo->name);
Fred Drake71b63ff2002-06-28 22:29:01 +0000136 hinfo->nameobj = name;
137 }
138 Py_XINCREF(name);
139 return name;
140}
141
Fred Drake85d835f2001-02-08 15:39:08 +0000142
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +0000143/* Convert a string of XML_Chars into a Unicode string.
144 Returns None if str is a null pointer. */
145
Fred Drake0582df92000-07-12 04:49:00 +0000146static PyObject *
Fred Drakeb91a36b2002-06-27 19:40:48 +0000147conv_string_to_unicode(const XML_Char *str)
Fred Drake0582df92000-07-12 04:49:00 +0000148{
Fred Drake71b63ff2002-06-28 22:29:01 +0000149 /* XXX currently this code assumes that XML_Char is 8-bit,
Fred Drake0582df92000-07-12 04:49:00 +0000150 and hence in UTF-8. */
151 /* UTF-8 from Expat, Unicode desired */
152 if (str == NULL) {
153 Py_INCREF(Py_None);
154 return Py_None;
155 }
Fred Drake71b63ff2002-06-28 22:29:01 +0000156 return PyUnicode_DecodeUTF8(str, strlen(str), "strict");
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +0000157}
158
Fred Drake0582df92000-07-12 04:49:00 +0000159static PyObject *
160conv_string_len_to_unicode(const XML_Char *str, int len)
161{
Fred Drake71b63ff2002-06-28 22:29:01 +0000162 /* XXX currently this code assumes that XML_Char is 8-bit,
Fred Drake0582df92000-07-12 04:49:00 +0000163 and hence in UTF-8. */
164 /* UTF-8 from Expat, Unicode desired */
165 if (str == NULL) {
166 Py_INCREF(Py_None);
167 return Py_None;
168 }
Fred Drake6f987622000-08-25 18:03:30 +0000169 return PyUnicode_DecodeUTF8((const char *)str, len, "strict");
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +0000170}
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +0000171
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000172/* Callback routines */
173
Martin v. Löwis5b68ce32001-10-21 08:53:52 +0000174static void clear_handlers(xmlparseobject *self, int initial);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000175
Martin v. Löwis069dde22003-01-21 10:58:18 +0000176/* This handler is used when an error has been detected, in the hope
177 that actual parsing can be terminated early. This will only help
178 if an external entity reference is encountered. */
179static int
180error_external_entity_ref_handler(XML_Parser parser,
181 const XML_Char *context,
182 const XML_Char *base,
183 const XML_Char *systemId,
184 const XML_Char *publicId)
185{
186 return 0;
187}
188
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000189/* Dummy character data handler used when an error (exception) has
190 been detected, and the actual parsing can be terminated early.
191 This is needed since character data handler can't be safely removed
192 from within the character data handler, but can be replaced. It is
193 used only from the character data handler trampoline, and must be
194 used right after `flag_error()` is called. */
195static void
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000196noop_character_data_handler(void *userData, const XML_Char *data, int len)
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000197{
198 /* Do nothing. */
199}
200
Fred Drake6f987622000-08-25 18:03:30 +0000201static void
202flag_error(xmlparseobject *self)
203{
Martin v. Löwis5b68ce32001-10-21 08:53:52 +0000204 clear_handlers(self, 0);
Martin v. Löwis069dde22003-01-21 10:58:18 +0000205 XML_SetExternalEntityRefHandler(self->itself,
206 error_external_entity_ref_handler);
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000207}
208
209static PyCodeObject*
210getcode(enum HandlerTypes slot, char* func_name, int lineno)
211{
Fred Drakebd6101c2001-02-14 18:29:45 +0000212 if (handler_info[slot].tb_code == NULL) {
Fred Drakebd6101c2001-02-14 18:29:45 +0000213 handler_info[slot].tb_code =
Alexandre Vassalotti7b82b402009-07-21 04:30:03 +0000214 PyCode_NewEmpty(__FILE__, func_name, lineno);
Fred Drakebd6101c2001-02-14 18:29:45 +0000215 }
216 return handler_info[slot].tb_code;
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000217}
218
Jeremy Hylton9263f572003-06-27 16:13:17 +0000219#ifdef FIX_TRACE
Martin v. Löwis7d6e19d2002-08-04 08:24:49 +0000220static int
221trace_frame(PyThreadState *tstate, PyFrameObject *f, int code, PyObject *val)
222{
223 int result = 0;
224 if (!tstate->use_tracing || tstate->tracing)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000225 return 0;
Martin v. Löwis7d6e19d2002-08-04 08:24:49 +0000226 if (tstate->c_profilefunc != NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000227 tstate->tracing++;
228 result = tstate->c_profilefunc(tstate->c_profileobj,
229 f, code , val);
230 tstate->use_tracing = ((tstate->c_tracefunc != NULL)
231 || (tstate->c_profilefunc != NULL));
232 tstate->tracing--;
233 if (result)
234 return result;
Martin v. Löwis7d6e19d2002-08-04 08:24:49 +0000235 }
236 if (tstate->c_tracefunc != NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000237 tstate->tracing++;
238 result = tstate->c_tracefunc(tstate->c_traceobj,
239 f, code , val);
240 tstate->use_tracing = ((tstate->c_tracefunc != NULL)
241 || (tstate->c_profilefunc != NULL));
242 tstate->tracing--;
243 }
Martin v. Löwis7d6e19d2002-08-04 08:24:49 +0000244 return result;
245}
Jeremy Hylton9263f572003-06-27 16:13:17 +0000246
247static int
248trace_frame_exc(PyThreadState *tstate, PyFrameObject *f)
249{
250 PyObject *type, *value, *traceback, *arg;
251 int err;
252
253 if (tstate->c_tracefunc == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000254 return 0;
Jeremy Hylton9263f572003-06-27 16:13:17 +0000255
256 PyErr_Fetch(&type, &value, &traceback);
257 if (value == NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000258 value = Py_None;
259 Py_INCREF(value);
Jeremy Hylton9263f572003-06-27 16:13:17 +0000260 }
Raymond Hettinger8ae46892003-10-12 19:09:37 +0000261 arg = PyTuple_Pack(3, type, value, traceback);
Jeremy Hylton9263f572003-06-27 16:13:17 +0000262 if (arg == NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000263 PyErr_Restore(type, value, traceback);
264 return 0;
Jeremy Hylton9263f572003-06-27 16:13:17 +0000265 }
266 err = trace_frame(tstate, f, PyTrace_EXCEPTION, arg);
267 Py_DECREF(arg);
268 if (err == 0)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000269 PyErr_Restore(type, value, traceback);
Jeremy Hylton9263f572003-06-27 16:13:17 +0000270 else {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000271 Py_XDECREF(type);
272 Py_XDECREF(value);
273 Py_XDECREF(traceback);
Jeremy Hylton9263f572003-06-27 16:13:17 +0000274 }
275 return err;
276}
Martin v. Löwis069dde22003-01-21 10:58:18 +0000277#endif
Martin v. Löwis7d6e19d2002-08-04 08:24:49 +0000278
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000279static PyObject*
Fred Drake39689c52004-08-13 03:12:57 +0000280call_with_frame(PyCodeObject *c, PyObject* func, PyObject* args,
281 xmlparseobject *self)
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000282{
Fred Drakebd6101c2001-02-14 18:29:45 +0000283 PyThreadState *tstate = PyThreadState_GET();
284 PyFrameObject *f;
285 PyObject *res;
286
287 if (c == NULL)
288 return NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000289
Jeremy Hylton9263f572003-06-27 16:13:17 +0000290 f = PyFrame_New(tstate, c, PyEval_GetGlobals(), NULL);
Fred Drakebd6101c2001-02-14 18:29:45 +0000291 if (f == NULL)
292 return NULL;
293 tstate->frame = f;
Jeremy Hylton9263f572003-06-27 16:13:17 +0000294#ifdef FIX_TRACE
295 if (trace_frame(tstate, f, PyTrace_CALL, Py_None) < 0) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000296 return NULL;
Martin v. Löwis7d6e19d2002-08-04 08:24:49 +0000297 }
Martin v. Löwis069dde22003-01-21 10:58:18 +0000298#endif
Fred Drakebd6101c2001-02-14 18:29:45 +0000299 res = PyEval_CallObject(func, args);
Jeremy Hylton9263f572003-06-27 16:13:17 +0000300 if (res == NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000301 if (tstate->curexc_traceback == NULL)
302 PyTraceBack_Here(f);
Fred Drake39689c52004-08-13 03:12:57 +0000303 XML_StopParser(self->itself, XML_FALSE);
Jeremy Hylton9263f572003-06-27 16:13:17 +0000304#ifdef FIX_TRACE
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000305 if (trace_frame_exc(tstate, f) < 0) {
306 return NULL;
307 }
Jeremy Hylton9263f572003-06-27 16:13:17 +0000308 }
Martin v. Löwis7d6e19d2002-08-04 08:24:49 +0000309 else {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000310 if (trace_frame(tstate, f, PyTrace_RETURN, res) < 0) {
311 Py_XDECREF(res);
312 res = NULL;
313 }
Martin v. Löwis7d6e19d2002-08-04 08:24:49 +0000314 }
Jeremy Hylton9263f572003-06-27 16:13:17 +0000315#else
316 }
Martin v. Löwis069dde22003-01-21 10:58:18 +0000317#endif
Fred Drakebd6101c2001-02-14 18:29:45 +0000318 tstate->frame = f->f_back;
319 Py_DECREF(f);
320 return res;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000321}
322
Fred Drakeb91a36b2002-06-27 19:40:48 +0000323static PyObject*
324string_intern(xmlparseobject *self, const char* str)
325{
Guido van Rossum4ca94712007-07-23 17:42:32 +0000326 PyObject *result = conv_string_to_unicode(str);
Fred Drakeb91a36b2002-06-27 19:40:48 +0000327 PyObject *value;
Neal Norwitz484d9a42005-09-30 04:46:49 +0000328 /* result can be NULL if the unicode conversion failed. */
329 if (!result)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000330 return result;
Fred Drakeb91a36b2002-06-27 19:40:48 +0000331 if (!self->intern)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000332 return result;
Fred Drakeb91a36b2002-06-27 19:40:48 +0000333 value = PyDict_GetItem(self->intern, result);
334 if (!value) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000335 if (PyDict_SetItem(self->intern, result, result) == 0)
Fred Drakeb91a36b2002-06-27 19:40:48 +0000336 return result;
337 else
338 return NULL;
339 }
340 Py_INCREF(value);
341 Py_DECREF(result);
342 return value;
343}
344
Fred Drake2a3d7db2002-06-28 22:56:48 +0000345/* Return 0 on success, -1 on exception.
346 * flag_error() will be called before return if needed.
347 */
348static int
349call_character_handler(xmlparseobject *self, const XML_Char *buffer, int len)
350{
351 PyObject *args;
352 PyObject *temp;
353
Georg Brandlc01537f2010-10-15 16:26:08 +0000354 if (!have_handler(self, CharacterData))
355 return -1;
356
Fred Drake2a3d7db2002-06-28 22:56:48 +0000357 args = PyTuple_New(1);
358 if (args == NULL)
359 return -1;
Guido van Rossum4ca94712007-07-23 17:42:32 +0000360 temp = (conv_string_len_to_unicode(buffer, len));
Fred Drake2a3d7db2002-06-28 22:56:48 +0000361 if (temp == NULL) {
362 Py_DECREF(args);
363 flag_error(self);
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000364 XML_SetCharacterDataHandler(self->itself,
365 noop_character_data_handler);
Fred Drake2a3d7db2002-06-28 22:56:48 +0000366 return -1;
367 }
368 PyTuple_SET_ITEM(args, 0, temp);
369 /* temp is now a borrowed reference; consider it unused. */
370 self->in_callback = 1;
371 temp = call_with_frame(getcode(CharacterData, "CharacterData", __LINE__),
Fred Drake39689c52004-08-13 03:12:57 +0000372 self->handlers[CharacterData], args, self);
Fred Drake2a3d7db2002-06-28 22:56:48 +0000373 /* temp is an owned reference again, or NULL */
374 self->in_callback = 0;
375 Py_DECREF(args);
376 if (temp == NULL) {
377 flag_error(self);
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000378 XML_SetCharacterDataHandler(self->itself,
379 noop_character_data_handler);
Fred Drake2a3d7db2002-06-28 22:56:48 +0000380 return -1;
381 }
382 Py_DECREF(temp);
383 return 0;
384}
385
386static int
387flush_character_buffer(xmlparseobject *self)
388{
389 int rc;
390 if (self->buffer == NULL || self->buffer_used == 0)
391 return 0;
392 rc = call_character_handler(self, self->buffer, self->buffer_used);
393 self->buffer_used = 0;
394 return rc;
395}
396
397static void
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000398my_CharacterDataHandler(void *userData, const XML_Char *data, int len)
Fred Drake2a3d7db2002-06-28 22:56:48 +0000399{
400 xmlparseobject *self = (xmlparseobject *) userData;
401 if (self->buffer == NULL)
402 call_character_handler(self, data, len);
403 else {
404 if ((self->buffer_used + len) > self->buffer_size) {
405 if (flush_character_buffer(self) < 0)
406 return;
407 /* handler might have changed; drop the rest on the floor
408 * if there isn't a handler anymore
409 */
410 if (!have_handler(self, CharacterData))
411 return;
412 }
413 if (len > self->buffer_size) {
414 call_character_handler(self, data, len);
415 self->buffer_used = 0;
416 }
417 else {
418 memcpy(self->buffer + self->buffer_used,
419 data, len * sizeof(XML_Char));
420 self->buffer_used += len;
421 }
422 }
423}
424
Fred Drake85d835f2001-02-08 15:39:08 +0000425static void
426my_StartElementHandler(void *userData,
Fred Drake71b63ff2002-06-28 22:29:01 +0000427 const XML_Char *name, const XML_Char *atts[])
Fred Drake85d835f2001-02-08 15:39:08 +0000428{
429 xmlparseobject *self = (xmlparseobject *)userData;
430
Fred Drake71b63ff2002-06-28 22:29:01 +0000431 if (have_handler(self, StartElement)) {
Fred Drake85d835f2001-02-08 15:39:08 +0000432 PyObject *container, *rv, *args;
433 int i, max;
434
Fred Drake2a3d7db2002-06-28 22:56:48 +0000435 if (flush_character_buffer(self) < 0)
436 return;
Fred Drake85d835f2001-02-08 15:39:08 +0000437 /* Set max to the number of slots filled in atts[]; max/2 is
438 * the number of attributes we need to process.
439 */
440 if (self->specified_attributes) {
441 max = XML_GetSpecifiedAttributeCount(self->itself);
442 }
443 else {
444 max = 0;
445 while (atts[max] != NULL)
446 max += 2;
447 }
448 /* Build the container. */
449 if (self->ordered_attributes)
450 container = PyList_New(max);
451 else
452 container = PyDict_New();
453 if (container == NULL) {
454 flag_error(self);
455 return;
456 }
457 for (i = 0; i < max; i += 2) {
Fred Drakeb91a36b2002-06-27 19:40:48 +0000458 PyObject *n = string_intern(self, (XML_Char *) atts[i]);
Fred Drake85d835f2001-02-08 15:39:08 +0000459 PyObject *v;
460 if (n == NULL) {
461 flag_error(self);
462 Py_DECREF(container);
463 return;
464 }
Guido van Rossum4ca94712007-07-23 17:42:32 +0000465 v = conv_string_to_unicode((XML_Char *) atts[i+1]);
Fred Drake85d835f2001-02-08 15:39:08 +0000466 if (v == NULL) {
467 flag_error(self);
468 Py_DECREF(container);
469 Py_DECREF(n);
470 return;
471 }
472 if (self->ordered_attributes) {
473 PyList_SET_ITEM(container, i, n);
474 PyList_SET_ITEM(container, i+1, v);
475 }
476 else if (PyDict_SetItem(container, n, v)) {
477 flag_error(self);
478 Py_DECREF(n);
479 Py_DECREF(v);
480 return;
481 }
482 else {
483 Py_DECREF(n);
484 Py_DECREF(v);
485 }
486 }
Neal Norwitz484d9a42005-09-30 04:46:49 +0000487 args = string_intern(self, name);
488 if (args != NULL)
489 args = Py_BuildValue("(NN)", args, container);
Fred Drake85d835f2001-02-08 15:39:08 +0000490 if (args == NULL) {
491 Py_DECREF(container);
492 return;
493 }
494 /* Container is now a borrowed reference; ignore it. */
Fred Drakebd6101c2001-02-14 18:29:45 +0000495 self->in_callback = 1;
496 rv = call_with_frame(getcode(StartElement, "StartElement", __LINE__),
Fred Drake39689c52004-08-13 03:12:57 +0000497 self->handlers[StartElement], args, self);
Fred Drakebd6101c2001-02-14 18:29:45 +0000498 self->in_callback = 0;
499 Py_DECREF(args);
Fred Drake85d835f2001-02-08 15:39:08 +0000500 if (rv == NULL) {
501 flag_error(self);
502 return;
Fred Drakebd6101c2001-02-14 18:29:45 +0000503 }
Fred Drake85d835f2001-02-08 15:39:08 +0000504 Py_DECREF(rv);
505 }
506}
507
508#define RC_HANDLER(RC, NAME, PARAMS, INIT, PARAM_FORMAT, CONVERSION, \
509 RETURN, GETUSERDATA) \
510static RC \
511my_##NAME##Handler PARAMS {\
512 xmlparseobject *self = GETUSERDATA ; \
513 PyObject *args = NULL; \
514 PyObject *rv = NULL; \
515 INIT \
516\
Fred Drake71b63ff2002-06-28 22:29:01 +0000517 if (have_handler(self, NAME)) { \
Fred Drake2a3d7db2002-06-28 22:56:48 +0000518 if (flush_character_buffer(self) < 0) \
519 return RETURN; \
Fred Drake85d835f2001-02-08 15:39:08 +0000520 args = Py_BuildValue PARAM_FORMAT ;\
Martin v. Löwis1d7c55f2001-11-10 13:57:55 +0000521 if (!args) { flag_error(self); return RETURN;} \
Fred Drakebd6101c2001-02-14 18:29:45 +0000522 self->in_callback = 1; \
Fred Drake85d835f2001-02-08 15:39:08 +0000523 rv = call_with_frame(getcode(NAME,#NAME,__LINE__), \
Fred Drake39689c52004-08-13 03:12:57 +0000524 self->handlers[NAME], args, self); \
Fred Drakebd6101c2001-02-14 18:29:45 +0000525 self->in_callback = 0; \
Fred Drake85d835f2001-02-08 15:39:08 +0000526 Py_DECREF(args); \
527 if (rv == NULL) { \
528 flag_error(self); \
529 return RETURN; \
530 } \
531 CONVERSION \
532 Py_DECREF(rv); \
533 } \
534 return RETURN; \
535}
536
Fred Drake6f987622000-08-25 18:03:30 +0000537#define VOID_HANDLER(NAME, PARAMS, PARAM_FORMAT) \
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000538 RC_HANDLER(void, NAME, PARAMS, ;, PARAM_FORMAT, ;, ;,\
539 (xmlparseobject *)userData)
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000540
Fred Drake6f987622000-08-25 18:03:30 +0000541#define INT_HANDLER(NAME, PARAMS, PARAM_FORMAT)\
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000542 RC_HANDLER(int, NAME, PARAMS, int rc=0;, PARAM_FORMAT, \
543 rc = PyLong_AsLong(rv);, rc, \
544 (xmlparseobject *)userData)
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000545
Fred Drake71b63ff2002-06-28 22:29:01 +0000546VOID_HANDLER(EndElement,
547 (void *userData, const XML_Char *name),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000548 ("(N)", string_intern(self, name)))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000549
Fred Drake6f987622000-08-25 18:03:30 +0000550VOID_HANDLER(ProcessingInstruction,
Fred Drake71b63ff2002-06-28 22:29:01 +0000551 (void *userData,
552 const XML_Char *target,
Fred Drake85d835f2001-02-08 15:39:08 +0000553 const XML_Char *data),
Guido van Rossum4ca94712007-07-23 17:42:32 +0000554 ("(NO&)", string_intern(self, target), conv_string_to_unicode ,data))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000555
Fred Drake6f987622000-08-25 18:03:30 +0000556VOID_HANDLER(UnparsedEntityDecl,
Fred Drake71b63ff2002-06-28 22:29:01 +0000557 (void *userData,
Fred Drake85d835f2001-02-08 15:39:08 +0000558 const XML_Char *entityName,
559 const XML_Char *base,
560 const XML_Char *systemId,
561 const XML_Char *publicId,
562 const XML_Char *notationName),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000563 ("(NNNNN)",
Fred Drake71b63ff2002-06-28 22:29:01 +0000564 string_intern(self, entityName), string_intern(self, base),
565 string_intern(self, systemId), string_intern(self, publicId),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000566 string_intern(self, notationName)))
Fred Drake85d835f2001-02-08 15:39:08 +0000567
Fred Drake85d835f2001-02-08 15:39:08 +0000568VOID_HANDLER(EntityDecl,
569 (void *userData,
570 const XML_Char *entityName,
571 int is_parameter_entity,
572 const XML_Char *value,
573 int value_length,
574 const XML_Char *base,
575 const XML_Char *systemId,
576 const XML_Char *publicId,
577 const XML_Char *notationName),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000578 ("NiNNNNN",
579 string_intern(self, entityName), is_parameter_entity,
Guido van Rossum4ca94712007-07-23 17:42:32 +0000580 (conv_string_len_to_unicode(value, value_length)),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000581 string_intern(self, base), string_intern(self, systemId),
582 string_intern(self, publicId),
583 string_intern(self, notationName)))
Fred Drake85d835f2001-02-08 15:39:08 +0000584
585VOID_HANDLER(XmlDecl,
586 (void *userData,
587 const XML_Char *version,
588 const XML_Char *encoding,
589 int standalone),
590 ("(O&O&i)",
Guido van Rossum4ca94712007-07-23 17:42:32 +0000591 conv_string_to_unicode ,version, conv_string_to_unicode ,encoding,
Fred Drake85d835f2001-02-08 15:39:08 +0000592 standalone))
593
594static PyObject *
595conv_content_model(XML_Content * const model,
Fred Drakeb91a36b2002-06-27 19:40:48 +0000596 PyObject *(*conv_string)(const XML_Char *))
Fred Drake85d835f2001-02-08 15:39:08 +0000597{
598 PyObject *result = NULL;
599 PyObject *children = PyTuple_New(model->numchildren);
600 int i;
601
602 if (children != NULL) {
Tim Peters9544fc52001-07-28 09:36:36 +0000603 assert(model->numchildren < INT_MAX);
604 for (i = 0; i < (int)model->numchildren; ++i) {
Fred Drake85d835f2001-02-08 15:39:08 +0000605 PyObject *child = conv_content_model(&model->children[i],
606 conv_string);
607 if (child == NULL) {
608 Py_XDECREF(children);
609 return NULL;
610 }
611 PyTuple_SET_ITEM(children, i, child);
612 }
613 result = Py_BuildValue("(iiO&N)",
614 model->type, model->quant,
615 conv_string,model->name, children);
616 }
617 return result;
618}
619
Fred Drake06dd8cf2003-02-02 03:54:17 +0000620static void
621my_ElementDeclHandler(void *userData,
622 const XML_Char *name,
623 XML_Content *model)
Fred Drake85d835f2001-02-08 15:39:08 +0000624{
Fred Drake06dd8cf2003-02-02 03:54:17 +0000625 xmlparseobject *self = (xmlparseobject *)userData;
626 PyObject *args = NULL;
Fred Drake85d835f2001-02-08 15:39:08 +0000627
Fred Drake06dd8cf2003-02-02 03:54:17 +0000628 if (have_handler(self, ElementDecl)) {
629 PyObject *rv = NULL;
630 PyObject *modelobj, *nameobj;
631
632 if (flush_character_buffer(self) < 0)
633 goto finally;
Guido van Rossum4ca94712007-07-23 17:42:32 +0000634 modelobj = conv_content_model(model, (conv_string_to_unicode));
Fred Drake06dd8cf2003-02-02 03:54:17 +0000635 if (modelobj == NULL) {
636 flag_error(self);
637 goto finally;
638 }
639 nameobj = string_intern(self, name);
640 if (nameobj == NULL) {
641 Py_DECREF(modelobj);
642 flag_error(self);
643 goto finally;
644 }
Michael W. Hudson0bb84542004-08-03 11:31:31 +0000645 args = Py_BuildValue("NN", nameobj, modelobj);
Fred Drake06dd8cf2003-02-02 03:54:17 +0000646 if (args == NULL) {
647 Py_DECREF(modelobj);
648 flag_error(self);
649 goto finally;
650 }
651 self->in_callback = 1;
652 rv = call_with_frame(getcode(ElementDecl, "ElementDecl", __LINE__),
Fred Drake39689c52004-08-13 03:12:57 +0000653 self->handlers[ElementDecl], args, self);
Fred Drake06dd8cf2003-02-02 03:54:17 +0000654 self->in_callback = 0;
655 if (rv == NULL) {
656 flag_error(self);
657 goto finally;
658 }
659 Py_DECREF(rv);
660 }
661 finally:
662 Py_XDECREF(args);
663 XML_FreeContentModel(self->itself, model);
664 return;
665}
Fred Drake85d835f2001-02-08 15:39:08 +0000666
667VOID_HANDLER(AttlistDecl,
668 (void *userData,
669 const XML_Char *elname,
670 const XML_Char *attname,
671 const XML_Char *att_type,
672 const XML_Char *dflt,
673 int isrequired),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000674 ("(NNO&O&i)",
675 string_intern(self, elname), string_intern(self, attname),
Guido van Rossum4ca94712007-07-23 17:42:32 +0000676 conv_string_to_unicode ,att_type, conv_string_to_unicode ,dflt,
Fred Drake85d835f2001-02-08 15:39:08 +0000677 isrequired))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000678
Martin v. Löwisc847f402003-01-21 11:09:21 +0000679#if XML_COMBINED_VERSION >= 19504
Martin v. Löwis069dde22003-01-21 10:58:18 +0000680VOID_HANDLER(SkippedEntity,
681 (void *userData,
682 const XML_Char *entityName,
683 int is_parameter_entity),
684 ("Ni",
685 string_intern(self, entityName), is_parameter_entity))
Martin v. Löwisc847f402003-01-21 11:09:21 +0000686#endif
Martin v. Löwis069dde22003-01-21 10:58:18 +0000687
Fred Drake71b63ff2002-06-28 22:29:01 +0000688VOID_HANDLER(NotationDecl,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000689 (void *userData,
690 const XML_Char *notationName,
691 const XML_Char *base,
692 const XML_Char *systemId,
693 const XML_Char *publicId),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000694 ("(NNNN)",
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000695 string_intern(self, notationName), string_intern(self, base),
696 string_intern(self, systemId), string_intern(self, publicId)))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000697
Fred Drake6f987622000-08-25 18:03:30 +0000698VOID_HANDLER(StartNamespaceDecl,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000699 (void *userData,
700 const XML_Char *prefix,
701 const XML_Char *uri),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000702 ("(NN)",
703 string_intern(self, prefix), string_intern(self, uri)))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000704
Fred Drake6f987622000-08-25 18:03:30 +0000705VOID_HANDLER(EndNamespaceDecl,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000706 (void *userData,
707 const XML_Char *prefix),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000708 ("(N)", string_intern(self, prefix)))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000709
Fred Drake6f987622000-08-25 18:03:30 +0000710VOID_HANDLER(Comment,
Fred Drakeb91a36b2002-06-27 19:40:48 +0000711 (void *userData, const XML_Char *data),
Guido van Rossum4ca94712007-07-23 17:42:32 +0000712 ("(O&)", conv_string_to_unicode ,data))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000713
Fred Drake6f987622000-08-25 18:03:30 +0000714VOID_HANDLER(StartCdataSection,
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000715 (void *userData),
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000716 ("()"))
Fred Drake71b63ff2002-06-28 22:29:01 +0000717
Fred Drake6f987622000-08-25 18:03:30 +0000718VOID_HANDLER(EndCdataSection,
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000719 (void *userData),
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000720 ("()"))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000721
Fred Drake6f987622000-08-25 18:03:30 +0000722VOID_HANDLER(Default,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000723 (void *userData, const XML_Char *s, int len),
724 ("(N)", (conv_string_len_to_unicode(s,len))))
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +0000725
Fred Drake6f987622000-08-25 18:03:30 +0000726VOID_HANDLER(DefaultHandlerExpand,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000727 (void *userData, const XML_Char *s, int len),
728 ("(N)", (conv_string_len_to_unicode(s,len))))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000729
Fred Drake71b63ff2002-06-28 22:29:01 +0000730INT_HANDLER(NotStandalone,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000731 (void *userData),
732 ("()"))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000733
Fred Drake6f987622000-08-25 18:03:30 +0000734RC_HANDLER(int, ExternalEntityRef,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000735 (XML_Parser parser,
736 const XML_Char *context,
737 const XML_Char *base,
738 const XML_Char *systemId,
739 const XML_Char *publicId),
740 int rc=0;,
Fred Drakeb91a36b2002-06-27 19:40:48 +0000741 ("(O&NNN)",
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000742 conv_string_to_unicode ,context, string_intern(self, base),
743 string_intern(self, systemId), string_intern(self, publicId)),
744 rc = PyLong_AsLong(rv);, rc,
745 XML_GetUserData(parser))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000746
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000747/* XXX UnknownEncodingHandler */
748
Fred Drake85d835f2001-02-08 15:39:08 +0000749VOID_HANDLER(StartDoctypeDecl,
750 (void *userData, const XML_Char *doctypeName,
751 const XML_Char *sysid, const XML_Char *pubid,
752 int has_internal_subset),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000753 ("(NNNi)", string_intern(self, doctypeName),
754 string_intern(self, sysid), string_intern(self, pubid),
Fred Drake85d835f2001-02-08 15:39:08 +0000755 has_internal_subset))
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000756
757VOID_HANDLER(EndDoctypeDecl, (void *userData), ("()"))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000758
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000759/* ---------------------------------------------------------------- */
760
Fred Drake71b63ff2002-06-28 22:29:01 +0000761static PyObject *
762get_parse_result(xmlparseobject *self, int rv)
763{
764 if (PyErr_Occurred()) {
765 return NULL;
766 }
767 if (rv == 0) {
Martin v. Löwis069dde22003-01-21 10:58:18 +0000768 return set_error(self, XML_GetErrorCode(self->itself));
Fred Drake71b63ff2002-06-28 22:29:01 +0000769 }
Fred Drake2a3d7db2002-06-28 22:56:48 +0000770 if (flush_character_buffer(self) < 0) {
771 return NULL;
772 }
Christian Heimes217cfd12007-12-02 14:31:20 +0000773 return PyLong_FromLong(rv);
Fred Drake71b63ff2002-06-28 22:29:01 +0000774}
775
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000776PyDoc_STRVAR(xmlparse_Parse__doc__,
Thomas Wouters35317302000-07-22 16:34:15 +0000777"Parse(data[, isfinal])\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000778Parse XML data. `isfinal' should be true at end of input.");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000779
780static PyObject *
Fred Drake0582df92000-07-12 04:49:00 +0000781xmlparse_Parse(xmlparseobject *self, PyObject *args)
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000782{
Fred Drake0582df92000-07-12 04:49:00 +0000783 char *s;
784 int slen;
785 int isFinal = 0;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000786
Fred Drake0582df92000-07-12 04:49:00 +0000787 if (!PyArg_ParseTuple(args, "s#|i:Parse", &s, &slen, &isFinal))
788 return NULL;
Fred Drake71b63ff2002-06-28 22:29:01 +0000789
790 return get_parse_result(self, XML_Parse(self->itself, s, slen, isFinal));
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000791}
792
Fred Drakeca1f4262000-09-21 20:10:23 +0000793/* File reading copied from cPickle */
794
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000795#define BUF_SIZE 2048
796
Fred Drake0582df92000-07-12 04:49:00 +0000797static int
798readinst(char *buf, int buf_size, PyObject *meth)
799{
800 PyObject *arg = NULL;
801 PyObject *bytes = NULL;
802 PyObject *str = NULL;
Victor Stinner0fcab4a2011-01-04 12:59:15 +0000803 Py_ssize_t len = -1;
Guido van Rossum98297ee2007-11-06 21:34:58 +0000804 char *ptr;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000805
Christian Heimes217cfd12007-12-02 14:31:20 +0000806 if ((bytes = PyLong_FromLong(buf_size)) == NULL)
Fred Drake0582df92000-07-12 04:49:00 +0000807 goto finally;
Fred Drake676940b2000-09-22 15:21:31 +0000808
Fred Drake7b6caff2003-07-21 17:05:56 +0000809 if ((arg = PyTuple_New(1)) == NULL) {
810 Py_DECREF(bytes);
Fred Drake0582df92000-07-12 04:49:00 +0000811 goto finally;
Fred Drake7b6caff2003-07-21 17:05:56 +0000812 }
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000813
Tim Peters954eef72000-09-22 06:01:11 +0000814 PyTuple_SET_ITEM(arg, 0, bytes);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000815
Martin v. Löwis9171f022004-10-13 19:50:11 +0000816 str = PyObject_Call(meth, arg, NULL);
Martin v. Löwis9171f022004-10-13 19:50:11 +0000817 if (str == NULL)
Fred Drake0582df92000-07-12 04:49:00 +0000818 goto finally;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000819
Christian Heimes72b710a2008-05-26 13:28:38 +0000820 if (PyBytes_Check(str))
821 ptr = PyBytes_AS_STRING(str);
Christian Heimes9c4756e2008-05-26 13:22:05 +0000822 else if (PyByteArray_Check(str))
823 ptr = PyByteArray_AS_STRING(str);
Guido van Rossum98297ee2007-11-06 21:34:58 +0000824 else {
Fred Drake71b63ff2002-06-28 22:29:01 +0000825 PyErr_Format(PyExc_TypeError,
Guido van Rossum4ca94712007-07-23 17:42:32 +0000826 "read() did not return a bytes object (type=%.400s)",
Christian Heimes90aa7642007-12-19 02:45:37 +0000827 Py_TYPE(str)->tp_name);
Fred Drake0582df92000-07-12 04:49:00 +0000828 goto finally;
829 }
Christian Heimes90aa7642007-12-19 02:45:37 +0000830 len = Py_SIZE(str);
Fred Drake0582df92000-07-12 04:49:00 +0000831 if (len > buf_size) {
832 PyErr_Format(PyExc_ValueError,
833 "read() returned too much data: "
Victor Stinner9d6f9362011-01-04 22:00:04 +0000834 "%i bytes requested, %zd returned",
Fred Drake0582df92000-07-12 04:49:00 +0000835 buf_size, len);
Fred Drake0582df92000-07-12 04:49:00 +0000836 goto finally;
837 }
Guido van Rossum98297ee2007-11-06 21:34:58 +0000838 memcpy(buf, ptr, len);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000839finally:
Fred Drake0582df92000-07-12 04:49:00 +0000840 Py_XDECREF(arg);
Fred Drakeca1f4262000-09-21 20:10:23 +0000841 Py_XDECREF(str);
Victor Stinnered7e2222011-01-04 21:58:10 +0000842 /* len <= buf_size <= INT_MAX (see above) */
Victor Stinner0fcab4a2011-01-04 12:59:15 +0000843 return (int)len;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000844}
845
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000846PyDoc_STRVAR(xmlparse_ParseFile__doc__,
Thomas Wouters35317302000-07-22 16:34:15 +0000847"ParseFile(file)\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000848Parse XML data from file-like object.");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000849
850static PyObject *
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000851xmlparse_ParseFile(xmlparseobject *self, PyObject *f)
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000852{
Fred Drake0582df92000-07-12 04:49:00 +0000853 int rv = 1;
Fred Drake0582df92000-07-12 04:49:00 +0000854 PyObject *readmethod = NULL;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000855
Benjamin Peterson4e7f2852010-08-08 16:54:58 +0000856
857 readmethod = PyObject_GetAttrString(f, "read");
858 if (readmethod == NULL) {
859 PyErr_Clear();
860 PyErr_SetString(PyExc_TypeError,
861 "argument must have 'read' attribute");
862 return NULL;
Fred Drake0582df92000-07-12 04:49:00 +0000863 }
864 for (;;) {
865 int bytes_read;
866 void *buf = XML_GetBuffer(self->itself, BUF_SIZE);
Fred Drake7b6caff2003-07-21 17:05:56 +0000867 if (buf == NULL) {
Fred Drakef239c6d2003-07-21 17:22:43 +0000868 Py_XDECREF(readmethod);
Fred Drake0582df92000-07-12 04:49:00 +0000869 return PyErr_NoMemory();
Fred Drake7b6caff2003-07-21 17:05:56 +0000870 }
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000871
Benjamin Peterson4e7f2852010-08-08 16:54:58 +0000872 bytes_read = readinst(buf, BUF_SIZE, readmethod);
873 if (bytes_read < 0) {
874 Py_DECREF(readmethod);
875 return NULL;
Fred Drake0582df92000-07-12 04:49:00 +0000876 }
877 rv = XML_ParseBuffer(self->itself, bytes_read, bytes_read == 0);
Fred Drake7b6caff2003-07-21 17:05:56 +0000878 if (PyErr_Occurred()) {
879 Py_XDECREF(readmethod);
Fred Drake0582df92000-07-12 04:49:00 +0000880 return NULL;
Fred Drake7b6caff2003-07-21 17:05:56 +0000881 }
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000882
Fred Drake0582df92000-07-12 04:49:00 +0000883 if (!rv || bytes_read == 0)
884 break;
885 }
Fred Drake7b6caff2003-07-21 17:05:56 +0000886 Py_XDECREF(readmethod);
Fred Drake71b63ff2002-06-28 22:29:01 +0000887 return get_parse_result(self, rv);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000888}
889
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000890PyDoc_STRVAR(xmlparse_SetBase__doc__,
Thomas Wouters35317302000-07-22 16:34:15 +0000891"SetBase(base_url)\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000892Set the base URL for the parser.");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000893
894static PyObject *
Fred Drake0582df92000-07-12 04:49:00 +0000895xmlparse_SetBase(xmlparseobject *self, PyObject *args)
896{
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000897 char *base;
898
Fred Drake0582df92000-07-12 04:49:00 +0000899 if (!PyArg_ParseTuple(args, "s:SetBase", &base))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000900 return NULL;
Fred Drake0582df92000-07-12 04:49:00 +0000901 if (!XML_SetBase(self->itself, base)) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000902 return PyErr_NoMemory();
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000903 }
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000904 Py_INCREF(Py_None);
905 return Py_None;
906}
907
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000908PyDoc_STRVAR(xmlparse_GetBase__doc__,
Thomas Wouters35317302000-07-22 16:34:15 +0000909"GetBase() -> url\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000910Return base URL string for the parser.");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000911
912static PyObject *
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000913xmlparse_GetBase(xmlparseobject *self, PyObject *unused)
Fred Drake0582df92000-07-12 04:49:00 +0000914{
Fred Drake0582df92000-07-12 04:49:00 +0000915 return Py_BuildValue("z", XML_GetBase(self->itself));
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000916}
917
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000918PyDoc_STRVAR(xmlparse_GetInputContext__doc__,
Fred Drakebd6101c2001-02-14 18:29:45 +0000919"GetInputContext() -> string\n\
920Return the untranslated text of the input that caused the current event.\n\
921If the event was generated by a large amount of text (such as a start tag\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000922for an element with many attributes), not all of the text may be available.");
Fred Drakebd6101c2001-02-14 18:29:45 +0000923
924static PyObject *
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000925xmlparse_GetInputContext(xmlparseobject *self, PyObject *unused)
Fred Drakebd6101c2001-02-14 18:29:45 +0000926{
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000927 if (self->in_callback) {
928 int offset, size;
929 const char *buffer
930 = XML_GetInputContext(self->itself, &offset, &size);
Fred Drakebd6101c2001-02-14 18:29:45 +0000931
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000932 if (buffer != NULL)
Christian Heimes72b710a2008-05-26 13:28:38 +0000933 return PyBytes_FromStringAndSize(buffer + offset,
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000934 size - offset);
935 else
936 Py_RETURN_NONE;
Fred Drakebd6101c2001-02-14 18:29:45 +0000937 }
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000938 else
939 Py_RETURN_NONE;
Fred Drakebd6101c2001-02-14 18:29:45 +0000940}
Fred Drakebd6101c2001-02-14 18:29:45 +0000941
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000942PyDoc_STRVAR(xmlparse_ExternalEntityParserCreate__doc__,
Fred Drake2d4ac202001-01-03 15:36:25 +0000943"ExternalEntityParserCreate(context[, encoding])\n\
Tim Peters51dc9682000-09-24 22:12:45 +0000944Create a parser for parsing an external entity based on the\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000945information passed to the ExternalEntityRefHandler.");
Lars Gustäbel4a30a072000-09-24 20:50:52 +0000946
947static PyObject *
948xmlparse_ExternalEntityParserCreate(xmlparseobject *self, PyObject *args)
949{
950 char *context;
951 char *encoding = NULL;
952 xmlparseobject *new_parser;
953 int i;
954
Martin v. Löwisc57428d2001-09-19 09:55:09 +0000955 if (!PyArg_ParseTuple(args, "z|s:ExternalEntityParserCreate",
Fred Drakecde79132001-04-25 16:01:30 +0000956 &context, &encoding)) {
957 return NULL;
Lars Gustäbel4a30a072000-09-24 20:50:52 +0000958 }
959
Martin v. Löwis894258c2001-09-23 10:20:10 +0000960 new_parser = PyObject_GC_New(xmlparseobject, &Xmlparsetype);
Fred Drake85d835f2001-02-08 15:39:08 +0000961 if (new_parser == NULL)
962 return NULL;
Fred Drake2a3d7db2002-06-28 22:56:48 +0000963 new_parser->buffer_size = self->buffer_size;
964 new_parser->buffer_used = 0;
Victor Stinnerb4ba9862010-09-10 22:25:19 +0000965 new_parser->buffer = NULL;
Fred Drake85d835f2001-02-08 15:39:08 +0000966 new_parser->ordered_attributes = self->ordered_attributes;
967 new_parser->specified_attributes = self->specified_attributes;
Fred Drakebd6101c2001-02-14 18:29:45 +0000968 new_parser->in_callback = 0;
Martin v. Löwis069dde22003-01-21 10:58:18 +0000969 new_parser->ns_prefixes = self->ns_prefixes;
Lars Gustäbel4a30a072000-09-24 20:50:52 +0000970 new_parser->itself = XML_ExternalEntityParserCreate(self->itself, context,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +0000971 encoding);
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000972 new_parser->handlers = 0;
Fred Drakeb91a36b2002-06-27 19:40:48 +0000973 new_parser->intern = self->intern;
974 Py_XINCREF(new_parser->intern);
Martin v. Löwis894258c2001-09-23 10:20:10 +0000975 PyObject_GC_Track(new_parser);
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000976
Victor Stinnerb4ba9862010-09-10 22:25:19 +0000977 if (self->buffer != NULL) {
978 new_parser->buffer = malloc(new_parser->buffer_size);
979 if (new_parser->buffer == NULL) {
980 Py_DECREF(new_parser);
981 return PyErr_NoMemory();
982 }
983 }
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000984 if (!new_parser->itself) {
Fred Drake85d835f2001-02-08 15:39:08 +0000985 Py_DECREF(new_parser);
986 return PyErr_NoMemory();
Lars Gustäbel4a30a072000-09-24 20:50:52 +0000987 }
988
989 XML_SetUserData(new_parser->itself, (void *)new_parser);
990
991 /* allocate and clear handlers first */
Fred Drake2a3d7db2002-06-28 22:56:48 +0000992 for (i = 0; handler_info[i].name != NULL; i++)
Fred Drake85d835f2001-02-08 15:39:08 +0000993 /* do nothing */;
Lars Gustäbel4a30a072000-09-24 20:50:52 +0000994
Fred Drake2a3d7db2002-06-28 22:56:48 +0000995 new_parser->handlers = malloc(sizeof(PyObject *) * i);
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000996 if (!new_parser->handlers) {
Fred Drake85d835f2001-02-08 15:39:08 +0000997 Py_DECREF(new_parser);
998 return PyErr_NoMemory();
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000999 }
Martin v. Löwis5b68ce32001-10-21 08:53:52 +00001000 clear_handlers(new_parser, 1);
Lars Gustäbel4a30a072000-09-24 20:50:52 +00001001
1002 /* then copy handlers from self */
1003 for (i = 0; handler_info[i].name != NULL; i++) {
Fred Drake71b63ff2002-06-28 22:29:01 +00001004 PyObject *handler = self->handlers[i];
1005 if (handler != NULL) {
1006 Py_INCREF(handler);
1007 new_parser->handlers[i] = handler;
1008 handler_info[i].setter(new_parser->itself,
Fred Drake85d835f2001-02-08 15:39:08 +00001009 handler_info[i].handler);
1010 }
Lars Gustäbel4a30a072000-09-24 20:50:52 +00001011 }
Fred Drake71b63ff2002-06-28 22:29:01 +00001012 return (PyObject *)new_parser;
Lars Gustäbel4a30a072000-09-24 20:50:52 +00001013}
1014
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001015PyDoc_STRVAR(xmlparse_SetParamEntityParsing__doc__,
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001016"SetParamEntityParsing(flag) -> success\n\
1017Controls parsing of parameter entities (including the external DTD\n\
1018subset). Possible flag values are XML_PARAM_ENTITY_PARSING_NEVER,\n\
1019XML_PARAM_ENTITY_PARSING_UNLESS_STANDALONE and\n\
1020XML_PARAM_ENTITY_PARSING_ALWAYS. Returns true if setting the flag\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001021was successful.");
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001022
1023static PyObject*
Fred Drakebd6101c2001-02-14 18:29:45 +00001024xmlparse_SetParamEntityParsing(xmlparseobject *p, PyObject* args)
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001025{
Fred Drake85d835f2001-02-08 15:39:08 +00001026 int flag;
1027 if (!PyArg_ParseTuple(args, "i", &flag))
1028 return NULL;
Fred Drakebd6101c2001-02-14 18:29:45 +00001029 flag = XML_SetParamEntityParsing(p->itself, flag);
Christian Heimes217cfd12007-12-02 14:31:20 +00001030 return PyLong_FromLong(flag);
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001031}
1032
Martin v. Löwisc847f402003-01-21 11:09:21 +00001033
1034#if XML_COMBINED_VERSION >= 19505
Martin v. Löwis069dde22003-01-21 10:58:18 +00001035PyDoc_STRVAR(xmlparse_UseForeignDTD__doc__,
1036"UseForeignDTD([flag])\n\
1037Allows the application to provide an artificial external subset if one is\n\
1038not specified as part of the document instance. This readily allows the\n\
1039use of a 'default' document type controlled by the application, while still\n\
1040getting the advantage of providing document type information to the parser.\n\
1041'flag' defaults to True if not provided.");
1042
1043static PyObject *
1044xmlparse_UseForeignDTD(xmlparseobject *self, PyObject *args)
1045{
1046 PyObject *flagobj = NULL;
1047 XML_Bool flag = XML_TRUE;
1048 enum XML_Error rc;
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001049 if (!PyArg_UnpackTuple(args, "UseForeignDTD", 0, 1, &flagobj))
Martin v. Löwis069dde22003-01-21 10:58:18 +00001050 return NULL;
1051 if (flagobj != NULL)
1052 flag = PyObject_IsTrue(flagobj) ? XML_TRUE : XML_FALSE;
1053 rc = XML_UseForeignDTD(self->itself, flag);
1054 if (rc != XML_ERROR_NONE) {
1055 return set_error(self, rc);
1056 }
1057 Py_INCREF(Py_None);
1058 return Py_None;
1059}
Martin v. Löwisc847f402003-01-21 11:09:21 +00001060#endif
Martin v. Löwis069dde22003-01-21 10:58:18 +00001061
Amaury Forgeot d'Arcba4105c2008-07-02 21:41:01 +00001062static PyObject *xmlparse_dir(PyObject *self, PyObject* noargs);
1063
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001064static struct PyMethodDef xmlparse_methods[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001065 {"Parse", (PyCFunction)xmlparse_Parse,
1066 METH_VARARGS, xmlparse_Parse__doc__},
Fred Drake0582df92000-07-12 04:49:00 +00001067 {"ParseFile", (PyCFunction)xmlparse_ParseFile,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001068 METH_O, xmlparse_ParseFile__doc__},
Fred Drake0582df92000-07-12 04:49:00 +00001069 {"SetBase", (PyCFunction)xmlparse_SetBase,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001070 METH_VARARGS, xmlparse_SetBase__doc__},
Fred Drake0582df92000-07-12 04:49:00 +00001071 {"GetBase", (PyCFunction)xmlparse_GetBase,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001072 METH_NOARGS, xmlparse_GetBase__doc__},
Lars Gustäbel4a30a072000-09-24 20:50:52 +00001073 {"ExternalEntityParserCreate", (PyCFunction)xmlparse_ExternalEntityParserCreate,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001074 METH_VARARGS, xmlparse_ExternalEntityParserCreate__doc__},
Fred Drakebd6101c2001-02-14 18:29:45 +00001075 {"SetParamEntityParsing", (PyCFunction)xmlparse_SetParamEntityParsing,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001076 METH_VARARGS, xmlparse_SetParamEntityParsing__doc__},
Fred Drakebd6101c2001-02-14 18:29:45 +00001077 {"GetInputContext", (PyCFunction)xmlparse_GetInputContext,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001078 METH_NOARGS, xmlparse_GetInputContext__doc__},
Martin v. Löwisc847f402003-01-21 11:09:21 +00001079#if XML_COMBINED_VERSION >= 19505
Martin v. Löwis069dde22003-01-21 10:58:18 +00001080 {"UseForeignDTD", (PyCFunction)xmlparse_UseForeignDTD,
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001081 METH_VARARGS, xmlparse_UseForeignDTD__doc__},
Martin v. Löwisc847f402003-01-21 11:09:21 +00001082#endif
Amaury Forgeot d'Arcba4105c2008-07-02 21:41:01 +00001083 {"__dir__", xmlparse_dir, METH_NOARGS},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001084 {NULL, NULL} /* sentinel */
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001085};
1086
1087/* ---------- */
1088
1089
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001090
Fred Drake71b63ff2002-06-28 22:29:01 +00001091/* pyexpat international encoding support.
1092 Make it as simple as possible.
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001093*/
1094
Martin v. Löwis3af7cc02001-01-22 08:19:10 +00001095static char template_buffer[257];
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001096
Fred Drake71b63ff2002-06-28 22:29:01 +00001097static void
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001098init_template_buffer(void)
1099{
1100 int i;
Fred Drakebb66a202001-03-01 20:48:17 +00001101 for (i = 0; i < 256; i++) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001102 template_buffer[i] = i;
Tim Peters63cb99e2001-02-17 18:12:50 +00001103 }
Fred Drakebb66a202001-03-01 20:48:17 +00001104 template_buffer[256] = 0;
Tim Peters63cb99e2001-02-17 18:12:50 +00001105}
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001106
Fred Drake71b63ff2002-06-28 22:29:01 +00001107static int
1108PyUnknownEncodingHandler(void *encodingHandlerData,
1109 const XML_Char *name,
1110 XML_Encoding *info)
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001111{
Fred Drakebb66a202001-03-01 20:48:17 +00001112 PyUnicodeObject *_u_string = NULL;
1113 int result = 0;
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001114 int i;
Fred Drake71b63ff2002-06-28 22:29:01 +00001115
Fred Drakebb66a202001-03-01 20:48:17 +00001116 /* Yes, supports only 8bit encodings */
1117 _u_string = (PyUnicodeObject *)
1118 PyUnicode_Decode(template_buffer, 256, name, "replace");
Fred Drake71b63ff2002-06-28 22:29:01 +00001119
Fred Drakebb66a202001-03-01 20:48:17 +00001120 if (_u_string == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001121 return result;
Fred Drake71b63ff2002-06-28 22:29:01 +00001122
Fred Drakebb66a202001-03-01 20:48:17 +00001123 for (i = 0; i < 256; i++) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001124 /* Stupid to access directly, but fast */
1125 Py_UNICODE c = _u_string->str[i];
1126 if (c == Py_UNICODE_REPLACEMENT_CHARACTER)
1127 info->map[i] = -1;
1128 else
1129 info->map[i] = c;
Tim Peters63cb99e2001-02-17 18:12:50 +00001130 }
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001131 info->data = NULL;
1132 info->convert = NULL;
1133 info->release = NULL;
Fred Drake71b63ff2002-06-28 22:29:01 +00001134 result = 1;
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001135 Py_DECREF(_u_string);
1136 return result;
1137}
1138
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001139
1140static PyObject *
Fred Drakeb91a36b2002-06-27 19:40:48 +00001141newxmlparseobject(char *encoding, char *namespace_separator, PyObject *intern)
Fred Drake0582df92000-07-12 04:49:00 +00001142{
1143 int i;
1144 xmlparseobject *self;
Fred Drake71b63ff2002-06-28 22:29:01 +00001145
Martin v. Löwis894258c2001-09-23 10:20:10 +00001146 self = PyObject_GC_New(xmlparseobject, &Xmlparsetype);
Fred Drake0582df92000-07-12 04:49:00 +00001147 if (self == NULL)
1148 return NULL;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001149
Fred Drake2a3d7db2002-06-28 22:56:48 +00001150 self->buffer = NULL;
1151 self->buffer_size = CHARACTER_DATA_BUFFER_SIZE;
1152 self->buffer_used = 0;
Fred Drake85d835f2001-02-08 15:39:08 +00001153 self->ordered_attributes = 0;
1154 self->specified_attributes = 0;
Fred Drakebd6101c2001-02-14 18:29:45 +00001155 self->in_callback = 0;
Martin v. Löwis069dde22003-01-21 10:58:18 +00001156 self->ns_prefixes = 0;
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001157 self->handlers = NULL;
Fred Drakecde79132001-04-25 16:01:30 +00001158 if (namespace_separator != NULL) {
Fred Drake0582df92000-07-12 04:49:00 +00001159 self->itself = XML_ParserCreateNS(encoding, *namespace_separator);
1160 }
Fred Drake85d835f2001-02-08 15:39:08 +00001161 else {
Fred Drake0582df92000-07-12 04:49:00 +00001162 self->itself = XML_ParserCreate(encoding);
1163 }
Fred Drakeb91a36b2002-06-27 19:40:48 +00001164 self->intern = intern;
1165 Py_XINCREF(self->intern);
Martin v. Löwis894258c2001-09-23 10:20:10 +00001166 PyObject_GC_Track(self);
Fred Drake0582df92000-07-12 04:49:00 +00001167 if (self->itself == NULL) {
Fred Drake71b63ff2002-06-28 22:29:01 +00001168 PyErr_SetString(PyExc_RuntimeError,
Fred Drake0582df92000-07-12 04:49:00 +00001169 "XML_ParserCreate failed");
1170 Py_DECREF(self);
1171 return NULL;
1172 }
1173 XML_SetUserData(self->itself, (void *)self);
Fred Drake7c75bf22002-07-01 14:02:31 +00001174 XML_SetUnknownEncodingHandler(self->itself,
1175 (XML_UnknownEncodingHandler) PyUnknownEncodingHandler, NULL);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001176
Fred Drake2a3d7db2002-06-28 22:56:48 +00001177 for (i = 0; handler_info[i].name != NULL; i++)
Fred Drake0582df92000-07-12 04:49:00 +00001178 /* do nothing */;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001179
Fred Drake7c75bf22002-07-01 14:02:31 +00001180 self->handlers = malloc(sizeof(PyObject *) * i);
1181 if (!self->handlers) {
Fred Drake71b63ff2002-06-28 22:29:01 +00001182 Py_DECREF(self);
1183 return PyErr_NoMemory();
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001184 }
Martin v. Löwis5b68ce32001-10-21 08:53:52 +00001185 clear_handlers(self, 1);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001186
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001187 return (PyObject*)self;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001188}
1189
1190
1191static void
Fred Drake0582df92000-07-12 04:49:00 +00001192xmlparse_dealloc(xmlparseobject *self)
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001193{
Fred Drake0582df92000-07-12 04:49:00 +00001194 int i;
Martin v. Löwis894258c2001-09-23 10:20:10 +00001195 PyObject_GC_UnTrack(self);
Fred Drake85d835f2001-02-08 15:39:08 +00001196 if (self->itself != NULL)
Fred Drake0582df92000-07-12 04:49:00 +00001197 XML_ParserFree(self->itself);
1198 self->itself = NULL;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001199
Fred Drake85d835f2001-02-08 15:39:08 +00001200 if (self->handlers != NULL) {
Fred Drakecde79132001-04-25 16:01:30 +00001201 PyObject *temp;
Fred Drake85d835f2001-02-08 15:39:08 +00001202 for (i = 0; handler_info[i].name != NULL; i++) {
Fred Drakecde79132001-04-25 16:01:30 +00001203 temp = self->handlers[i];
1204 self->handlers[i] = NULL;
1205 Py_XDECREF(temp);
Fred Drake85d835f2001-02-08 15:39:08 +00001206 }
1207 free(self->handlers);
Fred Drake71b63ff2002-06-28 22:29:01 +00001208 self->handlers = NULL;
Fred Drake0582df92000-07-12 04:49:00 +00001209 }
Fred Drake2a3d7db2002-06-28 22:56:48 +00001210 if (self->buffer != NULL) {
1211 free(self->buffer);
1212 self->buffer = NULL;
1213 }
Fred Drakeb91a36b2002-06-27 19:40:48 +00001214 Py_XDECREF(self->intern);
Martin v. Löwis894258c2001-09-23 10:20:10 +00001215 PyObject_GC_Del(self);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001216}
1217
Fred Drake0582df92000-07-12 04:49:00 +00001218static int
Alexander Belopolskye239d232010-12-08 23:31:48 +00001219handlername2int(PyObject *name)
Fred Drake0582df92000-07-12 04:49:00 +00001220{
1221 int i;
Fred Drake71b63ff2002-06-28 22:29:01 +00001222 for (i = 0; handler_info[i].name != NULL; i++) {
Alexander Belopolskye239d232010-12-08 23:31:48 +00001223 if (PyUnicode_CompareWithASCIIString(
1224 name, handler_info[i].name) == 0) {
Fred Drake0582df92000-07-12 04:49:00 +00001225 return i;
1226 }
1227 }
1228 return -1;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001229}
1230
1231static PyObject *
Fred Drake71b63ff2002-06-28 22:29:01 +00001232get_pybool(int istrue)
1233{
1234 PyObject *result = istrue ? Py_True : Py_False;
1235 Py_INCREF(result);
1236 return result;
1237}
1238
1239static PyObject *
Amaury Forgeot d'Arcba4105c2008-07-02 21:41:01 +00001240xmlparse_getattro(xmlparseobject *self, PyObject *nameobj)
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001241{
Alexander Belopolskye239d232010-12-08 23:31:48 +00001242 Py_UNICODE *name;
Amaury Forgeot d'Arcba4105c2008-07-02 21:41:01 +00001243 int handlernum = -1;
1244
Alexander Belopolskye239d232010-12-08 23:31:48 +00001245 if (!PyUnicode_Check(nameobj))
1246 goto generic;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001247
Alexander Belopolskye239d232010-12-08 23:31:48 +00001248 handlernum = handlername2int(nameobj);
Fred Drake71b63ff2002-06-28 22:29:01 +00001249
1250 if (handlernum != -1) {
1251 PyObject *result = self->handlers[handlernum];
1252 if (result == NULL)
1253 result = Py_None;
1254 Py_INCREF(result);
1255 return result;
1256 }
Alexander Belopolskye239d232010-12-08 23:31:48 +00001257
1258 name = PyUnicode_AS_UNICODE(nameobj);
Fred Drake71b63ff2002-06-28 22:29:01 +00001259 if (name[0] == 'E') {
Alexander Belopolskye239d232010-12-08 23:31:48 +00001260 if (PyUnicode_CompareWithASCIIString(nameobj, "ErrorCode") == 0)
Christian Heimes217cfd12007-12-02 14:31:20 +00001261 return PyLong_FromLong((long)
Fred Drake71b63ff2002-06-28 22:29:01 +00001262 XML_GetErrorCode(self->itself));
Alexander Belopolskye239d232010-12-08 23:31:48 +00001263 if (PyUnicode_CompareWithASCIIString(nameobj, "ErrorLineNumber") == 0)
Christian Heimes217cfd12007-12-02 14:31:20 +00001264 return PyLong_FromLong((long)
Fred Drake71b63ff2002-06-28 22:29:01 +00001265 XML_GetErrorLineNumber(self->itself));
Alexander Belopolskye239d232010-12-08 23:31:48 +00001266 if (PyUnicode_CompareWithASCIIString(nameobj, "ErrorColumnNumber") == 0)
Christian Heimes217cfd12007-12-02 14:31:20 +00001267 return PyLong_FromLong((long)
Fred Drake71b63ff2002-06-28 22:29:01 +00001268 XML_GetErrorColumnNumber(self->itself));
Alexander Belopolskye239d232010-12-08 23:31:48 +00001269 if (PyUnicode_CompareWithASCIIString(nameobj, "ErrorByteIndex") == 0)
Christian Heimes217cfd12007-12-02 14:31:20 +00001270 return PyLong_FromLong((long)
Fred Drake71b63ff2002-06-28 22:29:01 +00001271 XML_GetErrorByteIndex(self->itself));
1272 }
Dave Cole3203efb2004-08-26 00:37:31 +00001273 if (name[0] == 'C') {
Alexander Belopolskye239d232010-12-08 23:31:48 +00001274 if (PyUnicode_CompareWithASCIIString(nameobj, "CurrentLineNumber") == 0)
Christian Heimes217cfd12007-12-02 14:31:20 +00001275 return PyLong_FromLong((long)
Dave Cole3203efb2004-08-26 00:37:31 +00001276 XML_GetCurrentLineNumber(self->itself));
Alexander Belopolskye239d232010-12-08 23:31:48 +00001277 if (PyUnicode_CompareWithASCIIString(nameobj, "CurrentColumnNumber") == 0)
Christian Heimes217cfd12007-12-02 14:31:20 +00001278 return PyLong_FromLong((long)
Dave Cole3203efb2004-08-26 00:37:31 +00001279 XML_GetCurrentColumnNumber(self->itself));
Alexander Belopolskye239d232010-12-08 23:31:48 +00001280 if (PyUnicode_CompareWithASCIIString(nameobj, "CurrentByteIndex") == 0)
Christian Heimes217cfd12007-12-02 14:31:20 +00001281 return PyLong_FromLong((long)
Dave Cole3203efb2004-08-26 00:37:31 +00001282 XML_GetCurrentByteIndex(self->itself));
1283 }
Fred Drake2a3d7db2002-06-28 22:56:48 +00001284 if (name[0] == 'b') {
Alexander Belopolskye239d232010-12-08 23:31:48 +00001285 if (PyUnicode_CompareWithASCIIString(nameobj, "buffer_size") == 0)
Christian Heimes217cfd12007-12-02 14:31:20 +00001286 return PyLong_FromLong((long) self->buffer_size);
Alexander Belopolskye239d232010-12-08 23:31:48 +00001287 if (PyUnicode_CompareWithASCIIString(nameobj, "buffer_text") == 0)
Fred Drake2a3d7db2002-06-28 22:56:48 +00001288 return get_pybool(self->buffer != NULL);
Alexander Belopolskye239d232010-12-08 23:31:48 +00001289 if (PyUnicode_CompareWithASCIIString(nameobj, "buffer_used") == 0)
Christian Heimes217cfd12007-12-02 14:31:20 +00001290 return PyLong_FromLong((long) self->buffer_used);
Fred Drake2a3d7db2002-06-28 22:56:48 +00001291 }
Alexander Belopolskye239d232010-12-08 23:31:48 +00001292 if (PyUnicode_CompareWithASCIIString(nameobj, "namespace_prefixes") == 0)
Martin v. Löwis069dde22003-01-21 10:58:18 +00001293 return get_pybool(self->ns_prefixes);
Alexander Belopolskye239d232010-12-08 23:31:48 +00001294 if (PyUnicode_CompareWithASCIIString(nameobj, "ordered_attributes") == 0)
Fred Drake71b63ff2002-06-28 22:29:01 +00001295 return get_pybool(self->ordered_attributes);
Alexander Belopolskye239d232010-12-08 23:31:48 +00001296 if (PyUnicode_CompareWithASCIIString(nameobj, "specified_attributes") == 0)
Fred Drake71b63ff2002-06-28 22:29:01 +00001297 return get_pybool((long) self->specified_attributes);
Alexander Belopolskye239d232010-12-08 23:31:48 +00001298 if (PyUnicode_CompareWithASCIIString(nameobj, "intern") == 0) {
Fred Drakeb91a36b2002-06-27 19:40:48 +00001299 if (self->intern == NULL) {
1300 Py_INCREF(Py_None);
1301 return Py_None;
1302 }
1303 else {
1304 Py_INCREF(self->intern);
1305 return self->intern;
1306 }
1307 }
Alexander Belopolskye239d232010-12-08 23:31:48 +00001308 generic:
Amaury Forgeot d'Arcba4105c2008-07-02 21:41:01 +00001309 return PyObject_GenericGetAttr((PyObject*)self, nameobj);
Neal Norwitz8dfc4a92007-08-11 06:39:53 +00001310}
1311
1312static PyObject *
1313xmlparse_dir(PyObject *self, PyObject* noargs)
1314{
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001315#define APPEND(list, str) \
1316 do { \
1317 PyObject *o = PyUnicode_FromString(str); \
1318 if (o != NULL) \
1319 PyList_Append(list, o); \
1320 Py_XDECREF(o); \
Martin v. Löwis069dde22003-01-21 10:58:18 +00001321 } while (0)
Neal Norwitzfa56e2d2003-01-19 15:40:09 +00001322
Neal Norwitz8dfc4a92007-08-11 06:39:53 +00001323 int i;
1324 PyObject *rc = PyList_New(0);
1325 if (!rc)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001326 return NULL;
Neal Norwitz8dfc4a92007-08-11 06:39:53 +00001327 for (i = 0; handler_info[i].name != NULL; i++) {
1328 PyObject *o = get_handler_name(&handler_info[i]);
1329 if (o != NULL)
1330 PyList_Append(rc, o);
1331 Py_XDECREF(o);
1332 }
1333 APPEND(rc, "ErrorCode");
1334 APPEND(rc, "ErrorLineNumber");
1335 APPEND(rc, "ErrorColumnNumber");
1336 APPEND(rc, "ErrorByteIndex");
1337 APPEND(rc, "CurrentLineNumber");
1338 APPEND(rc, "CurrentColumnNumber");
1339 APPEND(rc, "CurrentByteIndex");
1340 APPEND(rc, "buffer_size");
1341 APPEND(rc, "buffer_text");
1342 APPEND(rc, "buffer_used");
1343 APPEND(rc, "namespace_prefixes");
1344 APPEND(rc, "ordered_attributes");
1345 APPEND(rc, "specified_attributes");
1346 APPEND(rc, "intern");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001347
Neal Norwitzfa56e2d2003-01-19 15:40:09 +00001348#undef APPEND
Neal Norwitz8dfc4a92007-08-11 06:39:53 +00001349
1350 if (PyErr_Occurred()) {
1351 Py_DECREF(rc);
1352 rc = NULL;
Fred Drake0582df92000-07-12 04:49:00 +00001353 }
Neal Norwitz8dfc4a92007-08-11 06:39:53 +00001354
1355 return rc;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001356}
1357
Fred Drake6f987622000-08-25 18:03:30 +00001358static int
Alexander Belopolskye239d232010-12-08 23:31:48 +00001359sethandler(xmlparseobject *self, PyObject *name, PyObject* v)
Fred Drake0582df92000-07-12 04:49:00 +00001360{
1361 int handlernum = handlername2int(name);
Fred Drake71b63ff2002-06-28 22:29:01 +00001362 if (handlernum >= 0) {
1363 xmlhandler c_handler = NULL;
1364 PyObject *temp = self->handlers[handlernum];
1365
Thomas Wouters0e3f5912006-08-11 14:57:12 +00001366 if (v == Py_None) {
1367 /* If this is the character data handler, and a character
1368 data handler is already active, we need to be more
1369 careful. What we can safely do is replace the existing
1370 character data handler callback function with a no-op
1371 function that will refuse to call Python. The downside
1372 is that this doesn't completely remove the character
1373 data handler from the C layer if there's any callback
1374 active, so Expat does a little more work than it
1375 otherwise would, but that's really an odd case. A more
1376 elaborate system of handlers and state could remove the
1377 C handler more effectively. */
1378 if (handlernum == CharacterData && self->in_callback)
1379 c_handler = noop_character_data_handler;
Fred Drake71b63ff2002-06-28 22:29:01 +00001380 v = NULL;
Thomas Wouters0e3f5912006-08-11 14:57:12 +00001381 }
Fred Drake71b63ff2002-06-28 22:29:01 +00001382 else if (v != NULL) {
1383 Py_INCREF(v);
1384 c_handler = handler_info[handlernum].handler;
1385 }
Fred Drake0582df92000-07-12 04:49:00 +00001386 self->handlers[handlernum] = v;
Fred Drake71b63ff2002-06-28 22:29:01 +00001387 Py_XDECREF(temp);
1388 handler_info[handlernum].setter(self->itself, c_handler);
Fred Drake0582df92000-07-12 04:49:00 +00001389 return 1;
1390 }
1391 return 0;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001392}
1393
1394static int
Alexander Belopolskye239d232010-12-08 23:31:48 +00001395xmlparse_setattro(xmlparseobject *self, PyObject *name, PyObject *v)
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001396{
Fred Drake6f987622000-08-25 18:03:30 +00001397 /* Set attribute 'name' to value 'v'. v==NULL means delete */
Fred Drake85d835f2001-02-08 15:39:08 +00001398 if (v == NULL) {
Fred Drake6f987622000-08-25 18:03:30 +00001399 PyErr_SetString(PyExc_RuntimeError, "Cannot delete attribute");
1400 return -1;
1401 }
Alexander Belopolskye239d232010-12-08 23:31:48 +00001402 assert(PyUnicode_Check(name));
1403 if (PyUnicode_CompareWithASCIIString(name, "buffer_text") == 0) {
Fred Drake2a3d7db2002-06-28 22:56:48 +00001404 if (PyObject_IsTrue(v)) {
1405 if (self->buffer == NULL) {
1406 self->buffer = malloc(self->buffer_size);
1407 if (self->buffer == NULL) {
1408 PyErr_NoMemory();
1409 return -1;
1410 }
1411 self->buffer_used = 0;
1412 }
1413 }
1414 else if (self->buffer != NULL) {
1415 if (flush_character_buffer(self) < 0)
1416 return -1;
1417 free(self->buffer);
1418 self->buffer = NULL;
1419 }
1420 return 0;
1421 }
Alexander Belopolskye239d232010-12-08 23:31:48 +00001422 if (PyUnicode_CompareWithASCIIString(name, "namespace_prefixes") == 0) {
Martin v. Löwis069dde22003-01-21 10:58:18 +00001423 if (PyObject_IsTrue(v))
1424 self->ns_prefixes = 1;
1425 else
1426 self->ns_prefixes = 0;
1427 XML_SetReturnNSTriplet(self->itself, self->ns_prefixes);
1428 return 0;
1429 }
Alexander Belopolskye239d232010-12-08 23:31:48 +00001430 if (PyUnicode_CompareWithASCIIString(name, "ordered_attributes") == 0) {
Fred Drake85d835f2001-02-08 15:39:08 +00001431 if (PyObject_IsTrue(v))
1432 self->ordered_attributes = 1;
1433 else
1434 self->ordered_attributes = 0;
1435 return 0;
1436 }
Alexander Belopolskye239d232010-12-08 23:31:48 +00001437 if (PyUnicode_CompareWithASCIIString(name, "specified_attributes") == 0) {
Fred Drake85d835f2001-02-08 15:39:08 +00001438 if (PyObject_IsTrue(v))
1439 self->specified_attributes = 1;
1440 else
1441 self->specified_attributes = 0;
Fred Drake6f987622000-08-25 18:03:30 +00001442 return 0;
1443 }
Christian Heimes2380ac72008-01-09 00:17:24 +00001444
Alexander Belopolskye239d232010-12-08 23:31:48 +00001445 if (PyUnicode_CompareWithASCIIString(name, "buffer_size") == 0) {
Christian Heimes2380ac72008-01-09 00:17:24 +00001446 long new_buffer_size;
1447 if (!PyLong_Check(v)) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001448 PyErr_SetString(PyExc_TypeError, "buffer_size must be an integer");
1449 return -1;
Christian Heimes2380ac72008-01-09 00:17:24 +00001450 }
1451
1452 new_buffer_size=PyLong_AS_LONG(v);
1453 /* trivial case -- no change */
1454 if (new_buffer_size == self->buffer_size) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001455 return 0;
Christian Heimes2380ac72008-01-09 00:17:24 +00001456 }
1457
1458 if (new_buffer_size <= 0) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001459 PyErr_SetString(PyExc_ValueError, "buffer_size must be greater than zero");
1460 return -1;
Christian Heimes2380ac72008-01-09 00:17:24 +00001461 }
1462
1463 /* check maximum */
1464 if (new_buffer_size > INT_MAX) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001465 char errmsg[100];
1466 sprintf(errmsg, "buffer_size must not be greater than %i", INT_MAX);
1467 PyErr_SetString(PyExc_ValueError, errmsg);
1468 return -1;
Christian Heimes2380ac72008-01-09 00:17:24 +00001469 }
1470
1471 if (self->buffer != NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001472 /* there is already a buffer */
1473 if (self->buffer_used != 0) {
1474 flush_character_buffer(self);
1475 }
1476 /* free existing buffer */
1477 free(self->buffer);
Christian Heimes2380ac72008-01-09 00:17:24 +00001478 }
1479 self->buffer = malloc(new_buffer_size);
1480 if (self->buffer == NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001481 PyErr_NoMemory();
1482 return -1;
1483 }
Christian Heimes2380ac72008-01-09 00:17:24 +00001484 self->buffer_size = new_buffer_size;
1485 return 0;
1486 }
1487
Alexander Belopolskye239d232010-12-08 23:31:48 +00001488 if (PyUnicode_CompareWithASCIIString(name, "CharacterDataHandler") == 0) {
Fred Drake2a3d7db2002-06-28 22:56:48 +00001489 /* If we're changing the character data handler, flush all
1490 * cached data with the old handler. Not sure there's a
1491 * "right" thing to do, though, but this probably won't
1492 * happen.
1493 */
1494 if (flush_character_buffer(self) < 0)
1495 return -1;
1496 }
Fred Drake6f987622000-08-25 18:03:30 +00001497 if (sethandler(self, name, v)) {
1498 return 0;
1499 }
Alexander Belopolskye239d232010-12-08 23:31:48 +00001500 PyErr_SetObject(PyExc_AttributeError, name);
Fred Drake6f987622000-08-25 18:03:30 +00001501 return -1;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001502}
1503
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001504static int
1505xmlparse_traverse(xmlparseobject *op, visitproc visit, void *arg)
1506{
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00001507 int i;
1508 for (i = 0; handler_info[i].name != NULL; i++)
1509 Py_VISIT(op->handlers[i]);
Fred Drakecde79132001-04-25 16:01:30 +00001510 return 0;
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001511}
1512
1513static int
1514xmlparse_clear(xmlparseobject *op)
1515{
Martin v. Löwis5b68ce32001-10-21 08:53:52 +00001516 clear_handlers(op, 0);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00001517 Py_CLEAR(op->intern);
Fred Drakecde79132001-04-25 16:01:30 +00001518 return 0;
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001519}
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001520
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001521PyDoc_STRVAR(Xmlparsetype__doc__, "XML parser");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001522
1523static PyTypeObject Xmlparsetype = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001524 PyVarObject_HEAD_INIT(NULL, 0)
1525 "pyexpat.xmlparser", /*tp_name*/
Antoine Pitrou23683ef2011-01-04 00:00:31 +00001526 sizeof(xmlparseobject), /*tp_basicsize*/
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001527 0, /*tp_itemsize*/
1528 /* methods */
1529 (destructor)xmlparse_dealloc, /*tp_dealloc*/
1530 (printfunc)0, /*tp_print*/
1531 0, /*tp_getattr*/
Alexander Belopolskye239d232010-12-08 23:31:48 +00001532 0, /*tp_setattr*/
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001533 0, /*tp_reserved*/
1534 (reprfunc)0, /*tp_repr*/
1535 0, /*tp_as_number*/
1536 0, /*tp_as_sequence*/
1537 0, /*tp_as_mapping*/
1538 (hashfunc)0, /*tp_hash*/
1539 (ternaryfunc)0, /*tp_call*/
1540 (reprfunc)0, /*tp_str*/
1541 (getattrofunc)xmlparse_getattro, /* tp_getattro */
Alexander Belopolskye239d232010-12-08 23:31:48 +00001542 (setattrofunc)xmlparse_setattro, /* tp_setattro */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001543 0, /* tp_as_buffer */
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001544 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC, /*tp_flags*/
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001545 Xmlparsetype__doc__, /* tp_doc - Documentation string */
1546 (traverseproc)xmlparse_traverse, /* tp_traverse */
1547 (inquiry)xmlparse_clear, /* tp_clear */
1548 0, /* tp_richcompare */
1549 0, /* tp_weaklistoffset */
1550 0, /* tp_iter */
1551 0, /* tp_iternext */
1552 xmlparse_methods, /* tp_methods */
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001553};
1554
1555/* End of code for xmlparser objects */
1556/* -------------------------------------------------------- */
1557
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001558PyDoc_STRVAR(pyexpat_ParserCreate__doc__,
Fred Drake0582df92000-07-12 04:49:00 +00001559"ParserCreate([encoding[, namespace_separator]]) -> parser\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001560Return a new XML parser object.");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001561
1562static PyObject *
Fred Drake0582df92000-07-12 04:49:00 +00001563pyexpat_ParserCreate(PyObject *notused, PyObject *args, PyObject *kw)
1564{
Fred Drakecde79132001-04-25 16:01:30 +00001565 char *encoding = NULL;
1566 char *namespace_separator = NULL;
Fred Drakeb91a36b2002-06-27 19:40:48 +00001567 PyObject *intern = NULL;
1568 PyObject *result;
1569 int intern_decref = 0;
Martin v. Löwis15e62742006-02-27 16:46:16 +00001570 static char *kwlist[] = {"encoding", "namespace_separator",
Jeremy Hyltonaf68c872005-12-10 18:50:16 +00001571 "intern", NULL};
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001572
Fred Drakeb91a36b2002-06-27 19:40:48 +00001573 if (!PyArg_ParseTupleAndKeywords(args, kw, "|zzO:ParserCreate", kwlist,
1574 &encoding, &namespace_separator, &intern))
Fred Drakecde79132001-04-25 16:01:30 +00001575 return NULL;
1576 if (namespace_separator != NULL
1577 && strlen(namespace_separator) > 1) {
1578 PyErr_SetString(PyExc_ValueError,
1579 "namespace_separator must be at most one"
1580 " character, omitted, or None");
1581 return NULL;
1582 }
Fred Drakeb91a36b2002-06-27 19:40:48 +00001583 /* Explicitly passing None means no interning is desired.
1584 Not passing anything means that a new dictionary is used. */
1585 if (intern == Py_None)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001586 intern = NULL;
Fred Drakeb91a36b2002-06-27 19:40:48 +00001587 else if (intern == NULL) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001588 intern = PyDict_New();
1589 if (!intern)
1590 return NULL;
1591 intern_decref = 1;
Fred Drake71b63ff2002-06-28 22:29:01 +00001592 }
Fred Drakeb91a36b2002-06-27 19:40:48 +00001593 else if (!PyDict_Check(intern)) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001594 PyErr_SetString(PyExc_TypeError, "intern must be a dictionary");
1595 return NULL;
Fred Drakeb91a36b2002-06-27 19:40:48 +00001596 }
1597
1598 result = newxmlparseobject(encoding, namespace_separator, intern);
1599 if (intern_decref) {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001600 Py_DECREF(intern);
Fred Drakeb91a36b2002-06-27 19:40:48 +00001601 }
1602 return result;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001603}
1604
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001605PyDoc_STRVAR(pyexpat_ErrorString__doc__,
Fred Drake0582df92000-07-12 04:49:00 +00001606"ErrorString(errno) -> string\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001607Returns string error for given number.");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001608
1609static PyObject *
Fred Drake0582df92000-07-12 04:49:00 +00001610pyexpat_ErrorString(PyObject *self, PyObject *args)
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001611{
Fred Drake0582df92000-07-12 04:49:00 +00001612 long code = 0;
1613
1614 if (!PyArg_ParseTuple(args, "l:ErrorString", &code))
1615 return NULL;
1616 return Py_BuildValue("z", XML_ErrorString((int)code));
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001617}
1618
1619/* List of methods defined in the module */
1620
1621static struct PyMethodDef pyexpat_methods[] = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001622 {"ParserCreate", (PyCFunction)pyexpat_ParserCreate,
Fred Drake0582df92000-07-12 04:49:00 +00001623 METH_VARARGS|METH_KEYWORDS, pyexpat_ParserCreate__doc__},
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001624 {"ErrorString", (PyCFunction)pyexpat_ErrorString,
1625 METH_VARARGS, pyexpat_ErrorString__doc__},
Fred Drake71b63ff2002-06-28 22:29:01 +00001626
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001627 {NULL, (PyCFunction)NULL, 0, NULL} /* sentinel */
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001628};
1629
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +00001630/* Module docstring */
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001631
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001632PyDoc_STRVAR(pyexpat_module_documentation,
1633"Python wrapper for Expat parser.");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001634
Fred Drake4113b132001-03-24 19:58:26 +00001635/* Return a Python string that represents the version number without the
1636 * extra cruft added by revision control, even if the right options were
1637 * given to the "cvs export" command to make it not include the extra
1638 * cruft.
1639 */
1640static PyObject *
1641get_version_string(void)
1642{
1643 static char *rcsid = "$Revision$";
1644 char *rev = rcsid;
1645 int i = 0;
1646
Neal Norwitz30b5c5d2005-12-19 06:05:18 +00001647 while (!isdigit(Py_CHARMASK(*rev)))
Fred Drake4113b132001-03-24 19:58:26 +00001648 ++rev;
1649 while (rev[i] != ' ' && rev[i] != '\0')
1650 ++i;
1651
Neal Norwitz392c5be2007-08-25 17:20:32 +00001652 return PyUnicode_FromStringAndSize(rev, i);
Fred Drake4113b132001-03-24 19:58:26 +00001653}
1654
Fred Drakecde79132001-04-25 16:01:30 +00001655/* Initialization function for the module */
1656
1657#ifndef MODULE_NAME
1658#define MODULE_NAME "pyexpat"
1659#endif
1660
1661#ifndef MODULE_INITFUNC
Martin v. Löwis1a214512008-06-11 05:26:20 +00001662#define MODULE_INITFUNC PyInit_pyexpat
Fred Drakecde79132001-04-25 16:01:30 +00001663#endif
1664
Martin v. Löwis069dde22003-01-21 10:58:18 +00001665#ifndef PyMODINIT_FUNC
1666# ifdef MS_WINDOWS
1667# define PyMODINIT_FUNC __declspec(dllexport) void
1668# else
1669# define PyMODINIT_FUNC void
1670# endif
1671#endif
1672
Mark Hammond8235ea12002-07-19 06:55:41 +00001673PyMODINIT_FUNC MODULE_INITFUNC(void); /* avoid compiler warnings */
Fred Drakecde79132001-04-25 16:01:30 +00001674
Martin v. Löwis1a214512008-06-11 05:26:20 +00001675static struct PyModuleDef pyexpatmodule = {
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001676 PyModuleDef_HEAD_INIT,
1677 MODULE_NAME,
1678 pyexpat_module_documentation,
1679 -1,
1680 pyexpat_methods,
1681 NULL,
1682 NULL,
1683 NULL,
1684 NULL
Martin v. Löwis1a214512008-06-11 05:26:20 +00001685};
1686
Martin v. Löwis069dde22003-01-21 10:58:18 +00001687PyMODINIT_FUNC
1688MODULE_INITFUNC(void)
Fred Drake0582df92000-07-12 04:49:00 +00001689{
1690 PyObject *m, *d;
Neal Norwitz392c5be2007-08-25 17:20:32 +00001691 PyObject *errmod_name = PyUnicode_FromString(MODULE_NAME ".errors");
Fred Drake85d835f2001-02-08 15:39:08 +00001692 PyObject *errors_module;
1693 PyObject *modelmod_name;
1694 PyObject *model_module;
Fred Drake0582df92000-07-12 04:49:00 +00001695 PyObject *sys_modules;
Georg Brandlb4dac712010-10-15 14:46:48 +00001696 PyObject *tmpnum, *tmpstr;
1697 PyObject *codes_dict;
1698 PyObject *rev_codes_dict;
1699 int res;
Fredrik Lundhd7a42882005-12-13 20:43:04 +00001700 static struct PyExpat_CAPI capi;
Georg Brandlb4dac712010-10-15 14:46:48 +00001701 PyObject *capi_object;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001702
Fred Drake6f987622000-08-25 18:03:30 +00001703 if (errmod_name == NULL)
Martin v. Löwis1a214512008-06-11 05:26:20 +00001704 return NULL;
Neal Norwitz392c5be2007-08-25 17:20:32 +00001705 modelmod_name = PyUnicode_FromString(MODULE_NAME ".model");
Fred Drake85d835f2001-02-08 15:39:08 +00001706 if (modelmod_name == NULL)
Martin v. Löwis1a214512008-06-11 05:26:20 +00001707 return NULL;
Fred Drake6f987622000-08-25 18:03:30 +00001708
Amaury Forgeot d'Arcba4105c2008-07-02 21:41:01 +00001709 if (PyType_Ready(&Xmlparsetype) < 0)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001710 return NULL;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001711
Fred Drake0582df92000-07-12 04:49:00 +00001712 /* Create the module and add the functions */
Martin v. Löwis1a214512008-06-11 05:26:20 +00001713 m = PyModule_Create(&pyexpatmodule);
Neal Norwitz1ac754f2006-01-19 06:09:39 +00001714 if (m == NULL)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001715 return NULL;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001716
Fred Drake0582df92000-07-12 04:49:00 +00001717 /* Add some symbolic constants to the module */
Fred Drakebd6101c2001-02-14 18:29:45 +00001718 if (ErrorObject == NULL) {
1719 ErrorObject = PyErr_NewException("xml.parsers.expat.ExpatError",
Fred Drake93adb692000-09-23 04:55:48 +00001720 NULL, NULL);
Fred Drakebd6101c2001-02-14 18:29:45 +00001721 if (ErrorObject == NULL)
Martin v. Löwis1a214512008-06-11 05:26:20 +00001722 return NULL;
Fred Drakebd6101c2001-02-14 18:29:45 +00001723 }
1724 Py_INCREF(ErrorObject);
Fred Drake93adb692000-09-23 04:55:48 +00001725 PyModule_AddObject(m, "error", ErrorObject);
Fred Drakebd6101c2001-02-14 18:29:45 +00001726 Py_INCREF(ErrorObject);
1727 PyModule_AddObject(m, "ExpatError", ErrorObject);
Fred Drake4ba298c2000-10-29 04:57:53 +00001728 Py_INCREF(&Xmlparsetype);
1729 PyModule_AddObject(m, "XMLParserType", (PyObject *) &Xmlparsetype);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001730
Fred Drake4113b132001-03-24 19:58:26 +00001731 PyModule_AddObject(m, "__version__", get_version_string());
Fred Drake738293d2000-12-21 17:25:07 +00001732 PyModule_AddStringConstant(m, "EXPAT_VERSION",
1733 (char *) XML_ExpatVersion());
Fred Drake85d835f2001-02-08 15:39:08 +00001734 {
1735 XML_Expat_Version info = XML_ExpatVersionInfo();
1736 PyModule_AddObject(m, "version_info",
1737 Py_BuildValue("(iii)", info.major,
1738 info.minor, info.micro));
1739 }
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001740 init_template_buffer();
Fred Drake0582df92000-07-12 04:49:00 +00001741 /* XXX When Expat supports some way of figuring out how it was
Fred Drake71b63ff2002-06-28 22:29:01 +00001742 compiled, this should check and set native_encoding
1743 appropriately.
Fred Drake0582df92000-07-12 04:49:00 +00001744 */
Fred Drake93adb692000-09-23 04:55:48 +00001745 PyModule_AddStringConstant(m, "native_encoding", "UTF-8");
Fred Drakec23b5232000-08-24 21:57:43 +00001746
Fred Drake85d835f2001-02-08 15:39:08 +00001747 sys_modules = PySys_GetObject("modules");
Fred Drake93adb692000-09-23 04:55:48 +00001748 d = PyModule_GetDict(m);
Fred Drake6f987622000-08-25 18:03:30 +00001749 errors_module = PyDict_GetItem(d, errmod_name);
1750 if (errors_module == NULL) {
Fred Drakecde79132001-04-25 16:01:30 +00001751 errors_module = PyModule_New(MODULE_NAME ".errors");
Fred Drake6f987622000-08-25 18:03:30 +00001752 if (errors_module != NULL) {
Fred Drake6f987622000-08-25 18:03:30 +00001753 PyDict_SetItem(sys_modules, errmod_name, errors_module);
Fred Drake93adb692000-09-23 04:55:48 +00001754 /* gives away the reference to errors_module */
1755 PyModule_AddObject(m, "errors", errors_module);
Fred Drakec23b5232000-08-24 21:57:43 +00001756 }
1757 }
Fred Drake6f987622000-08-25 18:03:30 +00001758 Py_DECREF(errmod_name);
Fred Drake85d835f2001-02-08 15:39:08 +00001759 model_module = PyDict_GetItem(d, modelmod_name);
1760 if (model_module == NULL) {
Fred Drakecde79132001-04-25 16:01:30 +00001761 model_module = PyModule_New(MODULE_NAME ".model");
Fred Drake85d835f2001-02-08 15:39:08 +00001762 if (model_module != NULL) {
1763 PyDict_SetItem(sys_modules, modelmod_name, model_module);
1764 /* gives away the reference to model_module */
1765 PyModule_AddObject(m, "model", model_module);
1766 }
1767 }
1768 Py_DECREF(modelmod_name);
1769 if (errors_module == NULL || model_module == NULL)
1770 /* Don't core dump later! */
Martin v. Löwis1a214512008-06-11 05:26:20 +00001771 return NULL;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001772
Martin v. Löwisc847f402003-01-21 11:09:21 +00001773#if XML_COMBINED_VERSION > 19505
Martin v. Löwis069dde22003-01-21 10:58:18 +00001774 {
1775 const XML_Feature *features = XML_GetFeatureList();
1776 PyObject *list = PyList_New(0);
1777 if (list == NULL)
1778 /* just ignore it */
1779 PyErr_Clear();
1780 else {
1781 int i = 0;
1782 for (; features[i].feature != XML_FEATURE_END; ++i) {
1783 int ok;
1784 PyObject *item = Py_BuildValue("si", features[i].name,
1785 features[i].value);
1786 if (item == NULL) {
1787 Py_DECREF(list);
1788 list = NULL;
1789 break;
1790 }
1791 ok = PyList_Append(list, item);
1792 Py_DECREF(item);
1793 if (ok < 0) {
1794 PyErr_Clear();
1795 break;
1796 }
1797 }
1798 if (list != NULL)
1799 PyModule_AddObject(m, "features", list);
1800 }
1801 }
Martin v. Löwisc847f402003-01-21 11:09:21 +00001802#endif
Fred Drake6f987622000-08-25 18:03:30 +00001803
Georg Brandlb4dac712010-10-15 14:46:48 +00001804 codes_dict = PyDict_New();
1805 rev_codes_dict = PyDict_New();
1806 if (codes_dict == NULL || rev_codes_dict == NULL) {
1807 Py_XDECREF(codes_dict);
1808 Py_XDECREF(rev_codes_dict);
1809 return NULL;
1810 }
Victor Stinner0fcab4a2011-01-04 12:59:15 +00001811
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001812#define MYCONST(name) \
Georg Brandlb4dac712010-10-15 14:46:48 +00001813 if (PyModule_AddStringConstant(errors_module, #name, \
1814 (char *)XML_ErrorString(name)) < 0) \
1815 return NULL; \
1816 tmpnum = PyLong_FromLong(name); \
1817 if (tmpnum == NULL) return NULL; \
1818 res = PyDict_SetItemString(codes_dict, \
1819 XML_ErrorString(name), tmpnum); \
1820 if (res < 0) return NULL; \
1821 tmpstr = PyUnicode_FromString(XML_ErrorString(name)); \
1822 if (tmpstr == NULL) return NULL; \
1823 res = PyDict_SetItem(rev_codes_dict, tmpnum, tmpstr); \
1824 Py_DECREF(tmpstr); \
1825 Py_DECREF(tmpnum); \
1826 if (res < 0) return NULL; \
Fred Drake7bd9f412000-07-04 23:51:31 +00001827
Fred Drake0582df92000-07-12 04:49:00 +00001828 MYCONST(XML_ERROR_NO_MEMORY);
1829 MYCONST(XML_ERROR_SYNTAX);
1830 MYCONST(XML_ERROR_NO_ELEMENTS);
1831 MYCONST(XML_ERROR_INVALID_TOKEN);
1832 MYCONST(XML_ERROR_UNCLOSED_TOKEN);
1833 MYCONST(XML_ERROR_PARTIAL_CHAR);
1834 MYCONST(XML_ERROR_TAG_MISMATCH);
1835 MYCONST(XML_ERROR_DUPLICATE_ATTRIBUTE);
1836 MYCONST(XML_ERROR_JUNK_AFTER_DOC_ELEMENT);
1837 MYCONST(XML_ERROR_PARAM_ENTITY_REF);
1838 MYCONST(XML_ERROR_UNDEFINED_ENTITY);
1839 MYCONST(XML_ERROR_RECURSIVE_ENTITY_REF);
1840 MYCONST(XML_ERROR_ASYNC_ENTITY);
1841 MYCONST(XML_ERROR_BAD_CHAR_REF);
1842 MYCONST(XML_ERROR_BINARY_ENTITY_REF);
1843 MYCONST(XML_ERROR_ATTRIBUTE_EXTERNAL_ENTITY_REF);
1844 MYCONST(XML_ERROR_MISPLACED_XML_PI);
1845 MYCONST(XML_ERROR_UNKNOWN_ENCODING);
1846 MYCONST(XML_ERROR_INCORRECT_ENCODING);
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001847 MYCONST(XML_ERROR_UNCLOSED_CDATA_SECTION);
1848 MYCONST(XML_ERROR_EXTERNAL_ENTITY_HANDLING);
1849 MYCONST(XML_ERROR_NOT_STANDALONE);
Fred Drake283b6702004-08-04 22:28:16 +00001850 MYCONST(XML_ERROR_UNEXPECTED_STATE);
1851 MYCONST(XML_ERROR_ENTITY_DECLARED_IN_PE);
1852 MYCONST(XML_ERROR_FEATURE_REQUIRES_XML_DTD);
1853 MYCONST(XML_ERROR_CANT_CHANGE_FEATURE_ONCE_PARSING);
1854 /* Added in Expat 1.95.7. */
1855 MYCONST(XML_ERROR_UNBOUND_PREFIX);
1856 /* Added in Expat 1.95.8. */
1857 MYCONST(XML_ERROR_UNDECLARING_PREFIX);
1858 MYCONST(XML_ERROR_INCOMPLETE_PE);
1859 MYCONST(XML_ERROR_XML_DECL);
1860 MYCONST(XML_ERROR_TEXT_DECL);
1861 MYCONST(XML_ERROR_PUBLICID);
1862 MYCONST(XML_ERROR_SUSPENDED);
1863 MYCONST(XML_ERROR_NOT_SUSPENDED);
1864 MYCONST(XML_ERROR_ABORTED);
1865 MYCONST(XML_ERROR_FINISHED);
1866 MYCONST(XML_ERROR_SUSPEND_PE);
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001867
Georg Brandlb4dac712010-10-15 14:46:48 +00001868 if (PyModule_AddStringConstant(errors_module, "__doc__",
1869 "Constants used to describe "
1870 "error conditions.") < 0)
1871 return NULL;
Fred Drake85d835f2001-02-08 15:39:08 +00001872
Georg Brandlb4dac712010-10-15 14:46:48 +00001873 if (PyModule_AddObject(errors_module, "codes", codes_dict) < 0)
1874 return NULL;
1875 if (PyModule_AddObject(errors_module, "messages", rev_codes_dict) < 0)
1876 return NULL;
Victor Stinner0fcab4a2011-01-04 12:59:15 +00001877
Fred Drake93adb692000-09-23 04:55:48 +00001878#undef MYCONST
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001879
Fred Drake85d835f2001-02-08 15:39:08 +00001880#define MYCONST(c) PyModule_AddIntConstant(m, #c, c)
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001881 MYCONST(XML_PARAM_ENTITY_PARSING_NEVER);
1882 MYCONST(XML_PARAM_ENTITY_PARSING_UNLESS_STANDALONE);
1883 MYCONST(XML_PARAM_ENTITY_PARSING_ALWAYS);
Fred Drake85d835f2001-02-08 15:39:08 +00001884#undef MYCONST
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001885
Fred Drake85d835f2001-02-08 15:39:08 +00001886#define MYCONST(c) PyModule_AddIntConstant(model_module, #c, c)
1887 PyModule_AddStringConstant(model_module, "__doc__",
1888 "Constants used to interpret content model information.");
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001889
Fred Drake85d835f2001-02-08 15:39:08 +00001890 MYCONST(XML_CTYPE_EMPTY);
1891 MYCONST(XML_CTYPE_ANY);
1892 MYCONST(XML_CTYPE_MIXED);
1893 MYCONST(XML_CTYPE_NAME);
1894 MYCONST(XML_CTYPE_CHOICE);
1895 MYCONST(XML_CTYPE_SEQ);
1896
1897 MYCONST(XML_CQUANT_NONE);
1898 MYCONST(XML_CQUANT_OPT);
1899 MYCONST(XML_CQUANT_REP);
1900 MYCONST(XML_CQUANT_PLUS);
1901#undef MYCONST
Fredrik Lundhc3345042005-12-13 19:49:55 +00001902
1903 /* initialize pyexpat dispatch table */
Fredrik Lundhd7a42882005-12-13 20:43:04 +00001904 capi.size = sizeof(capi);
Fredrik Lundhcc117db2005-12-13 21:55:36 +00001905 capi.magic = PyExpat_CAPI_MAGIC;
Fredrik Lundhd7a42882005-12-13 20:43:04 +00001906 capi.MAJOR_VERSION = XML_MAJOR_VERSION;
1907 capi.MINOR_VERSION = XML_MINOR_VERSION;
1908 capi.MICRO_VERSION = XML_MICRO_VERSION;
1909 capi.ErrorString = XML_ErrorString;
Fredrik Lundhcc117db2005-12-13 21:55:36 +00001910 capi.GetErrorCode = XML_GetErrorCode;
1911 capi.GetErrorColumnNumber = XML_GetErrorColumnNumber;
1912 capi.GetErrorLineNumber = XML_GetErrorLineNumber;
Fredrik Lundhd7a42882005-12-13 20:43:04 +00001913 capi.Parse = XML_Parse;
1914 capi.ParserCreate_MM = XML_ParserCreate_MM;
1915 capi.ParserFree = XML_ParserFree;
1916 capi.SetCharacterDataHandler = XML_SetCharacterDataHandler;
1917 capi.SetCommentHandler = XML_SetCommentHandler;
1918 capi.SetDefaultHandlerExpand = XML_SetDefaultHandlerExpand;
1919 capi.SetElementHandler = XML_SetElementHandler;
1920 capi.SetNamespaceDeclHandler = XML_SetNamespaceDeclHandler;
1921 capi.SetProcessingInstructionHandler = XML_SetProcessingInstructionHandler;
1922 capi.SetUnknownEncodingHandler = XML_SetUnknownEncodingHandler;
1923 capi.SetUserData = XML_SetUserData;
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001924
Benjamin Petersonb173f782009-05-05 22:31:58 +00001925 /* export using capsule */
1926 capi_object = PyCapsule_New(&capi, PyExpat_CAPSULE_NAME, NULL);
Fredrik Lundhd7a42882005-12-13 20:43:04 +00001927 if (capi_object)
1928 PyModule_AddObject(m, "expat_CAPI", capi_object);
Martin v. Löwis1a214512008-06-11 05:26:20 +00001929 return m;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001930}
1931
Fred Drake6f987622000-08-25 18:03:30 +00001932static void
Martin v. Löwis5b68ce32001-10-21 08:53:52 +00001933clear_handlers(xmlparseobject *self, int initial)
Fred Drake0582df92000-07-12 04:49:00 +00001934{
Fred Drakecde79132001-04-25 16:01:30 +00001935 int i = 0;
1936 PyObject *temp;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001937
Fred Drake71b63ff2002-06-28 22:29:01 +00001938 for (; handler_info[i].name != NULL; i++) {
Martin v. Löwis5b68ce32001-10-21 08:53:52 +00001939 if (initial)
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001940 self->handlers[i] = NULL;
1941 else {
Fred Drakecde79132001-04-25 16:01:30 +00001942 temp = self->handlers[i];
1943 self->handlers[i] = NULL;
1944 Py_XDECREF(temp);
Antoine Pitrouf95a1b32010-05-09 15:52:27 +00001945 handler_info[i].setter(self->itself, NULL);
Fred Drakecde79132001-04-25 16:01:30 +00001946 }
Fred Drakecde79132001-04-25 16:01:30 +00001947 }
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001948}
1949
Tim Peters0c322792002-07-17 16:49:03 +00001950static struct HandlerInfo handler_info[] = {
Fred Drake71b63ff2002-06-28 22:29:01 +00001951 {"StartElementHandler",
1952 (xmlhandlersetter)XML_SetStartElementHandler,
Fred Drake0582df92000-07-12 04:49:00 +00001953 (xmlhandler)my_StartElementHandler},
Fred Drake71b63ff2002-06-28 22:29:01 +00001954 {"EndElementHandler",
1955 (xmlhandlersetter)XML_SetEndElementHandler,
Fred Drake0582df92000-07-12 04:49:00 +00001956 (xmlhandler)my_EndElementHandler},
Fred Drake71b63ff2002-06-28 22:29:01 +00001957 {"ProcessingInstructionHandler",
Fred Drake0582df92000-07-12 04:49:00 +00001958 (xmlhandlersetter)XML_SetProcessingInstructionHandler,
1959 (xmlhandler)my_ProcessingInstructionHandler},
Fred Drake71b63ff2002-06-28 22:29:01 +00001960 {"CharacterDataHandler",
Fred Drake0582df92000-07-12 04:49:00 +00001961 (xmlhandlersetter)XML_SetCharacterDataHandler,
1962 (xmlhandler)my_CharacterDataHandler},
Fred Drake71b63ff2002-06-28 22:29:01 +00001963 {"UnparsedEntityDeclHandler",
Fred Drake0582df92000-07-12 04:49:00 +00001964 (xmlhandlersetter)XML_SetUnparsedEntityDeclHandler,
Fred Drake2a3d7db2002-06-28 22:56:48 +00001965 (xmlhandler)my_UnparsedEntityDeclHandler},
Fred Drake71b63ff2002-06-28 22:29:01 +00001966 {"NotationDeclHandler",
Fred Drake0582df92000-07-12 04:49:00 +00001967 (xmlhandlersetter)XML_SetNotationDeclHandler,
Fred Drake2a3d7db2002-06-28 22:56:48 +00001968 (xmlhandler)my_NotationDeclHandler},
Fred Drake71b63ff2002-06-28 22:29:01 +00001969 {"StartNamespaceDeclHandler",
1970 (xmlhandlersetter)XML_SetStartNamespaceDeclHandler,
Fred Drake2a3d7db2002-06-28 22:56:48 +00001971 (xmlhandler)my_StartNamespaceDeclHandler},
Fred Drake71b63ff2002-06-28 22:29:01 +00001972 {"EndNamespaceDeclHandler",
1973 (xmlhandlersetter)XML_SetEndNamespaceDeclHandler,
Fred Drake2a3d7db2002-06-28 22:56:48 +00001974 (xmlhandler)my_EndNamespaceDeclHandler},
Fred Drake0582df92000-07-12 04:49:00 +00001975 {"CommentHandler",
1976 (xmlhandlersetter)XML_SetCommentHandler,
1977 (xmlhandler)my_CommentHandler},
1978 {"StartCdataSectionHandler",
Fred Drake71b63ff2002-06-28 22:29:01 +00001979 (xmlhandlersetter)XML_SetStartCdataSectionHandler,
Fred Drake0582df92000-07-12 04:49:00 +00001980 (xmlhandler)my_StartCdataSectionHandler},
1981 {"EndCdataSectionHandler",
Fred Drake71b63ff2002-06-28 22:29:01 +00001982 (xmlhandlersetter)XML_SetEndCdataSectionHandler,
Fred Drake0582df92000-07-12 04:49:00 +00001983 (xmlhandler)my_EndCdataSectionHandler},
1984 {"DefaultHandler",
1985 (xmlhandlersetter)XML_SetDefaultHandler,
1986 (xmlhandler)my_DefaultHandler},
1987 {"DefaultHandlerExpand",
1988 (xmlhandlersetter)XML_SetDefaultHandlerExpand,
1989 (xmlhandler)my_DefaultHandlerExpandHandler},
1990 {"NotStandaloneHandler",
1991 (xmlhandlersetter)XML_SetNotStandaloneHandler,
1992 (xmlhandler)my_NotStandaloneHandler},
1993 {"ExternalEntityRefHandler",
1994 (xmlhandlersetter)XML_SetExternalEntityRefHandler,
Fred Drake2a3d7db2002-06-28 22:56:48 +00001995 (xmlhandler)my_ExternalEntityRefHandler},
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001996 {"StartDoctypeDeclHandler",
Fred Drake71b63ff2002-06-28 22:29:01 +00001997 (xmlhandlersetter)XML_SetStartDoctypeDeclHandler,
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001998 (xmlhandler)my_StartDoctypeDeclHandler},
1999 {"EndDoctypeDeclHandler",
Fred Drake71b63ff2002-06-28 22:29:01 +00002000 (xmlhandlersetter)XML_SetEndDoctypeDeclHandler,
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00002001 (xmlhandler)my_EndDoctypeDeclHandler},
Fred Drake85d835f2001-02-08 15:39:08 +00002002 {"EntityDeclHandler",
2003 (xmlhandlersetter)XML_SetEntityDeclHandler,
2004 (xmlhandler)my_EntityDeclHandler},
2005 {"XmlDeclHandler",
2006 (xmlhandlersetter)XML_SetXmlDeclHandler,
2007 (xmlhandler)my_XmlDeclHandler},
2008 {"ElementDeclHandler",
2009 (xmlhandlersetter)XML_SetElementDeclHandler,
2010 (xmlhandler)my_ElementDeclHandler},
2011 {"AttlistDeclHandler",
2012 (xmlhandlersetter)XML_SetAttlistDeclHandler,
2013 (xmlhandler)my_AttlistDeclHandler},
Martin v. Löwisc847f402003-01-21 11:09:21 +00002014#if XML_COMBINED_VERSION >= 19504
Martin v. Löwis069dde22003-01-21 10:58:18 +00002015 {"SkippedEntityHandler",
2016 (xmlhandlersetter)XML_SetSkippedEntityHandler,
2017 (xmlhandler)my_SkippedEntityHandler},
Martin v. Löwisc847f402003-01-21 11:09:21 +00002018#endif
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00002019
Fred Drake0582df92000-07-12 04:49:00 +00002020 {NULL, NULL, NULL} /* sentinel */
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00002021};