blob: 658569e92f3790f4ff59a0a3194653c24913813c [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
Martin v. Löwisb4fcf4d2002-06-30 06:40:55 +000011#ifndef PyDoc_STRVAR
Martin v. Löwis069dde22003-01-21 10:58:18 +000012
13/*
14 * fdrake says:
15 * Don't change the PyDoc_STR macro definition to (str), because
16 * '''the parentheses cause compile failures
17 * ("non-constant static initializer" or something like that)
18 * on some platforms (Irix?)'''
19 */
Fred Drakef57b22a2002-09-02 15:54:06 +000020#define PyDoc_STR(str) str
Fred Drake7c75bf22002-07-01 14:02:31 +000021#define PyDoc_VAR(name) static char name[]
Martin v. Löwisb4fcf4d2002-06-30 06:40:55 +000022#define PyDoc_STRVAR(name,str) PyDoc_VAR(name) = PyDoc_STR(str)
Martin v. Löwis0078f6c2001-01-21 10:18:10 +000023#endif
24
Jeremy Hylton9263f572003-06-27 16:13:17 +000025#define FIX_TRACE
Martin v. Löwis339d0f72001-08-17 18:39:25 +000026
Fred Drake0582df92000-07-12 04:49:00 +000027enum HandlerTypes {
28 StartElement,
29 EndElement,
30 ProcessingInstruction,
31 CharacterData,
32 UnparsedEntityDecl,
33 NotationDecl,
34 StartNamespaceDecl,
35 EndNamespaceDecl,
36 Comment,
37 StartCdataSection,
38 EndCdataSection,
39 Default,
40 DefaultHandlerExpand,
41 NotStandalone,
Martin v. Löwis0078f6c2001-01-21 10:18:10 +000042 ExternalEntityRef,
43 StartDoctypeDecl,
44 EndDoctypeDecl,
Fred Drake85d835f2001-02-08 15:39:08 +000045 EntityDecl,
46 XmlDecl,
47 ElementDecl,
48 AttlistDecl,
Martin v. Löwisc847f402003-01-21 11:09:21 +000049#if XML_COMBINED_VERSION >= 19504
Martin v. Löwis069dde22003-01-21 10:58:18 +000050 SkippedEntity,
Martin v. Löwisc847f402003-01-21 11:09:21 +000051#endif
Fred Drake85d835f2001-02-08 15:39:08 +000052 _DummyDecl
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +000053};
54
55static PyObject *ErrorObject;
56
57/* ----------------------------------------------------- */
58
59/* Declarations for objects of type xmlparser */
60
61typedef struct {
Fred Drake0582df92000-07-12 04:49:00 +000062 PyObject_HEAD
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +000063
Fred Drake0582df92000-07-12 04:49:00 +000064 XML_Parser itself;
Fred Drake85d835f2001-02-08 15:39:08 +000065 int ordered_attributes; /* Return attributes as a list. */
66 int specified_attributes; /* Report only specified attributes. */
Fred Drakebd6101c2001-02-14 18:29:45 +000067 int in_callback; /* Is a callback active? */
Martin v. Löwis069dde22003-01-21 10:58:18 +000068 int ns_prefixes; /* Namespace-triplets mode? */
Fred Drake2a3d7db2002-06-28 22:56:48 +000069 XML_Char *buffer; /* Buffer used when accumulating characters */
70 /* NULL if not enabled */
71 int buffer_size; /* Size of buffer, in XML_Char units */
72 int buffer_used; /* Buffer units in use */
Fred Drakeb91a36b2002-06-27 19:40:48 +000073 PyObject *intern; /* Dictionary to intern strings */
Fred Drake0582df92000-07-12 04:49:00 +000074 PyObject **handlers;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +000075} xmlparseobject;
76
Fred Drake2a3d7db2002-06-28 22:56:48 +000077#define CHARACTER_DATA_BUFFER_SIZE 8192
78
Jeremy Hylton938ace62002-07-17 16:30:39 +000079static PyTypeObject Xmlparsetype;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +000080
Fred Drake117ac852002-09-24 16:24:54 +000081typedef void (*xmlhandlersetter)(XML_Parser self, void *meth);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +000082typedef void* xmlhandler;
83
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +000084struct HandlerInfo {
Fred Drake0582df92000-07-12 04:49:00 +000085 const char *name;
86 xmlhandlersetter setter;
87 xmlhandler handler;
Martin v. Löwis0078f6c2001-01-21 10:18:10 +000088 PyCodeObject *tb_code;
Fred Drake71b63ff2002-06-28 22:29:01 +000089 PyObject *nameobj;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +000090};
91
Jeremy Hylton938ace62002-07-17 16:30:39 +000092static struct HandlerInfo handler_info[64];
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +000093
Fred Drakebd6101c2001-02-14 18:29:45 +000094/* Set an integer attribute on the error object; return true on success,
95 * false on an exception.
96 */
97static int
98set_error_attr(PyObject *err, char *name, int value)
99{
100 PyObject *v = PyInt_FromLong(value);
Fred Drake85d835f2001-02-08 15:39:08 +0000101
Neal Norwitz2f5e9902006-03-08 06:36:45 +0000102 if (v == NULL || PyObject_SetAttrString(err, name, v) == -1) {
103 Py_XDECREF(v);
Fred Drakebd6101c2001-02-14 18:29:45 +0000104 return 0;
105 }
Michael W. Hudson0bb84542004-08-03 11:31:31 +0000106 Py_DECREF(v);
Fred Drakebd6101c2001-02-14 18:29:45 +0000107 return 1;
108}
109
110/* Build and set an Expat exception, including positioning
111 * information. Always returns NULL.
112 */
Fred Drake85d835f2001-02-08 15:39:08 +0000113static PyObject *
Martin v. Löwis069dde22003-01-21 10:58:18 +0000114set_error(xmlparseobject *self, enum XML_Error code)
Fred Drake85d835f2001-02-08 15:39:08 +0000115{
116 PyObject *err;
117 char buffer[256];
118 XML_Parser parser = self->itself;
Fred Drakebd6101c2001-02-14 18:29:45 +0000119 int lineno = XML_GetErrorLineNumber(parser);
120 int column = XML_GetErrorColumnNumber(parser);
Fred Drake85d835f2001-02-08 15:39:08 +0000121
Martin v. Löwis6b2cf0e2002-06-30 06:03:35 +0000122 /* There is no risk of overflowing this buffer, since
123 even for 64-bit integers, there is sufficient space. */
124 sprintf(buffer, "%.200s: line %i, column %i",
Fred Drakebd6101c2001-02-14 18:29:45 +0000125 XML_ErrorString(code), lineno, column);
Fred Drake85d835f2001-02-08 15:39:08 +0000126 err = PyObject_CallFunction(ErrorObject, "s", buffer);
Fred Drakebd6101c2001-02-14 18:29:45 +0000127 if ( err != NULL
128 && set_error_attr(err, "code", code)
129 && set_error_attr(err, "offset", column)
130 && set_error_attr(err, "lineno", lineno)) {
131 PyErr_SetObject(ErrorObject, err);
Fred Drake85d835f2001-02-08 15:39:08 +0000132 }
Neal Norwitz2f5e9902006-03-08 06:36:45 +0000133 Py_XDECREF(err);
Fred Drake85d835f2001-02-08 15:39:08 +0000134 return NULL;
135}
136
Fred Drake71b63ff2002-06-28 22:29:01 +0000137static int
138have_handler(xmlparseobject *self, int type)
139{
140 PyObject *handler = self->handlers[type];
141 return handler != NULL;
142}
143
144static PyObject *
145get_handler_name(struct HandlerInfo *hinfo)
146{
147 PyObject *name = hinfo->nameobj;
148 if (name == NULL) {
Neal Norwitz392c5be2007-08-25 17:20:32 +0000149 name = PyUnicode_FromString(hinfo->name);
Fred Drake71b63ff2002-06-28 22:29:01 +0000150 hinfo->nameobj = name;
151 }
152 Py_XINCREF(name);
153 return name;
154}
155
Fred Drake85d835f2001-02-08 15:39:08 +0000156
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +0000157/* Convert a string of XML_Chars into a Unicode string.
158 Returns None if str is a null pointer. */
159
Fred Drake0582df92000-07-12 04:49:00 +0000160static PyObject *
Fred Drakeb91a36b2002-06-27 19:40:48 +0000161conv_string_to_unicode(const XML_Char *str)
Fred Drake0582df92000-07-12 04:49:00 +0000162{
Fred Drake71b63ff2002-06-28 22:29:01 +0000163 /* XXX currently this code assumes that XML_Char is 8-bit,
Fred Drake0582df92000-07-12 04:49:00 +0000164 and hence in UTF-8. */
165 /* UTF-8 from Expat, Unicode desired */
166 if (str == NULL) {
167 Py_INCREF(Py_None);
168 return Py_None;
169 }
Fred Drake71b63ff2002-06-28 22:29:01 +0000170 return PyUnicode_DecodeUTF8(str, strlen(str), "strict");
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +0000171}
172
Fred Drake0582df92000-07-12 04:49:00 +0000173static PyObject *
174conv_string_len_to_unicode(const XML_Char *str, int len)
175{
Fred Drake71b63ff2002-06-28 22:29:01 +0000176 /* XXX currently this code assumes that XML_Char is 8-bit,
Fred Drake0582df92000-07-12 04:49:00 +0000177 and hence in UTF-8. */
178 /* UTF-8 from Expat, Unicode desired */
179 if (str == NULL) {
180 Py_INCREF(Py_None);
181 return Py_None;
182 }
Fred Drake6f987622000-08-25 18:03:30 +0000183 return PyUnicode_DecodeUTF8((const char *)str, len, "strict");
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +0000184}
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +0000185
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000186/* Callback routines */
187
Martin v. Löwis5b68ce32001-10-21 08:53:52 +0000188static void clear_handlers(xmlparseobject *self, int initial);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000189
Martin v. Löwis069dde22003-01-21 10:58:18 +0000190/* This handler is used when an error has been detected, in the hope
191 that actual parsing can be terminated early. This will only help
192 if an external entity reference is encountered. */
193static int
194error_external_entity_ref_handler(XML_Parser parser,
195 const XML_Char *context,
196 const XML_Char *base,
197 const XML_Char *systemId,
198 const XML_Char *publicId)
199{
200 return 0;
201}
202
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000203/* Dummy character data handler used when an error (exception) has
204 been detected, and the actual parsing can be terminated early.
205 This is needed since character data handler can't be safely removed
206 from within the character data handler, but can be replaced. It is
207 used only from the character data handler trampoline, and must be
208 used right after `flag_error()` is called. */
209static void
210noop_character_data_handler(void *userData, const XML_Char *data, int len)
211{
212 /* Do nothing. */
213}
214
Fred Drake6f987622000-08-25 18:03:30 +0000215static void
216flag_error(xmlparseobject *self)
217{
Martin v. Löwis5b68ce32001-10-21 08:53:52 +0000218 clear_handlers(self, 0);
Martin v. Löwis069dde22003-01-21 10:58:18 +0000219 XML_SetExternalEntityRefHandler(self->itself,
220 error_external_entity_ref_handler);
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000221}
222
223static PyCodeObject*
224getcode(enum HandlerTypes slot, char* func_name, int lineno)
225{
Fred Drakebd6101c2001-02-14 18:29:45 +0000226 PyObject *code = NULL;
227 PyObject *name = NULL;
228 PyObject *nulltuple = NULL;
229 PyObject *filename = NULL;
230
231 if (handler_info[slot].tb_code == NULL) {
232 code = PyString_FromString("");
233 if (code == NULL)
234 goto failed;
Guido van Rossum00bc0e02007-10-15 02:52:41 +0000235 name = PyUnicode_FromString(func_name);
Fred Drakebd6101c2001-02-14 18:29:45 +0000236 if (name == NULL)
237 goto failed;
238 nulltuple = PyTuple_New(0);
239 if (nulltuple == NULL)
240 goto failed;
Guido van Rossum00bc0e02007-10-15 02:52:41 +0000241 filename = PyUnicode_DecodeFSDefault(__FILE__);
Fred Drakebd6101c2001-02-14 18:29:45 +0000242 handler_info[slot].tb_code =
243 PyCode_New(0, /* argcount */
Guido van Rossum4f72a782006-10-27 23:31:49 +0000244 0, /* kwonlyargcount */
Fred Drakebd6101c2001-02-14 18:29:45 +0000245 0, /* nlocals */
246 0, /* stacksize */
247 0, /* flags */
248 code, /* code */
249 nulltuple, /* consts */
250 nulltuple, /* names */
251 nulltuple, /* varnames */
Martin v. Löwis76192ee2001-02-06 09:34:40 +0000252#if PYTHON_API_VERSION >= 1010
Fred Drakebd6101c2001-02-14 18:29:45 +0000253 nulltuple, /* freevars */
254 nulltuple, /* cellvars */
Martin v. Löwis76192ee2001-02-06 09:34:40 +0000255#endif
Fred Drakebd6101c2001-02-14 18:29:45 +0000256 filename, /* filename */
257 name, /* name */
258 lineno, /* firstlineno */
259 code /* lnotab */
260 );
261 if (handler_info[slot].tb_code == NULL)
262 goto failed;
263 Py_DECREF(code);
264 Py_DECREF(nulltuple);
265 Py_DECREF(filename);
266 Py_DECREF(name);
267 }
268 return handler_info[slot].tb_code;
269 failed:
270 Py_XDECREF(code);
271 Py_XDECREF(name);
272 return NULL;
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000273}
274
Jeremy Hylton9263f572003-06-27 16:13:17 +0000275#ifdef FIX_TRACE
Martin v. Löwis7d6e19d2002-08-04 08:24:49 +0000276static int
277trace_frame(PyThreadState *tstate, PyFrameObject *f, int code, PyObject *val)
278{
279 int result = 0;
280 if (!tstate->use_tracing || tstate->tracing)
281 return 0;
282 if (tstate->c_profilefunc != NULL) {
283 tstate->tracing++;
284 result = tstate->c_profilefunc(tstate->c_profileobj,
285 f, code , val);
286 tstate->use_tracing = ((tstate->c_tracefunc != NULL)
287 || (tstate->c_profilefunc != NULL));
288 tstate->tracing--;
289 if (result)
290 return result;
291 }
292 if (tstate->c_tracefunc != NULL) {
293 tstate->tracing++;
294 result = tstate->c_tracefunc(tstate->c_traceobj,
295 f, code , val);
296 tstate->use_tracing = ((tstate->c_tracefunc != NULL)
297 || (tstate->c_profilefunc != NULL));
298 tstate->tracing--;
299 }
300 return result;
301}
Jeremy Hylton9263f572003-06-27 16:13:17 +0000302
303static int
304trace_frame_exc(PyThreadState *tstate, PyFrameObject *f)
305{
306 PyObject *type, *value, *traceback, *arg;
307 int err;
308
309 if (tstate->c_tracefunc == NULL)
310 return 0;
311
312 PyErr_Fetch(&type, &value, &traceback);
313 if (value == NULL) {
314 value = Py_None;
315 Py_INCREF(value);
316 }
Martin v. Löwis9171f022004-10-13 19:50:11 +0000317#if PY_VERSION_HEX < 0x02040000
318 arg = Py_BuildValue("(OOO)", type, value, traceback);
319#else
Raymond Hettinger8ae46892003-10-12 19:09:37 +0000320 arg = PyTuple_Pack(3, type, value, traceback);
Martin v. Löwis9171f022004-10-13 19:50:11 +0000321#endif
Jeremy Hylton9263f572003-06-27 16:13:17 +0000322 if (arg == NULL) {
323 PyErr_Restore(type, value, traceback);
324 return 0;
325 }
326 err = trace_frame(tstate, f, PyTrace_EXCEPTION, arg);
327 Py_DECREF(arg);
328 if (err == 0)
329 PyErr_Restore(type, value, traceback);
330 else {
331 Py_XDECREF(type);
332 Py_XDECREF(value);
333 Py_XDECREF(traceback);
334 }
335 return err;
336}
Martin v. Löwis069dde22003-01-21 10:58:18 +0000337#endif
Martin v. Löwis7d6e19d2002-08-04 08:24:49 +0000338
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000339static PyObject*
Fred Drake39689c52004-08-13 03:12:57 +0000340call_with_frame(PyCodeObject *c, PyObject* func, PyObject* args,
341 xmlparseobject *self)
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000342{
Fred Drakebd6101c2001-02-14 18:29:45 +0000343 PyThreadState *tstate = PyThreadState_GET();
344 PyFrameObject *f;
345 PyObject *res;
346
347 if (c == NULL)
348 return NULL;
Martin v. Löwis7d6e19d2002-08-04 08:24:49 +0000349
Jeremy Hylton9263f572003-06-27 16:13:17 +0000350 f = PyFrame_New(tstate, c, PyEval_GetGlobals(), NULL);
Fred Drakebd6101c2001-02-14 18:29:45 +0000351 if (f == NULL)
352 return NULL;
353 tstate->frame = f;
Jeremy Hylton9263f572003-06-27 16:13:17 +0000354#ifdef FIX_TRACE
355 if (trace_frame(tstate, f, PyTrace_CALL, Py_None) < 0) {
Martin v. Löwis7d6e19d2002-08-04 08:24:49 +0000356 return NULL;
357 }
Martin v. Löwis069dde22003-01-21 10:58:18 +0000358#endif
Fred Drakebd6101c2001-02-14 18:29:45 +0000359 res = PyEval_CallObject(func, args);
Jeremy Hylton9263f572003-06-27 16:13:17 +0000360 if (res == NULL) {
361 if (tstate->curexc_traceback == NULL)
362 PyTraceBack_Here(f);
Fred Drake39689c52004-08-13 03:12:57 +0000363 XML_StopParser(self->itself, XML_FALSE);
Jeremy Hylton9263f572003-06-27 16:13:17 +0000364#ifdef FIX_TRACE
365 if (trace_frame_exc(tstate, f) < 0) {
366 return NULL;
367 }
368 }
Martin v. Löwis7d6e19d2002-08-04 08:24:49 +0000369 else {
Jeremy Hylton9263f572003-06-27 16:13:17 +0000370 if (trace_frame(tstate, f, PyTrace_RETURN, res) < 0) {
Martin v. Löwis7d6e19d2002-08-04 08:24:49 +0000371 Py_XDECREF(res);
372 res = NULL;
373 }
374 }
Jeremy Hylton9263f572003-06-27 16:13:17 +0000375#else
376 }
Martin v. Löwis069dde22003-01-21 10:58:18 +0000377#endif
Fred Drakebd6101c2001-02-14 18:29:45 +0000378 tstate->frame = f->f_back;
379 Py_DECREF(f);
380 return res;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000381}
382
Fred Drakeb91a36b2002-06-27 19:40:48 +0000383static PyObject*
384string_intern(xmlparseobject *self, const char* str)
385{
Guido van Rossum4ca94712007-07-23 17:42:32 +0000386 PyObject *result = conv_string_to_unicode(str);
Fred Drakeb91a36b2002-06-27 19:40:48 +0000387 PyObject *value;
Neal Norwitz484d9a42005-09-30 04:46:49 +0000388 /* result can be NULL if the unicode conversion failed. */
389 if (!result)
390 return result;
Fred Drakeb91a36b2002-06-27 19:40:48 +0000391 if (!self->intern)
392 return result;
393 value = PyDict_GetItem(self->intern, result);
394 if (!value) {
395 if (PyDict_SetItem(self->intern, result, result) == 0)
396 return result;
397 else
398 return NULL;
399 }
400 Py_INCREF(value);
401 Py_DECREF(result);
402 return value;
403}
404
Fred Drake2a3d7db2002-06-28 22:56:48 +0000405/* Return 0 on success, -1 on exception.
406 * flag_error() will be called before return if needed.
407 */
408static int
409call_character_handler(xmlparseobject *self, const XML_Char *buffer, int len)
410{
411 PyObject *args;
412 PyObject *temp;
413
414 args = PyTuple_New(1);
415 if (args == NULL)
416 return -1;
Guido van Rossum4ca94712007-07-23 17:42:32 +0000417 temp = (conv_string_len_to_unicode(buffer, len));
Fred Drake2a3d7db2002-06-28 22:56:48 +0000418 if (temp == NULL) {
419 Py_DECREF(args);
420 flag_error(self);
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000421 XML_SetCharacterDataHandler(self->itself,
422 noop_character_data_handler);
Fred Drake2a3d7db2002-06-28 22:56:48 +0000423 return -1;
424 }
425 PyTuple_SET_ITEM(args, 0, temp);
426 /* temp is now a borrowed reference; consider it unused. */
427 self->in_callback = 1;
428 temp = call_with_frame(getcode(CharacterData, "CharacterData", __LINE__),
Fred Drake39689c52004-08-13 03:12:57 +0000429 self->handlers[CharacterData], args, self);
Fred Drake2a3d7db2002-06-28 22:56:48 +0000430 /* temp is an owned reference again, or NULL */
431 self->in_callback = 0;
432 Py_DECREF(args);
433 if (temp == NULL) {
434 flag_error(self);
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000435 XML_SetCharacterDataHandler(self->itself,
436 noop_character_data_handler);
Fred Drake2a3d7db2002-06-28 22:56:48 +0000437 return -1;
438 }
439 Py_DECREF(temp);
440 return 0;
441}
442
443static int
444flush_character_buffer(xmlparseobject *self)
445{
446 int rc;
447 if (self->buffer == NULL || self->buffer_used == 0)
448 return 0;
449 rc = call_character_handler(self, self->buffer, self->buffer_used);
450 self->buffer_used = 0;
451 return rc;
452}
453
454static void
455my_CharacterDataHandler(void *userData, const XML_Char *data, int len)
456{
457 xmlparseobject *self = (xmlparseobject *) userData;
458 if (self->buffer == NULL)
459 call_character_handler(self, data, len);
460 else {
461 if ((self->buffer_used + len) > self->buffer_size) {
462 if (flush_character_buffer(self) < 0)
463 return;
464 /* handler might have changed; drop the rest on the floor
465 * if there isn't a handler anymore
466 */
467 if (!have_handler(self, CharacterData))
468 return;
469 }
470 if (len > self->buffer_size) {
471 call_character_handler(self, data, len);
472 self->buffer_used = 0;
473 }
474 else {
475 memcpy(self->buffer + self->buffer_used,
476 data, len * sizeof(XML_Char));
477 self->buffer_used += len;
478 }
479 }
480}
481
Fred Drake85d835f2001-02-08 15:39:08 +0000482static void
483my_StartElementHandler(void *userData,
Fred Drake71b63ff2002-06-28 22:29:01 +0000484 const XML_Char *name, const XML_Char *atts[])
Fred Drake85d835f2001-02-08 15:39:08 +0000485{
486 xmlparseobject *self = (xmlparseobject *)userData;
487
Fred Drake71b63ff2002-06-28 22:29:01 +0000488 if (have_handler(self, StartElement)) {
Fred Drake85d835f2001-02-08 15:39:08 +0000489 PyObject *container, *rv, *args;
490 int i, max;
491
Fred Drake2a3d7db2002-06-28 22:56:48 +0000492 if (flush_character_buffer(self) < 0)
493 return;
Fred Drake85d835f2001-02-08 15:39:08 +0000494 /* Set max to the number of slots filled in atts[]; max/2 is
495 * the number of attributes we need to process.
496 */
497 if (self->specified_attributes) {
498 max = XML_GetSpecifiedAttributeCount(self->itself);
499 }
500 else {
501 max = 0;
502 while (atts[max] != NULL)
503 max += 2;
504 }
505 /* Build the container. */
506 if (self->ordered_attributes)
507 container = PyList_New(max);
508 else
509 container = PyDict_New();
510 if (container == NULL) {
511 flag_error(self);
512 return;
513 }
514 for (i = 0; i < max; i += 2) {
Fred Drakeb91a36b2002-06-27 19:40:48 +0000515 PyObject *n = string_intern(self, (XML_Char *) atts[i]);
Fred Drake85d835f2001-02-08 15:39:08 +0000516 PyObject *v;
517 if (n == NULL) {
518 flag_error(self);
519 Py_DECREF(container);
520 return;
521 }
Guido van Rossum4ca94712007-07-23 17:42:32 +0000522 v = conv_string_to_unicode((XML_Char *) atts[i+1]);
Fred Drake85d835f2001-02-08 15:39:08 +0000523 if (v == NULL) {
524 flag_error(self);
525 Py_DECREF(container);
526 Py_DECREF(n);
527 return;
528 }
529 if (self->ordered_attributes) {
530 PyList_SET_ITEM(container, i, n);
531 PyList_SET_ITEM(container, i+1, v);
532 }
533 else if (PyDict_SetItem(container, n, v)) {
534 flag_error(self);
535 Py_DECREF(n);
536 Py_DECREF(v);
537 return;
538 }
539 else {
540 Py_DECREF(n);
541 Py_DECREF(v);
542 }
543 }
Neal Norwitz484d9a42005-09-30 04:46:49 +0000544 args = string_intern(self, name);
545 if (args != NULL)
546 args = Py_BuildValue("(NN)", args, container);
Fred Drake85d835f2001-02-08 15:39:08 +0000547 if (args == NULL) {
548 Py_DECREF(container);
549 return;
550 }
551 /* Container is now a borrowed reference; ignore it. */
Fred Drakebd6101c2001-02-14 18:29:45 +0000552 self->in_callback = 1;
553 rv = call_with_frame(getcode(StartElement, "StartElement", __LINE__),
Fred Drake39689c52004-08-13 03:12:57 +0000554 self->handlers[StartElement], args, self);
Fred Drakebd6101c2001-02-14 18:29:45 +0000555 self->in_callback = 0;
556 Py_DECREF(args);
Fred Drake85d835f2001-02-08 15:39:08 +0000557 if (rv == NULL) {
558 flag_error(self);
559 return;
Fred Drakebd6101c2001-02-14 18:29:45 +0000560 }
Fred Drake85d835f2001-02-08 15:39:08 +0000561 Py_DECREF(rv);
562 }
563}
564
565#define RC_HANDLER(RC, NAME, PARAMS, INIT, PARAM_FORMAT, CONVERSION, \
566 RETURN, GETUSERDATA) \
567static RC \
568my_##NAME##Handler PARAMS {\
569 xmlparseobject *self = GETUSERDATA ; \
570 PyObject *args = NULL; \
571 PyObject *rv = NULL; \
572 INIT \
573\
Fred Drake71b63ff2002-06-28 22:29:01 +0000574 if (have_handler(self, NAME)) { \
Fred Drake2a3d7db2002-06-28 22:56:48 +0000575 if (flush_character_buffer(self) < 0) \
576 return RETURN; \
Fred Drake85d835f2001-02-08 15:39:08 +0000577 args = Py_BuildValue PARAM_FORMAT ;\
Martin v. Löwis1d7c55f2001-11-10 13:57:55 +0000578 if (!args) { flag_error(self); return RETURN;} \
Fred Drakebd6101c2001-02-14 18:29:45 +0000579 self->in_callback = 1; \
Fred Drake85d835f2001-02-08 15:39:08 +0000580 rv = call_with_frame(getcode(NAME,#NAME,__LINE__), \
Fred Drake39689c52004-08-13 03:12:57 +0000581 self->handlers[NAME], args, self); \
Fred Drakebd6101c2001-02-14 18:29:45 +0000582 self->in_callback = 0; \
Fred Drake85d835f2001-02-08 15:39:08 +0000583 Py_DECREF(args); \
584 if (rv == NULL) { \
585 flag_error(self); \
586 return RETURN; \
587 } \
588 CONVERSION \
589 Py_DECREF(rv); \
590 } \
591 return RETURN; \
592}
593
Fred Drake6f987622000-08-25 18:03:30 +0000594#define VOID_HANDLER(NAME, PARAMS, PARAM_FORMAT) \
595 RC_HANDLER(void, NAME, PARAMS, ;, PARAM_FORMAT, ;, ;,\
596 (xmlparseobject *)userData)
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000597
Fred Drake6f987622000-08-25 18:03:30 +0000598#define INT_HANDLER(NAME, PARAMS, PARAM_FORMAT)\
599 RC_HANDLER(int, NAME, PARAMS, int rc=0;, PARAM_FORMAT, \
600 rc = PyInt_AsLong(rv);, rc, \
601 (xmlparseobject *)userData)
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000602
Fred Drake71b63ff2002-06-28 22:29:01 +0000603VOID_HANDLER(EndElement,
604 (void *userData, const XML_Char *name),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000605 ("(N)", string_intern(self, name)))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000606
Fred Drake6f987622000-08-25 18:03:30 +0000607VOID_HANDLER(ProcessingInstruction,
Fred Drake71b63ff2002-06-28 22:29:01 +0000608 (void *userData,
609 const XML_Char *target,
Fred Drake85d835f2001-02-08 15:39:08 +0000610 const XML_Char *data),
Guido van Rossum4ca94712007-07-23 17:42:32 +0000611 ("(NO&)", string_intern(self, target), conv_string_to_unicode ,data))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000612
Fred Drake6f987622000-08-25 18:03:30 +0000613VOID_HANDLER(UnparsedEntityDecl,
Fred Drake71b63ff2002-06-28 22:29:01 +0000614 (void *userData,
Fred Drake85d835f2001-02-08 15:39:08 +0000615 const XML_Char *entityName,
616 const XML_Char *base,
617 const XML_Char *systemId,
618 const XML_Char *publicId,
619 const XML_Char *notationName),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000620 ("(NNNNN)",
Fred Drake71b63ff2002-06-28 22:29:01 +0000621 string_intern(self, entityName), string_intern(self, base),
622 string_intern(self, systemId), string_intern(self, publicId),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000623 string_intern(self, notationName)))
Fred Drake85d835f2001-02-08 15:39:08 +0000624
Fred Drake85d835f2001-02-08 15:39:08 +0000625VOID_HANDLER(EntityDecl,
626 (void *userData,
627 const XML_Char *entityName,
628 int is_parameter_entity,
629 const XML_Char *value,
630 int value_length,
631 const XML_Char *base,
632 const XML_Char *systemId,
633 const XML_Char *publicId,
634 const XML_Char *notationName),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000635 ("NiNNNNN",
636 string_intern(self, entityName), is_parameter_entity,
Guido van Rossum4ca94712007-07-23 17:42:32 +0000637 (conv_string_len_to_unicode(value, value_length)),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000638 string_intern(self, base), string_intern(self, systemId),
639 string_intern(self, publicId),
640 string_intern(self, notationName)))
Fred Drake85d835f2001-02-08 15:39:08 +0000641
642VOID_HANDLER(XmlDecl,
643 (void *userData,
644 const XML_Char *version,
645 const XML_Char *encoding,
646 int standalone),
647 ("(O&O&i)",
Guido van Rossum4ca94712007-07-23 17:42:32 +0000648 conv_string_to_unicode ,version, conv_string_to_unicode ,encoding,
Fred Drake85d835f2001-02-08 15:39:08 +0000649 standalone))
650
651static PyObject *
652conv_content_model(XML_Content * const model,
Fred Drakeb91a36b2002-06-27 19:40:48 +0000653 PyObject *(*conv_string)(const XML_Char *))
Fred Drake85d835f2001-02-08 15:39:08 +0000654{
655 PyObject *result = NULL;
656 PyObject *children = PyTuple_New(model->numchildren);
657 int i;
658
659 if (children != NULL) {
Tim Peters9544fc52001-07-28 09:36:36 +0000660 assert(model->numchildren < INT_MAX);
661 for (i = 0; i < (int)model->numchildren; ++i) {
Fred Drake85d835f2001-02-08 15:39:08 +0000662 PyObject *child = conv_content_model(&model->children[i],
663 conv_string);
664 if (child == NULL) {
665 Py_XDECREF(children);
666 return NULL;
667 }
668 PyTuple_SET_ITEM(children, i, child);
669 }
670 result = Py_BuildValue("(iiO&N)",
671 model->type, model->quant,
672 conv_string,model->name, children);
673 }
674 return result;
675}
676
Fred Drake06dd8cf2003-02-02 03:54:17 +0000677static void
678my_ElementDeclHandler(void *userData,
679 const XML_Char *name,
680 XML_Content *model)
Fred Drake85d835f2001-02-08 15:39:08 +0000681{
Fred Drake06dd8cf2003-02-02 03:54:17 +0000682 xmlparseobject *self = (xmlparseobject *)userData;
683 PyObject *args = NULL;
Fred Drake85d835f2001-02-08 15:39:08 +0000684
Fred Drake06dd8cf2003-02-02 03:54:17 +0000685 if (have_handler(self, ElementDecl)) {
686 PyObject *rv = NULL;
687 PyObject *modelobj, *nameobj;
688
689 if (flush_character_buffer(self) < 0)
690 goto finally;
Guido van Rossum4ca94712007-07-23 17:42:32 +0000691 modelobj = conv_content_model(model, (conv_string_to_unicode));
Fred Drake06dd8cf2003-02-02 03:54:17 +0000692 if (modelobj == NULL) {
693 flag_error(self);
694 goto finally;
695 }
696 nameobj = string_intern(self, name);
697 if (nameobj == NULL) {
698 Py_DECREF(modelobj);
699 flag_error(self);
700 goto finally;
701 }
Michael W. Hudson0bb84542004-08-03 11:31:31 +0000702 args = Py_BuildValue("NN", nameobj, modelobj);
Fred Drake06dd8cf2003-02-02 03:54:17 +0000703 if (args == NULL) {
704 Py_DECREF(modelobj);
705 flag_error(self);
706 goto finally;
707 }
708 self->in_callback = 1;
709 rv = call_with_frame(getcode(ElementDecl, "ElementDecl", __LINE__),
Fred Drake39689c52004-08-13 03:12:57 +0000710 self->handlers[ElementDecl], args, self);
Fred Drake06dd8cf2003-02-02 03:54:17 +0000711 self->in_callback = 0;
712 if (rv == NULL) {
713 flag_error(self);
714 goto finally;
715 }
716 Py_DECREF(rv);
717 }
718 finally:
719 Py_XDECREF(args);
720 XML_FreeContentModel(self->itself, model);
721 return;
722}
Fred Drake85d835f2001-02-08 15:39:08 +0000723
724VOID_HANDLER(AttlistDecl,
725 (void *userData,
726 const XML_Char *elname,
727 const XML_Char *attname,
728 const XML_Char *att_type,
729 const XML_Char *dflt,
730 int isrequired),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000731 ("(NNO&O&i)",
732 string_intern(self, elname), string_intern(self, attname),
Guido van Rossum4ca94712007-07-23 17:42:32 +0000733 conv_string_to_unicode ,att_type, conv_string_to_unicode ,dflt,
Fred Drake85d835f2001-02-08 15:39:08 +0000734 isrequired))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000735
Martin v. Löwisc847f402003-01-21 11:09:21 +0000736#if XML_COMBINED_VERSION >= 19504
Martin v. Löwis069dde22003-01-21 10:58:18 +0000737VOID_HANDLER(SkippedEntity,
738 (void *userData,
739 const XML_Char *entityName,
740 int is_parameter_entity),
741 ("Ni",
742 string_intern(self, entityName), is_parameter_entity))
Martin v. Löwisc847f402003-01-21 11:09:21 +0000743#endif
Martin v. Löwis069dde22003-01-21 10:58:18 +0000744
Fred Drake71b63ff2002-06-28 22:29:01 +0000745VOID_HANDLER(NotationDecl,
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +0000746 (void *userData,
747 const XML_Char *notationName,
748 const XML_Char *base,
749 const XML_Char *systemId,
750 const XML_Char *publicId),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000751 ("(NNNN)",
Fred Drake71b63ff2002-06-28 22:29:01 +0000752 string_intern(self, notationName), string_intern(self, base),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000753 string_intern(self, systemId), string_intern(self, publicId)))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000754
Fred Drake6f987622000-08-25 18:03:30 +0000755VOID_HANDLER(StartNamespaceDecl,
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +0000756 (void *userData,
757 const XML_Char *prefix,
758 const XML_Char *uri),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000759 ("(NN)",
760 string_intern(self, prefix), string_intern(self, uri)))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000761
Fred Drake6f987622000-08-25 18:03:30 +0000762VOID_HANDLER(EndNamespaceDecl,
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +0000763 (void *userData,
764 const XML_Char *prefix),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000765 ("(N)", string_intern(self, prefix)))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000766
Fred Drake6f987622000-08-25 18:03:30 +0000767VOID_HANDLER(Comment,
Fred Drakeb91a36b2002-06-27 19:40:48 +0000768 (void *userData, const XML_Char *data),
Guido van Rossum4ca94712007-07-23 17:42:32 +0000769 ("(O&)", conv_string_to_unicode ,data))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000770
Fred Drake6f987622000-08-25 18:03:30 +0000771VOID_HANDLER(StartCdataSection,
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000772 (void *userData),
Fred Drake6f987622000-08-25 18:03:30 +0000773 ("()"))
Fred Drake71b63ff2002-06-28 22:29:01 +0000774
Fred Drake6f987622000-08-25 18:03:30 +0000775VOID_HANDLER(EndCdataSection,
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000776 (void *userData),
Fred Drake6f987622000-08-25 18:03:30 +0000777 ("()"))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000778
Fred Drake6f987622000-08-25 18:03:30 +0000779VOID_HANDLER(Default,
Fred Drake71b63ff2002-06-28 22:29:01 +0000780 (void *userData, const XML_Char *s, int len),
Guido van Rossum4ca94712007-07-23 17:42:32 +0000781 ("(N)", (conv_string_len_to_unicode(s,len))))
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +0000782
Fred Drake6f987622000-08-25 18:03:30 +0000783VOID_HANDLER(DefaultHandlerExpand,
Fred Drake71b63ff2002-06-28 22:29:01 +0000784 (void *userData, const XML_Char *s, int len),
Guido van Rossum4ca94712007-07-23 17:42:32 +0000785 ("(N)", (conv_string_len_to_unicode(s,len))))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000786
Fred Drake71b63ff2002-06-28 22:29:01 +0000787INT_HANDLER(NotStandalone,
788 (void *userData),
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +0000789 ("()"))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000790
Fred Drake6f987622000-08-25 18:03:30 +0000791RC_HANDLER(int, ExternalEntityRef,
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +0000792 (XML_Parser parser,
793 const XML_Char *context,
794 const XML_Char *base,
795 const XML_Char *systemId,
796 const XML_Char *publicId),
797 int rc=0;,
Fred Drakeb91a36b2002-06-27 19:40:48 +0000798 ("(O&NNN)",
Guido van Rossum4ca94712007-07-23 17:42:32 +0000799 conv_string_to_unicode ,context, string_intern(self, base),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000800 string_intern(self, systemId), string_intern(self, publicId)),
Fred Drake6f987622000-08-25 18:03:30 +0000801 rc = PyInt_AsLong(rv);, rc,
802 XML_GetUserData(parser))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000803
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000804/* XXX UnknownEncodingHandler */
805
Fred Drake85d835f2001-02-08 15:39:08 +0000806VOID_HANDLER(StartDoctypeDecl,
807 (void *userData, const XML_Char *doctypeName,
808 const XML_Char *sysid, const XML_Char *pubid,
809 int has_internal_subset),
Fred Drakeb91a36b2002-06-27 19:40:48 +0000810 ("(NNNi)", string_intern(self, doctypeName),
811 string_intern(self, sysid), string_intern(self, pubid),
Fred Drake85d835f2001-02-08 15:39:08 +0000812 has_internal_subset))
Martin v. Löwis0078f6c2001-01-21 10:18:10 +0000813
814VOID_HANDLER(EndDoctypeDecl, (void *userData), ("()"))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000815
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000816/* ---------------------------------------------------------------- */
817
Fred Drake71b63ff2002-06-28 22:29:01 +0000818static PyObject *
819get_parse_result(xmlparseobject *self, int rv)
820{
821 if (PyErr_Occurred()) {
822 return NULL;
823 }
824 if (rv == 0) {
Martin v. Löwis069dde22003-01-21 10:58:18 +0000825 return set_error(self, XML_GetErrorCode(self->itself));
Fred Drake71b63ff2002-06-28 22:29:01 +0000826 }
Fred Drake2a3d7db2002-06-28 22:56:48 +0000827 if (flush_character_buffer(self) < 0) {
828 return NULL;
829 }
Fred Drake71b63ff2002-06-28 22:29:01 +0000830 return PyInt_FromLong(rv);
831}
832
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000833PyDoc_STRVAR(xmlparse_Parse__doc__,
Thomas Wouters35317302000-07-22 16:34:15 +0000834"Parse(data[, isfinal])\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000835Parse XML data. `isfinal' should be true at end of input.");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000836
837static PyObject *
Fred Drake0582df92000-07-12 04:49:00 +0000838xmlparse_Parse(xmlparseobject *self, PyObject *args)
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000839{
Fred Drake0582df92000-07-12 04:49:00 +0000840 char *s;
841 int slen;
842 int isFinal = 0;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000843
Fred Drake0582df92000-07-12 04:49:00 +0000844 if (!PyArg_ParseTuple(args, "s#|i:Parse", &s, &slen, &isFinal))
845 return NULL;
Fred Drake71b63ff2002-06-28 22:29:01 +0000846
847 return get_parse_result(self, XML_Parse(self->itself, s, slen, isFinal));
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000848}
849
Fred Drakeca1f4262000-09-21 20:10:23 +0000850/* File reading copied from cPickle */
851
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000852#define BUF_SIZE 2048
853
Fred Drake0582df92000-07-12 04:49:00 +0000854static int
855readinst(char *buf, int buf_size, PyObject *meth)
856{
857 PyObject *arg = NULL;
858 PyObject *bytes = NULL;
859 PyObject *str = NULL;
860 int len = -1;
Guido van Rossum98297ee2007-11-06 21:34:58 +0000861 char *ptr;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000862
Fred Drake676940b2000-09-22 15:21:31 +0000863 if ((bytes = PyInt_FromLong(buf_size)) == NULL)
Fred Drake0582df92000-07-12 04:49:00 +0000864 goto finally;
Fred Drake676940b2000-09-22 15:21:31 +0000865
Fred Drake7b6caff2003-07-21 17:05:56 +0000866 if ((arg = PyTuple_New(1)) == NULL) {
867 Py_DECREF(bytes);
Fred Drake0582df92000-07-12 04:49:00 +0000868 goto finally;
Fred Drake7b6caff2003-07-21 17:05:56 +0000869 }
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000870
Tim Peters954eef72000-09-22 06:01:11 +0000871 PyTuple_SET_ITEM(arg, 0, bytes);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000872
Martin v. Löwis9171f022004-10-13 19:50:11 +0000873#if PY_VERSION_HEX < 0x02020000
874 str = PyObject_CallObject(meth, arg);
875#else
876 str = PyObject_Call(meth, arg, NULL);
877#endif
878 if (str == NULL)
Fred Drake0582df92000-07-12 04:49:00 +0000879 goto finally;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000880
Guido van Rossum98297ee2007-11-06 21:34:58 +0000881 if (PyString_Check(str))
882 ptr = PyString_AS_STRING(str);
883 else if (PyBytes_Check(str))
884 ptr = PyBytes_AS_STRING(str);
885 else {
Fred Drake71b63ff2002-06-28 22:29:01 +0000886 PyErr_Format(PyExc_TypeError,
Guido van Rossum4ca94712007-07-23 17:42:32 +0000887 "read() did not return a bytes object (type=%.400s)",
Martin v. Löwis9f2e3462007-07-21 17:22:18 +0000888 Py_Type(str)->tp_name);
Fred Drake0582df92000-07-12 04:49:00 +0000889 goto finally;
890 }
Guido van Rossum98297ee2007-11-06 21:34:58 +0000891 len = Py_Size(str);
Fred Drake0582df92000-07-12 04:49:00 +0000892 if (len > buf_size) {
893 PyErr_Format(PyExc_ValueError,
894 "read() returned too much data: "
895 "%i bytes requested, %i returned",
896 buf_size, len);
Fred Drake0582df92000-07-12 04:49:00 +0000897 goto finally;
898 }
Guido van Rossum98297ee2007-11-06 21:34:58 +0000899 memcpy(buf, ptr, len);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000900finally:
Fred Drake0582df92000-07-12 04:49:00 +0000901 Py_XDECREF(arg);
Fred Drakeca1f4262000-09-21 20:10:23 +0000902 Py_XDECREF(str);
Fred Drake0582df92000-07-12 04:49:00 +0000903 return len;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000904}
905
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000906PyDoc_STRVAR(xmlparse_ParseFile__doc__,
Thomas Wouters35317302000-07-22 16:34:15 +0000907"ParseFile(file)\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000908Parse XML data from file-like object.");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000909
910static PyObject *
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000911xmlparse_ParseFile(xmlparseobject *self, PyObject *f)
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000912{
Fred Drake0582df92000-07-12 04:49:00 +0000913 int rv = 1;
Fred Drake0582df92000-07-12 04:49:00 +0000914 FILE *fp;
915 PyObject *readmethod = NULL;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000916
Guido van Rossumda5b8f22007-06-12 23:30:11 +0000917 {
Fred Drake0582df92000-07-12 04:49:00 +0000918 fp = NULL;
Fred Drakeca1f4262000-09-21 20:10:23 +0000919 readmethod = PyObject_GetAttrString(f, "read");
920 if (readmethod == NULL) {
Fred Drake0582df92000-07-12 04:49:00 +0000921 PyErr_Clear();
Fred Drake71b63ff2002-06-28 22:29:01 +0000922 PyErr_SetString(PyExc_TypeError,
Fred Drake0582df92000-07-12 04:49:00 +0000923 "argument must have 'read' attribute");
Fred Drake814f9fe2002-07-19 22:03:03 +0000924 return NULL;
Fred Drake0582df92000-07-12 04:49:00 +0000925 }
926 }
927 for (;;) {
928 int bytes_read;
929 void *buf = XML_GetBuffer(self->itself, BUF_SIZE);
Fred Drake7b6caff2003-07-21 17:05:56 +0000930 if (buf == NULL) {
Fred Drakef239c6d2003-07-21 17:22:43 +0000931 Py_XDECREF(readmethod);
Fred Drake0582df92000-07-12 04:49:00 +0000932 return PyErr_NoMemory();
Fred Drake7b6caff2003-07-21 17:05:56 +0000933 }
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000934
Fred Drake0582df92000-07-12 04:49:00 +0000935 if (fp) {
936 bytes_read = fread(buf, sizeof(char), BUF_SIZE, fp);
937 if (bytes_read < 0) {
938 PyErr_SetFromErrno(PyExc_IOError);
939 return NULL;
940 }
941 }
942 else {
943 bytes_read = readinst(buf, BUF_SIZE, readmethod);
Fred Drake7b6caff2003-07-21 17:05:56 +0000944 if (bytes_read < 0) {
945 Py_DECREF(readmethod);
Fred Drake0582df92000-07-12 04:49:00 +0000946 return NULL;
Fred Drake7b6caff2003-07-21 17:05:56 +0000947 }
Fred Drake0582df92000-07-12 04:49:00 +0000948 }
949 rv = XML_ParseBuffer(self->itself, bytes_read, bytes_read == 0);
Fred Drake7b6caff2003-07-21 17:05:56 +0000950 if (PyErr_Occurred()) {
951 Py_XDECREF(readmethod);
Fred Drake0582df92000-07-12 04:49:00 +0000952 return NULL;
Fred Drake7b6caff2003-07-21 17:05:56 +0000953 }
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000954
Fred Drake0582df92000-07-12 04:49:00 +0000955 if (!rv || bytes_read == 0)
956 break;
957 }
Fred Drake7b6caff2003-07-21 17:05:56 +0000958 Py_XDECREF(readmethod);
Fred Drake71b63ff2002-06-28 22:29:01 +0000959 return get_parse_result(self, rv);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000960}
961
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000962PyDoc_STRVAR(xmlparse_SetBase__doc__,
Thomas Wouters35317302000-07-22 16:34:15 +0000963"SetBase(base_url)\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000964Set the base URL for the parser.");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000965
966static PyObject *
Fred Drake0582df92000-07-12 04:49:00 +0000967xmlparse_SetBase(xmlparseobject *self, PyObject *args)
968{
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000969 char *base;
970
Fred Drake0582df92000-07-12 04:49:00 +0000971 if (!PyArg_ParseTuple(args, "s:SetBase", &base))
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000972 return NULL;
Fred Drake0582df92000-07-12 04:49:00 +0000973 if (!XML_SetBase(self->itself, base)) {
974 return PyErr_NoMemory();
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000975 }
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000976 Py_INCREF(Py_None);
977 return Py_None;
978}
979
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000980PyDoc_STRVAR(xmlparse_GetBase__doc__,
Thomas Wouters35317302000-07-22 16:34:15 +0000981"GetBase() -> url\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000982Return base URL string for the parser.");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000983
984static PyObject *
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000985xmlparse_GetBase(xmlparseobject *self, PyObject *unused)
Fred Drake0582df92000-07-12 04:49:00 +0000986{
Fred Drake0582df92000-07-12 04:49:00 +0000987 return Py_BuildValue("z", XML_GetBase(self->itself));
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +0000988}
989
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +0000990PyDoc_STRVAR(xmlparse_GetInputContext__doc__,
Fred Drakebd6101c2001-02-14 18:29:45 +0000991"GetInputContext() -> string\n\
992Return the untranslated text of the input that caused the current event.\n\
993If 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 +0000994for an element with many attributes), not all of the text may be available.");
Fred Drakebd6101c2001-02-14 18:29:45 +0000995
996static PyObject *
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000997xmlparse_GetInputContext(xmlparseobject *self, PyObject *unused)
Fred Drakebd6101c2001-02-14 18:29:45 +0000998{
Thomas Wouters4d70c3d2006-06-08 14:42:34 +0000999 if (self->in_callback) {
1000 int offset, size;
1001 const char *buffer
1002 = XML_GetInputContext(self->itself, &offset, &size);
Fred Drakebd6101c2001-02-14 18:29:45 +00001003
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001004 if (buffer != NULL)
Guido van Rossum98297ee2007-11-06 21:34:58 +00001005 return PyString_FromStringAndSize(buffer + offset,
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001006 size - offset);
1007 else
1008 Py_RETURN_NONE;
Fred Drakebd6101c2001-02-14 18:29:45 +00001009 }
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001010 else
1011 Py_RETURN_NONE;
Fred Drakebd6101c2001-02-14 18:29:45 +00001012}
Fred Drakebd6101c2001-02-14 18:29:45 +00001013
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001014PyDoc_STRVAR(xmlparse_ExternalEntityParserCreate__doc__,
Fred Drake2d4ac202001-01-03 15:36:25 +00001015"ExternalEntityParserCreate(context[, encoding])\n\
Tim Peters51dc9682000-09-24 22:12:45 +00001016Create a parser for parsing an external entity based on the\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001017information passed to the ExternalEntityRefHandler.");
Lars Gustäbel4a30a072000-09-24 20:50:52 +00001018
1019static PyObject *
1020xmlparse_ExternalEntityParserCreate(xmlparseobject *self, PyObject *args)
1021{
1022 char *context;
1023 char *encoding = NULL;
1024 xmlparseobject *new_parser;
1025 int i;
1026
Martin v. Löwisc57428d2001-09-19 09:55:09 +00001027 if (!PyArg_ParseTuple(args, "z|s:ExternalEntityParserCreate",
Fred Drakecde79132001-04-25 16:01:30 +00001028 &context, &encoding)) {
1029 return NULL;
Lars Gustäbel4a30a072000-09-24 20:50:52 +00001030 }
1031
Martin v. Löwis894258c2001-09-23 10:20:10 +00001032#ifndef Py_TPFLAGS_HAVE_GC
Martin v. Löwisb4fcf4d2002-06-30 06:40:55 +00001033 /* Python versions 2.0 and 2.1 */
Lars Gustäbel4a30a072000-09-24 20:50:52 +00001034 new_parser = PyObject_New(xmlparseobject, &Xmlparsetype);
Martin v. Löwis894258c2001-09-23 10:20:10 +00001035#else
1036 /* Python versions 2.2 and later */
1037 new_parser = PyObject_GC_New(xmlparseobject, &Xmlparsetype);
1038#endif
Fred Drake85d835f2001-02-08 15:39:08 +00001039
1040 if (new_parser == NULL)
1041 return NULL;
Fred Drake2a3d7db2002-06-28 22:56:48 +00001042 new_parser->buffer_size = self->buffer_size;
1043 new_parser->buffer_used = 0;
1044 if (self->buffer != NULL) {
1045 new_parser->buffer = malloc(new_parser->buffer_size);
1046 if (new_parser->buffer == NULL) {
Fred Drakeb28467b2002-07-02 15:44:36 +00001047#ifndef Py_TPFLAGS_HAVE_GC
1048 /* Code for versions 2.0 and 2.1 */
1049 PyObject_Del(new_parser);
1050#else
1051 /* Code for versions 2.2 and later. */
Fred Drake2a3d7db2002-06-28 22:56:48 +00001052 PyObject_GC_Del(new_parser);
Fred Drakeb28467b2002-07-02 15:44:36 +00001053#endif
Fred Drake2a3d7db2002-06-28 22:56:48 +00001054 return PyErr_NoMemory();
1055 }
1056 }
1057 else
1058 new_parser->buffer = NULL;
Fred Drake85d835f2001-02-08 15:39:08 +00001059 new_parser->ordered_attributes = self->ordered_attributes;
1060 new_parser->specified_attributes = self->specified_attributes;
Fred Drakebd6101c2001-02-14 18:29:45 +00001061 new_parser->in_callback = 0;
Martin v. Löwis069dde22003-01-21 10:58:18 +00001062 new_parser->ns_prefixes = self->ns_prefixes;
Lars Gustäbel4a30a072000-09-24 20:50:52 +00001063 new_parser->itself = XML_ExternalEntityParserCreate(self->itself, context,
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001064 encoding);
1065 new_parser->handlers = 0;
Fred Drakeb91a36b2002-06-27 19:40:48 +00001066 new_parser->intern = self->intern;
1067 Py_XINCREF(new_parser->intern);
Martin v. Löwis894258c2001-09-23 10:20:10 +00001068#ifdef Py_TPFLAGS_HAVE_GC
1069 PyObject_GC_Track(new_parser);
1070#else
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001071 PyObject_GC_Init(new_parser);
Martin v. Löwis894258c2001-09-23 10:20:10 +00001072#endif
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001073
1074 if (!new_parser->itself) {
Fred Drake85d835f2001-02-08 15:39:08 +00001075 Py_DECREF(new_parser);
1076 return PyErr_NoMemory();
Lars Gustäbel4a30a072000-09-24 20:50:52 +00001077 }
1078
1079 XML_SetUserData(new_parser->itself, (void *)new_parser);
1080
1081 /* allocate and clear handlers first */
Fred Drake2a3d7db2002-06-28 22:56:48 +00001082 for (i = 0; handler_info[i].name != NULL; i++)
Fred Drake85d835f2001-02-08 15:39:08 +00001083 /* do nothing */;
Lars Gustäbel4a30a072000-09-24 20:50:52 +00001084
Fred Drake2a3d7db2002-06-28 22:56:48 +00001085 new_parser->handlers = malloc(sizeof(PyObject *) * i);
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001086 if (!new_parser->handlers) {
Fred Drake85d835f2001-02-08 15:39:08 +00001087 Py_DECREF(new_parser);
1088 return PyErr_NoMemory();
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001089 }
Martin v. Löwis5b68ce32001-10-21 08:53:52 +00001090 clear_handlers(new_parser, 1);
Lars Gustäbel4a30a072000-09-24 20:50:52 +00001091
1092 /* then copy handlers from self */
1093 for (i = 0; handler_info[i].name != NULL; i++) {
Fred Drake71b63ff2002-06-28 22:29:01 +00001094 PyObject *handler = self->handlers[i];
1095 if (handler != NULL) {
1096 Py_INCREF(handler);
1097 new_parser->handlers[i] = handler;
1098 handler_info[i].setter(new_parser->itself,
Fred Drake85d835f2001-02-08 15:39:08 +00001099 handler_info[i].handler);
1100 }
Lars Gustäbel4a30a072000-09-24 20:50:52 +00001101 }
Fred Drake71b63ff2002-06-28 22:29:01 +00001102 return (PyObject *)new_parser;
Lars Gustäbel4a30a072000-09-24 20:50:52 +00001103}
1104
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001105PyDoc_STRVAR(xmlparse_SetParamEntityParsing__doc__,
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001106"SetParamEntityParsing(flag) -> success\n\
1107Controls parsing of parameter entities (including the external DTD\n\
1108subset). Possible flag values are XML_PARAM_ENTITY_PARSING_NEVER,\n\
1109XML_PARAM_ENTITY_PARSING_UNLESS_STANDALONE and\n\
1110XML_PARAM_ENTITY_PARSING_ALWAYS. Returns true if setting the flag\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001111was successful.");
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001112
1113static PyObject*
Fred Drakebd6101c2001-02-14 18:29:45 +00001114xmlparse_SetParamEntityParsing(xmlparseobject *p, PyObject* args)
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001115{
Fred Drake85d835f2001-02-08 15:39:08 +00001116 int flag;
1117 if (!PyArg_ParseTuple(args, "i", &flag))
1118 return NULL;
Fred Drakebd6101c2001-02-14 18:29:45 +00001119 flag = XML_SetParamEntityParsing(p->itself, flag);
Fred Drake85d835f2001-02-08 15:39:08 +00001120 return PyInt_FromLong(flag);
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001121}
1122
Martin v. Löwisc847f402003-01-21 11:09:21 +00001123
1124#if XML_COMBINED_VERSION >= 19505
Martin v. Löwis069dde22003-01-21 10:58:18 +00001125PyDoc_STRVAR(xmlparse_UseForeignDTD__doc__,
1126"UseForeignDTD([flag])\n\
1127Allows the application to provide an artificial external subset if one is\n\
1128not specified as part of the document instance. This readily allows the\n\
1129use of a 'default' document type controlled by the application, while still\n\
1130getting the advantage of providing document type information to the parser.\n\
1131'flag' defaults to True if not provided.");
1132
1133static PyObject *
1134xmlparse_UseForeignDTD(xmlparseobject *self, PyObject *args)
1135{
1136 PyObject *flagobj = NULL;
1137 XML_Bool flag = XML_TRUE;
1138 enum XML_Error rc;
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001139 if (!PyArg_UnpackTuple(args, "UseForeignDTD", 0, 1, &flagobj))
Martin v. Löwis069dde22003-01-21 10:58:18 +00001140 return NULL;
1141 if (flagobj != NULL)
1142 flag = PyObject_IsTrue(flagobj) ? XML_TRUE : XML_FALSE;
1143 rc = XML_UseForeignDTD(self->itself, flag);
1144 if (rc != XML_ERROR_NONE) {
1145 return set_error(self, rc);
1146 }
1147 Py_INCREF(Py_None);
1148 return Py_None;
1149}
Martin v. Löwisc847f402003-01-21 11:09:21 +00001150#endif
Martin v. Löwis069dde22003-01-21 10:58:18 +00001151
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001152static struct PyMethodDef xmlparse_methods[] = {
Fred Drake0582df92000-07-12 04:49:00 +00001153 {"Parse", (PyCFunction)xmlparse_Parse,
Fred Drakebd6101c2001-02-14 18:29:45 +00001154 METH_VARARGS, xmlparse_Parse__doc__},
Fred Drake0582df92000-07-12 04:49:00 +00001155 {"ParseFile", (PyCFunction)xmlparse_ParseFile,
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001156 METH_O, xmlparse_ParseFile__doc__},
Fred Drake0582df92000-07-12 04:49:00 +00001157 {"SetBase", (PyCFunction)xmlparse_SetBase,
Martin v. Löwis069dde22003-01-21 10:58:18 +00001158 METH_VARARGS, xmlparse_SetBase__doc__},
Fred Drake0582df92000-07-12 04:49:00 +00001159 {"GetBase", (PyCFunction)xmlparse_GetBase,
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001160 METH_NOARGS, xmlparse_GetBase__doc__},
Lars Gustäbel4a30a072000-09-24 20:50:52 +00001161 {"ExternalEntityParserCreate", (PyCFunction)xmlparse_ExternalEntityParserCreate,
Martin v. Löwis069dde22003-01-21 10:58:18 +00001162 METH_VARARGS, xmlparse_ExternalEntityParserCreate__doc__},
Fred Drakebd6101c2001-02-14 18:29:45 +00001163 {"SetParamEntityParsing", (PyCFunction)xmlparse_SetParamEntityParsing,
1164 METH_VARARGS, xmlparse_SetParamEntityParsing__doc__},
Fred Drakebd6101c2001-02-14 18:29:45 +00001165 {"GetInputContext", (PyCFunction)xmlparse_GetInputContext,
Thomas Wouters4d70c3d2006-06-08 14:42:34 +00001166 METH_NOARGS, xmlparse_GetInputContext__doc__},
Martin v. Löwisc847f402003-01-21 11:09:21 +00001167#if XML_COMBINED_VERSION >= 19505
Martin v. Löwis069dde22003-01-21 10:58:18 +00001168 {"UseForeignDTD", (PyCFunction)xmlparse_UseForeignDTD,
1169 METH_VARARGS, xmlparse_UseForeignDTD__doc__},
Martin v. Löwisc847f402003-01-21 11:09:21 +00001170#endif
Martin v. Löwis069dde22003-01-21 10:58:18 +00001171 {NULL, NULL} /* sentinel */
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001172};
1173
1174/* ---------- */
1175
1176
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001177
Fred Drake71b63ff2002-06-28 22:29:01 +00001178/* pyexpat international encoding support.
1179 Make it as simple as possible.
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001180*/
1181
Martin v. Löwis3af7cc02001-01-22 08:19:10 +00001182static char template_buffer[257];
Fred Drakebb66a202001-03-01 20:48:17 +00001183PyObject *template_string = NULL;
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001184
Fred Drake71b63ff2002-06-28 22:29:01 +00001185static void
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001186init_template_buffer(void)
1187{
1188 int i;
Fred Drakebb66a202001-03-01 20:48:17 +00001189 for (i = 0; i < 256; i++) {
1190 template_buffer[i] = i;
Tim Peters63cb99e2001-02-17 18:12:50 +00001191 }
Fred Drakebb66a202001-03-01 20:48:17 +00001192 template_buffer[256] = 0;
Tim Peters63cb99e2001-02-17 18:12:50 +00001193}
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001194
Fred Drake71b63ff2002-06-28 22:29:01 +00001195static int
1196PyUnknownEncodingHandler(void *encodingHandlerData,
1197 const XML_Char *name,
1198 XML_Encoding *info)
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001199{
Fred Drakebb66a202001-03-01 20:48:17 +00001200 PyUnicodeObject *_u_string = NULL;
1201 int result = 0;
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001202 int i;
Fred Drake71b63ff2002-06-28 22:29:01 +00001203
Fred Drakebb66a202001-03-01 20:48:17 +00001204 /* Yes, supports only 8bit encodings */
1205 _u_string = (PyUnicodeObject *)
1206 PyUnicode_Decode(template_buffer, 256, name, "replace");
Fred Drake71b63ff2002-06-28 22:29:01 +00001207
Fred Drakebb66a202001-03-01 20:48:17 +00001208 if (_u_string == NULL)
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001209 return result;
Fred Drake71b63ff2002-06-28 22:29:01 +00001210
Fred Drakebb66a202001-03-01 20:48:17 +00001211 for (i = 0; i < 256; i++) {
1212 /* Stupid to access directly, but fast */
1213 Py_UNICODE c = _u_string->str[i];
1214 if (c == Py_UNICODE_REPLACEMENT_CHARACTER)
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001215 info->map[i] = -1;
Fred Drakebb66a202001-03-01 20:48:17 +00001216 else
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001217 info->map[i] = c;
Tim Peters63cb99e2001-02-17 18:12:50 +00001218 }
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001219 info->data = NULL;
1220 info->convert = NULL;
1221 info->release = NULL;
Fred Drake71b63ff2002-06-28 22:29:01 +00001222 result = 1;
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001223 Py_DECREF(_u_string);
1224 return result;
1225}
1226
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001227
1228static PyObject *
Fred Drakeb91a36b2002-06-27 19:40:48 +00001229newxmlparseobject(char *encoding, char *namespace_separator, PyObject *intern)
Fred Drake0582df92000-07-12 04:49:00 +00001230{
1231 int i;
1232 xmlparseobject *self;
Fred Drake71b63ff2002-06-28 22:29:01 +00001233
Martin v. Löwis894258c2001-09-23 10:20:10 +00001234#ifdef Py_TPFLAGS_HAVE_GC
1235 /* Code for versions 2.2 and later */
1236 self = PyObject_GC_New(xmlparseobject, &Xmlparsetype);
1237#else
Fred Drake0582df92000-07-12 04:49:00 +00001238 self = PyObject_New(xmlparseobject, &Xmlparsetype);
Martin v. Löwis894258c2001-09-23 10:20:10 +00001239#endif
Fred Drake0582df92000-07-12 04:49:00 +00001240 if (self == NULL)
1241 return NULL;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001242
Fred Drake2a3d7db2002-06-28 22:56:48 +00001243 self->buffer = NULL;
1244 self->buffer_size = CHARACTER_DATA_BUFFER_SIZE;
1245 self->buffer_used = 0;
Fred Drake85d835f2001-02-08 15:39:08 +00001246 self->ordered_attributes = 0;
1247 self->specified_attributes = 0;
Fred Drakebd6101c2001-02-14 18:29:45 +00001248 self->in_callback = 0;
Martin v. Löwis069dde22003-01-21 10:58:18 +00001249 self->ns_prefixes = 0;
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001250 self->handlers = NULL;
Fred Drakecde79132001-04-25 16:01:30 +00001251 if (namespace_separator != NULL) {
Fred Drake0582df92000-07-12 04:49:00 +00001252 self->itself = XML_ParserCreateNS(encoding, *namespace_separator);
1253 }
Fred Drake85d835f2001-02-08 15:39:08 +00001254 else {
Fred Drake0582df92000-07-12 04:49:00 +00001255 self->itself = XML_ParserCreate(encoding);
1256 }
Fred Drakeb91a36b2002-06-27 19:40:48 +00001257 self->intern = intern;
1258 Py_XINCREF(self->intern);
Martin v. Löwis894258c2001-09-23 10:20:10 +00001259#ifdef Py_TPFLAGS_HAVE_GC
1260 PyObject_GC_Track(self);
1261#else
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001262 PyObject_GC_Init(self);
Martin v. Löwis894258c2001-09-23 10:20:10 +00001263#endif
Fred Drake0582df92000-07-12 04:49:00 +00001264 if (self->itself == NULL) {
Fred Drake71b63ff2002-06-28 22:29:01 +00001265 PyErr_SetString(PyExc_RuntimeError,
Fred Drake0582df92000-07-12 04:49:00 +00001266 "XML_ParserCreate failed");
1267 Py_DECREF(self);
1268 return NULL;
1269 }
1270 XML_SetUserData(self->itself, (void *)self);
Fred Drake7c75bf22002-07-01 14:02:31 +00001271 XML_SetUnknownEncodingHandler(self->itself,
1272 (XML_UnknownEncodingHandler) PyUnknownEncodingHandler, NULL);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001273
Fred Drake2a3d7db2002-06-28 22:56:48 +00001274 for (i = 0; handler_info[i].name != NULL; i++)
Fred Drake0582df92000-07-12 04:49:00 +00001275 /* do nothing */;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001276
Fred Drake7c75bf22002-07-01 14:02:31 +00001277 self->handlers = malloc(sizeof(PyObject *) * i);
1278 if (!self->handlers) {
Fred Drake71b63ff2002-06-28 22:29:01 +00001279 Py_DECREF(self);
1280 return PyErr_NoMemory();
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001281 }
Martin v. Löwis5b68ce32001-10-21 08:53:52 +00001282 clear_handlers(self, 1);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001283
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001284 return (PyObject*)self;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001285}
1286
1287
1288static void
Fred Drake0582df92000-07-12 04:49:00 +00001289xmlparse_dealloc(xmlparseobject *self)
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001290{
Fred Drake0582df92000-07-12 04:49:00 +00001291 int i;
Martin v. Löwis894258c2001-09-23 10:20:10 +00001292#ifdef Py_TPFLAGS_HAVE_GC
1293 PyObject_GC_UnTrack(self);
1294#else
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001295 PyObject_GC_Fini(self);
Martin v. Löwis894258c2001-09-23 10:20:10 +00001296#endif
Fred Drake85d835f2001-02-08 15:39:08 +00001297 if (self->itself != NULL)
Fred Drake0582df92000-07-12 04:49:00 +00001298 XML_ParserFree(self->itself);
1299 self->itself = NULL;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001300
Fred Drake85d835f2001-02-08 15:39:08 +00001301 if (self->handlers != NULL) {
Fred Drakecde79132001-04-25 16:01:30 +00001302 PyObject *temp;
Fred Drake85d835f2001-02-08 15:39:08 +00001303 for (i = 0; handler_info[i].name != NULL; i++) {
Fred Drakecde79132001-04-25 16:01:30 +00001304 temp = self->handlers[i];
1305 self->handlers[i] = NULL;
1306 Py_XDECREF(temp);
Fred Drake85d835f2001-02-08 15:39:08 +00001307 }
1308 free(self->handlers);
Fred Drake71b63ff2002-06-28 22:29:01 +00001309 self->handlers = NULL;
Fred Drake0582df92000-07-12 04:49:00 +00001310 }
Fred Drake2a3d7db2002-06-28 22:56:48 +00001311 if (self->buffer != NULL) {
1312 free(self->buffer);
1313 self->buffer = NULL;
1314 }
Fred Drakeb91a36b2002-06-27 19:40:48 +00001315 Py_XDECREF(self->intern);
Martin v. Löwis894258c2001-09-23 10:20:10 +00001316#ifndef Py_TPFLAGS_HAVE_GC
Martin v. Löwisb4fcf4d2002-06-30 06:40:55 +00001317 /* Code for versions 2.0 and 2.1 */
Fred Drake0582df92000-07-12 04:49:00 +00001318 PyObject_Del(self);
Martin v. Löwis894258c2001-09-23 10:20:10 +00001319#else
1320 /* Code for versions 2.2 and later. */
1321 PyObject_GC_Del(self);
1322#endif
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001323}
1324
Fred Drake0582df92000-07-12 04:49:00 +00001325static int
1326handlername2int(const char *name)
1327{
1328 int i;
Fred Drake71b63ff2002-06-28 22:29:01 +00001329 for (i = 0; handler_info[i].name != NULL; i++) {
Fred Drake0582df92000-07-12 04:49:00 +00001330 if (strcmp(name, handler_info[i].name) == 0) {
1331 return i;
1332 }
1333 }
1334 return -1;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001335}
1336
1337static PyObject *
Fred Drake71b63ff2002-06-28 22:29:01 +00001338get_pybool(int istrue)
1339{
1340 PyObject *result = istrue ? Py_True : Py_False;
1341 Py_INCREF(result);
1342 return result;
1343}
1344
1345static PyObject *
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001346xmlparse_getattr(xmlparseobject *self, char *name)
1347{
Fred Drake71b63ff2002-06-28 22:29:01 +00001348 int handlernum = handlername2int(name);
1349
1350 if (handlernum != -1) {
1351 PyObject *result = self->handlers[handlernum];
1352 if (result == NULL)
1353 result = Py_None;
1354 Py_INCREF(result);
1355 return result;
1356 }
1357 if (name[0] == 'E') {
1358 if (strcmp(name, "ErrorCode") == 0)
1359 return PyInt_FromLong((long)
1360 XML_GetErrorCode(self->itself));
1361 if (strcmp(name, "ErrorLineNumber") == 0)
1362 return PyInt_FromLong((long)
1363 XML_GetErrorLineNumber(self->itself));
1364 if (strcmp(name, "ErrorColumnNumber") == 0)
1365 return PyInt_FromLong((long)
1366 XML_GetErrorColumnNumber(self->itself));
1367 if (strcmp(name, "ErrorByteIndex") == 0)
1368 return PyInt_FromLong((long)
1369 XML_GetErrorByteIndex(self->itself));
1370 }
Dave Cole3203efb2004-08-26 00:37:31 +00001371 if (name[0] == 'C') {
1372 if (strcmp(name, "CurrentLineNumber") == 0)
1373 return PyInt_FromLong((long)
1374 XML_GetCurrentLineNumber(self->itself));
1375 if (strcmp(name, "CurrentColumnNumber") == 0)
1376 return PyInt_FromLong((long)
1377 XML_GetCurrentColumnNumber(self->itself));
1378 if (strcmp(name, "CurrentByteIndex") == 0)
1379 return PyInt_FromLong((long)
1380 XML_GetCurrentByteIndex(self->itself));
1381 }
Fred Drake2a3d7db2002-06-28 22:56:48 +00001382 if (name[0] == 'b') {
1383 if (strcmp(name, "buffer_size") == 0)
1384 return PyInt_FromLong((long) self->buffer_size);
1385 if (strcmp(name, "buffer_text") == 0)
1386 return get_pybool(self->buffer != NULL);
1387 if (strcmp(name, "buffer_used") == 0)
1388 return PyInt_FromLong((long) self->buffer_used);
1389 }
Martin v. Löwis069dde22003-01-21 10:58:18 +00001390 if (strcmp(name, "namespace_prefixes") == 0)
1391 return get_pybool(self->ns_prefixes);
Fred Drake85d835f2001-02-08 15:39:08 +00001392 if (strcmp(name, "ordered_attributes") == 0)
Fred Drake71b63ff2002-06-28 22:29:01 +00001393 return get_pybool(self->ordered_attributes);
Fred Drake85d835f2001-02-08 15:39:08 +00001394 if (strcmp(name, "specified_attributes") == 0)
Fred Drake71b63ff2002-06-28 22:29:01 +00001395 return get_pybool((long) self->specified_attributes);
Fred Drakeb91a36b2002-06-27 19:40:48 +00001396 if (strcmp(name, "intern") == 0) {
1397 if (self->intern == NULL) {
1398 Py_INCREF(Py_None);
1399 return Py_None;
1400 }
1401 else {
1402 Py_INCREF(self->intern);
1403 return self->intern;
1404 }
1405 }
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001406
Neal Norwitz8dfc4a92007-08-11 06:39:53 +00001407 return Py_FindMethod(xmlparse_methods, (PyObject *)self, name);
1408}
1409
1410static PyObject *
1411xmlparse_dir(PyObject *self, PyObject* noargs)
1412{
Neal Norwitzfa56e2d2003-01-19 15:40:09 +00001413#define APPEND(list, str) \
Martin v. Löwis069dde22003-01-21 10:58:18 +00001414 do { \
Neal Norwitz392c5be2007-08-25 17:20:32 +00001415 PyObject *o = PyUnicode_FromString(str); \
Martin v. Löwis069dde22003-01-21 10:58:18 +00001416 if (o != NULL) \
1417 PyList_Append(list, o); \
1418 Py_XDECREF(o); \
1419 } while (0)
Neal Norwitzfa56e2d2003-01-19 15:40:09 +00001420
Neal Norwitz8dfc4a92007-08-11 06:39:53 +00001421 int i;
1422 PyObject *rc = PyList_New(0);
1423 if (!rc)
1424 return NULL;
1425 for (i = 0; handler_info[i].name != NULL; i++) {
1426 PyObject *o = get_handler_name(&handler_info[i]);
1427 if (o != NULL)
1428 PyList_Append(rc, o);
1429 Py_XDECREF(o);
1430 }
1431 APPEND(rc, "ErrorCode");
1432 APPEND(rc, "ErrorLineNumber");
1433 APPEND(rc, "ErrorColumnNumber");
1434 APPEND(rc, "ErrorByteIndex");
1435 APPEND(rc, "CurrentLineNumber");
1436 APPEND(rc, "CurrentColumnNumber");
1437 APPEND(rc, "CurrentByteIndex");
1438 APPEND(rc, "buffer_size");
1439 APPEND(rc, "buffer_text");
1440 APPEND(rc, "buffer_used");
1441 APPEND(rc, "namespace_prefixes");
1442 APPEND(rc, "ordered_attributes");
1443 APPEND(rc, "specified_attributes");
1444 APPEND(rc, "intern");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001445
Neal Norwitzfa56e2d2003-01-19 15:40:09 +00001446#undef APPEND
Neal Norwitz8dfc4a92007-08-11 06:39:53 +00001447
1448 if (PyErr_Occurred()) {
1449 Py_DECREF(rc);
1450 rc = NULL;
Fred Drake0582df92000-07-12 04:49:00 +00001451 }
Neal Norwitz8dfc4a92007-08-11 06:39:53 +00001452
1453 return rc;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001454}
1455
Fred Drake6f987622000-08-25 18:03:30 +00001456static int
1457sethandler(xmlparseobject *self, const char *name, PyObject* v)
Fred Drake0582df92000-07-12 04:49:00 +00001458{
1459 int handlernum = handlername2int(name);
Fred Drake71b63ff2002-06-28 22:29:01 +00001460 if (handlernum >= 0) {
1461 xmlhandler c_handler = NULL;
1462 PyObject *temp = self->handlers[handlernum];
1463
Thomas Wouters0e3f5912006-08-11 14:57:12 +00001464 if (v == Py_None) {
1465 /* If this is the character data handler, and a character
1466 data handler is already active, we need to be more
1467 careful. What we can safely do is replace the existing
1468 character data handler callback function with a no-op
1469 function that will refuse to call Python. The downside
1470 is that this doesn't completely remove the character
1471 data handler from the C layer if there's any callback
1472 active, so Expat does a little more work than it
1473 otherwise would, but that's really an odd case. A more
1474 elaborate system of handlers and state could remove the
1475 C handler more effectively. */
1476 if (handlernum == CharacterData && self->in_callback)
1477 c_handler = noop_character_data_handler;
Fred Drake71b63ff2002-06-28 22:29:01 +00001478 v = NULL;
Thomas Wouters0e3f5912006-08-11 14:57:12 +00001479 }
Fred Drake71b63ff2002-06-28 22:29:01 +00001480 else if (v != NULL) {
1481 Py_INCREF(v);
1482 c_handler = handler_info[handlernum].handler;
1483 }
Fred Drake0582df92000-07-12 04:49:00 +00001484 self->handlers[handlernum] = v;
Fred Drake71b63ff2002-06-28 22:29:01 +00001485 Py_XDECREF(temp);
1486 handler_info[handlernum].setter(self->itself, c_handler);
Fred Drake0582df92000-07-12 04:49:00 +00001487 return 1;
1488 }
1489 return 0;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001490}
1491
1492static int
Fred Drake6f987622000-08-25 18:03:30 +00001493xmlparse_setattr(xmlparseobject *self, char *name, PyObject *v)
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001494{
Fred Drake6f987622000-08-25 18:03:30 +00001495 /* Set attribute 'name' to value 'v'. v==NULL means delete */
Fred Drake85d835f2001-02-08 15:39:08 +00001496 if (v == NULL) {
Fred Drake6f987622000-08-25 18:03:30 +00001497 PyErr_SetString(PyExc_RuntimeError, "Cannot delete attribute");
1498 return -1;
1499 }
Fred Drake2a3d7db2002-06-28 22:56:48 +00001500 if (strcmp(name, "buffer_text") == 0) {
1501 if (PyObject_IsTrue(v)) {
1502 if (self->buffer == NULL) {
1503 self->buffer = malloc(self->buffer_size);
1504 if (self->buffer == NULL) {
1505 PyErr_NoMemory();
1506 return -1;
1507 }
1508 self->buffer_used = 0;
1509 }
1510 }
1511 else if (self->buffer != NULL) {
1512 if (flush_character_buffer(self) < 0)
1513 return -1;
1514 free(self->buffer);
1515 self->buffer = NULL;
1516 }
1517 return 0;
1518 }
Martin v. Löwis069dde22003-01-21 10:58:18 +00001519 if (strcmp(name, "namespace_prefixes") == 0) {
1520 if (PyObject_IsTrue(v))
1521 self->ns_prefixes = 1;
1522 else
1523 self->ns_prefixes = 0;
1524 XML_SetReturnNSTriplet(self->itself, self->ns_prefixes);
1525 return 0;
1526 }
Fred Drake85d835f2001-02-08 15:39:08 +00001527 if (strcmp(name, "ordered_attributes") == 0) {
1528 if (PyObject_IsTrue(v))
1529 self->ordered_attributes = 1;
1530 else
1531 self->ordered_attributes = 0;
1532 return 0;
1533 }
Fred Drake85d835f2001-02-08 15:39:08 +00001534 if (strcmp(name, "specified_attributes") == 0) {
1535 if (PyObject_IsTrue(v))
1536 self->specified_attributes = 1;
1537 else
1538 self->specified_attributes = 0;
Fred Drake6f987622000-08-25 18:03:30 +00001539 return 0;
1540 }
Fred Drake2a3d7db2002-06-28 22:56:48 +00001541 if (strcmp(name, "CharacterDataHandler") == 0) {
1542 /* If we're changing the character data handler, flush all
1543 * cached data with the old handler. Not sure there's a
1544 * "right" thing to do, though, but this probably won't
1545 * happen.
1546 */
1547 if (flush_character_buffer(self) < 0)
1548 return -1;
1549 }
Fred Drake6f987622000-08-25 18:03:30 +00001550 if (sethandler(self, name, v)) {
1551 return 0;
1552 }
1553 PyErr_SetString(PyExc_AttributeError, name);
1554 return -1;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001555}
1556
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001557static int
1558xmlparse_traverse(xmlparseobject *op, visitproc visit, void *arg)
1559{
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00001560 int i;
1561 for (i = 0; handler_info[i].name != NULL; i++)
1562 Py_VISIT(op->handlers[i]);
Fred Drakecde79132001-04-25 16:01:30 +00001563 return 0;
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001564}
1565
1566static int
1567xmlparse_clear(xmlparseobject *op)
1568{
Martin v. Löwis5b68ce32001-10-21 08:53:52 +00001569 clear_handlers(op, 0);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00001570 Py_CLEAR(op->intern);
Fred Drakecde79132001-04-25 16:01:30 +00001571 return 0;
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001572}
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001573
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001574PyDoc_STRVAR(Xmlparsetype__doc__, "XML parser");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001575
Neal Norwitz8dfc4a92007-08-11 06:39:53 +00001576static PyMethodDef xmlparse_tp_methods[] = {
1577 {"__dir__", xmlparse_dir, METH_NOARGS}
1578};
1579
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001580static PyTypeObject Xmlparsetype = {
Martin v. Löwis9f2e3462007-07-21 17:22:18 +00001581 PyVarObject_HEAD_INIT(NULL, 0)
Guido van Rossum14648392001-12-08 18:02:58 +00001582 "pyexpat.xmlparser", /*tp_name*/
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001583 sizeof(xmlparseobject) + PyGC_HEAD_SIZE,/*tp_basicsize*/
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +00001584 0, /*tp_itemsize*/
1585 /* methods */
1586 (destructor)xmlparse_dealloc, /*tp_dealloc*/
1587 (printfunc)0, /*tp_print*/
1588 (getattrfunc)xmlparse_getattr, /*tp_getattr*/
1589 (setattrfunc)xmlparse_setattr, /*tp_setattr*/
1590 (cmpfunc)0, /*tp_compare*/
1591 (reprfunc)0, /*tp_repr*/
1592 0, /*tp_as_number*/
1593 0, /*tp_as_sequence*/
1594 0, /*tp_as_mapping*/
1595 (hashfunc)0, /*tp_hash*/
1596 (ternaryfunc)0, /*tp_call*/
1597 (reprfunc)0, /*tp_str*/
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001598 0, /* tp_getattro */
1599 0, /* tp_setattro */
1600 0, /* tp_as_buffer */
Martin v. Löwis894258c2001-09-23 10:20:10 +00001601#ifdef Py_TPFLAGS_HAVE_GC
Fred Drake71b63ff2002-06-28 22:29:01 +00001602 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_HAVE_GC, /*tp_flags*/
Martin v. Löwis894258c2001-09-23 10:20:10 +00001603#else
Fred Drake71b63ff2002-06-28 22:29:01 +00001604 Py_TPFLAGS_DEFAULT | Py_TPFLAGS_GC, /*tp_flags*/
Martin v. Löwis894258c2001-09-23 10:20:10 +00001605#endif
Martin v. Löwis069dde22003-01-21 10:58:18 +00001606 Xmlparsetype__doc__, /* tp_doc - Documentation string */
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001607 (traverseproc)xmlparse_traverse, /* tp_traverse */
Neal Norwitz8dfc4a92007-08-11 06:39:53 +00001608 (inquiry)xmlparse_clear, /* tp_clear */
1609 0, /* tp_richcompare */
1610 0, /* tp_weaklistoffset */
1611 0, /* tp_iter */
1612 0, /* tp_iternext */
1613 xmlparse_tp_methods /* tp_methods */
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001614};
1615
1616/* End of code for xmlparser objects */
1617/* -------------------------------------------------------- */
1618
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001619PyDoc_STRVAR(pyexpat_ParserCreate__doc__,
Fred Drake0582df92000-07-12 04:49:00 +00001620"ParserCreate([encoding[, namespace_separator]]) -> parser\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001621Return a new XML parser object.");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001622
1623static PyObject *
Fred Drake0582df92000-07-12 04:49:00 +00001624pyexpat_ParserCreate(PyObject *notused, PyObject *args, PyObject *kw)
1625{
Fred Drakecde79132001-04-25 16:01:30 +00001626 char *encoding = NULL;
1627 char *namespace_separator = NULL;
Fred Drakeb91a36b2002-06-27 19:40:48 +00001628 PyObject *intern = NULL;
1629 PyObject *result;
1630 int intern_decref = 0;
Martin v. Löwis15e62742006-02-27 16:46:16 +00001631 static char *kwlist[] = {"encoding", "namespace_separator",
Jeremy Hyltonaf68c872005-12-10 18:50:16 +00001632 "intern", NULL};
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001633
Fred Drakeb91a36b2002-06-27 19:40:48 +00001634 if (!PyArg_ParseTupleAndKeywords(args, kw, "|zzO:ParserCreate", kwlist,
1635 &encoding, &namespace_separator, &intern))
Fred Drakecde79132001-04-25 16:01:30 +00001636 return NULL;
1637 if (namespace_separator != NULL
1638 && strlen(namespace_separator) > 1) {
1639 PyErr_SetString(PyExc_ValueError,
1640 "namespace_separator must be at most one"
1641 " character, omitted, or None");
1642 return NULL;
1643 }
Fred Drakeb91a36b2002-06-27 19:40:48 +00001644 /* Explicitly passing None means no interning is desired.
1645 Not passing anything means that a new dictionary is used. */
1646 if (intern == Py_None)
1647 intern = NULL;
1648 else if (intern == NULL) {
1649 intern = PyDict_New();
1650 if (!intern)
1651 return NULL;
1652 intern_decref = 1;
Fred Drake71b63ff2002-06-28 22:29:01 +00001653 }
Fred Drakeb91a36b2002-06-27 19:40:48 +00001654 else if (!PyDict_Check(intern)) {
1655 PyErr_SetString(PyExc_TypeError, "intern must be a dictionary");
1656 return NULL;
1657 }
1658
1659 result = newxmlparseobject(encoding, namespace_separator, intern);
1660 if (intern_decref) {
1661 Py_DECREF(intern);
1662 }
1663 return result;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001664}
1665
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001666PyDoc_STRVAR(pyexpat_ErrorString__doc__,
Fred Drake0582df92000-07-12 04:49:00 +00001667"ErrorString(errno) -> string\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001668Returns string error for given number.");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001669
1670static PyObject *
Fred Drake0582df92000-07-12 04:49:00 +00001671pyexpat_ErrorString(PyObject *self, PyObject *args)
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001672{
Fred Drake0582df92000-07-12 04:49:00 +00001673 long code = 0;
1674
1675 if (!PyArg_ParseTuple(args, "l:ErrorString", &code))
1676 return NULL;
1677 return Py_BuildValue("z", XML_ErrorString((int)code));
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001678}
1679
1680/* List of methods defined in the module */
1681
1682static struct PyMethodDef pyexpat_methods[] = {
Fred Drake0582df92000-07-12 04:49:00 +00001683 {"ParserCreate", (PyCFunction)pyexpat_ParserCreate,
1684 METH_VARARGS|METH_KEYWORDS, pyexpat_ParserCreate__doc__},
1685 {"ErrorString", (PyCFunction)pyexpat_ErrorString,
1686 METH_VARARGS, pyexpat_ErrorString__doc__},
Fred Drake71b63ff2002-06-28 22:29:01 +00001687
Fred Drake0582df92000-07-12 04:49:00 +00001688 {NULL, (PyCFunction)NULL, 0, NULL} /* sentinel */
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001689};
1690
Andrew M. Kuchlingbeba0562000-06-27 00:33:30 +00001691/* Module docstring */
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001692
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001693PyDoc_STRVAR(pyexpat_module_documentation,
1694"Python wrapper for Expat parser.");
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001695
Fred Drake4113b132001-03-24 19:58:26 +00001696/* Return a Python string that represents the version number without the
1697 * extra cruft added by revision control, even if the right options were
1698 * given to the "cvs export" command to make it not include the extra
1699 * cruft.
1700 */
1701static PyObject *
1702get_version_string(void)
1703{
1704 static char *rcsid = "$Revision$";
1705 char *rev = rcsid;
1706 int i = 0;
1707
Neal Norwitz30b5c5d2005-12-19 06:05:18 +00001708 while (!isdigit(Py_CHARMASK(*rev)))
Fred Drake4113b132001-03-24 19:58:26 +00001709 ++rev;
1710 while (rev[i] != ' ' && rev[i] != '\0')
1711 ++i;
1712
Neal Norwitz392c5be2007-08-25 17:20:32 +00001713 return PyUnicode_FromStringAndSize(rev, i);
Fred Drake4113b132001-03-24 19:58:26 +00001714}
1715
Fred Drakecde79132001-04-25 16:01:30 +00001716/* Initialization function for the module */
1717
1718#ifndef MODULE_NAME
1719#define MODULE_NAME "pyexpat"
1720#endif
1721
1722#ifndef MODULE_INITFUNC
1723#define MODULE_INITFUNC initpyexpat
1724#endif
1725
Martin v. Löwis069dde22003-01-21 10:58:18 +00001726#ifndef PyMODINIT_FUNC
1727# ifdef MS_WINDOWS
1728# define PyMODINIT_FUNC __declspec(dllexport) void
1729# else
1730# define PyMODINIT_FUNC void
1731# endif
1732#endif
1733
Mark Hammond8235ea12002-07-19 06:55:41 +00001734PyMODINIT_FUNC MODULE_INITFUNC(void); /* avoid compiler warnings */
Fred Drakecde79132001-04-25 16:01:30 +00001735
Martin v. Löwis069dde22003-01-21 10:58:18 +00001736PyMODINIT_FUNC
1737MODULE_INITFUNC(void)
Fred Drake0582df92000-07-12 04:49:00 +00001738{
1739 PyObject *m, *d;
Neal Norwitz392c5be2007-08-25 17:20:32 +00001740 PyObject *errmod_name = PyUnicode_FromString(MODULE_NAME ".errors");
Fred Drake85d835f2001-02-08 15:39:08 +00001741 PyObject *errors_module;
1742 PyObject *modelmod_name;
1743 PyObject *model_module;
Fred Drake0582df92000-07-12 04:49:00 +00001744 PyObject *sys_modules;
Fredrik Lundhd7a42882005-12-13 20:43:04 +00001745 static struct PyExpat_CAPI capi;
1746 PyObject* capi_object;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001747
Fred Drake6f987622000-08-25 18:03:30 +00001748 if (errmod_name == NULL)
1749 return;
Neal Norwitz392c5be2007-08-25 17:20:32 +00001750 modelmod_name = PyUnicode_FromString(MODULE_NAME ".model");
Fred Drake85d835f2001-02-08 15:39:08 +00001751 if (modelmod_name == NULL)
1752 return;
Fred Drake6f987622000-08-25 18:03:30 +00001753
Martin v. Löwis9f2e3462007-07-21 17:22:18 +00001754 Py_Type(&Xmlparsetype) = &PyType_Type;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001755
Fred Drake0582df92000-07-12 04:49:00 +00001756 /* Create the module and add the functions */
Fred Drakecde79132001-04-25 16:01:30 +00001757 m = Py_InitModule3(MODULE_NAME, pyexpat_methods,
Fred Drake85d835f2001-02-08 15:39:08 +00001758 pyexpat_module_documentation);
Neal Norwitz1ac754f2006-01-19 06:09:39 +00001759 if (m == NULL)
1760 return;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001761
Fred Drake0582df92000-07-12 04:49:00 +00001762 /* Add some symbolic constants to the module */
Fred Drakebd6101c2001-02-14 18:29:45 +00001763 if (ErrorObject == NULL) {
1764 ErrorObject = PyErr_NewException("xml.parsers.expat.ExpatError",
Fred Drake93adb692000-09-23 04:55:48 +00001765 NULL, NULL);
Fred Drakebd6101c2001-02-14 18:29:45 +00001766 if (ErrorObject == NULL)
1767 return;
1768 }
1769 Py_INCREF(ErrorObject);
Fred Drake93adb692000-09-23 04:55:48 +00001770 PyModule_AddObject(m, "error", ErrorObject);
Fred Drakebd6101c2001-02-14 18:29:45 +00001771 Py_INCREF(ErrorObject);
1772 PyModule_AddObject(m, "ExpatError", ErrorObject);
Fred Drake4ba298c2000-10-29 04:57:53 +00001773 Py_INCREF(&Xmlparsetype);
1774 PyModule_AddObject(m, "XMLParserType", (PyObject *) &Xmlparsetype);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001775
Fred Drake4113b132001-03-24 19:58:26 +00001776 PyModule_AddObject(m, "__version__", get_version_string());
Fred Drake738293d2000-12-21 17:25:07 +00001777 PyModule_AddStringConstant(m, "EXPAT_VERSION",
1778 (char *) XML_ExpatVersion());
Fred Drake85d835f2001-02-08 15:39:08 +00001779 {
1780 XML_Expat_Version info = XML_ExpatVersionInfo();
1781 PyModule_AddObject(m, "version_info",
1782 Py_BuildValue("(iii)", info.major,
1783 info.minor, info.micro));
1784 }
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001785 init_template_buffer();
Fred Drake0582df92000-07-12 04:49:00 +00001786 /* XXX When Expat supports some way of figuring out how it was
Fred Drake71b63ff2002-06-28 22:29:01 +00001787 compiled, this should check and set native_encoding
1788 appropriately.
Fred Drake0582df92000-07-12 04:49:00 +00001789 */
Fred Drake93adb692000-09-23 04:55:48 +00001790 PyModule_AddStringConstant(m, "native_encoding", "UTF-8");
Fred Drakec23b5232000-08-24 21:57:43 +00001791
Fred Drake85d835f2001-02-08 15:39:08 +00001792 sys_modules = PySys_GetObject("modules");
Fred Drake93adb692000-09-23 04:55:48 +00001793 d = PyModule_GetDict(m);
Fred Drake6f987622000-08-25 18:03:30 +00001794 errors_module = PyDict_GetItem(d, errmod_name);
1795 if (errors_module == NULL) {
Fred Drakecde79132001-04-25 16:01:30 +00001796 errors_module = PyModule_New(MODULE_NAME ".errors");
Fred Drake6f987622000-08-25 18:03:30 +00001797 if (errors_module != NULL) {
Fred Drake6f987622000-08-25 18:03:30 +00001798 PyDict_SetItem(sys_modules, errmod_name, errors_module);
Fred Drake93adb692000-09-23 04:55:48 +00001799 /* gives away the reference to errors_module */
1800 PyModule_AddObject(m, "errors", errors_module);
Fred Drakec23b5232000-08-24 21:57:43 +00001801 }
1802 }
Fred Drake6f987622000-08-25 18:03:30 +00001803 Py_DECREF(errmod_name);
Fred Drake85d835f2001-02-08 15:39:08 +00001804 model_module = PyDict_GetItem(d, modelmod_name);
1805 if (model_module == NULL) {
Fred Drakecde79132001-04-25 16:01:30 +00001806 model_module = PyModule_New(MODULE_NAME ".model");
Fred Drake85d835f2001-02-08 15:39:08 +00001807 if (model_module != NULL) {
1808 PyDict_SetItem(sys_modules, modelmod_name, model_module);
1809 /* gives away the reference to model_module */
1810 PyModule_AddObject(m, "model", model_module);
1811 }
1812 }
1813 Py_DECREF(modelmod_name);
1814 if (errors_module == NULL || model_module == NULL)
1815 /* Don't core dump later! */
Fred Drake6f987622000-08-25 18:03:30 +00001816 return;
Martin v. Löwis069dde22003-01-21 10:58:18 +00001817
Martin v. Löwisc847f402003-01-21 11:09:21 +00001818#if XML_COMBINED_VERSION > 19505
Martin v. Löwis069dde22003-01-21 10:58:18 +00001819 {
1820 const XML_Feature *features = XML_GetFeatureList();
1821 PyObject *list = PyList_New(0);
1822 if (list == NULL)
1823 /* just ignore it */
1824 PyErr_Clear();
1825 else {
1826 int i = 0;
1827 for (; features[i].feature != XML_FEATURE_END; ++i) {
1828 int ok;
1829 PyObject *item = Py_BuildValue("si", features[i].name,
1830 features[i].value);
1831 if (item == NULL) {
1832 Py_DECREF(list);
1833 list = NULL;
1834 break;
1835 }
1836 ok = PyList_Append(list, item);
1837 Py_DECREF(item);
1838 if (ok < 0) {
1839 PyErr_Clear();
1840 break;
1841 }
1842 }
1843 if (list != NULL)
1844 PyModule_AddObject(m, "features", list);
1845 }
1846 }
Martin v. Löwisc847f402003-01-21 11:09:21 +00001847#endif
Fred Drake6f987622000-08-25 18:03:30 +00001848
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001849#define MYCONST(name) \
Fred Drake93adb692000-09-23 04:55:48 +00001850 PyModule_AddStringConstant(errors_module, #name, \
1851 (char*)XML_ErrorString(name))
Fred Drake7bd9f412000-07-04 23:51:31 +00001852
Fred Drake0582df92000-07-12 04:49:00 +00001853 MYCONST(XML_ERROR_NO_MEMORY);
1854 MYCONST(XML_ERROR_SYNTAX);
1855 MYCONST(XML_ERROR_NO_ELEMENTS);
1856 MYCONST(XML_ERROR_INVALID_TOKEN);
1857 MYCONST(XML_ERROR_UNCLOSED_TOKEN);
1858 MYCONST(XML_ERROR_PARTIAL_CHAR);
1859 MYCONST(XML_ERROR_TAG_MISMATCH);
1860 MYCONST(XML_ERROR_DUPLICATE_ATTRIBUTE);
1861 MYCONST(XML_ERROR_JUNK_AFTER_DOC_ELEMENT);
1862 MYCONST(XML_ERROR_PARAM_ENTITY_REF);
1863 MYCONST(XML_ERROR_UNDEFINED_ENTITY);
1864 MYCONST(XML_ERROR_RECURSIVE_ENTITY_REF);
1865 MYCONST(XML_ERROR_ASYNC_ENTITY);
1866 MYCONST(XML_ERROR_BAD_CHAR_REF);
1867 MYCONST(XML_ERROR_BINARY_ENTITY_REF);
1868 MYCONST(XML_ERROR_ATTRIBUTE_EXTERNAL_ENTITY_REF);
1869 MYCONST(XML_ERROR_MISPLACED_XML_PI);
1870 MYCONST(XML_ERROR_UNKNOWN_ENCODING);
1871 MYCONST(XML_ERROR_INCORRECT_ENCODING);
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001872 MYCONST(XML_ERROR_UNCLOSED_CDATA_SECTION);
1873 MYCONST(XML_ERROR_EXTERNAL_ENTITY_HANDLING);
1874 MYCONST(XML_ERROR_NOT_STANDALONE);
Fred Drake283b6702004-08-04 22:28:16 +00001875 MYCONST(XML_ERROR_UNEXPECTED_STATE);
1876 MYCONST(XML_ERROR_ENTITY_DECLARED_IN_PE);
1877 MYCONST(XML_ERROR_FEATURE_REQUIRES_XML_DTD);
1878 MYCONST(XML_ERROR_CANT_CHANGE_FEATURE_ONCE_PARSING);
1879 /* Added in Expat 1.95.7. */
1880 MYCONST(XML_ERROR_UNBOUND_PREFIX);
1881 /* Added in Expat 1.95.8. */
1882 MYCONST(XML_ERROR_UNDECLARING_PREFIX);
1883 MYCONST(XML_ERROR_INCOMPLETE_PE);
1884 MYCONST(XML_ERROR_XML_DECL);
1885 MYCONST(XML_ERROR_TEXT_DECL);
1886 MYCONST(XML_ERROR_PUBLICID);
1887 MYCONST(XML_ERROR_SUSPENDED);
1888 MYCONST(XML_ERROR_NOT_SUSPENDED);
1889 MYCONST(XML_ERROR_ABORTED);
1890 MYCONST(XML_ERROR_FINISHED);
1891 MYCONST(XML_ERROR_SUSPEND_PE);
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001892
Fred Drake85d835f2001-02-08 15:39:08 +00001893 PyModule_AddStringConstant(errors_module, "__doc__",
1894 "Constants used to describe error conditions.");
1895
Fred Drake93adb692000-09-23 04:55:48 +00001896#undef MYCONST
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001897
Fred Drake85d835f2001-02-08 15:39:08 +00001898#define MYCONST(c) PyModule_AddIntConstant(m, #c, c)
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001899 MYCONST(XML_PARAM_ENTITY_PARSING_NEVER);
1900 MYCONST(XML_PARAM_ENTITY_PARSING_UNLESS_STANDALONE);
1901 MYCONST(XML_PARAM_ENTITY_PARSING_ALWAYS);
Fred Drake85d835f2001-02-08 15:39:08 +00001902#undef MYCONST
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001903
Fred Drake85d835f2001-02-08 15:39:08 +00001904#define MYCONST(c) PyModule_AddIntConstant(model_module, #c, c)
1905 PyModule_AddStringConstant(model_module, "__doc__",
1906 "Constants used to interpret content model information.");
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00001907
Fred Drake85d835f2001-02-08 15:39:08 +00001908 MYCONST(XML_CTYPE_EMPTY);
1909 MYCONST(XML_CTYPE_ANY);
1910 MYCONST(XML_CTYPE_MIXED);
1911 MYCONST(XML_CTYPE_NAME);
1912 MYCONST(XML_CTYPE_CHOICE);
1913 MYCONST(XML_CTYPE_SEQ);
1914
1915 MYCONST(XML_CQUANT_NONE);
1916 MYCONST(XML_CQUANT_OPT);
1917 MYCONST(XML_CQUANT_REP);
1918 MYCONST(XML_CQUANT_PLUS);
1919#undef MYCONST
Fredrik Lundhc3345042005-12-13 19:49:55 +00001920
1921 /* initialize pyexpat dispatch table */
Fredrik Lundhd7a42882005-12-13 20:43:04 +00001922 capi.size = sizeof(capi);
Fredrik Lundhcc117db2005-12-13 21:55:36 +00001923 capi.magic = PyExpat_CAPI_MAGIC;
Fredrik Lundhd7a42882005-12-13 20:43:04 +00001924 capi.MAJOR_VERSION = XML_MAJOR_VERSION;
1925 capi.MINOR_VERSION = XML_MINOR_VERSION;
1926 capi.MICRO_VERSION = XML_MICRO_VERSION;
1927 capi.ErrorString = XML_ErrorString;
Fredrik Lundhcc117db2005-12-13 21:55:36 +00001928 capi.GetErrorCode = XML_GetErrorCode;
1929 capi.GetErrorColumnNumber = XML_GetErrorColumnNumber;
1930 capi.GetErrorLineNumber = XML_GetErrorLineNumber;
Fredrik Lundhd7a42882005-12-13 20:43:04 +00001931 capi.Parse = XML_Parse;
1932 capi.ParserCreate_MM = XML_ParserCreate_MM;
1933 capi.ParserFree = XML_ParserFree;
1934 capi.SetCharacterDataHandler = XML_SetCharacterDataHandler;
1935 capi.SetCommentHandler = XML_SetCommentHandler;
1936 capi.SetDefaultHandlerExpand = XML_SetDefaultHandlerExpand;
1937 capi.SetElementHandler = XML_SetElementHandler;
1938 capi.SetNamespaceDeclHandler = XML_SetNamespaceDeclHandler;
1939 capi.SetProcessingInstructionHandler = XML_SetProcessingInstructionHandler;
1940 capi.SetUnknownEncodingHandler = XML_SetUnknownEncodingHandler;
1941 capi.SetUserData = XML_SetUserData;
Fredrik Lundhc3345042005-12-13 19:49:55 +00001942
1943 /* export as cobject */
Fredrik Lundhcc117db2005-12-13 21:55:36 +00001944 capi_object = PyCObject_FromVoidPtr(&capi, NULL);
Fredrik Lundhd7a42882005-12-13 20:43:04 +00001945 if (capi_object)
1946 PyModule_AddObject(m, "expat_CAPI", capi_object);
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001947}
1948
Fred Drake6f987622000-08-25 18:03:30 +00001949static void
Martin v. Löwis5b68ce32001-10-21 08:53:52 +00001950clear_handlers(xmlparseobject *self, int initial)
Fred Drake0582df92000-07-12 04:49:00 +00001951{
Fred Drakecde79132001-04-25 16:01:30 +00001952 int i = 0;
1953 PyObject *temp;
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001954
Fred Drake71b63ff2002-06-28 22:29:01 +00001955 for (; handler_info[i].name != NULL; i++) {
Martin v. Löwis5b68ce32001-10-21 08:53:52 +00001956 if (initial)
Fred Drake71b63ff2002-06-28 22:29:01 +00001957 self->handlers[i] = NULL;
Martin v. Löwis5b68ce32001-10-21 08:53:52 +00001958 else {
Fred Drakecde79132001-04-25 16:01:30 +00001959 temp = self->handlers[i];
1960 self->handlers[i] = NULL;
1961 Py_XDECREF(temp);
Martin v. Löwis5b68ce32001-10-21 08:53:52 +00001962 handler_info[i].setter(self->itself, NULL);
Fred Drakecde79132001-04-25 16:01:30 +00001963 }
Fred Drakecde79132001-04-25 16:01:30 +00001964 }
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00001965}
1966
Tim Peters0c322792002-07-17 16:49:03 +00001967static struct HandlerInfo handler_info[] = {
Fred Drake71b63ff2002-06-28 22:29:01 +00001968 {"StartElementHandler",
1969 (xmlhandlersetter)XML_SetStartElementHandler,
Fred Drake0582df92000-07-12 04:49:00 +00001970 (xmlhandler)my_StartElementHandler},
Fred Drake71b63ff2002-06-28 22:29:01 +00001971 {"EndElementHandler",
1972 (xmlhandlersetter)XML_SetEndElementHandler,
Fred Drake0582df92000-07-12 04:49:00 +00001973 (xmlhandler)my_EndElementHandler},
Fred Drake71b63ff2002-06-28 22:29:01 +00001974 {"ProcessingInstructionHandler",
Fred Drake0582df92000-07-12 04:49:00 +00001975 (xmlhandlersetter)XML_SetProcessingInstructionHandler,
1976 (xmlhandler)my_ProcessingInstructionHandler},
Fred Drake71b63ff2002-06-28 22:29:01 +00001977 {"CharacterDataHandler",
Fred Drake0582df92000-07-12 04:49:00 +00001978 (xmlhandlersetter)XML_SetCharacterDataHandler,
1979 (xmlhandler)my_CharacterDataHandler},
Fred Drake71b63ff2002-06-28 22:29:01 +00001980 {"UnparsedEntityDeclHandler",
Fred Drake0582df92000-07-12 04:49:00 +00001981 (xmlhandlersetter)XML_SetUnparsedEntityDeclHandler,
Fred Drake2a3d7db2002-06-28 22:56:48 +00001982 (xmlhandler)my_UnparsedEntityDeclHandler},
Fred Drake71b63ff2002-06-28 22:29:01 +00001983 {"NotationDeclHandler",
Fred Drake0582df92000-07-12 04:49:00 +00001984 (xmlhandlersetter)XML_SetNotationDeclHandler,
Fred Drake2a3d7db2002-06-28 22:56:48 +00001985 (xmlhandler)my_NotationDeclHandler},
Fred Drake71b63ff2002-06-28 22:29:01 +00001986 {"StartNamespaceDeclHandler",
1987 (xmlhandlersetter)XML_SetStartNamespaceDeclHandler,
Fred Drake2a3d7db2002-06-28 22:56:48 +00001988 (xmlhandler)my_StartNamespaceDeclHandler},
Fred Drake71b63ff2002-06-28 22:29:01 +00001989 {"EndNamespaceDeclHandler",
1990 (xmlhandlersetter)XML_SetEndNamespaceDeclHandler,
Fred Drake2a3d7db2002-06-28 22:56:48 +00001991 (xmlhandler)my_EndNamespaceDeclHandler},
Fred Drake0582df92000-07-12 04:49:00 +00001992 {"CommentHandler",
1993 (xmlhandlersetter)XML_SetCommentHandler,
1994 (xmlhandler)my_CommentHandler},
1995 {"StartCdataSectionHandler",
Fred Drake71b63ff2002-06-28 22:29:01 +00001996 (xmlhandlersetter)XML_SetStartCdataSectionHandler,
Fred Drake0582df92000-07-12 04:49:00 +00001997 (xmlhandler)my_StartCdataSectionHandler},
1998 {"EndCdataSectionHandler",
Fred Drake71b63ff2002-06-28 22:29:01 +00001999 (xmlhandlersetter)XML_SetEndCdataSectionHandler,
Fred Drake0582df92000-07-12 04:49:00 +00002000 (xmlhandler)my_EndCdataSectionHandler},
2001 {"DefaultHandler",
2002 (xmlhandlersetter)XML_SetDefaultHandler,
2003 (xmlhandler)my_DefaultHandler},
2004 {"DefaultHandlerExpand",
2005 (xmlhandlersetter)XML_SetDefaultHandlerExpand,
2006 (xmlhandler)my_DefaultHandlerExpandHandler},
2007 {"NotStandaloneHandler",
2008 (xmlhandlersetter)XML_SetNotStandaloneHandler,
2009 (xmlhandler)my_NotStandaloneHandler},
2010 {"ExternalEntityRefHandler",
2011 (xmlhandlersetter)XML_SetExternalEntityRefHandler,
Fred Drake2a3d7db2002-06-28 22:56:48 +00002012 (xmlhandler)my_ExternalEntityRefHandler},
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00002013 {"StartDoctypeDeclHandler",
Fred Drake71b63ff2002-06-28 22:29:01 +00002014 (xmlhandlersetter)XML_SetStartDoctypeDeclHandler,
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00002015 (xmlhandler)my_StartDoctypeDeclHandler},
2016 {"EndDoctypeDeclHandler",
Fred Drake71b63ff2002-06-28 22:29:01 +00002017 (xmlhandlersetter)XML_SetEndDoctypeDeclHandler,
Martin v. Löwis0078f6c2001-01-21 10:18:10 +00002018 (xmlhandler)my_EndDoctypeDeclHandler},
Fred Drake85d835f2001-02-08 15:39:08 +00002019 {"EntityDeclHandler",
2020 (xmlhandlersetter)XML_SetEntityDeclHandler,
2021 (xmlhandler)my_EntityDeclHandler},
2022 {"XmlDeclHandler",
2023 (xmlhandlersetter)XML_SetXmlDeclHandler,
2024 (xmlhandler)my_XmlDeclHandler},
2025 {"ElementDeclHandler",
2026 (xmlhandlersetter)XML_SetElementDeclHandler,
2027 (xmlhandler)my_ElementDeclHandler},
2028 {"AttlistDeclHandler",
2029 (xmlhandlersetter)XML_SetAttlistDeclHandler,
2030 (xmlhandler)my_AttlistDeclHandler},
Martin v. Löwisc847f402003-01-21 11:09:21 +00002031#if XML_COMBINED_VERSION >= 19504
Martin v. Löwis069dde22003-01-21 10:58:18 +00002032 {"SkippedEntityHandler",
2033 (xmlhandlersetter)XML_SetSkippedEntityHandler,
2034 (xmlhandler)my_SkippedEntityHandler},
Martin v. Löwisc847f402003-01-21 11:09:21 +00002035#endif
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00002036
Fred Drake0582df92000-07-12 04:49:00 +00002037 {NULL, NULL, NULL} /* sentinel */
Andrew M. Kuchlingb7f10532000-03-31 15:43:31 +00002038};