2 Copyright (c) 1998, 1999, 2000 Thai Open Source Software Center Ltd
3 See the file copying.txt for copying permission.
6 /* In 2001, this was part of the Expat package. We copied it into
7 Xmlrpc-c because it's easier on the user than making him get and
8 link Expat separately, and we don't expect to benefit from separate
11 But we changed all the external symbols that in Expat are named
12 "XML_xxxx" to "xmlrpc_XML_xxxx" because people do link Xmlrpc-c
13 libraries into programs that also link Expat (a good example is
14 where an Apache module uses Xmlrpc-c). We don't want our names to
20 #include "xmlrpc_config.h"
26 #define XML_ENCODE_MAX XML_UTF16_ENCODE_MAX
27 #define XmlConvert XmlUtf16Convert
28 #define XmlGetInternalEncoding xmlrpc_XmlGetUtf16InternalEncoding
29 #define XmlGetInternalEncodingNS xmlrpc_XmlGetUtf16InternalEncodingNS
30 #define XmlEncode xmlrpc_XmlUtf16Encode
31 #define MUST_CONVERT(enc, s) (!(enc)->isUtf16 || (((unsigned long)s) & 1))
32 typedef unsigned short ICHAR;
34 #define XML_ENCODE_MAX XML_UTF8_ENCODE_MAX
35 #define XmlConvert XmlUtf8Convert
36 #define XmlGetInternalEncoding xmlrpc_XmlGetUtf8InternalEncoding
37 #define XmlGetInternalEncodingNS xmlrpc_XmlGetUtf8InternalEncodingNS
38 #define XmlEncode xmlrpc_XmlUtf8Encode
39 #define MUST_CONVERT(enc, s) (!(enc)->isUtf8)
46 #define XmlInitEncodingNS xmlrpc_XmlInitEncoding
47 #define XmlInitUnknownEncodingNS xmlrpc_XmlInitUnknownEncoding
48 #undef XmlGetInternalEncodingNS
49 #define XmlGetInternalEncodingNS XmlGetInternalEncoding
50 #define XmlParseXmlDeclNS xmlrpc_XmlParseXmlDecl
54 #ifdef XML_UNICODE_WCHAR_T
55 #define XML_T(x) L ## x
60 /* Round up n to be a multiple of sz, where sz is a power of 2. */
61 #define ROUND_UP(n, sz) (((n) + ((sz) - 1)) & ~((sz) - 1))
66 typedef const XML_Char *KEY;
84 #define INIT_TAG_BUF_SIZE 32 /* must be a multiple of sizeof(XML_Char) */
85 #define INIT_DATA_BUF_SIZE 1024
86 #define INIT_ATTS_SIZE 16
87 #define INIT_BLOCK_SIZE 1024
88 #define INIT_BUFFER_SIZE 1024
90 #define EXPAND_SPARE 24
92 typedef struct binding {
93 struct prefix *prefix;
94 struct binding *nextTagBinding;
95 struct binding *prevPrefixBinding;
96 const struct attribute_id *attId;
102 typedef struct prefix {
103 const XML_Char *name;
109 const XML_Char *localPart;
124 const XML_Char *name;
125 const XML_Char *textPtr;
127 const XML_Char *systemId;
128 const XML_Char *base;
129 const XML_Char *publicId;
130 const XML_Char *notation;
134 typedef struct block {
148 /* The XML_Char before the name is used to determine whether
149 an attribute has been specified. */
150 typedef struct attribute_id {
158 const ATTRIBUTE_ID *id;
160 const XML_Char *value;
164 const XML_Char *name;
166 const ATTRIBUTE_ID *idAtt;
168 int allocDefaultAtts;
169 DEFAULT_ATTRIBUTE *defaultAtts;
173 HASH_TABLE generalEntities;
174 HASH_TABLE elementTypes;
175 HASH_TABLE attributeIds;
181 HASH_TABLE paramEntities;
183 PREFIX defaultPrefix;
186 typedef struct open_internal_entity {
187 const char *internalEventPtr;
188 const char *internalEventEndPtr;
189 struct open_internal_entity *next;
191 } OPEN_INTERNAL_ENTITY;
193 typedef enum XML_Error Processor(XML_Parser parser,
196 const char **endPtr);
198 static Processor prologProcessor;
199 static Processor prologInitProcessor;
200 static Processor contentProcessor;
201 static Processor cdataSectionProcessor;
203 static Processor ignoreSectionProcessor;
205 static Processor epilogProcessor;
206 static Processor errorProcessor;
207 static Processor externalEntityInitProcessor;
208 static Processor externalEntityInitProcessor2;
209 static Processor externalEntityInitProcessor3;
210 static Processor externalEntityContentProcessor;
212 static enum XML_Error
213 handleUnknownEncoding(XML_Parser parser, const XML_Char *encodingName);
214 static enum XML_Error
215 processXmlDecl(XML_Parser parser, int isGeneralTextEntity, const char *, const char *);
216 static enum XML_Error
217 initializeEncoding(XML_Parser parser);
218 static enum XML_Error
219 doProlog(XML_Parser parser, const ENCODING *enc, const char *s,
220 const char *end, int tok, const char *next, const char **nextPtr);
221 static enum XML_Error
222 doContent(XML_Parser parser, int startTagLevel, const ENCODING *enc,
223 const char *start, const char *end, const char **endPtr);
224 static enum XML_Error
225 doCdataSection(XML_Parser parser, const ENCODING *, const char **startPtr, const char *end, const char **nextPtr);
227 static enum XML_Error
228 doIgnoreSection(XML_Parser parser, const ENCODING *, const char **startPtr, const char *end, const char **nextPtr);
230 static enum XML_Error storeAtts(XML_Parser parser, const ENCODING *, const char *s,
231 TAG_NAME *tagNamePtr, BINDING **bindingsPtr);
233 int addBinding(XML_Parser parser, PREFIX *prefix, const ATTRIBUTE_ID *attId, const XML_Char *uri, BINDING **bindingsPtr);
235 defineAttribute(ELEMENT_TYPE *type, ATTRIBUTE_ID *, int isCdata, int isId, const XML_Char *dfltValue);
236 static enum XML_Error
237 storeAttributeValue(XML_Parser parser, const ENCODING *, int isCdata, const char *, const char *,
239 static enum XML_Error
240 appendAttributeValue(XML_Parser parser, const ENCODING *, int isCdata, const char *, const char *,
242 static ATTRIBUTE_ID *
243 getAttributeId(XML_Parser parser, const ENCODING *enc, const char *start, const char *end);
244 static int setElementTypePrefix(XML_Parser parser, ELEMENT_TYPE *);
245 static enum XML_Error
246 storeEntityValue(XML_Parser parser, const ENCODING *enc, const char *start, const char *end);
248 reportProcessingInstruction(XML_Parser parser, const ENCODING *enc, const char *start, const char *end);
250 reportComment(XML_Parser parser, const ENCODING *enc, const char *start, const char *end);
252 reportDefault(XML_Parser parser, const ENCODING *enc, const char *start, const char *end);
254 static const XML_Char *getContext(XML_Parser parser);
255 static int setContext(XML_Parser parser, const XML_Char *context);
256 static void normalizePublicId(XML_Char *s);
257 static int dtdInit(DTD *);
258 static void dtdDestroy(DTD *);
259 static int dtdCopy(DTD *newDtd, const DTD *oldDtd);
260 static int copyEntityTable(HASH_TABLE *, STRING_POOL *, const HASH_TABLE *);
262 static void dtdSwap(DTD *, DTD *);
264 static NAMED *lookup(HASH_TABLE *table, KEY name, size_t createSize);
265 static void hashTableInit(HASH_TABLE *);
266 static void hashTableDestroy(HASH_TABLE *);
267 static void hashTableIterInit(HASH_TABLE_ITER *, const HASH_TABLE *);
268 static NAMED *hashTableIterNext(HASH_TABLE_ITER *);
269 static void poolInit(STRING_POOL *);
270 static void poolClear(STRING_POOL *);
271 static void poolDestroy(STRING_POOL *);
272 static XML_Char *poolAppend(STRING_POOL *pool, const ENCODING *enc,
273 const char *ptr, const char *end);
274 static XML_Char *poolStoreString(STRING_POOL *pool, const ENCODING *enc,
275 const char *ptr, const char *end);
276 static int poolGrow(STRING_POOL *pool);
277 static const XML_Char *poolCopyString(STRING_POOL *pool, const XML_Char *s);
278 static const XML_Char *poolCopyStringN(STRING_POOL *pool, const XML_Char *s, int n);
280 #define poolStart(pool) ((pool)->start)
281 #define poolEnd(pool) ((pool)->ptr)
282 #define poolLength(pool) ((pool)->ptr - (pool)->start)
283 #define poolChop(pool) ((void)--(pool->ptr))
284 #define poolLastChar(pool) (((pool)->ptr)[-1])
285 #define poolDiscard(pool) ((pool)->ptr = (pool)->start)
286 #define poolFinish(pool) ((pool)->start = (pool)->ptr)
287 #define poolAppendChar(pool, c) \
288 (((pool)->ptr == (pool)->end && !poolGrow(pool)) \
290 : ((*((pool)->ptr)++ = c), 1))
293 /* The first member must be userData so that the XML_GetUserData macro works. */
297 /* first character to be parsed */
298 const char *m_bufferPtr;
299 /* past last character to be parsed */
301 /* allocated end of buffer */
302 const char *m_bufferLim;
303 long m_parseEndByteIndex;
304 const char *m_parseEndPtr;
306 XML_Char *m_dataBufEnd;
307 XML_StartElementHandler m_startElementHandler;
308 XML_EndElementHandler m_endElementHandler;
309 XML_CharacterDataHandler m_characterDataHandler;
310 XML_ProcessingInstructionHandler m_processingInstructionHandler;
311 XML_CommentHandler m_commentHandler;
312 XML_StartCdataSectionHandler m_startCdataSectionHandler;
313 XML_EndCdataSectionHandler m_endCdataSectionHandler;
314 XML_DefaultHandler m_defaultHandler;
315 XML_StartDoctypeDeclHandler m_startDoctypeDeclHandler;
316 XML_EndDoctypeDeclHandler m_endDoctypeDeclHandler;
317 XML_UnparsedEntityDeclHandler m_unparsedEntityDeclHandler;
318 XML_NotationDeclHandler m_notationDeclHandler;
319 XML_ExternalParsedEntityDeclHandler m_externalParsedEntityDeclHandler;
320 XML_InternalParsedEntityDeclHandler m_internalParsedEntityDeclHandler;
321 XML_StartNamespaceDeclHandler m_startNamespaceDeclHandler;
322 XML_EndNamespaceDeclHandler m_endNamespaceDeclHandler;
323 XML_NotStandaloneHandler m_notStandaloneHandler;
324 XML_ExternalEntityRefHandler m_externalEntityRefHandler;
325 void *m_externalEntityRefHandlerArg;
326 XML_UnknownEncodingHandler m_unknownEncodingHandler;
327 const ENCODING *m_encoding;
328 INIT_ENCODING m_initEncoding;
329 const ENCODING *m_internalEncoding;
330 const XML_Char *m_protocolEncodingName;
332 void *m_unknownEncodingMem;
333 void *m_unknownEncodingData;
334 void *m_unknownEncodingHandlerData;
335 void (*m_unknownEncodingRelease)(void *);
336 PROLOG_STATE m_prologState;
337 Processor *m_processor;
338 enum XML_Error m_errorCode;
339 const char *m_eventPtr;
340 const char *m_eventEndPtr;
341 const char *m_positionPtr;
342 OPEN_INTERNAL_ENTITY *m_openInternalEntities;
343 int m_defaultExpandInternalEntities;
345 ENTITY *m_declEntity;
346 const XML_Char *m_declNotationName;
347 const XML_Char *m_declNotationPublicId;
348 ELEMENT_TYPE *m_declElementType;
349 ATTRIBUTE_ID *m_declAttributeId;
350 char m_declAttributeIsCdata;
351 char m_declAttributeIsId;
353 const XML_Char *m_curBase;
356 BINDING *m_inheritedBindings;
357 BINDING *m_freeBindingList;
359 int m_nSpecifiedAtts;
363 STRING_POOL m_tempPool;
364 STRING_POOL m_temp2Pool;
365 char *m_groupConnector;
366 unsigned m_groupSize;
367 int m_hadExternalDoctype;
368 XML_Char m_namespaceSeparator;
370 enum XML_ParamEntityParsing m_paramEntityParsing;
371 XML_Parser m_parentParser;
375 #define userData (((Parser *)parser)->m_userData)
376 #define handlerArg (((Parser *)parser)->m_handlerArg)
377 #define startElementHandler (((Parser *)parser)->m_startElementHandler)
378 #define endElementHandler (((Parser *)parser)->m_endElementHandler)
379 #define characterDataHandler (((Parser *)parser)->m_characterDataHandler)
380 #define processingInstructionHandler (((Parser *)parser)->m_processingInstructionHandler)
381 #define commentHandler (((Parser *)parser)->m_commentHandler)
382 #define startCdataSectionHandler (((Parser *)parser)->m_startCdataSectionHandler)
383 #define endCdataSectionHandler (((Parser *)parser)->m_endCdataSectionHandler)
384 #define defaultHandler (((Parser *)parser)->m_defaultHandler)
385 #define startDoctypeDeclHandler (((Parser *)parser)->m_startDoctypeDeclHandler)
386 #define endDoctypeDeclHandler (((Parser *)parser)->m_endDoctypeDeclHandler)
387 #define unparsedEntityDeclHandler (((Parser *)parser)->m_unparsedEntityDeclHandler)
388 #define notationDeclHandler (((Parser *)parser)->m_notationDeclHandler)
389 #define externalParsedEntityDeclHandler (((Parser *)parser)->m_externalParsedEntityDeclHandler)
390 #define internalParsedEntityDeclHandler (((Parser *)parser)->m_internalParsedEntityDeclHandler)
391 #define startNamespaceDeclHandler (((Parser *)parser)->m_startNamespaceDeclHandler)
392 #define endNamespaceDeclHandler (((Parser *)parser)->m_endNamespaceDeclHandler)
393 #define notStandaloneHandler (((Parser *)parser)->m_notStandaloneHandler)
394 #define externalEntityRefHandler (((Parser *)parser)->m_externalEntityRefHandler)
395 #define externalEntityRefHandlerArg (((Parser *)parser)->m_externalEntityRefHandlerArg)
396 #define unknownEncodingHandler (((Parser *)parser)->m_unknownEncodingHandler)
397 #define encoding (((Parser *)parser)->m_encoding)
398 #define initEncoding (((Parser *)parser)->m_initEncoding)
399 #define internalEncoding (((Parser *)parser)->m_internalEncoding)
400 #define unknownEncodingMem (((Parser *)parser)->m_unknownEncodingMem)
401 #define unknownEncodingData (((Parser *)parser)->m_unknownEncodingData)
402 #define unknownEncodingHandlerData \
403 (((Parser *)parser)->m_unknownEncodingHandlerData)
404 #define unknownEncodingRelease (((Parser *)parser)->m_unknownEncodingRelease)
405 #define protocolEncodingName (((Parser *)parser)->m_protocolEncodingName)
406 #define ns (((Parser *)parser)->m_ns)
407 #define prologState (((Parser *)parser)->m_prologState)
408 #define processor (((Parser *)parser)->m_processor)
409 #define errorCode (((Parser *)parser)->m_errorCode)
410 #define eventPtr (((Parser *)parser)->m_eventPtr)
411 #define eventEndPtr (((Parser *)parser)->m_eventEndPtr)
412 #define positionPtr (((Parser *)parser)->m_positionPtr)
413 #define position (((Parser *)parser)->m_position)
414 #define openInternalEntities (((Parser *)parser)->m_openInternalEntities)
415 #define defaultExpandInternalEntities (((Parser *)parser)->m_defaultExpandInternalEntities)
416 #define tagLevel (((Parser *)parser)->m_tagLevel)
417 #define buffer (((Parser *)parser)->m_buffer)
418 #define bufferPtr (((Parser *)parser)->m_bufferPtr)
419 #define bufferEnd (((Parser *)parser)->m_bufferEnd)
420 #define parseEndByteIndex (((Parser *)parser)->m_parseEndByteIndex)
421 #define parseEndPtr (((Parser *)parser)->m_parseEndPtr)
422 #define bufferLim (((Parser *)parser)->m_bufferLim)
423 #define dataBuf (((Parser *)parser)->m_dataBuf)
424 #define dataBufEnd (((Parser *)parser)->m_dataBufEnd)
425 #define dtd (((Parser *)parser)->m_dtd)
426 #define curBase (((Parser *)parser)->m_curBase)
427 #define declEntity (((Parser *)parser)->m_declEntity)
428 #define declNotationName (((Parser *)parser)->m_declNotationName)
429 #define declNotationPublicId (((Parser *)parser)->m_declNotationPublicId)
430 #define declElementType (((Parser *)parser)->m_declElementType)
431 #define declAttributeId (((Parser *)parser)->m_declAttributeId)
432 #define declAttributeIsCdata (((Parser *)parser)->m_declAttributeIsCdata)
433 #define declAttributeIsId (((Parser *)parser)->m_declAttributeIsId)
434 #define freeTagList (((Parser *)parser)->m_freeTagList)
435 #define freeBindingList (((Parser *)parser)->m_freeBindingList)
436 #define inheritedBindings (((Parser *)parser)->m_inheritedBindings)
437 #define tagStack (((Parser *)parser)->m_tagStack)
438 #define atts (((Parser *)parser)->m_atts)
439 #define attsSize (((Parser *)parser)->m_attsSize)
440 #define nSpecifiedAtts (((Parser *)parser)->m_nSpecifiedAtts)
441 #define idAttIndex (((Parser *)parser)->m_idAttIndex)
442 #define tempPool (((Parser *)parser)->m_tempPool)
443 #define temp2Pool (((Parser *)parser)->m_temp2Pool)
444 #define groupConnector (((Parser *)parser)->m_groupConnector)
445 #define groupSize (((Parser *)parser)->m_groupSize)
446 #define hadExternalDoctype (((Parser *)parser)->m_hadExternalDoctype)
447 #define namespaceSeparator (((Parser *)parser)->m_namespaceSeparator)
449 #define parentParser (((Parser *)parser)->m_parentParser)
450 #define paramEntityParsing (((Parser *)parser)->m_paramEntityParsing)
455 Parser *asParser(XML_Parser parser)
463 xmlrpc_XML_ParserCreate(const XML_Char *encodingName)
465 XML_Parser parser = malloc(sizeof(Parser));
468 processor = prologInitProcessor;
469 xmlrpc_XmlPrologStateInit(&prologState);
472 startElementHandler = 0;
473 endElementHandler = 0;
474 characterDataHandler = 0;
475 processingInstructionHandler = 0;
477 startCdataSectionHandler = 0;
478 endCdataSectionHandler = 0;
480 startDoctypeDeclHandler = 0;
481 endDoctypeDeclHandler = 0;
482 unparsedEntityDeclHandler = 0;
483 notationDeclHandler = 0;
484 externalParsedEntityDeclHandler = 0;
485 internalParsedEntityDeclHandler = 0;
486 startNamespaceDeclHandler = 0;
487 endNamespaceDeclHandler = 0;
488 notStandaloneHandler = 0;
489 externalEntityRefHandler = 0;
490 externalEntityRefHandlerArg = parser;
491 unknownEncodingHandler = 0;
495 parseEndByteIndex = 0;
501 declNotationName = 0;
502 declNotationPublicId = 0;
503 memset(&position, 0, sizeof(POSITION));
504 errorCode = XML_ERROR_NONE;
508 openInternalEntities = 0;
513 inheritedBindings = 0;
514 attsSize = INIT_ATTS_SIZE;
515 atts = malloc(attsSize * sizeof(ATTRIBUTE));
517 dataBuf = malloc(INIT_DATA_BUF_SIZE * sizeof(XML_Char));
520 hadExternalDoctype = 0;
521 unknownEncodingMem = 0;
522 unknownEncodingRelease = 0;
523 unknownEncodingData = 0;
524 unknownEncodingHandlerData = 0;
525 namespaceSeparator = '!';
528 paramEntityParsing = XML_PARAM_ENTITY_PARSING_NEVER;
532 poolInit(&temp2Pool);
533 protocolEncodingName = encodingName ? poolCopyString(&tempPool, encodingName) : 0;
535 if (!dtdInit(&dtd) || !atts || !dataBuf
536 || (encodingName && !protocolEncodingName)) {
537 xmlrpc_XML_ParserFree(parser);
540 dataBufEnd = dataBuf + INIT_DATA_BUF_SIZE;
541 xmlrpc_XmlInitEncoding(&initEncoding, &encoding, 0);
542 internalEncoding = XmlGetInternalEncoding();
547 xmlrpc_XML_ParserCreateNS(const XML_Char *encodingName, XML_Char nsSep)
550 const XML_Char implicitContext[] = {
551 XML_T('x'), XML_T('m'), XML_T('l'), XML_T('='),
552 XML_T('h'), XML_T('t'), XML_T('t'), XML_T('p'), XML_T(':'),
553 XML_T('/'), XML_T('/'), XML_T('w'), XML_T('w'), XML_T('w'),
554 XML_T('.'), XML_T('w'), XML_T('3'),
555 XML_T('.'), XML_T('o'), XML_T('r'), XML_T('g'),
556 XML_T('/'), XML_T('X'), XML_T('M'), XML_T('L'),
557 XML_T('/'), XML_T('1'), XML_T('9'), XML_T('9'), XML_T('8'),
558 XML_T('/'), XML_T('n'), XML_T('a'), XML_T('m'), XML_T('e'),
559 XML_T('s'), XML_T('p'), XML_T('a'), XML_T('c'), XML_T('e'),
563 XML_Parser parser = xmlrpc_XML_ParserCreate(encodingName);
565 XmlInitEncodingNS(&initEncoding, &encoding, 0);
567 internalEncoding = XmlGetInternalEncodingNS();
568 namespaceSeparator = nsSep;
570 if (!setContext(parser, implicitContext)) {
571 xmlrpc_XML_ParserFree(parser);
578 xmlrpc_XML_SetEncoding(XML_Parser parser, const XML_Char *encodingName)
581 protocolEncodingName = 0;
583 protocolEncodingName = poolCopyString(&tempPool, encodingName);
584 if (!protocolEncodingName)
591 xmlrpc_XML_ExternalEntityParserCreate(XML_Parser oldParser,
592 const XML_Char *context,
593 const XML_Char *encodingName)
595 XML_Parser parser = oldParser;
597 XML_StartElementHandler oldStartElementHandler = startElementHandler;
598 XML_EndElementHandler oldEndElementHandler = endElementHandler;
599 XML_CharacterDataHandler oldCharacterDataHandler = characterDataHandler;
600 XML_ProcessingInstructionHandler oldProcessingInstructionHandler = processingInstructionHandler;
601 XML_CommentHandler oldCommentHandler = commentHandler;
602 XML_StartCdataSectionHandler oldStartCdataSectionHandler = startCdataSectionHandler;
603 XML_EndCdataSectionHandler oldEndCdataSectionHandler = endCdataSectionHandler;
604 XML_DefaultHandler oldDefaultHandler = defaultHandler;
605 XML_UnparsedEntityDeclHandler oldUnparsedEntityDeclHandler = unparsedEntityDeclHandler;
606 XML_NotationDeclHandler oldNotationDeclHandler = notationDeclHandler;
607 XML_ExternalParsedEntityDeclHandler oldExternalParsedEntityDeclHandler = externalParsedEntityDeclHandler;
608 XML_InternalParsedEntityDeclHandler oldInternalParsedEntityDeclHandler = internalParsedEntityDeclHandler;
609 XML_StartNamespaceDeclHandler oldStartNamespaceDeclHandler = startNamespaceDeclHandler;
610 XML_EndNamespaceDeclHandler oldEndNamespaceDeclHandler = endNamespaceDeclHandler;
611 XML_NotStandaloneHandler oldNotStandaloneHandler = notStandaloneHandler;
612 XML_ExternalEntityRefHandler oldExternalEntityRefHandler = externalEntityRefHandler;
613 XML_UnknownEncodingHandler oldUnknownEncodingHandler = unknownEncodingHandler;
614 void *oldUserData = userData;
615 void *oldHandlerArg = handlerArg;
616 int oldDefaultExpandInternalEntities = defaultExpandInternalEntities;
617 void *oldExternalEntityRefHandlerArg = externalEntityRefHandlerArg;
619 int oldParamEntityParsing = paramEntityParsing;
622 ? xmlrpc_XML_ParserCreateNS(encodingName, namespaceSeparator)
623 : xmlrpc_XML_ParserCreate(encodingName));
626 startElementHandler = oldStartElementHandler;
627 endElementHandler = oldEndElementHandler;
628 characterDataHandler = oldCharacterDataHandler;
629 processingInstructionHandler = oldProcessingInstructionHandler;
630 commentHandler = oldCommentHandler;
631 startCdataSectionHandler = oldStartCdataSectionHandler;
632 endCdataSectionHandler = oldEndCdataSectionHandler;
633 defaultHandler = oldDefaultHandler;
634 unparsedEntityDeclHandler = oldUnparsedEntityDeclHandler;
635 notationDeclHandler = oldNotationDeclHandler;
636 externalParsedEntityDeclHandler = oldExternalParsedEntityDeclHandler;
637 internalParsedEntityDeclHandler = oldInternalParsedEntityDeclHandler;
638 startNamespaceDeclHandler = oldStartNamespaceDeclHandler;
639 endNamespaceDeclHandler = oldEndNamespaceDeclHandler;
640 notStandaloneHandler = oldNotStandaloneHandler;
641 externalEntityRefHandler = oldExternalEntityRefHandler;
642 unknownEncodingHandler = oldUnknownEncodingHandler;
643 userData = oldUserData;
644 if (oldUserData == oldHandlerArg)
645 handlerArg = userData;
648 if (oldExternalEntityRefHandlerArg != oldParser)
649 externalEntityRefHandlerArg = oldExternalEntityRefHandlerArg;
650 defaultExpandInternalEntities = oldDefaultExpandInternalEntities;
652 paramEntityParsing = oldParamEntityParsing;
655 if (!dtdCopy(&dtd, oldDtd) || !setContext(parser, context)) {
656 xmlrpc_XML_ParserFree(parser);
659 processor = externalEntityInitProcessor;
663 dtdSwap(&dtd, oldDtd);
664 parentParser = oldParser;
665 XmlPrologStateInitExternalEntity(&prologState);
667 hadExternalDoctype = 1;
674 void destroyBindings(BINDING *bindings)
677 BINDING *b = bindings;
680 bindings = b->nextTagBinding;
687 xmlrpc_XML_ParserFree(XML_Parser parser)
692 if (freeTagList == 0)
694 tagStack = freeTagList;
698 tagStack = tagStack->parent;
700 destroyBindings(p->bindings);
703 destroyBindings(freeBindingList);
704 destroyBindings(inheritedBindings);
705 poolDestroy(&tempPool);
706 poolDestroy(&temp2Pool);
709 if (hadExternalDoctype)
711 dtdSwap(&dtd, &((Parser *)parentParser)->m_dtd);
716 free(groupConnector);
719 free(unknownEncodingMem);
720 if (unknownEncodingRelease)
721 unknownEncodingRelease(unknownEncodingData);
726 xmlrpc_XML_UseParserAsHandlerArg(XML_Parser parser)
732 xmlrpc_XML_SetUserData(XML_Parser parser, void *p)
734 if (handlerArg == userData)
735 handlerArg = userData = p;
741 xmlrpc_XML_SetBase(XML_Parser parser, const XML_Char *p)
744 p = poolCopyString(&dtd.pool, p);
755 xmlrpc_XML_GetBase(XML_Parser parser)
761 xmlrpc_XML_GetSpecifiedAttributeCount(XML_Parser parser)
763 return nSpecifiedAtts;
767 xmlrpc_XML_GetIdAttributeIndex(XML_Parser parser)
773 xmlrpc_XML_SetElementHandler(XML_Parser parser,
774 XML_StartElementHandler start,
775 XML_EndElementHandler end)
777 startElementHandler = start;
778 endElementHandler = end;
782 xmlrpc_XML_SetCharacterDataHandler(XML_Parser parser,
783 XML_CharacterDataHandler handler)
785 characterDataHandler = handler;
789 xmlrpc_XML_SetProcessingInstructionHandler(
791 XML_ProcessingInstructionHandler handler)
793 processingInstructionHandler = handler;
797 xmlrpc_XML_SetCommentHandler(XML_Parser parser,
798 XML_CommentHandler handler)
800 commentHandler = handler;
804 xmlrpc_XML_SetCdataSectionHandler(XML_Parser parser,
805 XML_StartCdataSectionHandler start,
806 XML_EndCdataSectionHandler end)
808 startCdataSectionHandler = start;
809 endCdataSectionHandler = end;
813 xmlrpc_XML_SetDefaultHandler(XML_Parser parser,
814 XML_DefaultHandler handler)
816 defaultHandler = handler;
817 defaultExpandInternalEntities = 0;
821 xmlrpc_XML_SetDefaultHandlerExpand(XML_Parser parser,
822 XML_DefaultHandler handler)
824 defaultHandler = handler;
825 defaultExpandInternalEntities = 1;
829 xmlrpc_XML_SetDoctypeDeclHandler(XML_Parser parser,
830 XML_StartDoctypeDeclHandler start,
831 XML_EndDoctypeDeclHandler end)
833 startDoctypeDeclHandler = start;
834 endDoctypeDeclHandler = end;
838 xmlrpc_XML_SetUnparsedEntityDeclHandler(XML_Parser parser,
839 XML_UnparsedEntityDeclHandler handler)
841 unparsedEntityDeclHandler = handler;
845 xmlrpc_XML_SetExternalParsedEntityDeclHandler(
847 XML_ExternalParsedEntityDeclHandler handler)
849 externalParsedEntityDeclHandler = handler;
853 xmlrpc_XML_SetInternalParsedEntityDeclHandler(
855 XML_InternalParsedEntityDeclHandler handler)
857 internalParsedEntityDeclHandler = handler;
861 xmlrpc_XML_SetNotationDeclHandler(XML_Parser parser,
862 XML_NotationDeclHandler handler)
864 notationDeclHandler = handler;
868 xmlrpc_XML_SetNamespaceDeclHandler(XML_Parser parser,
869 XML_StartNamespaceDeclHandler start,
870 XML_EndNamespaceDeclHandler end)
872 startNamespaceDeclHandler = start;
873 endNamespaceDeclHandler = end;
877 xmlrpc_XML_SetNotStandaloneHandler(XML_Parser parser,
878 XML_NotStandaloneHandler handler)
880 notStandaloneHandler = handler;
884 xmlrpc_XML_SetExternalEntityRefHandler(XML_Parser parser,
885 XML_ExternalEntityRefHandler handler)
887 externalEntityRefHandler = handler;
891 xmlrpc_XML_SetExternalEntityRefHandlerArg(XML_Parser parser, void *arg)
894 externalEntityRefHandlerArg = arg;
896 externalEntityRefHandlerArg = parser;
900 xmlrpc_XML_SetUnknownEncodingHandler(XML_Parser parser,
901 XML_UnknownEncodingHandler handler,
904 unknownEncodingHandler = handler;
905 unknownEncodingHandlerData = data;
911 xmlrpc_XML_SetParamEntityParsing(
912 XML_Parser const parser ATTR_UNUSED,
913 enum XML_ParamEntityParsing const parsing) {
918 paramEntityParsing = parsing;
921 retval = parsing == XML_PARAM_ENTITY_PARSING_NEVER;
930 xmlrpc_XML_Parse(XML_Parser parser, const char *s, int len, int isFinal)
935 positionPtr = bufferPtr;
936 errorCode = processor(parser, bufferPtr, parseEndPtr = bufferEnd, 0);
937 if (errorCode == XML_ERROR_NONE)
939 eventEndPtr = eventPtr;
940 processor = errorProcessor;
943 else if (bufferPtr == bufferEnd) {
946 parseEndByteIndex += len;
949 errorCode = processor(parser, s, parseEndPtr = s + len, 0);
950 if (errorCode == XML_ERROR_NONE)
952 eventEndPtr = eventPtr;
953 processor = errorProcessor;
956 errorCode = processor(parser, s, parseEndPtr = s + len, &end);
957 if (errorCode != XML_ERROR_NONE) {
958 eventEndPtr = eventPtr;
959 processor = errorProcessor;
962 XmlUpdatePosition(encoding, positionPtr, end, &position);
963 nLeftOver = s + len - end;
965 if (buffer == 0 || nLeftOver > bufferLim - buffer) {
966 /* FIXME avoid integer overflow */
967 buffer = buffer == 0 ? malloc(len * 2) : realloc(buffer, len * 2);
968 /* FIXME storage leak if realloc fails */
970 errorCode = XML_ERROR_NO_MEMORY;
971 eventPtr = eventEndPtr = 0;
972 processor = errorProcessor;
975 bufferLim = buffer + len * 2;
977 memcpy(buffer, end, nLeftOver);
979 bufferEnd = buffer + nLeftOver;
984 memcpy(xmlrpc_XML_GetBuffer(parser, len), s, len);
985 return xmlrpc_XML_ParseBuffer(parser, len, isFinal);
990 xmlrpc_XML_ParseBuffer(XML_Parser parser, int len, int isFinal)
992 const char *start = bufferPtr;
995 parseEndByteIndex += len;
996 errorCode = processor(parser, start, parseEndPtr = bufferEnd,
997 isFinal ? (const char **)0 : &bufferPtr);
998 if (errorCode == XML_ERROR_NONE) {
1000 XmlUpdatePosition(encoding, positionPtr, bufferPtr, &position);
1004 eventEndPtr = eventPtr;
1005 processor = errorProcessor;
1011 xmlrpc_XML_GetBuffer(XML_Parser parser, int len)
1013 if (len > bufferLim - bufferEnd) {
1014 /* FIXME avoid integer overflow */
1015 int neededSize = len + (bufferEnd - bufferPtr);
1016 if (neededSize <= bufferLim - buffer) {
1017 memmove(buffer, bufferPtr, bufferEnd - bufferPtr);
1018 bufferEnd = buffer + (bufferEnd - bufferPtr);
1023 int bufferSize = bufferLim - bufferPtr;
1024 if (bufferSize == 0)
1025 bufferSize = INIT_BUFFER_SIZE;
1028 } while (bufferSize < neededSize);
1029 newBuf = malloc(bufferSize);
1031 errorCode = XML_ERROR_NO_MEMORY;
1034 bufferLim = newBuf + bufferSize;
1036 memcpy(newBuf, bufferPtr, bufferEnd - bufferPtr);
1039 bufferEnd = newBuf + (bufferEnd - bufferPtr);
1040 bufferPtr = buffer = newBuf;
1047 xmlrpc_XML_GetErrorCode(XML_Parser parser)
1053 xmlrpc_XML_GetCurrentByteIndex(XML_Parser parser)
1056 return parseEndByteIndex - (parseEndPtr - eventPtr);
1061 xmlrpc_XML_GetCurrentByteCount(XML_Parser parser)
1063 if (eventEndPtr && eventPtr)
1064 return eventEndPtr - eventPtr;
1069 xmlrpc_XML_GetCurrentLineNumber(XML_Parser parser)
1072 XmlUpdatePosition(encoding, positionPtr, eventPtr, &position);
1073 positionPtr = eventPtr;
1075 return position.lineNumber + 1;
1079 xmlrpc_XML_GetCurrentColumnNumber(XML_Parser parser)
1082 XmlUpdatePosition(encoding, positionPtr, eventPtr, &position);
1083 positionPtr = eventPtr;
1085 return position.columnNumber;
1089 xmlrpc_XML_DefaultCurrent(XML_Parser parser)
1091 if (defaultHandler) {
1092 if (openInternalEntities)
1093 reportDefault(parser,
1095 openInternalEntities->internalEventPtr,
1096 openInternalEntities->internalEventEndPtr);
1098 reportDefault(parser, encoding, eventPtr, eventEndPtr);
1103 xmlrpc_XML_ErrorString(int const code) {
1105 static const XML_LChar * const message[] = {
1107 XML_T("out of memory"),
1108 XML_T("syntax error"),
1109 XML_T("no element found"),
1110 XML_T("not well-formed"),
1111 XML_T("unclosed token"),
1112 XML_T("unclosed token"),
1113 XML_T("mismatched tag"),
1114 XML_T("duplicate attribute"),
1115 XML_T("junk after document element"),
1116 XML_T("illegal parameter entity reference"),
1117 XML_T("undefined entity"),
1118 XML_T("recursive entity reference"),
1119 XML_T("asynchronous entity"),
1120 XML_T("reference to invalid character number"),
1121 XML_T("reference to binary entity"),
1122 XML_T("reference to external entity in attribute"),
1123 XML_T("xml processing instruction not at start of external entity"),
1124 XML_T("unknown encoding"),
1125 XML_T("encoding specified in XML declaration is incorrect"),
1126 XML_T("unclosed CDATA section"),
1127 XML_T("error in processing external entity reference"),
1128 XML_T("document is not standalone")
1131 const XML_LChar * retval;
1133 if (code > 0 && (unsigned)code < ARRAY_SIZE(message))
1134 retval = message[code];
1142 enum XML_Error contentProcessor(XML_Parser parser,
1145 const char **endPtr)
1147 return doContent(parser, 0, encoding, start, end, endPtr);
1151 enum XML_Error externalEntityInitProcessor(XML_Parser parser,
1154 const char **endPtr)
1156 enum XML_Error result = initializeEncoding(parser);
1157 if (result != XML_ERROR_NONE)
1159 processor = externalEntityInitProcessor2;
1160 return externalEntityInitProcessor2(parser, start, end, endPtr);
1164 enum XML_Error externalEntityInitProcessor2(XML_Parser parser,
1167 const char **endPtr)
1170 int tok = XmlContentTok(encoding, start, end, &next);
1175 case XML_TOK_PARTIAL:
1178 return XML_ERROR_NONE;
1181 return XML_ERROR_UNCLOSED_TOKEN;
1182 case XML_TOK_PARTIAL_CHAR:
1185 return XML_ERROR_NONE;
1188 return XML_ERROR_PARTIAL_CHAR;
1190 processor = externalEntityInitProcessor3;
1191 return externalEntityInitProcessor3(parser, start, end, endPtr);
1195 enum XML_Error externalEntityInitProcessor3(XML_Parser parser,
1198 const char **endPtr)
1201 int tok = XmlContentTok(encoding, start, end, &next);
1203 case XML_TOK_XML_DECL:
1205 enum XML_Error result = processXmlDecl(parser, 1, start, next);
1206 if (result != XML_ERROR_NONE)
1211 case XML_TOK_PARTIAL:
1214 return XML_ERROR_NONE;
1217 return XML_ERROR_UNCLOSED_TOKEN;
1218 case XML_TOK_PARTIAL_CHAR:
1221 return XML_ERROR_NONE;
1224 return XML_ERROR_PARTIAL_CHAR;
1226 processor = externalEntityContentProcessor;
1228 return doContent(parser, 1, encoding, start, end, endPtr);
1232 enum XML_Error externalEntityContentProcessor(XML_Parser parser,
1235 const char **endPtr)
1237 return doContent(parser, 1, encoding, start, end, endPtr);
1240 static enum XML_Error
1241 doContent(XML_Parser parser,
1243 const ENCODING *enc,
1246 const char **nextPtr)
1248 const char **eventPP;
1249 const char **eventEndPP;
1250 if (enc == encoding) {
1251 eventPP = &eventPtr;
1252 eventEndPP = &eventEndPtr;
1255 eventPP = &(openInternalEntities->internalEventPtr);
1256 eventEndPP = &(openInternalEntities->internalEventEndPtr);
1260 const char *next = s; /* XmlContentTok doesn't always set the last arg */
1261 int tok = XmlContentTok(enc, s, end, &next);
1264 case XML_TOK_TRAILING_CR:
1267 return XML_ERROR_NONE;
1270 if (characterDataHandler) {
1272 characterDataHandler(handlerArg, &c, 1);
1274 else if (defaultHandler)
1275 reportDefault(parser, enc, s, end);
1276 if (startTagLevel == 0)
1277 return XML_ERROR_NO_ELEMENTS;
1278 if (tagLevel != startTagLevel)
1279 return XML_ERROR_ASYNC_ENTITY;
1280 return XML_ERROR_NONE;
1284 return XML_ERROR_NONE;
1286 if (startTagLevel > 0) {
1287 if (tagLevel != startTagLevel)
1288 return XML_ERROR_ASYNC_ENTITY;
1289 return XML_ERROR_NONE;
1291 return XML_ERROR_NO_ELEMENTS;
1292 case XML_TOK_INVALID:
1294 return XML_ERROR_INVALID_TOKEN;
1295 case XML_TOK_PARTIAL:
1298 return XML_ERROR_NONE;
1300 return XML_ERROR_UNCLOSED_TOKEN;
1301 case XML_TOK_PARTIAL_CHAR:
1304 return XML_ERROR_NONE;
1306 return XML_ERROR_PARTIAL_CHAR;
1307 case XML_TOK_ENTITY_REF:
1309 const XML_Char *name;
1311 XML_Char ch = XmlPredefinedEntityName(enc,
1312 s + enc->minBytesPerChar,
1313 next - enc->minBytesPerChar);
1315 if (characterDataHandler)
1316 characterDataHandler(handlerArg, &ch, 1);
1317 else if (defaultHandler)
1318 reportDefault(parser, enc, s, next);
1321 name = poolStoreString(&dtd.pool, enc,
1322 s + enc->minBytesPerChar,
1323 next - enc->minBytesPerChar);
1325 return XML_ERROR_NO_MEMORY;
1326 entity = (ENTITY *)lookup(&dtd.generalEntities, name, 0);
1327 poolDiscard(&dtd.pool);
1329 if (dtd.complete || dtd.standalone)
1330 return XML_ERROR_UNDEFINED_ENTITY;
1332 reportDefault(parser, enc, s, next);
1336 return XML_ERROR_RECURSIVE_ENTITY_REF;
1337 if (entity->notation)
1338 return XML_ERROR_BINARY_ENTITY_REF;
1340 if (entity->textPtr) {
1341 enum XML_Error result;
1342 OPEN_INTERNAL_ENTITY openEntity;
1343 if (defaultHandler && !defaultExpandInternalEntities) {
1344 reportDefault(parser, enc, s, next);
1348 openEntity.next = openInternalEntities;
1349 openInternalEntities = &openEntity;
1350 openEntity.entity = entity;
1351 openEntity.internalEventPtr = 0;
1352 openEntity.internalEventEndPtr = 0;
1353 result = doContent(parser,
1356 (char *)entity->textPtr,
1357 (char *)(entity->textPtr + entity->textLen),
1360 openInternalEntities = openEntity.next;
1364 else if (externalEntityRefHandler) {
1365 const XML_Char *context;
1367 context = getContext(parser);
1370 return XML_ERROR_NO_MEMORY;
1371 if (!externalEntityRefHandler(externalEntityRefHandlerArg,
1376 return XML_ERROR_EXTERNAL_ENTITY_HANDLING;
1377 poolDiscard(&tempPool);
1379 else if (defaultHandler)
1380 reportDefault(parser, enc, s, next);
1384 case XML_TOK_START_TAG_WITH_ATTS:
1385 if (!startElementHandler) {
1386 enum XML_Error result = storeAtts(parser, enc, s, 0, 0);
1391 case XML_TOK_START_TAG_NO_ATTS:
1396 freeTagList = freeTagList->parent;
1399 tag = malloc(sizeof(TAG));
1401 return XML_ERROR_NO_MEMORY;
1402 tag->buf = malloc(INIT_TAG_BUF_SIZE);
1404 return XML_ERROR_NO_MEMORY;
1405 tag->bufEnd = tag->buf + INIT_TAG_BUF_SIZE;
1408 tag->parent = tagStack;
1410 tag->name.localPart = 0;
1411 tag->rawName = s + enc->minBytesPerChar;
1412 tag->rawNameLength = XmlNameLength(enc, tag->rawName);
1414 /* Need to guarantee that:
1415 tag->buf + ROUND_UP(tag->rawNameLength, sizeof(XML_Char)) <= tag->bufEnd - sizeof(XML_Char) */
1416 if (tag->rawNameLength + (int)(sizeof(XML_Char) - 1) + (int)sizeof(XML_Char) > tag->bufEnd - tag->buf) {
1417 int bufSize = tag->rawNameLength * 4;
1418 bufSize = ROUND_UP(bufSize, sizeof(XML_Char));
1419 tag->buf = realloc(tag->buf, bufSize);
1421 return XML_ERROR_NO_MEMORY;
1422 tag->bufEnd = tag->buf + bufSize;
1424 memcpy(tag->buf, tag->rawName, tag->rawNameLength);
1425 tag->rawName = tag->buf;
1428 if (startElementHandler) {
1429 enum XML_Error result;
1432 const char *rawNameEnd = tag->rawName + tag->rawNameLength;
1433 const char *fromPtr = tag->rawName;
1436 toPtr = (XML_Char *)(tag->buf + ROUND_UP(tag->rawNameLength, sizeof(XML_Char)));
1438 toPtr = (XML_Char *)tag->buf;
1439 tag->name.str = toPtr;
1441 &fromPtr, rawNameEnd,
1442 (ICHAR **)&toPtr, (ICHAR *)tag->bufEnd - 1);
1443 if (fromPtr == rawNameEnd)
1445 bufSize = (tag->bufEnd - tag->buf) << 1;
1446 tag->buf = realloc(tag->buf, bufSize);
1448 return XML_ERROR_NO_MEMORY;
1449 tag->bufEnd = tag->buf + bufSize;
1451 tag->rawName = tag->buf;
1453 *toPtr = XML_T('\0');
1454 result = storeAtts(parser, enc, s, &(tag->name), &(tag->bindings));
1457 startElementHandler(handlerArg, tag->name.str, (const XML_Char **)atts);
1458 poolClear(&tempPool);
1463 reportDefault(parser, enc, s, next);
1467 case XML_TOK_EMPTY_ELEMENT_WITH_ATTS:
1468 if (!startElementHandler) {
1469 enum XML_Error result = storeAtts(parser, enc, s, 0, 0);
1474 case XML_TOK_EMPTY_ELEMENT_NO_ATTS:
1475 if (startElementHandler || endElementHandler) {
1476 const char *rawName = s + enc->minBytesPerChar;
1477 enum XML_Error result;
1478 BINDING *bindings = 0;
1480 name.str = poolStoreString(&tempPool, enc, rawName,
1481 rawName + XmlNameLength(enc, rawName));
1483 return XML_ERROR_NO_MEMORY;
1484 poolFinish(&tempPool);
1485 result = storeAtts(parser, enc, s, &name, &bindings);
1488 poolFinish(&tempPool);
1489 if (startElementHandler)
1490 startElementHandler(handlerArg, name.str, (const XML_Char **)atts);
1491 if (endElementHandler) {
1492 if (startElementHandler)
1493 *eventPP = *eventEndPP;
1494 endElementHandler(handlerArg, name.str);
1496 poolClear(&tempPool);
1498 BINDING *b = bindings;
1499 if (endNamespaceDeclHandler)
1500 endNamespaceDeclHandler(handlerArg, b->prefix->name);
1501 bindings = bindings->nextTagBinding;
1502 b->nextTagBinding = freeBindingList;
1503 freeBindingList = b;
1504 b->prefix->binding = b->prevPrefixBinding;
1507 else if (defaultHandler)
1508 reportDefault(parser, enc, s, next);
1510 return epilogProcessor(parser, next, end, nextPtr);
1512 case XML_TOK_END_TAG:
1513 if (tagLevel == startTagLevel)
1514 return XML_ERROR_ASYNC_ENTITY;
1517 const char *rawName;
1518 TAG *tag = tagStack;
1519 tagStack = tag->parent;
1520 tag->parent = freeTagList;
1522 rawName = s + enc->minBytesPerChar*2;
1523 len = XmlNameLength(enc, rawName);
1524 if (len != tag->rawNameLength
1525 || memcmp(tag->rawName, rawName, len) != 0) {
1527 return XML_ERROR_TAG_MISMATCH;
1530 if (endElementHandler && tag->name.str) {
1531 if (tag->name.localPart) {
1532 XML_Char *to = (XML_Char *)tag->name.str + tag->name.uriLen;
1533 const XML_Char *from = tag->name.localPart;
1534 while ((*to++ = *from++) != 0)
1537 endElementHandler(handlerArg, tag->name.str);
1539 else if (defaultHandler)
1540 reportDefault(parser, enc, s, next);
1541 while (tag->bindings) {
1542 BINDING *b = tag->bindings;
1543 if (endNamespaceDeclHandler)
1544 endNamespaceDeclHandler(handlerArg, b->prefix->name);
1545 tag->bindings = tag->bindings->nextTagBinding;
1546 b->nextTagBinding = freeBindingList;
1547 freeBindingList = b;
1548 b->prefix->binding = b->prevPrefixBinding;
1551 return epilogProcessor(parser, next, end, nextPtr);
1554 case XML_TOK_CHAR_REF:
1556 int n = XmlCharRefNumber(enc, s);
1558 return XML_ERROR_BAD_CHAR_REF;
1559 if (characterDataHandler) {
1560 XML_Char buf[XML_ENCODE_MAX];
1561 characterDataHandler(handlerArg, buf, XmlEncode(n, (ICHAR *)buf));
1563 else if (defaultHandler)
1564 reportDefault(parser, enc, s, next);
1567 case XML_TOK_XML_DECL:
1568 return XML_ERROR_MISPLACED_XML_PI;
1569 case XML_TOK_DATA_NEWLINE:
1570 if (characterDataHandler) {
1572 characterDataHandler(handlerArg, &c, 1);
1574 else if (defaultHandler)
1575 reportDefault(parser, enc, s, next);
1577 case XML_TOK_CDATA_SECT_OPEN:
1579 enum XML_Error result;
1580 if (startCdataSectionHandler)
1581 startCdataSectionHandler(handlerArg);
1583 /* Suppose you doing a transformation on a document that involves
1584 changing only the character data. You set up a defaultHandler
1585 and a characterDataHandler. The defaultHandler simply copies
1586 characters through. The characterDataHandler does the transformation
1587 and writes the characters out escaping them as necessary. This case
1588 will fail to work if we leave out the following two lines (because &
1589 and < inside CDATA sections will be incorrectly escaped).
1591 However, now we have a start/endCdataSectionHandler, so it seems
1592 easier to let the user deal with this. */
1594 else if (characterDataHandler)
1595 characterDataHandler(handlerArg, dataBuf, 0);
1597 else if (defaultHandler)
1598 reportDefault(parser, enc, s, next);
1599 result = doCdataSection(parser, enc, &next, end, nextPtr);
1601 processor = cdataSectionProcessor;
1606 case XML_TOK_TRAILING_RSQB:
1609 return XML_ERROR_NONE;
1611 if (characterDataHandler) {
1612 if (MUST_CONVERT(enc, s)) {
1613 ICHAR *dataPtr = (ICHAR *)dataBuf;
1614 XmlConvert(enc, &s, end, &dataPtr, (ICHAR *)dataBufEnd);
1615 characterDataHandler(handlerArg, dataBuf,
1616 dataPtr - (ICHAR *)dataBuf);
1619 characterDataHandler(handlerArg,
1621 (XML_Char *)end - (XML_Char *)s);
1623 else if (defaultHandler)
1624 reportDefault(parser, enc, s, end);
1625 if (startTagLevel == 0) {
1627 return XML_ERROR_NO_ELEMENTS;
1629 if (tagLevel != startTagLevel) {
1631 return XML_ERROR_ASYNC_ENTITY;
1633 return XML_ERROR_NONE;
1634 case XML_TOK_DATA_CHARS:
1635 if (characterDataHandler) {
1636 if (MUST_CONVERT(enc, s)) {
1638 ICHAR *dataPtr = (ICHAR *)dataBuf;
1639 XmlConvert(enc, &s, next, &dataPtr, (ICHAR *)dataBufEnd);
1641 characterDataHandler(handlerArg, dataBuf,
1642 dataPtr - (ICHAR *)dataBuf);
1649 characterDataHandler(handlerArg,
1651 (XML_Char *)next - (XML_Char *)s);
1653 else if (defaultHandler)
1654 reportDefault(parser, enc, s, next);
1657 if (!reportProcessingInstruction(parser, enc, s, next))
1658 return XML_ERROR_NO_MEMORY;
1660 case XML_TOK_COMMENT:
1661 if (!reportComment(parser, enc, s, next))
1662 return XML_ERROR_NO_MEMORY;
1666 reportDefault(parser, enc, s, next);
1669 *eventPP = s = next;
1674 /* If tagNamePtr is non-null, build a real list of attributes,
1675 otherwise just check the attributes for well-formedness. */
1677 static enum XML_Error storeAtts(XML_Parser parser, const ENCODING *enc,
1678 const char *attStr, TAG_NAME *tagNamePtr,
1679 BINDING **bindingsPtr)
1681 ELEMENT_TYPE *elementType = 0;
1682 int nDefaultAtts = 0;
1683 const XML_Char ** appAtts;
1684 /* the attribute list to pass to the application */
1690 const XML_Char *localPart;
1692 /* lookup the element type name */
1694 elementType = (ELEMENT_TYPE *)
1695 lookup(&dtd.elementTypes, tagNamePtr->str, 0);
1697 tagNamePtr->str = poolCopyString(&dtd.pool, tagNamePtr->str);
1698 if (!tagNamePtr->str)
1699 return XML_ERROR_NO_MEMORY;
1700 elementType = (ELEMENT_TYPE *)
1701 lookup(&dtd.elementTypes, tagNamePtr->str, sizeof(ELEMENT_TYPE));
1703 return XML_ERROR_NO_MEMORY;
1704 if (ns && !setElementTypePrefix(parser, elementType))
1705 return XML_ERROR_NO_MEMORY;
1707 nDefaultAtts = elementType->nDefaultAtts;
1709 /* get the attributes from the tokenizer */
1710 n = XmlGetAttributes(enc, attStr, attsSize, atts);
1711 if (n + nDefaultAtts > attsSize) {
1712 int oldAttsSize = attsSize;
1713 attsSize = n + nDefaultAtts + INIT_ATTS_SIZE;
1714 atts = realloc((void *)atts, attsSize * sizeof(ATTRIBUTE));
1716 return XML_ERROR_NO_MEMORY;
1717 if (n > oldAttsSize)
1718 XmlGetAttributes(enc, attStr, n, atts);
1720 appAtts = (const XML_Char **)atts;
1721 for (i = 0; i < n; i++) {
1722 /* add the name and value to the attribute list */
1723 ATTRIBUTE_ID *attId = getAttributeId(parser, enc, atts[i].name,
1725 + XmlNameLength(enc, atts[i].name));
1727 return XML_ERROR_NO_MEMORY;
1728 /* detect duplicate attributes */
1729 if ((attId->name)[-1]) {
1730 if (enc == encoding)
1731 eventPtr = atts[i].name;
1732 return XML_ERROR_DUPLICATE_ATTRIBUTE;
1734 (attId->name)[-1] = 1;
1735 appAtts[attIndex++] = attId->name;
1736 if (!atts[i].normalized) {
1737 enum XML_Error result;
1740 /* figure out whether declared as other than CDATA */
1741 if (attId->maybeTokenized) {
1743 for (j = 0; j < nDefaultAtts; j++) {
1744 if (attId == elementType->defaultAtts[j].id) {
1745 isCdata = elementType->defaultAtts[j].isCdata;
1751 /* normalize the attribute value */
1752 result = storeAttributeValue(parser, enc, isCdata,
1753 atts[i].valuePtr, atts[i].valueEnd,
1758 appAtts[attIndex] = poolStart(&tempPool);
1759 poolFinish(&tempPool);
1762 poolDiscard(&tempPool);
1764 else if (tagNamePtr) {
1765 /* the value did not need normalizing */
1767 poolStoreString(&tempPool, enc, atts[i].valuePtr, atts[i].valueEnd);
1768 if (appAtts[attIndex] == 0)
1769 return XML_ERROR_NO_MEMORY;
1770 poolFinish(&tempPool);
1772 /* handle prefixed attribute names */
1773 if (attId->prefix && tagNamePtr) {
1775 /* deal with namespace declarations here */
1776 if (!addBinding(parser, attId->prefix, attId, appAtts[attIndex],
1778 return XML_ERROR_NO_MEMORY;
1782 /* deal with other prefixed names later */
1785 (attId->name)[-1] = 2;
1793 nSpecifiedAtts = attIndex;
1794 if (elementType->idAtt && (elementType->idAtt->name)[-1]) {
1795 for (i = 0; i < attIndex; i += 2)
1796 if (appAtts[i] == elementType->idAtt->name) {
1803 /* do attribute defaulting */
1804 for (j = 0; j < nDefaultAtts; j++) {
1805 const DEFAULT_ATTRIBUTE *da = elementType->defaultAtts + j;
1806 if (!(da->id->name)[-1] && da->value) {
1807 if (da->id->prefix) {
1808 if (da->id->xmlns) {
1809 if (!addBinding(parser, da->id->prefix, da->id, da->value,
1811 return XML_ERROR_NO_MEMORY;
1814 (da->id->name)[-1] = 2;
1816 appAtts[attIndex++] = da->id->name;
1817 appAtts[attIndex++] = da->value;
1821 (da->id->name)[-1] = 1;
1822 appAtts[attIndex++] = da->id->name;
1823 appAtts[attIndex++] = da->value;
1827 appAtts[attIndex] = 0;
1831 /* expand prefixed attribute names */
1832 for (; i < attIndex; i += 2) {
1833 if (appAtts[i][-1] == 2) {
1835 ((XML_Char *)(appAtts[i]))[-1] = 0;
1836 id = (ATTRIBUTE_ID *)lookup(&dtd.attributeIds, appAtts[i], 0);
1837 if (id->prefix->binding) {
1839 const BINDING *b = id->prefix->binding;
1840 const XML_Char *s = appAtts[i];
1841 for (j = 0; j < b->uriLen; j++) {
1842 if (!poolAppendChar(&tempPool, b->uri[j]))
1843 return XML_ERROR_NO_MEMORY;
1848 if (!poolAppendChar(&tempPool, *s))
1849 return XML_ERROR_NO_MEMORY;
1851 appAtts[i] = poolStart(&tempPool);
1852 poolFinish(&tempPool);
1858 ((XML_Char *)(appAtts[i]))[-1] = 0;
1861 /* clear the flags that say whether attributes were specified */
1862 for (; i < attIndex; i += 2)
1863 ((XML_Char *)(appAtts[i]))[-1] = 0;
1865 return XML_ERROR_NONE;
1866 for (binding = *bindingsPtr; binding; binding = binding->nextTagBinding)
1867 binding->attId->name[-1] = 0;
1868 /* expand the element type name */
1869 if (elementType->prefix) {
1870 binding = elementType->prefix->binding;
1872 return XML_ERROR_NONE;
1873 localPart = tagNamePtr->str;
1874 while (*localPart++ != XML_T(':'))
1877 else if (dtd.defaultPrefix.binding) {
1878 binding = dtd.defaultPrefix.binding;
1879 localPart = tagNamePtr->str;
1882 return XML_ERROR_NONE;
1883 tagNamePtr->localPart = localPart;
1884 tagNamePtr->uriLen = binding->uriLen;
1885 for (i = 0; localPart[i++];)
1887 n = i + binding->uriLen;
1888 if (n > binding->uriAlloc) {
1890 XML_Char *uri = malloc((n + EXPAND_SPARE) * sizeof(XML_Char));
1892 return XML_ERROR_NO_MEMORY;
1893 binding->uriAlloc = n + EXPAND_SPARE;
1894 memcpy(uri, binding->uri, binding->uriLen * sizeof(XML_Char));
1895 for (p = tagStack; p; p = p->parent)
1896 if (p->name.str == binding->uri)
1901 memcpy(binding->uri + binding->uriLen, localPart, i * sizeof(XML_Char));
1902 tagNamePtr->str = binding->uri;
1903 return XML_ERROR_NONE;
1907 int addBinding(XML_Parser parser,
1909 const ATTRIBUTE_ID *attId,
1910 const XML_Char *uri,
1911 BINDING **bindingsPtr)
1915 for (len = 0; uri[len]; len++)
1917 if (namespaceSeparator)
1919 if (freeBindingList) {
1920 b = freeBindingList;
1921 if (len > b->uriAlloc) {
1922 b->uri = realloc(b->uri, sizeof(XML_Char) * (len + EXPAND_SPARE));
1925 b->uriAlloc = len + EXPAND_SPARE;
1927 freeBindingList = b->nextTagBinding;
1930 b = malloc(sizeof(BINDING));
1933 b->uri = malloc(sizeof(XML_Char) * (len + EXPAND_SPARE));
1938 b->uriAlloc = len + EXPAND_SPARE;
1941 memcpy(b->uri, uri, len * sizeof(XML_Char));
1942 if (namespaceSeparator)
1943 b->uri[len - 1] = namespaceSeparator;
1946 b->prevPrefixBinding = prefix->binding;
1947 if (*uri == XML_T('\0') && prefix == &dtd.defaultPrefix)
1948 prefix->binding = 0;
1950 prefix->binding = b;
1951 b->nextTagBinding = *bindingsPtr;
1953 if (startNamespaceDeclHandler)
1954 startNamespaceDeclHandler(handlerArg, prefix->name,
1955 prefix->binding ? uri : 0);
1959 /* The idea here is to avoid using stack for each CDATA section when
1960 the whole file is parsed with one call. */
1963 enum XML_Error cdataSectionProcessor(XML_Parser parser,
1966 const char **endPtr)
1968 enum XML_Error result =
1969 doCdataSection(parser, encoding, &start, end, endPtr);
1971 processor = contentProcessor;
1972 return contentProcessor(parser, start, end, endPtr);
1977 /* startPtr gets set to non-null is the section is closed, and to null if
1978 the section is not yet closed. */
1981 enum XML_Error doCdataSection(XML_Parser parser,
1982 const ENCODING *enc,
1983 const char **startPtr,
1985 const char **nextPtr)
1987 const char *s = *startPtr;
1988 const char **eventPP;
1989 const char **eventEndPP;
1990 if (enc == encoding) {
1991 eventPP = &eventPtr;
1993 eventEndPP = &eventEndPtr;
1996 eventPP = &(openInternalEntities->internalEventPtr);
1997 eventEndPP = &(openInternalEntities->internalEventEndPtr);
2003 int tok = XmlCdataSectionTok(enc, s, end, &next);
2006 case XML_TOK_CDATA_SECT_CLOSE:
2007 if (endCdataSectionHandler)
2008 endCdataSectionHandler(handlerArg);
2009 else if (defaultHandler)
2010 reportDefault(parser, enc, s, next);
2012 return XML_ERROR_NONE;
2013 case XML_TOK_DATA_NEWLINE:
2014 if (characterDataHandler) {
2016 characterDataHandler(handlerArg, &c, 1);
2018 else if (defaultHandler)
2019 reportDefault(parser, enc, s, next);
2021 case XML_TOK_DATA_CHARS:
2022 if (characterDataHandler) {
2023 if (MUST_CONVERT(enc, s)) {
2025 ICHAR *dataPtr = (ICHAR *)dataBuf;
2026 XmlConvert(enc, &s, next, &dataPtr, (ICHAR *)dataBufEnd);
2028 characterDataHandler(handlerArg, dataBuf, dataPtr - (ICHAR *)dataBuf);
2035 characterDataHandler(handlerArg,
2037 (XML_Char *)next - (XML_Char *)s);
2039 else if (defaultHandler)
2040 reportDefault(parser, enc, s, next);
2042 case XML_TOK_INVALID:
2044 return XML_ERROR_INVALID_TOKEN;
2045 case XML_TOK_PARTIAL_CHAR:
2048 return XML_ERROR_NONE;
2050 return XML_ERROR_PARTIAL_CHAR;
2051 case XML_TOK_PARTIAL:
2055 return XML_ERROR_NONE;
2057 return XML_ERROR_UNCLOSED_CDATA_SECTION;
2061 *eventPP = s = next;
2068 /* The idea here is to avoid using stack for each IGNORE section when
2069 the whole file is parsed with one call. */
2072 enum XML_Error ignoreSectionProcessor(XML_Parser parser,
2075 const char **endPtr)
2077 enum XML_Error result =
2078 doIgnoreSection(parser, encoding, &start, end, endPtr);
2080 processor = prologProcessor;
2081 return prologProcessor(parser, start, end, endPtr);
2086 /* startPtr gets set to non-null is the section is closed, and to null if
2087 the section is not yet closed. */
2090 enum XML_Error doIgnoreSection(XML_Parser parser,
2091 const ENCODING *enc,
2092 const char **startPtr,
2094 const char **nextPtr)
2098 const char *s = *startPtr;
2099 const char **eventPP;
2100 const char **eventEndPP;
2101 if (enc == encoding) {
2102 eventPP = &eventPtr;
2104 eventEndPP = &eventEndPtr;
2107 eventPP = &(openInternalEntities->internalEventPtr);
2108 eventEndPP = &(openInternalEntities->internalEventEndPtr);
2112 tok = XmlIgnoreSectionTok(enc, s, end, &next);
2115 case XML_TOK_IGNORE_SECT:
2117 reportDefault(parser, enc, s, next);
2119 return XML_ERROR_NONE;
2120 case XML_TOK_INVALID:
2122 return XML_ERROR_INVALID_TOKEN;
2123 case XML_TOK_PARTIAL_CHAR:
2126 return XML_ERROR_NONE;
2128 return XML_ERROR_PARTIAL_CHAR;
2129 case XML_TOK_PARTIAL:
2133 return XML_ERROR_NONE;
2135 return XML_ERROR_SYNTAX; /* XML_ERROR_UNCLOSED_IGNORE_SECTION */
2142 #endif /* XML_DTD */
2144 static enum XML_Error
2145 initializeEncoding(XML_Parser parser)
2149 char encodingBuf[128];
2150 if (!protocolEncodingName)
2154 for (i = 0; protocolEncodingName[i]; i++) {
2155 if (i == sizeof(encodingBuf) - 1
2156 || (protocolEncodingName[i] & ~0x7f) != 0) {
2157 encodingBuf[0] = '\0';
2160 encodingBuf[i] = (char)protocolEncodingName[i];
2162 encodingBuf[i] = '\0';
2166 s = protocolEncodingName;
2168 if ((ns ? XmlInitEncodingNS : xmlrpc_XmlInitEncoding)(&initEncoding, &encoding, s))
2169 return XML_ERROR_NONE;
2170 return handleUnknownEncoding(parser, protocolEncodingName);
2173 static enum XML_Error
2174 processXmlDecl(XML_Parser parser, int isGeneralTextEntity,
2175 const char *s, const char *next)
2177 const char *encodingName = 0;
2178 const ENCODING *newEncoding = 0;
2179 const char *version;
2180 int standalone = -1;
2183 : xmlrpc_XmlParseXmlDecl)(isGeneralTextEntity,
2192 return XML_ERROR_SYNTAX;
2193 if (!isGeneralTextEntity && standalone == 1) {
2196 if (paramEntityParsing == XML_PARAM_ENTITY_PARSING_UNLESS_STANDALONE)
2197 paramEntityParsing = XML_PARAM_ENTITY_PARSING_NEVER;
2198 #endif /* XML_DTD */
2201 reportDefault(parser, encoding, s, next);
2202 if (!protocolEncodingName) {
2204 if (newEncoding->minBytesPerChar != encoding->minBytesPerChar) {
2205 eventPtr = encodingName;
2206 return XML_ERROR_INCORRECT_ENCODING;
2208 encoding = newEncoding;
2210 else if (encodingName) {
2211 enum XML_Error result;
2212 const XML_Char * s =
2213 poolStoreString(&tempPool,
2217 + XmlNameLength(encoding, encodingName));
2219 return XML_ERROR_NO_MEMORY;
2220 result = handleUnknownEncoding(parser, s);
2221 poolDiscard(&tempPool);
2222 if (result == XML_ERROR_UNKNOWN_ENCODING)
2223 eventPtr = encodingName;
2227 return XML_ERROR_NONE;
2230 static enum XML_Error
2231 handleUnknownEncoding(XML_Parser parser, const XML_Char *encodingName)
2233 if (unknownEncodingHandler) {
2236 for (i = 0; i < 256; i++)
2241 if (unknownEncodingHandler(unknownEncodingHandlerData,
2242 encodingName, &info)) {
2244 unknownEncodingMem = malloc(xmlrpc_XmlSizeOfUnknownEncoding());
2245 if (!unknownEncodingMem) {
2247 info.release(info.data);
2248 return XML_ERROR_NO_MEMORY;
2251 ? XmlInitUnknownEncodingNS
2252 : xmlrpc_XmlInitUnknownEncoding)(unknownEncodingMem,
2257 unknownEncodingData = info.data;
2258 unknownEncodingRelease = info.release;
2260 return XML_ERROR_NONE;
2264 info.release(info.data);
2266 return XML_ERROR_UNKNOWN_ENCODING;
2269 static enum XML_Error
2270 prologInitProcessor(XML_Parser parser,
2273 const char **nextPtr)
2275 enum XML_Error result = initializeEncoding(parser);
2276 if (result != XML_ERROR_NONE)
2278 processor = prologProcessor;
2279 return prologProcessor(parser, s, end, nextPtr);
2282 static enum XML_Error
2283 prologProcessor(XML_Parser parser,
2286 const char **nextPtr)
2289 int tok = XmlPrologTok(encoding, s, end, &next);
2290 return doProlog(parser, encoding, s, end, tok, next, nextPtr);
2293 static enum XML_Error
2294 doProlog(XML_Parser parser,
2295 const ENCODING *enc,
2300 const char **nextPtr)
2303 static const XML_Char externalSubsetName[] = { '#' , '\0' };
2304 #endif /* XML_DTD */
2306 const char **eventPP;
2307 const char **eventEndPP;
2308 if (enc == encoding) {
2309 eventPP = &eventPtr;
2310 eventEndPP = &eventEndPtr;
2313 eventPP = &(openInternalEntities->internalEventPtr);
2314 eventEndPP = &(openInternalEntities->internalEventEndPtr);
2321 if (nextPtr != 0 && tok != XML_TOK_INVALID) {
2323 return XML_ERROR_NONE;
2326 case XML_TOK_INVALID:
2328 return XML_ERROR_INVALID_TOKEN;
2329 case XML_TOK_PARTIAL:
2330 return XML_ERROR_UNCLOSED_TOKEN;
2331 case XML_TOK_PARTIAL_CHAR:
2332 return XML_ERROR_PARTIAL_CHAR;
2335 if (enc != encoding)
2336 return XML_ERROR_NONE;
2338 if (XmlTokenRole(&prologState, XML_TOK_NONE, end, end, enc)
2340 return XML_ERROR_SYNTAX;
2341 hadExternalDoctype = 0;
2342 return XML_ERROR_NONE;
2344 #endif /* XML_DTD */
2345 return XML_ERROR_NO_ELEMENTS;
2352 role = XmlTokenRole(&prologState, tok, s, next, enc);
2354 case XML_ROLE_XML_DECL:
2356 enum XML_Error result = processXmlDecl(parser, 0, s, next);
2357 if (result != XML_ERROR_NONE)
2362 case XML_ROLE_DOCTYPE_NAME:
2363 if (startDoctypeDeclHandler) {
2364 const XML_Char *name = poolStoreString(&tempPool, enc, s, next);
2366 return XML_ERROR_NO_MEMORY;
2367 startDoctypeDeclHandler(handlerArg, name);
2368 poolClear(&tempPool);
2372 case XML_ROLE_TEXT_DECL:
2374 enum XML_Error result = processXmlDecl(parser, 1, s, next);
2375 if (result != XML_ERROR_NONE)
2380 #endif /* XML_DTD */
2381 case XML_ROLE_DOCTYPE_PUBLIC_ID:
2383 declEntity = (ENTITY *)lookup(&dtd.paramEntities,
2387 return XML_ERROR_NO_MEMORY;
2388 #endif /* XML_DTD */
2390 case XML_ROLE_ENTITY_PUBLIC_ID:
2391 if (!XmlIsPublicId(enc, s, next, eventPP))
2392 return XML_ERROR_SYNTAX;
2394 XML_Char *tem = poolStoreString(&dtd.pool,
2396 s + enc->minBytesPerChar,
2397 next - enc->minBytesPerChar);
2399 return XML_ERROR_NO_MEMORY;
2400 normalizePublicId(tem);
2401 declEntity->publicId = tem;
2402 poolFinish(&dtd.pool);
2405 case XML_ROLE_DOCTYPE_CLOSE:
2406 if (dtd.complete && hadExternalDoctype) {
2409 if (paramEntityParsing && externalEntityRefHandler) {
2410 ENTITY *entity = (ENTITY *)lookup(&dtd.paramEntities,
2413 if (!externalEntityRefHandler(externalEntityRefHandlerArg,
2418 return XML_ERROR_EXTERNAL_ENTITY_HANDLING;
2420 #endif /* XML_DTD */
2423 && notStandaloneHandler
2424 && !notStandaloneHandler(handlerArg))
2425 return XML_ERROR_NOT_STANDALONE;
2427 if (endDoctypeDeclHandler)
2428 endDoctypeDeclHandler(handlerArg);
2430 case XML_ROLE_INSTANCE_START:
2431 processor = contentProcessor;
2432 return contentProcessor(parser, s, end, nextPtr);
2433 case XML_ROLE_ATTLIST_ELEMENT_NAME:
2435 const XML_Char *name = poolStoreString(&dtd.pool, enc, s, next);
2437 return XML_ERROR_NO_MEMORY;
2438 declElementType = (ELEMENT_TYPE *)
2439 lookup(&dtd.elementTypes, name, sizeof(ELEMENT_TYPE));
2440 if (!declElementType)
2441 return XML_ERROR_NO_MEMORY;
2442 if (declElementType->name != name)
2443 poolDiscard(&dtd.pool);
2445 poolFinish(&dtd.pool);
2446 if (!setElementTypePrefix(parser, declElementType))
2447 return XML_ERROR_NO_MEMORY;
2451 case XML_ROLE_ATTRIBUTE_NAME:
2452 declAttributeId = getAttributeId(parser, enc, s, next);
2453 if (!declAttributeId)
2454 return XML_ERROR_NO_MEMORY;
2455 declAttributeIsCdata = 0;
2456 declAttributeIsId = 0;
2458 case XML_ROLE_ATTRIBUTE_TYPE_CDATA:
2459 declAttributeIsCdata = 1;
2461 case XML_ROLE_ATTRIBUTE_TYPE_ID:
2462 declAttributeIsId = 1;
2464 case XML_ROLE_IMPLIED_ATTRIBUTE_VALUE:
2465 case XML_ROLE_REQUIRED_ATTRIBUTE_VALUE:
2467 && !defineAttribute(declElementType, declAttributeId,
2468 declAttributeIsCdata,
2469 declAttributeIsId, 0))
2470 return XML_ERROR_NO_MEMORY;
2472 case XML_ROLE_DEFAULT_ATTRIBUTE_VALUE:
2473 case XML_ROLE_FIXED_ATTRIBUTE_VALUE:
2475 const XML_Char *attVal;
2476 enum XML_Error result
2477 = storeAttributeValue(parser, enc, declAttributeIsCdata,
2478 s + enc->minBytesPerChar,
2479 next - enc->minBytesPerChar,
2483 attVal = poolStart(&dtd.pool);
2484 poolFinish(&dtd.pool);
2486 /* ID attributes aren't allowed to have a default */
2487 && !defineAttribute(declElementType, declAttributeId,
2488 declAttributeIsCdata, 0, attVal))
2489 return XML_ERROR_NO_MEMORY;
2492 case XML_ROLE_ENTITY_VALUE:
2494 enum XML_Error result = storeEntityValue(parser, enc,
2495 s + enc->minBytesPerChar,
2496 next - enc->minBytesPerChar);
2498 declEntity->textPtr = poolStart(&dtd.pool);
2499 declEntity->textLen = poolLength(&dtd.pool);
2500 poolFinish(&dtd.pool);
2501 if (internalParsedEntityDeclHandler
2502 /* Check it's not a parameter entity */
2503 && ((ENTITY *)lookup(&dtd.generalEntities, declEntity->name, 0)
2506 internalParsedEntityDeclHandler(handlerArg,
2508 declEntity->textPtr,
2509 declEntity->textLen);
2513 poolDiscard(&dtd.pool);
2514 if (result != XML_ERROR_NONE)
2518 case XML_ROLE_DOCTYPE_SYSTEM_ID:
2521 && !paramEntityParsing
2522 #endif /* XML_DTD */
2523 && notStandaloneHandler
2524 && !notStandaloneHandler(handlerArg))
2525 return XML_ERROR_NOT_STANDALONE;
2526 hadExternalDoctype = 1;
2531 declEntity = (ENTITY *)lookup(&dtd.paramEntities,
2535 return XML_ERROR_NO_MEMORY;
2538 #endif /* XML_DTD */
2539 case XML_ROLE_ENTITY_SYSTEM_ID:
2541 declEntity->systemId = poolStoreString(&dtd.pool, enc,
2542 s + enc->minBytesPerChar,
2543 next - enc->minBytesPerChar);
2544 if (!declEntity->systemId)
2545 return XML_ERROR_NO_MEMORY;
2546 declEntity->base = curBase;
2547 poolFinish(&dtd.pool);
2550 case XML_ROLE_ENTITY_NOTATION_NAME:
2552 declEntity->notation = poolStoreString(&dtd.pool, enc, s, next);
2553 if (!declEntity->notation)
2554 return XML_ERROR_NO_MEMORY;
2555 poolFinish(&dtd.pool);
2556 if (unparsedEntityDeclHandler) {
2558 unparsedEntityDeclHandler(handlerArg,
2561 declEntity->systemId,
2562 declEntity->publicId,
2563 declEntity->notation);
2568 case XML_ROLE_EXTERNAL_GENERAL_ENTITY_NO_NOTATION:
2569 if (declEntity && externalParsedEntityDeclHandler) {
2571 externalParsedEntityDeclHandler(handlerArg,
2574 declEntity->systemId,
2575 declEntity->publicId);
2578 case XML_ROLE_GENERAL_ENTITY_NAME:
2580 const XML_Char *name;
2581 if (XmlPredefinedEntityName(enc, s, next)) {
2585 name = poolStoreString(&dtd.pool, enc, s, next);
2587 return XML_ERROR_NO_MEMORY;
2589 declEntity = (ENTITY *)
2590 lookup(&dtd.generalEntities, name, sizeof(ENTITY));
2592 return XML_ERROR_NO_MEMORY;
2593 if (declEntity->name != name) {
2594 poolDiscard(&dtd.pool);
2598 poolFinish(&dtd.pool);
2601 poolDiscard(&dtd.pool);
2606 case XML_ROLE_PARAM_ENTITY_NAME:
2609 const XML_Char *name = poolStoreString(&dtd.pool, enc, s, next);
2611 return XML_ERROR_NO_MEMORY;
2612 declEntity = (ENTITY *)
2613 lookup(&dtd.paramEntities, name, sizeof(ENTITY));
2615 return XML_ERROR_NO_MEMORY;
2616 if (declEntity->name != name) {
2617 poolDiscard(&dtd.pool);
2621 poolFinish(&dtd.pool);
2623 #else /* not XML_DTD */
2625 #endif /* not XML_DTD */
2627 case XML_ROLE_NOTATION_NAME:
2628 declNotationPublicId = 0;
2629 declNotationName = 0;
2630 if (notationDeclHandler) {
2631 declNotationName = poolStoreString(&tempPool, enc, s, next);
2632 if (!declNotationName)
2633 return XML_ERROR_NO_MEMORY;
2634 poolFinish(&tempPool);
2637 case XML_ROLE_NOTATION_PUBLIC_ID:
2638 if (!XmlIsPublicId(enc, s, next, eventPP))
2639 return XML_ERROR_SYNTAX;
2640 if (declNotationName) {
2641 XML_Char *tem = poolStoreString(&tempPool,
2643 s + enc->minBytesPerChar,
2644 next - enc->minBytesPerChar);
2646 return XML_ERROR_NO_MEMORY;
2647 normalizePublicId(tem);
2648 declNotationPublicId = tem;
2649 poolFinish(&tempPool);
2652 case XML_ROLE_NOTATION_SYSTEM_ID:
2653 if (declNotationName && notationDeclHandler) {
2654 const XML_Char *systemId
2655 = poolStoreString(&tempPool, enc,
2656 s + enc->minBytesPerChar,
2657 next - enc->minBytesPerChar);
2659 return XML_ERROR_NO_MEMORY;
2661 notationDeclHandler(handlerArg,
2665 declNotationPublicId);
2667 poolClear(&tempPool);
2669 case XML_ROLE_NOTATION_NO_SYSTEM_ID:
2670 if (declNotationPublicId && notationDeclHandler) {
2672 notationDeclHandler(handlerArg,
2676 declNotationPublicId);
2678 poolClear(&tempPool);
2680 case XML_ROLE_ERROR:
2682 case XML_TOK_PARAM_ENTITY_REF:
2683 return XML_ERROR_PARAM_ENTITY_REF;
2684 case XML_TOK_XML_DECL:
2685 return XML_ERROR_MISPLACED_XML_PI;
2687 return XML_ERROR_SYNTAX;
2690 case XML_ROLE_IGNORE_SECT:
2692 enum XML_Error result;
2694 reportDefault(parser, enc, s, next);
2695 result = doIgnoreSection(parser, enc, &next, end, nextPtr);
2697 processor = ignoreSectionProcessor;
2702 #endif /* XML_DTD */
2703 case XML_ROLE_GROUP_OPEN:
2704 if (prologState.level >= groupSize) {
2706 groupConnector = realloc(groupConnector, groupSize *= 2);
2708 groupConnector = malloc(groupSize = 32);
2709 if (!groupConnector)
2710 return XML_ERROR_NO_MEMORY;
2712 groupConnector[prologState.level] = 0;
2714 case XML_ROLE_GROUP_SEQUENCE:
2715 if (groupConnector[prologState.level] == '|')
2716 return XML_ERROR_SYNTAX;
2717 groupConnector[prologState.level] = ',';
2719 case XML_ROLE_GROUP_CHOICE:
2720 if (groupConnector[prologState.level] == ',')
2721 return XML_ERROR_SYNTAX;
2722 groupConnector[prologState.level] = '|';
2724 case XML_ROLE_PARAM_ENTITY_REF:
2726 case XML_ROLE_INNER_PARAM_ENTITY_REF:
2727 if (paramEntityParsing
2728 && (dtd.complete || role == XML_ROLE_INNER_PARAM_ENTITY_REF)) {
2729 const XML_Char *name;
2731 name = poolStoreString(&dtd.pool, enc,
2732 s + enc->minBytesPerChar,
2733 next - enc->minBytesPerChar);
2735 return XML_ERROR_NO_MEMORY;
2736 entity = (ENTITY *)lookup(&dtd.paramEntities, name, 0);
2737 poolDiscard(&dtd.pool);
2739 /* FIXME what to do if !dtd.complete? */
2740 return XML_ERROR_UNDEFINED_ENTITY;
2743 return XML_ERROR_RECURSIVE_ENTITY_REF;
2744 if (entity->textPtr) {
2745 enum XML_Error result;
2746 result = processInternalParamEntity(parser, entity);
2747 if (result != XML_ERROR_NONE)
2751 if (role == XML_ROLE_INNER_PARAM_ENTITY_REF)
2752 return XML_ERROR_PARAM_ENTITY_REF;
2753 if (externalEntityRefHandler) {
2756 if (!externalEntityRefHandler(externalEntityRefHandlerArg,
2760 entity->publicId)) {
2762 return XML_ERROR_EXTERNAL_ENTITY_HANDLING;
2769 #endif /* XML_DTD */
2771 && notStandaloneHandler
2772 && !notStandaloneHandler(handlerArg))
2773 return XML_ERROR_NOT_STANDALONE;
2776 reportDefault(parser, enc, s, next);
2781 if (!reportProcessingInstruction(parser, enc, s, next))
2782 return XML_ERROR_NO_MEMORY;
2784 case XML_TOK_COMMENT:
2785 if (!reportComment(parser, enc, s, next))
2786 return XML_ERROR_NO_MEMORY;
2791 if (defaultHandler) {
2794 case XML_TOK_COMMENT:
2796 case XML_TOK_XML_DECL:
2798 case XML_TOK_IGNORE_SECT:
2799 #endif /* XML_DTD */
2800 case XML_TOK_PARAM_ENTITY_REF:
2804 if (role != XML_ROLE_IGNORE_SECT)
2805 #endif /* XML_DTD */
2806 reportDefault(parser, enc, s, next);
2810 tok = XmlPrologTok(enc, s, end, &next);
2816 enum XML_Error epilogProcessor(XML_Parser parser,
2819 const char **nextPtr)
2821 processor = epilogProcessor;
2825 int tok = XmlPrologTok(encoding, s, end, &next);
2828 case -XML_TOK_PROLOG_S:
2829 if (defaultHandler) {
2831 reportDefault(parser, encoding, s, end);
2837 return XML_ERROR_NONE;
2838 case XML_TOK_PROLOG_S:
2840 reportDefault(parser, encoding, s, next);
2843 if (!reportProcessingInstruction(parser, encoding, s, next))
2844 return XML_ERROR_NO_MEMORY;
2846 case XML_TOK_COMMENT:
2847 if (!reportComment(parser, encoding, s, next))
2848 return XML_ERROR_NO_MEMORY;
2850 case XML_TOK_INVALID:
2852 return XML_ERROR_INVALID_TOKEN;
2853 case XML_TOK_PARTIAL:
2856 return XML_ERROR_NONE;
2858 return XML_ERROR_UNCLOSED_TOKEN;
2859 case XML_TOK_PARTIAL_CHAR:
2862 return XML_ERROR_NONE;
2864 return XML_ERROR_PARTIAL_CHAR;
2866 return XML_ERROR_JUNK_AFTER_DOC_ELEMENT;
2868 eventPtr = s = next;
2874 static enum XML_Error
2875 processInternalParamEntity(XML_Parser parser, ENTITY *entity)
2877 const char *s, *end, *next;
2879 enum XML_Error result;
2880 OPEN_INTERNAL_ENTITY openEntity;
2882 openEntity.next = openInternalEntities;
2883 openInternalEntities = &openEntity;
2884 openEntity.entity = entity;
2885 openEntity.internalEventPtr = 0;
2886 openEntity.internalEventEndPtr = 0;
2887 s = (char *)entity->textPtr;
2888 end = (char *)(entity->textPtr + entity->textLen);
2889 tok = XmlPrologTok(internalEncoding, s, end, &next);
2890 result = doProlog(parser, internalEncoding, s, end, tok, next, 0);
2892 openInternalEntities = openEntity.next;
2896 #endif /* XML_DTD */
2900 static enum XML_Error
2901 errorProcessor(XML_Parser const parser ATTR_UNUSED,
2902 const char * const s ATTR_UNUSED,
2903 const char * const end ATTR_UNUSED,
2904 const char ** const nextPtr ATTR_UNUSED) {
2911 static enum XML_Error
2912 storeAttributeValue(XML_Parser parser, const ENCODING *enc, int isCdata,
2913 const char *ptr, const char *end,
2916 enum XML_Error result =
2917 appendAttributeValue(parser, enc, isCdata, ptr, end, pool);
2920 if (!isCdata && poolLength(pool) && poolLastChar(pool) == 0x20)
2922 if (!poolAppendChar(pool, XML_T('\0')))
2923 return XML_ERROR_NO_MEMORY;
2924 return XML_ERROR_NONE;
2927 static enum XML_Error
2928 appendAttributeValue(XML_Parser parser, const ENCODING *enc, int isCdata,
2929 const char *ptr, const char *end,
2934 int tok = XmlAttributeValueTok(enc, ptr, end, &next);
2937 return XML_ERROR_NONE;
2938 case XML_TOK_INVALID:
2939 if (enc == encoding)
2941 return XML_ERROR_INVALID_TOKEN;
2942 case XML_TOK_PARTIAL:
2943 if (enc == encoding)
2945 return XML_ERROR_INVALID_TOKEN;
2946 case XML_TOK_CHAR_REF:
2948 XML_Char buf[XML_ENCODE_MAX];
2950 int n = XmlCharRefNumber(enc, ptr);
2952 if (enc == encoding)
2954 return XML_ERROR_BAD_CHAR_REF;
2957 && n == 0x20 /* space */
2958 && (poolLength(pool) == 0 || poolLastChar(pool) == 0x20))
2960 n = XmlEncode(n, (ICHAR *)buf);
2962 if (enc == encoding)
2964 return XML_ERROR_BAD_CHAR_REF;
2966 for (i = 0; i < n; i++) {
2967 if (!poolAppendChar(pool, buf[i]))
2968 return XML_ERROR_NO_MEMORY;
2972 case XML_TOK_DATA_CHARS:
2973 if (!poolAppend(pool, enc, ptr, next))
2974 return XML_ERROR_NO_MEMORY;
2977 case XML_TOK_TRAILING_CR:
2978 next = ptr + enc->minBytesPerChar;
2980 case XML_TOK_ATTRIBUTE_VALUE_S:
2981 case XML_TOK_DATA_NEWLINE:
2982 if (!isCdata && (poolLength(pool) == 0 || poolLastChar(pool) == 0x20))
2984 if (!poolAppendChar(pool, 0x20))
2985 return XML_ERROR_NO_MEMORY;
2987 case XML_TOK_ENTITY_REF:
2989 const XML_Char *name;
2991 XML_Char ch = XmlPredefinedEntityName(enc,
2992 ptr + enc->minBytesPerChar,
2993 next - enc->minBytesPerChar);
2995 if (!poolAppendChar(pool, ch))
2996 return XML_ERROR_NO_MEMORY;
2999 name = poolStoreString(&temp2Pool, enc,
3000 ptr + enc->minBytesPerChar,
3001 next - enc->minBytesPerChar);
3003 return XML_ERROR_NO_MEMORY;
3004 entity = (ENTITY *)lookup(&dtd.generalEntities, name, 0);
3005 poolDiscard(&temp2Pool);
3008 if (enc == encoding)
3010 return XML_ERROR_UNDEFINED_ENTITY;
3013 else if (entity->open) {
3014 if (enc == encoding)
3016 return XML_ERROR_RECURSIVE_ENTITY_REF;
3018 else if (entity->notation) {
3019 if (enc == encoding)
3021 return XML_ERROR_BINARY_ENTITY_REF;
3023 else if (!entity->textPtr) {
3024 if (enc == encoding)
3026 return XML_ERROR_ATTRIBUTE_EXTERNAL_ENTITY_REF;
3029 enum XML_Error result;
3030 const XML_Char *textEnd = entity->textPtr + entity->textLen;
3032 result = appendAttributeValue(parser, internalEncoding,
3033 isCdata, (char *)entity->textPtr,
3034 (char *)textEnd, pool);
3050 enum XML_Error storeEntityValue(XML_Parser parser,
3051 const ENCODING *enc,
3052 const char *entityTextPtr,
3053 const char *entityTextEnd)
3055 STRING_POOL *pool = &(dtd.pool);
3058 int tok = XmlEntityValueTok(enc, entityTextPtr, entityTextEnd, &next);
3060 case XML_TOK_PARAM_ENTITY_REF:
3062 if (parentParser || enc != encoding) {
3063 enum XML_Error result;
3064 const XML_Char *name;
3066 name = poolStoreString(&tempPool, enc,
3067 entityTextPtr + enc->minBytesPerChar,
3068 next - enc->minBytesPerChar);
3070 return XML_ERROR_NO_MEMORY;
3071 entity = (ENTITY *)lookup(&dtd.paramEntities, name, 0);
3072 poolDiscard(&tempPool);
3074 if (enc == encoding)
3075 eventPtr = entityTextPtr;
3076 return XML_ERROR_UNDEFINED_ENTITY;
3079 if (enc == encoding)
3080 eventPtr = entityTextPtr;
3081 return XML_ERROR_RECURSIVE_ENTITY_REF;
3083 if (entity->systemId) {
3084 if (enc == encoding)
3085 eventPtr = entityTextPtr;
3086 return XML_ERROR_PARAM_ENTITY_REF;
3089 result = storeEntityValue(parser,
3091 (char *)entity->textPtr,
3092 (char *)(entity->textPtr + entity->textLen));
3098 #endif /* XML_DTD */
3099 eventPtr = entityTextPtr;
3100 return XML_ERROR_SYNTAX;
3102 return XML_ERROR_NONE;
3103 case XML_TOK_ENTITY_REF:
3104 case XML_TOK_DATA_CHARS:
3105 if (!poolAppend(pool, enc, entityTextPtr, next))
3106 return XML_ERROR_NO_MEMORY;
3108 case XML_TOK_TRAILING_CR:
3109 next = entityTextPtr + enc->minBytesPerChar;
3111 case XML_TOK_DATA_NEWLINE:
3112 if (pool->end == pool->ptr && !poolGrow(pool))
3113 return XML_ERROR_NO_MEMORY;
3114 *(pool->ptr)++ = 0xA;
3116 case XML_TOK_CHAR_REF:
3118 XML_Char buf[XML_ENCODE_MAX];
3120 int n = XmlCharRefNumber(enc, entityTextPtr);
3122 if (enc == encoding)
3123 eventPtr = entityTextPtr;
3124 return XML_ERROR_BAD_CHAR_REF;
3126 n = XmlEncode(n, (ICHAR *)buf);
3128 if (enc == encoding)
3129 eventPtr = entityTextPtr;
3130 return XML_ERROR_BAD_CHAR_REF;
3132 for (i = 0; i < n; i++) {
3133 if (pool->end == pool->ptr && !poolGrow(pool))
3134 return XML_ERROR_NO_MEMORY;
3135 *(pool->ptr)++ = buf[i];
3139 case XML_TOK_PARTIAL:
3140 if (enc == encoding)
3141 eventPtr = entityTextPtr;
3142 return XML_ERROR_INVALID_TOKEN;
3143 case XML_TOK_INVALID:
3144 if (enc == encoding)
3146 return XML_ERROR_INVALID_TOKEN;
3150 entityTextPtr = next;
3156 normalizeLines(XML_Char *s)
3160 if (*s == XML_T('\0'))
3179 reportProcessingInstruction(XML_Parser parser,
3180 const ENCODING *enc,
3184 const XML_Char *target;
3187 if (!processingInstructionHandler) {
3189 reportDefault(parser, enc, start, end);
3192 start += enc->minBytesPerChar * 2;
3193 tem = start + XmlNameLength(enc, start);
3194 target = poolStoreString(&tempPool, enc, start, tem);
3197 poolFinish(&tempPool);
3198 data = poolStoreString(&tempPool, enc,
3200 end - enc->minBytesPerChar*2);
3203 normalizeLines(data);
3204 processingInstructionHandler(handlerArg, target, data);
3205 poolClear(&tempPool);
3210 reportComment(XML_Parser parser,
3211 const ENCODING *enc,
3216 if (!commentHandler) {
3218 reportDefault(parser, enc, start, end);
3221 data = poolStoreString(&tempPool,
3223 start + enc->minBytesPerChar * 4,
3224 end - enc->minBytesPerChar * 3);
3227 normalizeLines(data);
3228 commentHandler(handlerArg, data);
3229 poolClear(&tempPool);
3234 reportDefault(XML_Parser parser,
3235 const ENCODING *enc,
3239 if (MUST_CONVERT(enc, s)) {
3240 const char **eventPP;
3241 const char **eventEndPP;
3242 if (enc == encoding) {
3243 eventPP = &eventPtr;
3244 eventEndPP = &eventEndPtr;
3247 eventPP = &(openInternalEntities->internalEventPtr);
3248 eventEndPP = &(openInternalEntities->internalEventEndPtr);
3251 ICHAR *dataPtr = (ICHAR *)dataBuf;
3252 XmlConvert(enc, &s, end, &dataPtr, (ICHAR *)dataBufEnd);
3254 defaultHandler(handlerArg, dataBuf, dataPtr - (ICHAR *)dataBuf);
3259 defaultHandler(handlerArg, (XML_Char *)s, (XML_Char *)end - (XML_Char *)s);
3264 defineAttribute(ELEMENT_TYPE *type,
3265 ATTRIBUTE_ID *attId,
3268 const XML_Char *value)
3270 DEFAULT_ATTRIBUTE *att;
3271 if (value || isId) {
3272 /* The handling of default attributes gets messed up if we have
3273 a default which duplicates a non-default. */
3275 for (i = 0; i < type->nDefaultAtts; i++)
3276 if (attId == type->defaultAtts[i].id)
3278 if (isId && !type->idAtt && !attId->xmlns)
3279 type->idAtt = attId;
3281 if (type->nDefaultAtts == type->allocDefaultAtts) {
3282 if (type->allocDefaultAtts == 0) {
3283 type->allocDefaultAtts = 8;
3285 malloc(type->allocDefaultAtts*sizeof(DEFAULT_ATTRIBUTE));
3288 type->allocDefaultAtts *= 2;
3290 realloc(type->defaultAtts,
3291 type->allocDefaultAtts*sizeof(DEFAULT_ATTRIBUTE));
3293 if (!type->defaultAtts)
3296 att = type->defaultAtts + type->nDefaultAtts;
3299 att->isCdata = isCdata;
3301 attId->maybeTokenized = 1;
3302 type->nDefaultAtts += 1;
3306 static int setElementTypePrefix(XML_Parser parser, ELEMENT_TYPE *elementType)
3308 const XML_Char *name;
3309 for (name = elementType->name; *name; name++) {
3310 if (*name == XML_T(':')) {
3313 for (s = elementType->name; s != name; s++) {
3314 if (!poolAppendChar(&dtd.pool, *s))
3317 if (!poolAppendChar(&dtd.pool, XML_T('\0')))
3320 lookup(&dtd.prefixes, poolStart(&dtd.pool), sizeof(PREFIX));
3323 if (prefix->name == poolStart(&dtd.pool))
3324 poolFinish(&dtd.pool);
3326 poolDiscard(&dtd.pool);
3327 elementType->prefix = prefix;
3334 static ATTRIBUTE_ID *
3335 getAttributeId(XML_Parser parser,
3336 const ENCODING *enc,
3341 const XML_Char *name;
3342 if (!poolAppendChar(&dtd.pool, XML_T('\0')))
3344 name = poolStoreString(&dtd.pool, enc, start, end);
3348 id = (ATTRIBUTE_ID *)lookup(&dtd.attributeIds, name, sizeof(ATTRIBUTE_ID));
3351 if (id->name != name)
3352 poolDiscard(&dtd.pool);
3354 poolFinish(&dtd.pool);
3357 else if (name[0] == 'x'
3362 && (name[5] == XML_T('\0') || name[5] == XML_T(':'))) {
3363 if (name[5] == '\0')
3364 id->prefix = &dtd.defaultPrefix;
3366 id->prefix = (PREFIX *)lookup(&dtd.prefixes, name + 6, sizeof(PREFIX));
3371 for (i = 0; name[i]; i++) {
3372 if (name[i] == XML_T(':')) {
3374 for (j = 0; j < i; j++) {
3375 if (!poolAppendChar(&dtd.pool, name[j]))
3378 if (!poolAppendChar(&dtd.pool, XML_T('\0')))
3380 id->prefix = (PREFIX *)
3381 lookup(&dtd.prefixes, poolStart(&dtd.pool), sizeof(PREFIX));
3382 if (id->prefix->name == poolStart(&dtd.pool))
3383 poolFinish(&dtd.pool);
3385 poolDiscard(&dtd.pool);
3394 #define CONTEXT_SEP XML_T('\f')
3397 const XML_Char *getContext(XML_Parser parser)
3399 HASH_TABLE_ITER iter;
3402 if (dtd.defaultPrefix.binding) {
3405 if (!poolAppendChar(&tempPool, XML_T('=')))
3407 len = dtd.defaultPrefix.binding->uriLen;
3408 if (namespaceSeparator != XML_T('\0'))
3410 for (i = 0; i < len; i++)
3411 if (!poolAppendChar(&tempPool, dtd.defaultPrefix.binding->uri[i]))
3416 hashTableIterInit(&iter, &(dtd.prefixes));
3421 PREFIX *prefix = (PREFIX *)hashTableIterNext(&iter);
3424 if (!prefix->binding)
3426 if (needSep && !poolAppendChar(&tempPool, CONTEXT_SEP))
3428 for (s = prefix->name; *s; s++)
3429 if (!poolAppendChar(&tempPool, *s))
3431 if (!poolAppendChar(&tempPool, XML_T('=')))
3433 len = prefix->binding->uriLen;
3434 if (namespaceSeparator != XML_T('\0'))
3436 for (i = 0; i < len; i++)
3437 if (!poolAppendChar(&tempPool, prefix->binding->uri[i]))
3443 hashTableIterInit(&iter, &(dtd.generalEntities));
3446 ENTITY *e = (ENTITY *)hashTableIterNext(&iter);
3451 if (needSep && !poolAppendChar(&tempPool, CONTEXT_SEP))
3453 for (s = e->name; *s; s++)
3454 if (!poolAppendChar(&tempPool, *s))
3459 if (!poolAppendChar(&tempPool, XML_T('\0')))
3461 return tempPool.start;
3465 int setContext(XML_Parser parser, const XML_Char *context)
3467 const XML_Char *s = context;
3469 while (*context != XML_T('\0')) {
3470 if (*s == CONTEXT_SEP || *s == XML_T('\0')) {
3472 if (!poolAppendChar(&tempPool, XML_T('\0')))
3474 e = (ENTITY *)lookup(&dtd.generalEntities, poolStart(&tempPool), 0);
3477 if (*s != XML_T('\0'))
3480 poolDiscard(&tempPool);
3482 else if (*s == '=') {
3484 if (poolLength(&tempPool) == 0)
3485 prefix = &dtd.defaultPrefix;
3487 if (!poolAppendChar(&tempPool, XML_T('\0')))
3490 lookup(&dtd.prefixes, poolStart(&tempPool), sizeof(PREFIX));
3493 if (prefix->name == poolStart(&tempPool)) {
3494 prefix->name = poolCopyString(&dtd.pool, prefix->name);
3498 poolDiscard(&tempPool);
3500 for (context = s + 1;
3501 *context != CONTEXT_SEP && *context != XML_T('\0');
3503 if (!poolAppendChar(&tempPool, *context))
3505 if (!poolAppendChar(&tempPool, XML_T('\0')))
3507 if (!addBinding(parser, prefix, 0, poolStart(&tempPool),
3508 &inheritedBindings))
3510 poolDiscard(&tempPool);
3511 if (*context != XML_T('\0'))
3516 if (!poolAppendChar(&tempPool, *s))
3526 void normalizePublicId(XML_Char *publicId)
3528 XML_Char *p = publicId;
3530 for (s = publicId; *s; s++) {
3535 if (p != publicId && p[-1] != 0x20)
3542 if (p != publicId && p[-1] == 0x20)
3547 static int dtdInit(DTD *p)
3549 poolInit(&(p->pool));
3550 hashTableInit(&(p->generalEntities));
3551 hashTableInit(&(p->elementTypes));
3552 hashTableInit(&(p->attributeIds));
3553 hashTableInit(&(p->prefixes));
3557 hashTableInit(&(p->paramEntities));
3558 #endif /* XML_DTD */
3559 p->defaultPrefix.name = 0;
3560 p->defaultPrefix.binding = 0;
3566 static void dtdSwap(DTD *p1, DTD *p2)
3569 memcpy(&tem, p1, sizeof(DTD));
3570 memcpy(p1, p2, sizeof(DTD));
3571 memcpy(p2, &tem, sizeof(DTD));
3574 #endif /* XML_DTD */
3576 static void dtdDestroy(DTD *p)
3578 HASH_TABLE_ITER iter;
3579 hashTableIterInit(&iter, &(p->elementTypes));
3581 ELEMENT_TYPE *e = (ELEMENT_TYPE *)hashTableIterNext(&iter);
3584 if (e->allocDefaultAtts != 0)
3585 free(e->defaultAtts);
3587 hashTableDestroy(&(p->generalEntities));
3589 hashTableDestroy(&(p->paramEntities));
3590 #endif /* XML_DTD */
3591 hashTableDestroy(&(p->elementTypes));
3592 hashTableDestroy(&(p->attributeIds));
3593 hashTableDestroy(&(p->prefixes));
3594 poolDestroy(&(p->pool));
3597 /* Do a deep copy of the DTD. Return 0 for out of memory; non-zero otherwise.
3598 The new DTD has already been initialized. */
3600 static int dtdCopy(DTD *newDtd, const DTD *oldDtd)
3602 HASH_TABLE_ITER iter;
3604 /* Copy the prefix table. */
3606 hashTableIterInit(&iter, &(oldDtd->prefixes));
3608 const XML_Char *name;
3609 const PREFIX *oldP = (PREFIX *)hashTableIterNext(&iter);
3612 name = poolCopyString(&(newDtd->pool), oldP->name);
3615 if (!lookup(&(newDtd->prefixes), name, sizeof(PREFIX)))
3619 hashTableIterInit(&iter, &(oldDtd->attributeIds));
3621 /* Copy the attribute id table. */
3625 const XML_Char *name;
3626 const ATTRIBUTE_ID *oldA = (ATTRIBUTE_ID *)hashTableIterNext(&iter);
3630 /* Remember to allocate the scratch byte before the name. */
3631 if (!poolAppendChar(&(newDtd->pool), XML_T('\0')))
3633 name = poolCopyString(&(newDtd->pool), oldA->name);
3637 newA = (ATTRIBUTE_ID *)
3638 lookup(&(newDtd->attributeIds), name, sizeof(ATTRIBUTE_ID));
3641 newA->maybeTokenized = oldA->maybeTokenized;
3643 newA->xmlns = oldA->xmlns;
3644 if (oldA->prefix == &oldDtd->defaultPrefix)
3645 newA->prefix = &newDtd->defaultPrefix;
3647 newA->prefix = (PREFIX *)
3648 lookup(&(newDtd->prefixes), oldA->prefix->name, 0);
3652 /* Copy the element type table. */
3654 hashTableIterInit(&iter, &(oldDtd->elementTypes));
3659 const XML_Char *name;
3660 const ELEMENT_TYPE *oldE = (ELEMENT_TYPE *)hashTableIterNext(&iter);
3663 name = poolCopyString(&(newDtd->pool), oldE->name);
3666 newE = (ELEMENT_TYPE *)
3667 lookup(&(newDtd->elementTypes), name, sizeof(ELEMENT_TYPE));
3670 if (oldE->nDefaultAtts) {
3671 newE->defaultAtts = (DEFAULT_ATTRIBUTE *)
3672 malloc(oldE->nDefaultAtts * sizeof(DEFAULT_ATTRIBUTE));
3673 if (!newE->defaultAtts)
3677 newE->idAtt = (ATTRIBUTE_ID *)
3678 lookup(&(newDtd->attributeIds), oldE->idAtt->name, 0);
3679 newE->allocDefaultAtts = newE->nDefaultAtts = oldE->nDefaultAtts;
3681 newE->prefix = (PREFIX *)
3682 lookup(&(newDtd->prefixes), oldE->prefix->name, 0);
3683 for (i = 0; i < newE->nDefaultAtts; i++) {
3684 newE->defaultAtts[i].id = (ATTRIBUTE_ID *)
3685 lookup(&(newDtd->attributeIds), oldE->defaultAtts[i].id->name, 0);
3686 newE->defaultAtts[i].isCdata = oldE->defaultAtts[i].isCdata;
3687 if (oldE->defaultAtts[i].value) {
3688 newE->defaultAtts[i].value =
3689 poolCopyString(&(newDtd->pool), oldE->defaultAtts[i].value);
3690 if (!newE->defaultAtts[i].value)
3694 newE->defaultAtts[i].value = 0;
3698 /* Copy the entity tables. */
3699 if (!copyEntityTable(&(newDtd->generalEntities),
3701 &(oldDtd->generalEntities)))
3705 if (!copyEntityTable(&(newDtd->paramEntities),
3707 &(oldDtd->paramEntities)))
3709 #endif /* XML_DTD */
3711 newDtd->complete = oldDtd->complete;
3712 newDtd->standalone = oldDtd->standalone;
3716 static int copyEntityTable(HASH_TABLE *newTable,
3717 STRING_POOL *newPool,
3718 const HASH_TABLE *oldTable)
3720 HASH_TABLE_ITER iter;
3721 const XML_Char *cachedOldBase = 0;
3722 const XML_Char *cachedNewBase = 0;
3724 hashTableIterInit(&iter, oldTable);
3728 const XML_Char *name;
3729 const ENTITY *oldE = (ENTITY *)hashTableIterNext(&iter);
3732 name = poolCopyString(newPool, oldE->name);
3735 newE = (ENTITY *)lookup(newTable, name, sizeof(ENTITY));
3738 if (oldE->systemId) {
3739 const XML_Char *tem = poolCopyString(newPool, oldE->systemId);
3742 newE->systemId = tem;
3744 if (oldE->base == cachedOldBase)
3745 newE->base = cachedNewBase;
3747 cachedOldBase = oldE->base;
3748 tem = poolCopyString(newPool, cachedOldBase);
3751 cachedNewBase = newE->base = tem;
3756 const XML_Char *tem =
3757 poolCopyStringN(newPool, oldE->textPtr, oldE->textLen);
3760 newE->textPtr = tem;
3761 newE->textLen = oldE->textLen;
3763 if (oldE->notation) {
3764 const XML_Char *tem = poolCopyString(newPool, oldE->notation);
3767 newE->notation = tem;
3773 #define INIT_SIZE 64
3776 int keyeq(KEY s1, KEY s2)
3778 for (; *s1 == *s2; s1++, s2++)
3785 unsigned long hash(KEY s)
3787 unsigned long h = 0;
3789 h = (h << 5) + h + (unsigned char)*s++;
3794 NAMED *lookup(HASH_TABLE *table, KEY name, size_t createSize)
3797 if (table->size == 0) {
3800 table->v = calloc(INIT_SIZE, sizeof(NAMED *));
3803 table->size = INIT_SIZE;
3804 table->usedLim = INIT_SIZE / 2;
3805 i = hash(name) & (table->size - 1);
3808 unsigned long h = hash(name);
3809 for (i = h & (table->size - 1);
3811 i == 0 ? i = table->size - 1 : --i) {
3812 if (keyeq(name, table->v[i]->name))
3817 if (table->used == table->usedLim) {
3818 /* check for overflow */
3819 size_t newSize = table->size * 2;
3820 NAMED **newV = calloc(newSize, sizeof(NAMED *));
3823 for (i = 0; i < table->size; i++)
3826 for (j = hash(table->v[i]->name) & (newSize - 1);
3828 j == 0 ? j = newSize - 1 : --j)
3830 newV[j] = table->v[i];
3834 table->size = newSize;
3835 table->usedLim = newSize/2;
3836 for (i = h & (table->size - 1);
3838 i == 0 ? i = table->size - 1 : --i)
3842 table->v[i] = calloc(1, createSize);
3845 table->v[i]->name = name;
3851 void hashTableDestroy(HASH_TABLE *table)
3854 for (i = 0; i < table->size; i++) {
3855 NAMED *p = table->v[i];
3864 void hashTableInit(HASH_TABLE *p)
3873 void hashTableIterInit(HASH_TABLE_ITER *iter, const HASH_TABLE *table)
3876 iter->end = iter->p + table->size;
3880 NAMED *hashTableIterNext(HASH_TABLE_ITER *iter)
3882 while (iter->p != iter->end) {
3883 NAMED *tem = *(iter->p)++;
3892 void poolInit(STRING_POOL *pool)
3895 pool->freeBlocks = 0;
3902 void poolClear(STRING_POOL *pool)
3904 if (!pool->freeBlocks)
3905 pool->freeBlocks = pool->blocks;
3907 BLOCK *p = pool->blocks;
3909 BLOCK *tem = p->next;
3910 p->next = pool->freeBlocks;
3911 pool->freeBlocks = p;
3922 void poolDestroy(STRING_POOL *pool)
3924 BLOCK *p = pool->blocks;
3926 BLOCK *tem = p->next;
3931 p = pool->freeBlocks;
3933 BLOCK *tem = p->next;
3937 pool->freeBlocks = 0;
3944 XML_Char *poolAppend(STRING_POOL *pool, const ENCODING *enc,
3945 const char *ptr, const char *end)
3947 if (!pool->ptr && !poolGrow(pool))
3950 XmlConvert(enc, &ptr, end, (ICHAR **)&(pool->ptr), (ICHAR *)pool->end);
3953 if (!poolGrow(pool))
3959 static const XML_Char *poolCopyString(STRING_POOL *pool, const XML_Char *s)
3962 if (!poolAppendChar(pool, *s))
3970 static const XML_Char *
3971 poolCopyStringN(STRING_POOL *pool,
3975 if (!pool->ptr && !poolGrow(pool))
3977 for (; n > 0; --n, s++) {
3978 if (!poolAppendChar(pool, *s))
3988 XML_Char *poolStoreString(STRING_POOL *pool, const ENCODING *enc,
3989 const char *ptr, const char *end)
3991 if (!poolAppend(pool, enc, ptr, end))
3993 if (pool->ptr == pool->end && !poolGrow(pool))
4000 int poolGrow(STRING_POOL *pool)
4002 if (pool->freeBlocks) {
4003 if (pool->start == 0) {
4004 pool->blocks = pool->freeBlocks;
4005 pool->freeBlocks = pool->freeBlocks->next;
4006 pool->blocks->next = 0;
4007 pool->start = pool->blocks->s;
4008 pool->end = pool->start + pool->blocks->size;
4009 pool->ptr = pool->start;
4012 if (pool->end - pool->start < pool->freeBlocks->size) {
4013 BLOCK *tem = pool->freeBlocks->next;
4014 pool->freeBlocks->next = pool->blocks;
4015 pool->blocks = pool->freeBlocks;
4016 pool->freeBlocks = tem;
4017 memcpy(pool->blocks->s, pool->start,
4018 (pool->end - pool->start) * sizeof(XML_Char));
4019 pool->ptr = pool->blocks->s + (pool->ptr - pool->start);
4020 pool->start = pool->blocks->s;
4021 pool->end = pool->start + pool->blocks->size;
4025 if (pool->blocks && pool->start == pool->blocks->s) {
4026 int blockSize = (pool->end - pool->start)*2;
4027 pool->blocks = realloc(pool->blocks, offsetof(BLOCK, s) +
4028 blockSize * sizeof(XML_Char));
4031 pool->blocks->size = blockSize;
4032 pool->ptr = pool->blocks->s + (pool->ptr - pool->start);
4033 pool->start = pool->blocks->s;
4034 pool->end = pool->start + blockSize;
4038 int blockSize = pool->end - pool->start;
4039 if (blockSize < INIT_BLOCK_SIZE)
4040 blockSize = INIT_BLOCK_SIZE;
4043 tem = malloc(offsetof(BLOCK, s) + blockSize * sizeof(XML_Char));
4046 tem->size = blockSize;
4047 tem->next = pool->blocks;
4049 if (pool->ptr != pool->start)
4050 memcpy(tem->s, pool->start,
4051 (pool->ptr - pool->start) * sizeof(XML_Char));
4052 pool->ptr = tem->s + (pool->ptr - pool->start);
4053 pool->start = tem->s;
4054 pool->end = tem->s + blockSize;