summaryrefslogtreecommitdiffstats
path: root/Modules/expat/xmlparse.c
diff options
context:
space:
mode:
authorMartin v. Löwis <martin@v.loewis.de>2003-01-25 22:41:29 (GMT)
committerMartin v. Löwis <martin@v.loewis.de>2003-01-25 22:41:29 (GMT)
commitfc03a94aaccc9ae606ee3438ca21d65a335d43e9 (patch)
tree7aed4887ec4fa6679d1a9baaeb4e2bd5a6c43ece /Modules/expat/xmlparse.c
parent5a772d32f4904ffe935d4961e1f23dd359cc3e43 (diff)
downloadcpython-fc03a94aaccc9ae606ee3438ca21d65a335d43e9.zip
cpython-fc03a94aaccc9ae606ee3438ca21d65a335d43e9.tar.gz
cpython-fc03a94aaccc9ae606ee3438ca21d65a335d43e9.tar.bz2
Incorporate Expat 1.95.6.
Diffstat (limited to 'Modules/expat/xmlparse.c')
-rw-r--r--Modules/expat/xmlparse.c5374
1 files changed, 3228 insertions, 2146 deletions
diff --git a/Modules/expat/xmlparse.c b/Modules/expat/xmlparse.c
index c46b601..c465446 100644
--- a/Modules/expat/xmlparse.c
+++ b/Modules/expat/xmlparse.c
@@ -1,32 +1,42 @@
-/*
-Copyright (c) 1998, 1999, 2000 Thai Open Source Software Center Ltd
-See the file COPYING for copying permission.
+/* Copyright (c) 1998, 1999, 2000 Thai Open Source Software Center Ltd
+ See the file COPYING for copying permission.
*/
+/* Added to look for memcpy */
+#include <Python.h>
+
+#include <stddef.h>
+#include <string.h> /* memset(), memcpy() */
+
#ifdef COMPILED_FROM_DSP
-# include "winconfig.h"
-# define XMLPARSEAPI(type) __declspec(dllexport) type __cdecl
-# include "expat.h"
-# undef XMLPARSEAPI
+
+#include "winconfig.h"
+#define XMLPARSEAPI(type) type __cdecl
+#include "expat.h"
+#undef XMLPARSEAPI
+
+#elif defined(MACOS_CLASSIC)
+
+#include "macconfig.h"
+#include "expat.h"
+
#else
-#ifdef HAVE_CONFIG_H
-#include <config.h>
-#endif
+
+/* Unused - MvL
+#include <expat_config.h>
+*/
#ifdef __declspec
-# define XMLPARSEAPI(type) __declspec(dllexport) type __cdecl
+#define XMLPARSEAPI(type) type __cdecl
#endif
#include "expat.h"
#ifdef __declspec
-# undef XMLPARSEAPI
+#undef XMLPARSEAPI
#endif
#endif /* ndef COMPILED_FROM_DSP */
-#include <stddef.h>
-#include <string.h>
-
#ifdef XML_UNICODE
#define XML_ENCODE_MAX XML_UTF16_ENCODE_MAX
#define XmlConvert XmlUtf16Convert
@@ -56,15 +66,36 @@ typedef char ICHAR;
#endif
+#ifdef XML_UNICODE
+
#ifdef XML_UNICODE_WCHAR_T
-#define XML_T(x) L ## x
+#define XML_T(x) (const wchar_t)x
+#define XML_L(x) L ## x
#else
+#define XML_T(x) (const unsigned short)x
+#define XML_L(x) x
+#endif
+
+#else
+
#define XML_T(x) x
+#define XML_L(x) x
+
#endif
/* Round up n to be a multiple of sz, where sz is a power of 2. */
#define ROUND_UP(n, sz) (((n) + ((sz) - 1)) & ~((sz) - 1))
+/* Handle the case where memmove() doesn't exist. */
+#ifndef HAVE_MEMMOVE
+#ifdef HAVE_BCOPY
+#define memmove(d,s,l) bcopy((s),(d),(l))
+#else
+#error memmove does not exist on this platform, nor is a substitute available
+#endif /* HAVE_BCOPY */
+#endif /* HAVE_MEMMOVE */
+
+#include "internal.h"
#include "xmltok.h"
#include "xmlrole.h"
@@ -79,7 +110,7 @@ typedef struct {
size_t size;
size_t used;
size_t usedLim;
- XML_Memory_Handling_Suite *mem;
+ const XML_Memory_Handling_Suite *mem;
} HASH_TABLE;
typedef struct {
@@ -113,16 +144,32 @@ typedef struct prefix {
typedef struct {
const XML_Char *str;
const XML_Char *localPart;
+ const XML_Char *prefix;
+ int strLen;
int uriLen;
+ int prefixLen;
} TAG_NAME;
+/* TAG represents an open element.
+ The name of the element is stored in both the document and API
+ encodings. The memory buffer 'buf' is a separately-allocated
+ memory area which stores the name. During the XML_Parse()/
+ XMLParseBuffer() when the element is open, the memory for the 'raw'
+ version of the name (in the document encoding) is shared with the
+ document buffer. If the element is open across calls to
+ XML_Parse()/XML_ParseBuffer(), the buffer is re-allocated to
+ contain the 'raw' name as well.
+
+ A parser re-uses these structures, maintaining a list of allocated
+ TAG objects in a free list.
+*/
typedef struct tag {
- struct tag *parent;
- const char *rawName;
+ struct tag *parent; /* parent of this element */
+ const char *rawName; /* tagName in the original encoding */
int rawNameLength;
- TAG_NAME name;
- char *buf;
- char *bufEnd;
+ TAG_NAME name; /* tagName in the API encoding */
+ char *buf; /* buffer for name components */
+ char *bufEnd; /* end of the buffer */
BINDING *bindings;
} TAG;
@@ -134,20 +181,23 @@ typedef struct {
const XML_Char *base;
const XML_Char *publicId;
const XML_Char *notation;
- char open;
- char is_param;
+ XML_Bool open;
+ XML_Bool is_param;
+ XML_Bool is_internal; /* true if declared in internal subset outside PE */
} ENTITY;
typedef struct {
- enum XML_Content_Type type;
- enum XML_Content_Quant quant;
- const XML_Char * name;
- int firstchild;
- int lastchild;
- int childcnt;
- int nextsib;
+ enum XML_Content_Type type;
+ enum XML_Content_Quant quant;
+ const XML_Char * name;
+ int firstchild;
+ int lastchild;
+ int childcnt;
+ int nextsib;
} CONTENT_SCAFFOLD;
+#define INIT_SCAFFOLD_ELEMENTS 32
+
typedef struct block {
struct block *next;
int size;
@@ -160,21 +210,21 @@ typedef struct {
const XML_Char *end;
XML_Char *ptr;
XML_Char *start;
- XML_Memory_Handling_Suite *mem;
+ const XML_Memory_Handling_Suite *mem;
} STRING_POOL;
/* The XML_Char before the name is used to determine whether
-an attribute has been specified. */
+ an attribute has been specified. */
typedef struct attribute_id {
XML_Char *name;
PREFIX *prefix;
- char maybeTokenized;
- char xmlns;
+ XML_Bool maybeTokenized;
+ XML_Bool xmlns;
} ATTRIBUTE_ID;
typedef struct {
const ATTRIBUTE_ID *id;
- char isCdata;
+ XML_Bool isCdata;
const XML_Char *value;
} DEFAULT_ATTRIBUTE;
@@ -193,14 +243,21 @@ typedef struct {
HASH_TABLE attributeIds;
HASH_TABLE prefixes;
STRING_POOL pool;
- int complete;
- int standalone;
+ STRING_POOL entityValuePool;
+ /* false once a parameter entity reference has been skipped */
+ XML_Bool keepProcessing;
+ /* true once an internal or external PE reference has been encountered;
+ this includes the reference to an external subset */
+ XML_Bool hasParamEntityRefs;
+ XML_Bool standalone;
#ifdef XML_DTD
+ /* indicates if external PE has been read */
+ XML_Bool paramEntityRead;
HASH_TABLE paramEntities;
#endif /* XML_DTD */
PREFIX defaultPrefix;
/* === scaffolding for building content model === */
- int in_eldecl;
+ XML_Bool in_eldecl;
CONTENT_SCAFFOLD *scaffold;
unsigned contentStringLen;
unsigned scaffSize;
@@ -216,10 +273,10 @@ typedef struct open_internal_entity {
ENTITY *entity;
} OPEN_INTERNAL_ENTITY;
-typedef enum XML_Error Processor(XML_Parser parser,
- const char *start,
- const char *end,
- const char **endPtr);
+typedef enum XML_Error PTRCALL Processor(XML_Parser parser,
+ const char *start,
+ const char *end,
+ const char **endPtr);
static Processor prologProcessor;
static Processor prologInitProcessor;
@@ -227,6 +284,10 @@ static Processor contentProcessor;
static Processor cdataSectionProcessor;
#ifdef XML_DTD
static Processor ignoreSectionProcessor;
+static Processor externalParEntProcessor;
+static Processor externalParEntInitProcessor;
+static Processor entityValueProcessor;
+static Processor entityValueInitProcessor;
#endif /* XML_DTD */
static Processor epilogProcessor;
static Processor errorProcessor;
@@ -238,94 +299,118 @@ static Processor externalEntityContentProcessor;
static enum XML_Error
handleUnknownEncoding(XML_Parser parser, const XML_Char *encodingName);
static enum XML_Error
-processXmlDecl(XML_Parser parser, int isGeneralTextEntity, const char *, const char *);
+processXmlDecl(XML_Parser parser, int isGeneralTextEntity,
+ const char *, const char *);
static enum XML_Error
initializeEncoding(XML_Parser parser);
static enum XML_Error
doProlog(XML_Parser parser, const ENCODING *enc, const char *s,
- const char *end, int tok, const char *next, const char **nextPtr);
+ const char *end, int tok, const char *next, const char **nextPtr);
static enum XML_Error
processInternalParamEntity(XML_Parser parser, ENTITY *entity);
static enum XML_Error
doContent(XML_Parser parser, int startTagLevel, const ENCODING *enc,
- const char *start, const char *end, const char **endPtr);
+ const char *start, const char *end, const char **endPtr);
static enum XML_Error
-doCdataSection(XML_Parser parser, const ENCODING *, const char **startPtr, const char *end, const char **nextPtr);
+doCdataSection(XML_Parser parser, const ENCODING *, const char **startPtr,
+ const char *end, const char **nextPtr);
#ifdef XML_DTD
static enum XML_Error
-doIgnoreSection(XML_Parser parser, const ENCODING *, const char **startPtr, const char *end, const char **nextPtr);
+doIgnoreSection(XML_Parser parser, const ENCODING *, const char **startPtr,
+ const char *end, const char **nextPtr);
#endif /* XML_DTD */
-static enum XML_Error storeAtts(XML_Parser parser, const ENCODING *, const char *s,
- TAG_NAME *tagNamePtr, BINDING **bindingsPtr);
-static
-int addBinding(XML_Parser parser, PREFIX *prefix, const ATTRIBUTE_ID *attId, const XML_Char *uri, BINDING **bindingsPtr);
+static enum XML_Error
+storeAtts(XML_Parser parser, const ENCODING *,
+ const char *s, TAG_NAME *tagNamePtr, BINDING **bindingsPtr);
+static enum XML_Error
+addBinding(XML_Parser parser, PREFIX *prefix, const ATTRIBUTE_ID *attId,
+ const XML_Char *uri, BINDING **bindingsPtr);
static int
defineAttribute(ELEMENT_TYPE *type, ATTRIBUTE_ID *,
- int isCdata, int isId, const XML_Char *dfltValue,
- XML_Parser parser);
-
+ XML_Bool isCdata, XML_Bool isId, const XML_Char *dfltValue,
+ XML_Parser parser);
static enum XML_Error
-storeAttributeValue(XML_Parser parser, const ENCODING *, int isCdata, const char *, const char *,
- STRING_POOL *);
+storeAttributeValue(XML_Parser parser, const ENCODING *, XML_Bool isCdata,
+ const char *, const char *, STRING_POOL *);
static enum XML_Error
-appendAttributeValue(XML_Parser parser, const ENCODING *, int isCdata, const char *, const char *,
- STRING_POOL *);
+appendAttributeValue(XML_Parser parser, const ENCODING *, XML_Bool isCdata,
+ const char *, const char *, STRING_POOL *);
static ATTRIBUTE_ID *
-getAttributeId(XML_Parser parser, const ENCODING *enc, const char *start, const char *end);
-static int setElementTypePrefix(XML_Parser parser, ELEMENT_TYPE *);
+getAttributeId(XML_Parser parser, const ENCODING *enc, const char *start,
+ const char *end);
+static int
+setElementTypePrefix(XML_Parser parser, ELEMENT_TYPE *);
static enum XML_Error
-storeEntityValue(XML_Parser parser, const ENCODING *enc, const char *start, const char *end);
+storeEntityValue(XML_Parser parser, const ENCODING *enc, const char *start,
+ const char *end);
static int
-reportProcessingInstruction(XML_Parser parser, const ENCODING *enc, const char *start, const char *end);
+reportProcessingInstruction(XML_Parser parser, const ENCODING *enc,
+ const char *start, const char *end);
static int
-reportComment(XML_Parser parser, const ENCODING *enc, const char *start, const char *end);
+reportComment(XML_Parser parser, const ENCODING *enc, const char *start,
+ const char *end);
static void
-reportDefault(XML_Parser parser, const ENCODING *enc, const char *start, const char *end);
-
-static const XML_Char *getContext(XML_Parser parser);
-static int setContext(XML_Parser parser, const XML_Char *context);
-static void normalizePublicId(XML_Char *s);
-static int dtdInit(DTD *, XML_Parser parser);
-
-static void dtdDestroy(DTD *, XML_Parser parser);
-
-static int dtdCopy(DTD *newDtd, const DTD *oldDtd, XML_Parser parser);
-
-static int copyEntityTable(HASH_TABLE *, STRING_POOL *, const HASH_TABLE *,
- XML_Parser parser);
-
-#ifdef XML_DTD
-static void dtdSwap(DTD *, DTD *);
-#endif /* XML_DTD */
-
-static NAMED *lookup(HASH_TABLE *table, KEY name, size_t createSize);
-
-static void hashTableInit(HASH_TABLE *, XML_Memory_Handling_Suite *ms);
+reportDefault(XML_Parser parser, const ENCODING *enc, const char *start,
+ const char *end);
-static void hashTableDestroy(HASH_TABLE *);
-static void hashTableIterInit(HASH_TABLE_ITER *, const HASH_TABLE *);
-static NAMED *hashTableIterNext(HASH_TABLE_ITER *);
-static void poolInit(STRING_POOL *, XML_Memory_Handling_Suite *ms);
-static void poolClear(STRING_POOL *);
-static void poolDestroy(STRING_POOL *);
-static XML_Char *poolAppend(STRING_POOL *pool, const ENCODING *enc,
- const char *ptr, const char *end);
-static XML_Char *poolStoreString(STRING_POOL *pool, const ENCODING *enc,
- const char *ptr, const char *end);
+static const XML_Char * getContext(XML_Parser parser);
+static XML_Bool
+setContext(XML_Parser parser, const XML_Char *context);
-static int poolGrow(STRING_POOL *pool);
+static void FASTCALL normalizePublicId(XML_Char *s);
-static int nextScaffoldPart(XML_Parser parser);
-static XML_Content *build_model(XML_Parser parser);
-
-static const XML_Char *poolCopyString(STRING_POOL *pool, const XML_Char *s);
-static const XML_Char *poolCopyStringN(STRING_POOL *pool, const XML_Char *s, int n);
-static const XML_Char *poolAppendString(STRING_POOL *pool, const XML_Char *s);
-static ELEMENT_TYPE * getElementType(XML_Parser Paraser,
- const ENCODING *enc,
- const char *ptr,
- const char *end);
+static DTD * dtdCreate(const XML_Memory_Handling_Suite *ms);
+/* do not call if parentParser != NULL */
+static void dtdReset(DTD *p, const XML_Memory_Handling_Suite *ms);
+static void
+dtdDestroy(DTD *p, XML_Bool isDocEntity, const XML_Memory_Handling_Suite *ms);
+static int
+dtdCopy(DTD *newDtd, const DTD *oldDtd, const XML_Memory_Handling_Suite *ms);
+static int
+copyEntityTable(HASH_TABLE *, STRING_POOL *, const HASH_TABLE *);
+
+static NAMED *
+lookup(HASH_TABLE *table, KEY name, size_t createSize);
+static void FASTCALL
+hashTableInit(HASH_TABLE *, const XML_Memory_Handling_Suite *ms);
+static void FASTCALL hashTableClear(HASH_TABLE *);
+static void FASTCALL hashTableDestroy(HASH_TABLE *);
+static void FASTCALL
+hashTableIterInit(HASH_TABLE_ITER *, const HASH_TABLE *);
+static NAMED * FASTCALL hashTableIterNext(HASH_TABLE_ITER *);
+
+static void FASTCALL
+poolInit(STRING_POOL *, const XML_Memory_Handling_Suite *ms);
+static void FASTCALL poolClear(STRING_POOL *);
+static void FASTCALL poolDestroy(STRING_POOL *);
+static XML_Char *
+poolAppend(STRING_POOL *pool, const ENCODING *enc,
+ const char *ptr, const char *end);
+static XML_Char *
+poolStoreString(STRING_POOL *pool, const ENCODING *enc,
+ const char *ptr, const char *end);
+static XML_Bool FASTCALL poolGrow(STRING_POOL *pool);
+static const XML_Char * FASTCALL
+poolCopyString(STRING_POOL *pool, const XML_Char *s);
+static const XML_Char *
+poolCopyStringN(STRING_POOL *pool, const XML_Char *s, int n);
+static const XML_Char * FASTCALL
+poolAppendString(STRING_POOL *pool, const XML_Char *s);
+
+static int FASTCALL nextScaffoldPart(XML_Parser parser);
+static XML_Content * build_model(XML_Parser parser);
+static ELEMENT_TYPE *
+getElementType(XML_Parser parser, const ENCODING *enc,
+ const char *ptr, const char *end);
+
+static XML_Parser
+parserCreate(const XML_Char *encodingName,
+ const XML_Memory_Handling_Suite *memsuite,
+ const XML_Char *nameSep,
+ DTD *dtd);
+static void
+parserInit(XML_Parser parser, const XML_Char *encodingName);
#define poolStart(pool) ((pool)->start)
#define poolEnd(pool) ((pool)->ptr)
@@ -339,12 +424,13 @@ static ELEMENT_TYPE * getElementType(XML_Parser Paraser,
? 0 \
: ((*((pool)->ptr)++ = c), 1))
-typedef struct {
- /* The first member must be userData so that the XML_GetUserData macro works. */
+struct XML_ParserStruct {
+ /* The first member must be userData so that the XML_GetUserData
+ macro works. */
void *m_userData;
void *m_handlerArg;
char *m_buffer;
- XML_Memory_Handling_Suite m_mem;
+ const XML_Memory_Handling_Suite m_mem;
/* first character to be parsed */
const char *m_bufferPtr;
/* past last character to be parsed */
@@ -371,7 +457,8 @@ typedef struct {
XML_EndNamespaceDeclHandler m_endNamespaceDeclHandler;
XML_NotStandaloneHandler m_notStandaloneHandler;
XML_ExternalEntityRefHandler m_externalEntityRefHandler;
- void *m_externalEntityRefHandlerArg;
+ XML_Parser m_externalEntityRefHandlerArg;
+ XML_SkippedEntityHandler m_skippedEntityHandler;
XML_UnknownEncodingHandler m_unknownEncodingHandler;
XML_ElementDeclHandler m_elementDeclHandler;
XML_AttlistDeclHandler m_attlistDeclHandler;
@@ -381,8 +468,8 @@ typedef struct {
INIT_ENCODING m_initEncoding;
const ENCODING *m_internalEncoding;
const XML_Char *m_protocolEncodingName;
- int m_ns;
- int m_ns_triplets;
+ XML_Bool m_ns;
+ XML_Bool m_ns_triplets;
void *m_unknownEncodingMem;
void *m_unknownEncodingData;
void *m_unknownEncodingHandlerData;
@@ -394,7 +481,7 @@ typedef struct {
const char *m_eventEndPtr;
const char *m_positionPtr;
OPEN_INTERNAL_ENTITY *m_openInternalEntities;
- int m_defaultExpandInternalEntities;
+ XML_Bool m_defaultExpandInternalEntities;
int m_tagLevel;
ENTITY *m_declEntity;
const XML_Char *m_doctypeName;
@@ -405,9 +492,9 @@ typedef struct {
const XML_Char *m_declNotationPublicId;
ELEMENT_TYPE *m_declElementType;
ATTRIBUTE_ID *m_declAttributeId;
- char m_declAttributeIsCdata;
- char m_declAttributeIsId;
- DTD m_dtd;
+ XML_Bool m_declAttributeIsCdata;
+ XML_Bool m_declAttributeIsId;
+ DTD *m_dtd;
const XML_Char *m_curBase;
TAG *m_tagStack;
TAG *m_freeTagList;
@@ -422,304 +509,423 @@ typedef struct {
STRING_POOL m_temp2Pool;
char *m_groupConnector;
unsigned m_groupSize;
- int m_hadExternalDoctype;
XML_Char m_namespaceSeparator;
+ XML_Parser m_parentParser;
#ifdef XML_DTD
+ XML_Bool m_isParamEntity;
+ XML_Bool m_useForeignDTD;
enum XML_ParamEntityParsing m_paramEntityParsing;
- XML_Parser m_parentParser;
#endif
-} Parser;
-
-#define MALLOC(s) (((Parser *)parser)->m_mem.malloc_fcn((s)))
-#define REALLOC(p,s) (((Parser *)parser)->m_mem.realloc_fcn((p),(s)))
-#define FREE(p) (((Parser *)parser)->m_mem.free_fcn((p)))
-
-#define userData (((Parser *)parser)->m_userData)
-#define handlerArg (((Parser *)parser)->m_handlerArg)
-#define startElementHandler (((Parser *)parser)->m_startElementHandler)
-#define endElementHandler (((Parser *)parser)->m_endElementHandler)
-#define characterDataHandler (((Parser *)parser)->m_characterDataHandler)
-#define processingInstructionHandler (((Parser *)parser)->m_processingInstructionHandler)
-#define commentHandler (((Parser *)parser)->m_commentHandler)
-#define startCdataSectionHandler (((Parser *)parser)->m_startCdataSectionHandler)
-#define endCdataSectionHandler (((Parser *)parser)->m_endCdataSectionHandler)
-#define defaultHandler (((Parser *)parser)->m_defaultHandler)
-#define startDoctypeDeclHandler (((Parser *)parser)->m_startDoctypeDeclHandler)
-#define endDoctypeDeclHandler (((Parser *)parser)->m_endDoctypeDeclHandler)
-#define unparsedEntityDeclHandler (((Parser *)parser)->m_unparsedEntityDeclHandler)
-#define notationDeclHandler (((Parser *)parser)->m_notationDeclHandler)
-#define startNamespaceDeclHandler (((Parser *)parser)->m_startNamespaceDeclHandler)
-#define endNamespaceDeclHandler (((Parser *)parser)->m_endNamespaceDeclHandler)
-#define notStandaloneHandler (((Parser *)parser)->m_notStandaloneHandler)
-#define externalEntityRefHandler (((Parser *)parser)->m_externalEntityRefHandler)
-#define externalEntityRefHandlerArg (((Parser *)parser)->m_externalEntityRefHandlerArg)
-#define internalEntityRefHandler (((Parser *)parser)->m_internalEntityRefHandler)
-#define unknownEncodingHandler (((Parser *)parser)->m_unknownEncodingHandler)
-#define elementDeclHandler (((Parser *)parser)->m_elementDeclHandler)
-#define attlistDeclHandler (((Parser *)parser)->m_attlistDeclHandler)
-#define entityDeclHandler (((Parser *)parser)->m_entityDeclHandler)
-#define xmlDeclHandler (((Parser *)parser)->m_xmlDeclHandler)
-#define encoding (((Parser *)parser)->m_encoding)
-#define initEncoding (((Parser *)parser)->m_initEncoding)
-#define internalEncoding (((Parser *)parser)->m_internalEncoding)
-#define unknownEncodingMem (((Parser *)parser)->m_unknownEncodingMem)
-#define unknownEncodingData (((Parser *)parser)->m_unknownEncodingData)
+};
+
+#define MALLOC(s) (parser->m_mem.malloc_fcn((s)))
+#define REALLOC(p,s) (parser->m_mem.realloc_fcn((p),(s)))
+#define FREE(p) (parser->m_mem.free_fcn((p)))
+
+#define userData (parser->m_userData)
+#define handlerArg (parser->m_handlerArg)
+#define startElementHandler (parser->m_startElementHandler)
+#define endElementHandler (parser->m_endElementHandler)
+#define characterDataHandler (parser->m_characterDataHandler)
+#define processingInstructionHandler \
+ (parser->m_processingInstructionHandler)
+#define commentHandler (parser->m_commentHandler)
+#define startCdataSectionHandler \
+ (parser->m_startCdataSectionHandler)
+#define endCdataSectionHandler (parser->m_endCdataSectionHandler)
+#define defaultHandler (parser->m_defaultHandler)
+#define startDoctypeDeclHandler (parser->m_startDoctypeDeclHandler)
+#define endDoctypeDeclHandler (parser->m_endDoctypeDeclHandler)
+#define unparsedEntityDeclHandler \
+ (parser->m_unparsedEntityDeclHandler)
+#define notationDeclHandler (parser->m_notationDeclHandler)
+#define startNamespaceDeclHandler \
+ (parser->m_startNamespaceDeclHandler)
+#define endNamespaceDeclHandler (parser->m_endNamespaceDeclHandler)
+#define notStandaloneHandler (parser->m_notStandaloneHandler)
+#define externalEntityRefHandler \
+ (parser->m_externalEntityRefHandler)
+#define externalEntityRefHandlerArg \
+ (parser->m_externalEntityRefHandlerArg)
+#define internalEntityRefHandler \
+ (parser->m_internalEntityRefHandler)
+#define skippedEntityHandler (parser->m_skippedEntityHandler)
+#define unknownEncodingHandler (parser->m_unknownEncodingHandler)
+#define elementDeclHandler (parser->m_elementDeclHandler)
+#define attlistDeclHandler (parser->m_attlistDeclHandler)
+#define entityDeclHandler (parser->m_entityDeclHandler)
+#define xmlDeclHandler (parser->m_xmlDeclHandler)
+#define encoding (parser->m_encoding)
+#define initEncoding (parser->m_initEncoding)
+#define internalEncoding (parser->m_internalEncoding)
+#define unknownEncodingMem (parser->m_unknownEncodingMem)
+#define unknownEncodingData (parser->m_unknownEncodingData)
#define unknownEncodingHandlerData \
- (((Parser *)parser)->m_unknownEncodingHandlerData)
-#define unknownEncodingRelease (((Parser *)parser)->m_unknownEncodingRelease)
-#define protocolEncodingName (((Parser *)parser)->m_protocolEncodingName)
-#define ns (((Parser *)parser)->m_ns)
-#define ns_triplets (((Parser *)parser)->m_ns_triplets)
-#define prologState (((Parser *)parser)->m_prologState)
-#define processor (((Parser *)parser)->m_processor)
-#define errorCode (((Parser *)parser)->m_errorCode)
-#define eventPtr (((Parser *)parser)->m_eventPtr)
-#define eventEndPtr (((Parser *)parser)->m_eventEndPtr)
-#define positionPtr (((Parser *)parser)->m_positionPtr)
-#define position (((Parser *)parser)->m_position)
-#define openInternalEntities (((Parser *)parser)->m_openInternalEntities)
-#define defaultExpandInternalEntities (((Parser *)parser)->m_defaultExpandInternalEntities)
-#define tagLevel (((Parser *)parser)->m_tagLevel)
-#define buffer (((Parser *)parser)->m_buffer)
-#define bufferPtr (((Parser *)parser)->m_bufferPtr)
-#define bufferEnd (((Parser *)parser)->m_bufferEnd)
-#define parseEndByteIndex (((Parser *)parser)->m_parseEndByteIndex)
-#define parseEndPtr (((Parser *)parser)->m_parseEndPtr)
-#define bufferLim (((Parser *)parser)->m_bufferLim)
-#define dataBuf (((Parser *)parser)->m_dataBuf)
-#define dataBufEnd (((Parser *)parser)->m_dataBufEnd)
-#define dtd (((Parser *)parser)->m_dtd)
-#define curBase (((Parser *)parser)->m_curBase)
-#define declEntity (((Parser *)parser)->m_declEntity)
-#define doctypeName (((Parser *)parser)->m_doctypeName)
-#define doctypeSysid (((Parser *)parser)->m_doctypeSysid)
-#define doctypePubid (((Parser *)parser)->m_doctypePubid)
-#define declAttributeType (((Parser *)parser)->m_declAttributeType)
-#define declNotationName (((Parser *)parser)->m_declNotationName)
-#define declNotationPublicId (((Parser *)parser)->m_declNotationPublicId)
-#define declElementType (((Parser *)parser)->m_declElementType)
-#define declAttributeId (((Parser *)parser)->m_declAttributeId)
-#define declAttributeIsCdata (((Parser *)parser)->m_declAttributeIsCdata)
-#define declAttributeIsId (((Parser *)parser)->m_declAttributeIsId)
-#define freeTagList (((Parser *)parser)->m_freeTagList)
-#define freeBindingList (((Parser *)parser)->m_freeBindingList)
-#define inheritedBindings (((Parser *)parser)->m_inheritedBindings)
-#define tagStack (((Parser *)parser)->m_tagStack)
-#define atts (((Parser *)parser)->m_atts)
-#define attsSize (((Parser *)parser)->m_attsSize)
-#define nSpecifiedAtts (((Parser *)parser)->m_nSpecifiedAtts)
-#define idAttIndex (((Parser *)parser)->m_idAttIndex)
-#define tempPool (((Parser *)parser)->m_tempPool)
-#define temp2Pool (((Parser *)parser)->m_temp2Pool)
-#define groupConnector (((Parser *)parser)->m_groupConnector)
-#define groupSize (((Parser *)parser)->m_groupSize)
-#define hadExternalDoctype (((Parser *)parser)->m_hadExternalDoctype)
-#define namespaceSeparator (((Parser *)parser)->m_namespaceSeparator)
+ (parser->m_unknownEncodingHandlerData)
+#define unknownEncodingRelease (parser->m_unknownEncodingRelease)
+#define protocolEncodingName (parser->m_protocolEncodingName)
+#define ns (parser->m_ns)
+#define ns_triplets (parser->m_ns_triplets)
+#define prologState (parser->m_prologState)
+#define processor (parser->m_processor)
+#define errorCode (parser->m_errorCode)
+#define eventPtr (parser->m_eventPtr)
+#define eventEndPtr (parser->m_eventEndPtr)
+#define positionPtr (parser->m_positionPtr)
+#define position (parser->m_position)
+#define openInternalEntities (parser->m_openInternalEntities)
+#define defaultExpandInternalEntities \
+ (parser->m_defaultExpandInternalEntities)
+#define tagLevel (parser->m_tagLevel)
+#define buffer (parser->m_buffer)
+#define bufferPtr (parser->m_bufferPtr)
+#define bufferEnd (parser->m_bufferEnd)
+#define parseEndByteIndex (parser->m_parseEndByteIndex)
+#define parseEndPtr (parser->m_parseEndPtr)
+#define bufferLim (parser->m_bufferLim)
+#define dataBuf (parser->m_dataBuf)
+#define dataBufEnd (parser->m_dataBufEnd)
+#define _dtd (parser->m_dtd)
+#define curBase (parser->m_curBase)
+#define declEntity (parser->m_declEntity)
+#define doctypeName (parser->m_doctypeName)
+#define doctypeSysid (parser->m_doctypeSysid)
+#define doctypePubid (parser->m_doctypePubid)
+#define declAttributeType (parser->m_declAttributeType)
+#define declNotationName (parser->m_declNotationName)
+#define declNotationPublicId (parser->m_declNotationPublicId)
+#define declElementType (parser->m_declElementType)
+#define declAttributeId (parser->m_declAttributeId)
+#define declAttributeIsCdata (parser->m_declAttributeIsCdata)
+#define declAttributeIsId (parser->m_declAttributeIsId)
+#define freeTagList (parser->m_freeTagList)
+#define freeBindingList (parser->m_freeBindingList)
+#define inheritedBindings (parser->m_inheritedBindings)
+#define tagStack (parser->m_tagStack)
+#define atts (parser->m_atts)
+#define attsSize (parser->m_attsSize)
+#define nSpecifiedAtts (parser->m_nSpecifiedAtts)
+#define idAttIndex (parser->m_idAttIndex)
+#define tempPool (parser->m_tempPool)
+#define temp2Pool (parser->m_temp2Pool)
+#define groupConnector (parser->m_groupConnector)
+#define groupSize (parser->m_groupSize)
+#define namespaceSeparator (parser->m_namespaceSeparator)
+#define parentParser (parser->m_parentParser)
#ifdef XML_DTD
-#define parentParser (((Parser *)parser)->m_parentParser)
-#define paramEntityParsing (((Parser *)parser)->m_paramEntityParsing)
+#define isParamEntity (parser->m_isParamEntity)
+#define useForeignDTD (parser->m_useForeignDTD)
+#define paramEntityParsing (parser->m_paramEntityParsing)
#endif /* XML_DTD */
-#ifdef COMPILED_FROM_DSP
-BOOL WINAPI DllMain(HINSTANCE h, DWORD r, LPVOID p) {
- return TRUE;
-}
-#endif /* def COMPILED_FROM_DSP */
-
-#ifdef _MSC_VER
-#ifdef _DEBUG
-Parser *asParser(XML_Parser parser)
-{
- return parser;
-}
-#endif
-#endif
+#define parsing \
+ (parentParser \
+ ? \
+ (isParamEntity \
+ ? \
+ (processor != externalParEntInitProcessor) \
+ : \
+ (processor != externalEntityInitProcessor)) \
+ : \
+ (processor != prologInitProcessor))
-XML_Parser XML_ParserCreate(const XML_Char *encodingName)
+XML_Parser
+XML_ParserCreate(const XML_Char *encodingName)
{
return XML_ParserCreate_MM(encodingName, NULL, NULL);
}
-XML_Parser XML_ParserCreateNS(const XML_Char *encodingName, XML_Char nsSep)
+XML_Parser
+XML_ParserCreateNS(const XML_Char *encodingName, XML_Char nsSep)
{
XML_Char tmp[2];
*tmp = nsSep;
return XML_ParserCreate_MM(encodingName, NULL, tmp);
}
+static const XML_Char implicitContext[] = {
+ 'x', 'm', 'l', '=', 'h', 't', 't', 'p', ':', '/', '/',
+ 'w', 'w', 'w', '.', 'w', '3', '.', 'o', 'r', 'g', '/',
+ 'X', 'M', 'L', '/', '1', '9', '9', '8', '/',
+ 'n', 'a', 'm', 'e', 's', 'p', 'a', 'c', 'e', '\0'
+};
+
XML_Parser
XML_ParserCreate_MM(const XML_Char *encodingName,
- const XML_Memory_Handling_Suite *memsuite,
- const XML_Char *nameSep) {
-
- XML_Parser parser;
- static
- const XML_Char implicitContext[] = {
- XML_T('x'), XML_T('m'), XML_T('l'), XML_T('='),
- XML_T('h'), XML_T('t'), XML_T('t'), XML_T('p'), XML_T(':'),
- XML_T('/'), XML_T('/'), XML_T('w'), XML_T('w'), XML_T('w'),
- XML_T('.'), XML_T('w'), XML_T('3'),
- XML_T('.'), XML_T('o'), XML_T('r'), XML_T('g'),
- XML_T('/'), XML_T('X'), XML_T('M'), XML_T('L'),
- XML_T('/'), XML_T('1'), XML_T('9'), XML_T('9'), XML_T('8'),
- XML_T('/'), XML_T('n'), XML_T('a'), XML_T('m'), XML_T('e'),
- XML_T('s'), XML_T('p'), XML_T('a'), XML_T('c'), XML_T('e'),
- XML_T('\0')
- };
+ const XML_Memory_Handling_Suite *memsuite,
+ const XML_Char *nameSep)
+{
+ XML_Parser parser = parserCreate(encodingName, memsuite, nameSep, NULL);
+ if (parser != NULL && ns) {
+ /* implicit context only set for root parser, since child
+ parsers (i.e. external entity parsers) will inherit it
+ */
+ if (!setContext(parser, implicitContext)) {
+ XML_ParserFree(parser);
+ return NULL;
+ }
+ }
+ return parser;
+}
+static XML_Parser
+parserCreate(const XML_Char *encodingName,
+ const XML_Memory_Handling_Suite *memsuite,
+ const XML_Char *nameSep,
+ DTD *dtd)
+{
+ XML_Parser parser;
if (memsuite) {
XML_Memory_Handling_Suite *mtemp;
- parser = memsuite->malloc_fcn(sizeof(Parser));
- mtemp = &(((Parser *) parser)->m_mem);
- mtemp->malloc_fcn = memsuite->malloc_fcn;
- mtemp->realloc_fcn = memsuite->realloc_fcn;
- mtemp->free_fcn = memsuite->free_fcn;
+ parser = (XML_Parser)
+ memsuite->malloc_fcn(sizeof(struct XML_ParserStruct));
+ if (parser != NULL) {
+ mtemp = (XML_Memory_Handling_Suite *)&(parser->m_mem);
+ mtemp->malloc_fcn = memsuite->malloc_fcn;
+ mtemp->realloc_fcn = memsuite->realloc_fcn;
+ mtemp->free_fcn = memsuite->free_fcn;
+ }
}
else {
XML_Memory_Handling_Suite *mtemp;
- parser = malloc(sizeof(Parser));
- mtemp = &(((Parser *) parser)->m_mem);
- mtemp->malloc_fcn = malloc;
- mtemp->realloc_fcn = realloc;
- mtemp->free_fcn = free;
+ parser = (XML_Parser)malloc(sizeof(struct XML_ParserStruct));
+ if (parser != NULL) {
+ mtemp = (XML_Memory_Handling_Suite *)&(parser->m_mem);
+ mtemp->malloc_fcn = malloc;
+ mtemp->realloc_fcn = realloc;
+ mtemp->free_fcn = free;
+ }
}
if (!parser)
return parser;
- processor = prologInitProcessor;
- XmlPrologStateInit(&prologState);
- userData = 0;
- handlerArg = 0;
- startElementHandler = 0;
- endElementHandler = 0;
- characterDataHandler = 0;
- processingInstructionHandler = 0;
- commentHandler = 0;
- startCdataSectionHandler = 0;
- endCdataSectionHandler = 0;
- defaultHandler = 0;
- startDoctypeDeclHandler = 0;
- endDoctypeDeclHandler = 0;
- unparsedEntityDeclHandler = 0;
- notationDeclHandler = 0;
- startNamespaceDeclHandler = 0;
- endNamespaceDeclHandler = 0;
- notStandaloneHandler = 0;
- externalEntityRefHandler = 0;
- externalEntityRefHandlerArg = parser;
- unknownEncodingHandler = 0;
- elementDeclHandler = 0;
- attlistDeclHandler = 0;
- entityDeclHandler = 0;
- xmlDeclHandler = 0;
- buffer = 0;
- bufferPtr = 0;
- bufferEnd = 0;
- parseEndByteIndex = 0;
- parseEndPtr = 0;
- bufferLim = 0;
- declElementType = 0;
- declAttributeId = 0;
- declEntity = 0;
- doctypeName = 0;
- doctypeSysid = 0;
- doctypePubid = 0;
- declAttributeType = 0;
- declNotationName = 0;
- declNotationPublicId = 0;
- memset(&position, 0, sizeof(POSITION));
- errorCode = XML_ERROR_NONE;
- eventPtr = 0;
- eventEndPtr = 0;
- positionPtr = 0;
- openInternalEntities = 0;
- tagLevel = 0;
- tagStack = 0;
- freeTagList = 0;
- freeBindingList = 0;
- inheritedBindings = 0;
+
+ buffer = NULL;
+ bufferLim = NULL;
+
attsSize = INIT_ATTS_SIZE;
- atts = MALLOC(attsSize * sizeof(ATTRIBUTE));
- nSpecifiedAtts = 0;
- dataBuf = MALLOC(INIT_DATA_BUF_SIZE * sizeof(XML_Char));
+ atts = (ATTRIBUTE *)MALLOC(attsSize * sizeof(ATTRIBUTE));
+ if (atts == NULL) {
+ FREE(parser);
+ return NULL;
+ }
+ dataBuf = (XML_Char *)MALLOC(INIT_DATA_BUF_SIZE * sizeof(XML_Char));
+ if (dataBuf == NULL) {
+ FREE(atts);
+ FREE(parser);
+ return NULL;
+ }
+ dataBufEnd = dataBuf + INIT_DATA_BUF_SIZE;
+
+ if (dtd)
+ _dtd = dtd;
+ else {
+ _dtd = dtdCreate(&parser->m_mem);
+ if (_dtd == NULL) {
+ FREE(dataBuf);
+ FREE(atts);
+ FREE(parser);
+ return NULL;
+ }
+ }
+
+ freeBindingList = NULL;
+ freeTagList = NULL;
+
groupSize = 0;
- groupConnector = 0;
- hadExternalDoctype = 0;
- unknownEncodingMem = 0;
- unknownEncodingRelease = 0;
- unknownEncodingData = 0;
- unknownEncodingHandlerData = 0;
+ groupConnector = NULL;
+
+ unknownEncodingHandler = NULL;
+ unknownEncodingHandlerData = NULL;
+
namespaceSeparator = '!';
-#ifdef XML_DTD
- parentParser = 0;
- paramEntityParsing = XML_PARAM_ENTITY_PARSING_NEVER;
-#endif
- ns = 0;
- ns_triplets = 0;
- poolInit(&tempPool, &(((Parser *) parser)->m_mem));
- poolInit(&temp2Pool, &(((Parser *) parser)->m_mem));
- protocolEncodingName = encodingName ? poolCopyString(&tempPool, encodingName) : 0;
- curBase = 0;
- if (!dtdInit(&dtd, parser) || !atts || !dataBuf
- || (encodingName && !protocolEncodingName)) {
+ ns = XML_FALSE;
+ ns_triplets = XML_FALSE;
+
+ poolInit(&tempPool, &(parser->m_mem));
+ poolInit(&temp2Pool, &(parser->m_mem));
+ parserInit(parser, encodingName);
+
+ if (encodingName && !protocolEncodingName) {
XML_ParserFree(parser);
- return 0;
+ return NULL;
}
- dataBufEnd = dataBuf + INIT_DATA_BUF_SIZE;
if (nameSep) {
- XmlInitEncodingNS(&initEncoding, &encoding, 0);
- ns = 1;
+ ns = XML_TRUE;
internalEncoding = XmlGetInternalEncodingNS();
namespaceSeparator = *nameSep;
-
- if (! setContext(parser, implicitContext)) {
- XML_ParserFree(parser);
- return 0;
- }
}
else {
- XmlInitEncoding(&initEncoding, &encoding, 0);
internalEncoding = XmlGetInternalEncoding();
}
return parser;
-} /* End XML_ParserCreate_MM */
+}
-int XML_SetEncoding(XML_Parser parser, const XML_Char *encodingName)
+static void
+parserInit(XML_Parser parser, const XML_Char *encodingName)
{
- if (!encodingName)
- protocolEncodingName = 0;
+ processor = prologInitProcessor;
+ XmlPrologStateInit(&prologState);
+ protocolEncodingName = (encodingName != NULL
+ ? poolCopyString(&tempPool, encodingName)
+ : NULL);
+ curBase = NULL;
+ XmlInitEncoding(&initEncoding, &encoding, 0);
+ userData = NULL;
+ handlerArg = NULL;
+ startElementHandler = NULL;
+ endElementHandler = NULL;
+ characterDataHandler = NULL;
+ processingInstructionHandler = NULL;
+ commentHandler = NULL;
+ startCdataSectionHandler = NULL;
+ endCdataSectionHandler = NULL;
+ defaultHandler = NULL;
+ startDoctypeDeclHandler = NULL;
+ endDoctypeDeclHandler = NULL;
+ unparsedEntityDeclHandler = NULL;
+ notationDeclHandler = NULL;
+ startNamespaceDeclHandler = NULL;
+ endNamespaceDeclHandler = NULL;
+ notStandaloneHandler = NULL;
+ externalEntityRefHandler = NULL;
+ externalEntityRefHandlerArg = parser;
+ skippedEntityHandler = NULL;
+ elementDeclHandler = NULL;
+ attlistDeclHandler = NULL;
+ entityDeclHandler = NULL;
+ xmlDeclHandler = NULL;
+ bufferPtr = buffer;
+ bufferEnd = buffer;
+ parseEndByteIndex = 0;
+ parseEndPtr = NULL;
+ declElementType = NULL;
+ declAttributeId = NULL;
+ declEntity = NULL;
+ doctypeName = NULL;
+ doctypeSysid = NULL;
+ doctypePubid = NULL;
+ declAttributeType = NULL;
+ declNotationName = NULL;
+ declNotationPublicId = NULL;
+ declAttributeIsCdata = XML_FALSE;
+ declAttributeIsId = XML_FALSE;
+ memset(&position, 0, sizeof(POSITION));
+ errorCode = XML_ERROR_NONE;
+ eventPtr = NULL;
+ eventEndPtr = NULL;
+ positionPtr = NULL;
+ openInternalEntities = 0;
+ defaultExpandInternalEntities = XML_TRUE;
+ tagLevel = 0;
+ tagStack = NULL;
+ inheritedBindings = NULL;
+ nSpecifiedAtts = 0;
+ unknownEncodingMem = NULL;
+ unknownEncodingRelease = NULL;
+ unknownEncodingData = NULL;
+ parentParser = NULL;
+#ifdef XML_DTD
+ isParamEntity = XML_FALSE;
+ useForeignDTD = XML_FALSE;
+ paramEntityParsing = XML_PARAM_ENTITY_PARSING_NEVER;
+#endif
+}
+
+/* moves list of bindings to freeBindingList */
+static void FASTCALL
+moveToFreeBindingList(XML_Parser parser, BINDING *bindings)
+{
+ while (bindings) {
+ BINDING *b = bindings;
+ bindings = bindings->nextTagBinding;
+ b->nextTagBinding = freeBindingList;
+ freeBindingList = b;
+ }
+}
+
+XML_Bool
+XML_ParserReset(XML_Parser parser, const XML_Char *encodingName)
+{
+ TAG *tStk;
+ if (parentParser)
+ return XML_FALSE;
+ /* move tagStack to freeTagList */
+ tStk = tagStack;
+ while (tStk) {
+ TAG *tag = tStk;
+ tStk = tStk->parent;
+ tag->parent = freeTagList;
+ moveToFreeBindingList(parser, tag->bindings);
+ tag->bindings = NULL;
+ freeTagList = tag;
+ }
+ moveToFreeBindingList(parser, inheritedBindings);
+ if (unknownEncodingMem)
+ FREE(unknownEncodingMem);
+ if (unknownEncodingRelease)
+ unknownEncodingRelease(unknownEncodingData);
+ poolClear(&tempPool);
+ poolClear(&temp2Pool);
+ parserInit(parser, encodingName);
+ dtdReset(_dtd, &parser->m_mem);
+ return setContext(parser, implicitContext);
+}
+
+enum XML_Status
+XML_SetEncoding(XML_Parser parser, const XML_Char *encodingName)
+{
+ /* Block after XML_Parse()/XML_ParseBuffer() has been called.
+ XXX There's no way for the caller to determine which of the
+ XXX possible error cases caused the XML_STATUS_ERROR return.
+ */
+ if (parsing)
+ return XML_STATUS_ERROR;
+ if (encodingName == NULL)
+ protocolEncodingName = NULL;
else {
protocolEncodingName = poolCopyString(&tempPool, encodingName);
if (!protocolEncodingName)
- return 0;
+ return XML_STATUS_ERROR;
}
- return 1;
+ return XML_STATUS_OK;
}
-XML_Parser XML_ExternalEntityParserCreate(XML_Parser oldParser,
- const XML_Char *context,
- const XML_Char *encodingName)
+XML_Parser
+XML_ExternalEntityParserCreate(XML_Parser oldParser,
+ const XML_Char *context,
+ const XML_Char *encodingName)
{
XML_Parser parser = oldParser;
- DTD *oldDtd = &dtd;
+ DTD *newDtd = NULL;
+ DTD *oldDtd = _dtd;
XML_StartElementHandler oldStartElementHandler = startElementHandler;
XML_EndElementHandler oldEndElementHandler = endElementHandler;
XML_CharacterDataHandler oldCharacterDataHandler = characterDataHandler;
- XML_ProcessingInstructionHandler oldProcessingInstructionHandler = processingInstructionHandler;
+ XML_ProcessingInstructionHandler oldProcessingInstructionHandler
+ = processingInstructionHandler;
XML_CommentHandler oldCommentHandler = commentHandler;
- XML_StartCdataSectionHandler oldStartCdataSectionHandler = startCdataSectionHandler;
- XML_EndCdataSectionHandler oldEndCdataSectionHandler = endCdataSectionHandler;
+ XML_StartCdataSectionHandler oldStartCdataSectionHandler
+ = startCdataSectionHandler;
+ XML_EndCdataSectionHandler oldEndCdataSectionHandler
+ = endCdataSectionHandler;
XML_DefaultHandler oldDefaultHandler = defaultHandler;
- XML_UnparsedEntityDeclHandler oldUnparsedEntityDeclHandler = unparsedEntityDeclHandler;
+ XML_UnparsedEntityDeclHandler oldUnparsedEntityDeclHandler
+ = unparsedEntityDeclHandler;
XML_NotationDeclHandler oldNotationDeclHandler = notationDeclHandler;
- XML_StartNamespaceDeclHandler oldStartNamespaceDeclHandler = startNamespaceDeclHandler;
- XML_EndNamespaceDeclHandler oldEndNamespaceDeclHandler = endNamespaceDeclHandler;
+ XML_StartNamespaceDeclHandler oldStartNamespaceDeclHandler
+ = startNamespaceDeclHandler;
+ XML_EndNamespaceDeclHandler oldEndNamespaceDeclHandler
+ = endNamespaceDeclHandler;
XML_NotStandaloneHandler oldNotStandaloneHandler = notStandaloneHandler;
- XML_ExternalEntityRefHandler oldExternalEntityRefHandler = externalEntityRefHandler;
- XML_UnknownEncodingHandler oldUnknownEncodingHandler = unknownEncodingHandler;
+ XML_ExternalEntityRefHandler oldExternalEntityRefHandler
+ = externalEntityRefHandler;
+ XML_SkippedEntityHandler oldSkippedEntityHandler = skippedEntityHandler;
+ XML_UnknownEncodingHandler oldUnknownEncodingHandler
+ = unknownEncodingHandler;
XML_ElementDeclHandler oldElementDeclHandler = elementDeclHandler;
XML_AttlistDeclHandler oldAttlistDeclHandler = attlistDeclHandler;
XML_EntityDeclHandler oldEntityDeclHandler = entityDeclHandler;
@@ -728,27 +934,35 @@ XML_Parser XML_ExternalEntityParserCreate(XML_Parser oldParser,
void *oldUserData = userData;
void *oldHandlerArg = handlerArg;
- int oldDefaultExpandInternalEntities = defaultExpandInternalEntities;
- void *oldExternalEntityRefHandlerArg = externalEntityRefHandlerArg;
+ XML_Bool oldDefaultExpandInternalEntities = defaultExpandInternalEntities;
+ XML_Parser oldExternalEntityRefHandlerArg = externalEntityRefHandlerArg;
#ifdef XML_DTD
- int oldParamEntityParsing = paramEntityParsing;
+ enum XML_ParamEntityParsing oldParamEntityParsing = paramEntityParsing;
+ int oldInEntityValue = prologState.inEntityValue;
#endif
- int oldns_triplets = ns_triplets;
+ XML_Bool oldns_triplets = ns_triplets;
+
+#ifdef XML_DTD
+ if (!context)
+ newDtd = oldDtd;
+#endif /* XML_DTD */
+ /* Note that the magical uses of the pre-processor to make field
+ access look more like C++ require that `parser' be overwritten
+ here. This makes this function more painful to follow than it
+ would be otherwise.
+ */
if (ns) {
XML_Char tmp[2];
-
*tmp = namespaceSeparator;
- parser = XML_ParserCreate_MM(encodingName, &((Parser *)parser)->m_mem,
- tmp);
+ parser = parserCreate(encodingName, &parser->m_mem, tmp, newDtd);
}
else {
- parser = XML_ParserCreate_MM(encodingName, &((Parser *)parser)->m_mem,
- NULL);
+ parser = parserCreate(encodingName, &parser->m_mem, NULL, newDtd);
}
if (!parser)
- return 0;
+ return NULL;
startElementHandler = oldStartElementHandler;
endElementHandler = oldEndElementHandler;
@@ -764,6 +978,7 @@ XML_Parser XML_ExternalEntityParserCreate(XML_Parser oldParser,
endNamespaceDeclHandler = oldEndNamespaceDeclHandler;
notStandaloneHandler = oldNotStandaloneHandler;
externalEntityRefHandler = oldExternalEntityRefHandler;
+ skippedEntityHandler = oldSkippedEntityHandler;
unknownEncodingHandler = oldUnknownEncodingHandler;
elementDeclHandler = oldElementDeclHandler;
attlistDeclHandler = oldAttlistDeclHandler;
@@ -779,30 +994,38 @@ XML_Parser XML_ExternalEntityParserCreate(XML_Parser oldParser,
externalEntityRefHandlerArg = oldExternalEntityRefHandlerArg;
defaultExpandInternalEntities = oldDefaultExpandInternalEntities;
ns_triplets = oldns_triplets;
+ parentParser = oldParser;
#ifdef XML_DTD
paramEntityParsing = oldParamEntityParsing;
+ prologState.inEntityValue = oldInEntityValue;
if (context) {
#endif /* XML_DTD */
- if (!dtdCopy(&dtd, oldDtd, parser) || !setContext(parser, context)) {
+ if (!dtdCopy(_dtd, oldDtd, &parser->m_mem)
+ || !setContext(parser, context)) {
XML_ParserFree(parser);
- return 0;
+ return NULL;
}
processor = externalEntityInitProcessor;
#ifdef XML_DTD
}
else {
- dtdSwap(&dtd, oldDtd);
- parentParser = oldParser;
+ /* The DTD instance referenced by _dtd is shared between the document's
+ root parser and external PE parsers, therefore one does not need to
+ call setContext. In addition, one also *must* not call setContext,
+ because this would overwrite existing prefix->binding pointers in
+ _dtd with ones that get destroyed with the external PE parser.
+ This would leave those prefixes with dangling pointers.
+ */
+ isParamEntity = XML_TRUE;
XmlPrologStateInitExternalEntity(&prologState);
- dtd.complete = 1;
- hadExternalDoctype = 1;
+ processor = externalParEntInitProcessor;
}
#endif /* XML_DTD */
return parser;
}
-static
-void destroyBindings(BINDING *bindings, XML_Parser parser)
+static void FASTCALL
+destroyBindings(BINDING *bindings, XML_Parser parser)
{
for (;;) {
BINDING *b = bindings;
@@ -814,15 +1037,16 @@ void destroyBindings(BINDING *bindings, XML_Parser parser)
}
}
-void XML_ParserFree(XML_Parser parser)
+void
+XML_ParserFree(XML_Parser parser)
{
for (;;) {
TAG *p;
- if (tagStack == 0) {
- if (freeTagList == 0)
- break;
+ if (tagStack == NULL) {
+ if (freeTagList == NULL)
+ break;
tagStack = freeTagList;
- freeTagList = 0;
+ freeTagList = NULL;
}
p = tagStack;
tagStack = tagStack->parent;
@@ -835,13 +1059,14 @@ void XML_ParserFree(XML_Parser parser)
poolDestroy(&tempPool);
poolDestroy(&temp2Pool);
#ifdef XML_DTD
- if (parentParser) {
- if (hadExternalDoctype)
- dtd.complete = 0;
- dtdSwap(&dtd, &((Parser *)parentParser)->m_dtd);
- }
+ /* external parameter entity parsers share the DTD structure
+ parser->m_dtd with the root parser, so we must not destroy it
+ */
+ if (!isParamEntity && _dtd)
+#else
+ if (_dtd)
#endif /* XML_DTD */
- dtdDestroy(&dtd, parser);
+ dtdDestroy(_dtd, (XML_Bool)!parentParser, &parser->m_mem);
FREE((void *)atts);
if (groupConnector)
FREE(groupConnector);
@@ -855,17 +1080,37 @@ void XML_ParserFree(XML_Parser parser)
FREE(parser);
}
-void XML_UseParserAsHandlerArg(XML_Parser parser)
+void
+XML_UseParserAsHandlerArg(XML_Parser parser)
{
handlerArg = parser;
}
+enum XML_Error
+XML_UseForeignDTD(XML_Parser parser, XML_Bool useDTD)
+{
+#ifdef XML_DTD
+ /* block after XML_Parse()/XML_ParseBuffer() has been called */
+ if (parsing)
+ return XML_ERROR_CANT_CHANGE_FEATURE_ONCE_PARSING;
+ useForeignDTD = useDTD;
+ return XML_ERROR_NONE;
+#else
+ return XML_ERROR_FEATURE_REQUIRES_XML_DTD;
+#endif
+}
+
void
-XML_SetReturnNSTriplet(XML_Parser parser, int do_nst) {
- ns_triplets = do_nst;
+XML_SetReturnNSTriplet(XML_Parser parser, int do_nst)
+{
+ /* block after XML_Parse()/XML_ParseBuffer() has been called */
+ if (parsing)
+ return;
+ ns_triplets = do_nst ? XML_TRUE : XML_FALSE;
}
-void XML_SetUserData(XML_Parser parser, void *p)
+void
+XML_SetUserData(XML_Parser parser, void *p)
{
if (handlerArg == userData)
handlerArg = userData = p;
@@ -873,225 +1118,267 @@ void XML_SetUserData(XML_Parser parser, void *p)
userData = p;
}
-int XML_SetBase(XML_Parser parser, const XML_Char *p)
+enum XML_Status
+XML_SetBase(XML_Parser parser, const XML_Char *p)
{
if (p) {
- p = poolCopyString(&dtd.pool, p);
+ p = poolCopyString(&_dtd->pool, p);
if (!p)
- return 0;
+ return XML_STATUS_ERROR;
curBase = p;
}
else
- curBase = 0;
- return 1;
+ curBase = NULL;
+ return XML_STATUS_OK;
}
-const XML_Char *XML_GetBase(XML_Parser parser)
+const XML_Char *
+XML_GetBase(XML_Parser parser)
{
return curBase;
}
-int XML_GetSpecifiedAttributeCount(XML_Parser parser)
+int
+XML_GetSpecifiedAttributeCount(XML_Parser parser)
{
return nSpecifiedAtts;
}
-int XML_GetIdAttributeIndex(XML_Parser parser)
+int
+XML_GetIdAttributeIndex(XML_Parser parser)
{
return idAttIndex;
}
-void XML_SetElementHandler(XML_Parser parser,
- XML_StartElementHandler start,
- XML_EndElementHandler end)
+void
+XML_SetElementHandler(XML_Parser parser,
+ XML_StartElementHandler start,
+ XML_EndElementHandler end)
{
startElementHandler = start;
endElementHandler = end;
}
-void XML_SetStartElementHandler(XML_Parser parser,
- XML_StartElementHandler start) {
+void
+XML_SetStartElementHandler(XML_Parser parser,
+ XML_StartElementHandler start) {
startElementHandler = start;
}
-void XML_SetEndElementHandler(XML_Parser parser,
- XML_EndElementHandler end) {
+void
+XML_SetEndElementHandler(XML_Parser parser,
+ XML_EndElementHandler end) {
endElementHandler = end;
}
-void XML_SetCharacterDataHandler(XML_Parser parser,
- XML_CharacterDataHandler handler)
+void
+XML_SetCharacterDataHandler(XML_Parser parser,
+ XML_CharacterDataHandler handler)
{
characterDataHandler = handler;
}
-void XML_SetProcessingInstructionHandler(XML_Parser parser,
- XML_ProcessingInstructionHandler handler)
+void
+XML_SetProcessingInstructionHandler(XML_Parser parser,
+ XML_ProcessingInstructionHandler handler)
{
processingInstructionHandler = handler;
}
-void XML_SetCommentHandler(XML_Parser parser,
- XML_CommentHandler handler)
+void
+XML_SetCommentHandler(XML_Parser parser,
+ XML_CommentHandler handler)
{
commentHandler = handler;
}
-void XML_SetCdataSectionHandler(XML_Parser parser,
- XML_StartCdataSectionHandler start,
- XML_EndCdataSectionHandler end)
+void
+XML_SetCdataSectionHandler(XML_Parser parser,
+ XML_StartCdataSectionHandler start,
+ XML_EndCdataSectionHandler end)
{
startCdataSectionHandler = start;
endCdataSectionHandler = end;
}
-void XML_SetStartCdataSectionHandler(XML_Parser parser,
- XML_StartCdataSectionHandler start) {
+void
+XML_SetStartCdataSectionHandler(XML_Parser parser,
+ XML_StartCdataSectionHandler start) {
startCdataSectionHandler = start;
}
-void XML_SetEndCdataSectionHandler(XML_Parser parser,
- XML_EndCdataSectionHandler end) {
+void
+XML_SetEndCdataSectionHandler(XML_Parser parser,
+ XML_EndCdataSectionHandler end) {
endCdataSectionHandler = end;
}
-void XML_SetDefaultHandler(XML_Parser parser,
- XML_DefaultHandler handler)
+void
+XML_SetDefaultHandler(XML_Parser parser,
+ XML_DefaultHandler handler)
{
defaultHandler = handler;
- defaultExpandInternalEntities = 0;
+ defaultExpandInternalEntities = XML_FALSE;
}
-void XML_SetDefaultHandlerExpand(XML_Parser parser,
- XML_DefaultHandler handler)
+void
+XML_SetDefaultHandlerExpand(XML_Parser parser,
+ XML_DefaultHandler handler)
{
defaultHandler = handler;
- defaultExpandInternalEntities = 1;
+ defaultExpandInternalEntities = XML_TRUE;
}
-void XML_SetDoctypeDeclHandler(XML_Parser parser,
- XML_StartDoctypeDeclHandler start,
- XML_EndDoctypeDeclHandler end)
+void
+XML_SetDoctypeDeclHandler(XML_Parser parser,
+ XML_StartDoctypeDeclHandler start,
+ XML_EndDoctypeDeclHandler end)
{
startDoctypeDeclHandler = start;
endDoctypeDeclHandler = end;
}
-void XML_SetStartDoctypeDeclHandler(XML_Parser parser,
- XML_StartDoctypeDeclHandler start) {
+void
+XML_SetStartDoctypeDeclHandler(XML_Parser parser,
+ XML_StartDoctypeDeclHandler start) {
startDoctypeDeclHandler = start;
}
-void XML_SetEndDoctypeDeclHandler(XML_Parser parser,
- XML_EndDoctypeDeclHandler end) {
+void
+XML_SetEndDoctypeDeclHandler(XML_Parser parser,
+ XML_EndDoctypeDeclHandler end) {
endDoctypeDeclHandler = end;
}
-void XML_SetUnparsedEntityDeclHandler(XML_Parser parser,
- XML_UnparsedEntityDeclHandler handler)
+void
+XML_SetUnparsedEntityDeclHandler(XML_Parser parser,
+ XML_UnparsedEntityDeclHandler handler)
{
unparsedEntityDeclHandler = handler;
}
-void XML_SetNotationDeclHandler(XML_Parser parser,
- XML_NotationDeclHandler handler)
+void
+XML_SetNotationDeclHandler(XML_Parser parser,
+ XML_NotationDeclHandler handler)
{
notationDeclHandler = handler;
}
-void XML_SetNamespaceDeclHandler(XML_Parser parser,
- XML_StartNamespaceDeclHandler start,
- XML_EndNamespaceDeclHandler end)
+void
+XML_SetNamespaceDeclHandler(XML_Parser parser,
+ XML_StartNamespaceDeclHandler start,
+ XML_EndNamespaceDeclHandler end)
{
startNamespaceDeclHandler = start;
endNamespaceDeclHandler = end;
}
-void XML_SetStartNamespaceDeclHandler(XML_Parser parser,
- XML_StartNamespaceDeclHandler start) {
+void
+XML_SetStartNamespaceDeclHandler(XML_Parser parser,
+ XML_StartNamespaceDeclHandler start) {
startNamespaceDeclHandler = start;
}
-void XML_SetEndNamespaceDeclHandler(XML_Parser parser,
- XML_EndNamespaceDeclHandler end) {
+void
+XML_SetEndNamespaceDeclHandler(XML_Parser parser,
+ XML_EndNamespaceDeclHandler end) {
endNamespaceDeclHandler = end;
}
-
-void XML_SetNotStandaloneHandler(XML_Parser parser,
- XML_NotStandaloneHandler handler)
+void
+XML_SetNotStandaloneHandler(XML_Parser parser,
+ XML_NotStandaloneHandler handler)
{
notStandaloneHandler = handler;
}
-void XML_SetExternalEntityRefHandler(XML_Parser parser,
- XML_ExternalEntityRefHandler handler)
+void
+XML_SetExternalEntityRefHandler(XML_Parser parser,
+ XML_ExternalEntityRefHandler handler)
{
externalEntityRefHandler = handler;
}
-void XML_SetExternalEntityRefHandlerArg(XML_Parser parser, void *arg)
+void
+XML_SetExternalEntityRefHandlerArg(XML_Parser parser, void *arg)
{
if (arg)
- externalEntityRefHandlerArg = arg;
+ externalEntityRefHandlerArg = (XML_Parser)arg;
else
externalEntityRefHandlerArg = parser;
}
-void XML_SetUnknownEncodingHandler(XML_Parser parser,
- XML_UnknownEncodingHandler handler,
- void *data)
+void
+XML_SetSkippedEntityHandler(XML_Parser parser,
+ XML_SkippedEntityHandler handler)
+{
+ skippedEntityHandler = handler;
+}
+
+void
+XML_SetUnknownEncodingHandler(XML_Parser parser,
+ XML_UnknownEncodingHandler handler,
+ void *data)
{
unknownEncodingHandler = handler;
unknownEncodingHandlerData = data;
}
-void XML_SetElementDeclHandler(XML_Parser parser,
- XML_ElementDeclHandler eldecl)
+void
+XML_SetElementDeclHandler(XML_Parser parser,
+ XML_ElementDeclHandler eldecl)
{
elementDeclHandler = eldecl;
}
-void XML_SetAttlistDeclHandler(XML_Parser parser,
- XML_AttlistDeclHandler attdecl)
+void
+XML_SetAttlistDeclHandler(XML_Parser parser,
+ XML_AttlistDeclHandler attdecl)
{
attlistDeclHandler = attdecl;
}
-void XML_SetEntityDeclHandler(XML_Parser parser,
- XML_EntityDeclHandler handler)
+void
+XML_SetEntityDeclHandler(XML_Parser parser,
+ XML_EntityDeclHandler handler)
{
entityDeclHandler = handler;
}
-void XML_SetXmlDeclHandler(XML_Parser parser,
- XML_XmlDeclHandler handler) {
+void
+XML_SetXmlDeclHandler(XML_Parser parser,
+ XML_XmlDeclHandler handler) {
xmlDeclHandler = handler;
}
-int XML_SetParamEntityParsing(XML_Parser parser,
- enum XML_ParamEntityParsing parsing)
+int
+XML_SetParamEntityParsing(XML_Parser parser,
+ enum XML_ParamEntityParsing peParsing)
{
+ /* block after XML_Parse()/XML_ParseBuffer() has been called */
+ if (parsing)
+ return 0;
#ifdef XML_DTD
- paramEntityParsing = parsing;
+ paramEntityParsing = peParsing;
return 1;
#else
- return parsing == XML_PARAM_ENTITY_PARSING_NEVER;
+ return peParsing == XML_PARAM_ENTITY_PARSING_NEVER;
#endif
}
-int XML_Parse(XML_Parser parser, const char *s, int len, int isFinal)
+enum XML_Status
+XML_Parse(XML_Parser parser, const char *s, int len, int isFinal)
{
if (len == 0) {
if (!isFinal)
- return 1;
+ return XML_STATUS_OK;
positionPtr = bufferPtr;
errorCode = processor(parser, bufferPtr, parseEndPtr = bufferEnd, 0);
if (errorCode == XML_ERROR_NONE)
- return 1;
+ return XML_STATUS_OK;
eventEndPtr = eventPtr;
processor = errorProcessor;
- return 0;
+ return XML_STATUS_ERROR;
}
#ifndef XML_CONTEXT_BYTES
else if (bufferPtr == bufferEnd) {
@@ -1102,66 +1389,83 @@ int XML_Parse(XML_Parser parser, const char *s, int len, int isFinal)
if (isFinal) {
errorCode = processor(parser, s, parseEndPtr = s + len, 0);
if (errorCode == XML_ERROR_NONE)
- return 1;
+ return XML_STATUS_OK;
eventEndPtr = eventPtr;
processor = errorProcessor;
- return 0;
+ return XML_STATUS_ERROR;
}
errorCode = processor(parser, s, parseEndPtr = s + len, &end);
if (errorCode != XML_ERROR_NONE) {
eventEndPtr = eventPtr;
processor = errorProcessor;
- return 0;
+ return XML_STATUS_ERROR;
}
XmlUpdatePosition(encoding, positionPtr, end, &position);
+ positionPtr = end;
nLeftOver = s + len - end;
if (nLeftOver) {
- if (buffer == 0 || nLeftOver > bufferLim - buffer) {
- /* FIXME avoid integer overflow */
- buffer = buffer == 0 ? MALLOC(len * 2) : REALLOC(buffer, len * 2);
- /* FIXME storage leak if realloc fails */
- if (!buffer) {
- errorCode = XML_ERROR_NO_MEMORY;
- eventPtr = eventEndPtr = 0;
- processor = errorProcessor;
- return 0;
- }
- bufferLim = buffer + len * 2;
+ if (buffer == NULL || nLeftOver > bufferLim - buffer) {
+ /* FIXME avoid integer overflow */
+ char *temp;
+ temp = (buffer == NULL
+ ? (char *)MALLOC(len * 2)
+ : (char *)REALLOC(buffer, len * 2));
+ if (temp == NULL) {
+ errorCode = XML_ERROR_NO_MEMORY;
+ return XML_STATUS_ERROR;
+ }
+ buffer = temp;
+ if (!buffer) {
+ errorCode = XML_ERROR_NO_MEMORY;
+ eventPtr = eventEndPtr = NULL;
+ processor = errorProcessor;
+ return XML_STATUS_ERROR;
+ }
+ bufferLim = buffer + len * 2;
}
memcpy(buffer, end, nLeftOver);
bufferPtr = buffer;
bufferEnd = buffer + nLeftOver;
}
- return 1;
+ return XML_STATUS_OK;
}
#endif /* not defined XML_CONTEXT_BYTES */
else {
- memcpy(XML_GetBuffer(parser, len), s, len);
- return XML_ParseBuffer(parser, len, isFinal);
+ void *buff = XML_GetBuffer(parser, len);
+ if (buff == NULL)
+ return XML_STATUS_ERROR;
+ else {
+ memcpy(buff, s, len);
+ return XML_ParseBuffer(parser, len, isFinal);
+ }
}
}
-int XML_ParseBuffer(XML_Parser parser, int len, int isFinal)
+enum XML_Status
+XML_ParseBuffer(XML_Parser parser, int len, int isFinal)
{
const char *start = bufferPtr;
positionPtr = start;
bufferEnd += len;
parseEndByteIndex += len;
errorCode = processor(parser, start, parseEndPtr = bufferEnd,
- isFinal ? (const char **)0 : &bufferPtr);
+ isFinal ? (const char **)NULL : &bufferPtr);
if (errorCode == XML_ERROR_NONE) {
- if (!isFinal)
+ if (!isFinal) {
XmlUpdatePosition(encoding, positionPtr, bufferPtr, &position);
- return 1;
+ positionPtr = bufferPtr;
+ }
+ return XML_STATUS_OK;
}
else {
eventEndPtr = eventPtr;
processor = errorProcessor;
- return 0;
+ return XML_STATUS_ERROR;
}
}
-void *XML_GetBuffer(XML_Parser parser, int len)
+void *
+XML_GetBuffer(XML_Parser parser, int len)
{
if (len > bufferLim - bufferEnd) {
/* FIXME avoid integer overflow */
@@ -1176,10 +1480,10 @@ void *XML_GetBuffer(XML_Parser parser, int len)
if (neededSize <= bufferLim - buffer) {
#ifdef XML_CONTEXT_BYTES
if (keep < bufferPtr - buffer) {
- int offset = (bufferPtr - buffer) - keep;
- memmove(buffer, &buffer[offset], bufferEnd - bufferPtr + keep);
- bufferEnd -= offset;
- bufferPtr -= offset;
+ int offset = (bufferPtr - buffer) - keep;
+ memmove(buffer, &buffer[offset], bufferEnd - bufferPtr + keep);
+ bufferEnd -= offset;
+ bufferPtr -= offset;
}
#else
memmove(buffer, bufferPtr, bufferEnd - bufferPtr);
@@ -1191,35 +1495,35 @@ void *XML_GetBuffer(XML_Parser parser, int len)
char *newBuf;
int bufferSize = bufferLim - bufferPtr;
if (bufferSize == 0)
- bufferSize = INIT_BUFFER_SIZE;
+ bufferSize = INIT_BUFFER_SIZE;
do {
- bufferSize *= 2;
+ bufferSize *= 2;
} while (bufferSize < neededSize);
- newBuf = MALLOC(bufferSize);
+ newBuf = (char *)MALLOC(bufferSize);
if (newBuf == 0) {
- errorCode = XML_ERROR_NO_MEMORY;
- return 0;
+ errorCode = XML_ERROR_NO_MEMORY;
+ return NULL;
}
bufferLim = newBuf + bufferSize;
#ifdef XML_CONTEXT_BYTES
if (bufferPtr) {
- int keep = bufferPtr - buffer;
- if (keep > XML_CONTEXT_BYTES)
- keep = XML_CONTEXT_BYTES;
- memcpy(newBuf, &bufferPtr[-keep], bufferEnd - bufferPtr + keep);
- FREE(buffer);
- buffer = newBuf;
- bufferEnd = buffer + (bufferEnd - bufferPtr) + keep;
- bufferPtr = buffer + keep;
+ int keep = bufferPtr - buffer;
+ if (keep > XML_CONTEXT_BYTES)
+ keep = XML_CONTEXT_BYTES;
+ memcpy(newBuf, &bufferPtr[-keep], bufferEnd - bufferPtr + keep);
+ FREE(buffer);
+ buffer = newBuf;
+ bufferEnd = buffer + (bufferEnd - bufferPtr) + keep;
+ bufferPtr = buffer + keep;
}
else {
- bufferEnd = newBuf + (bufferEnd - bufferPtr);
- bufferPtr = buffer = newBuf;
+ bufferEnd = newBuf + (bufferEnd - bufferPtr);
+ bufferPtr = buffer = newBuf;
}
#else
if (bufferPtr) {
- memcpy(newBuf, bufferPtr, bufferEnd - bufferPtr);
- FREE(buffer);
+ memcpy(newBuf, bufferPtr, bufferEnd - bufferPtr);
+ FREE(buffer);
}
bufferEnd = newBuf + (bufferEnd - bufferPtr);
bufferPtr = buffer = newBuf;
@@ -1229,26 +1533,30 @@ void *XML_GetBuffer(XML_Parser parser, int len)
return bufferEnd;
}
-enum XML_Error XML_GetErrorCode(XML_Parser parser)
+enum XML_Error
+XML_GetErrorCode(XML_Parser parser)
{
return errorCode;
}
-long XML_GetCurrentByteIndex(XML_Parser parser)
+long
+XML_GetCurrentByteIndex(XML_Parser parser)
{
if (eventPtr)
return parseEndByteIndex - (parseEndPtr - eventPtr);
return -1;
}
-int XML_GetCurrentByteCount(XML_Parser parser)
+int
+XML_GetCurrentByteCount(XML_Parser parser)
{
if (eventEndPtr && eventPtr)
return eventEndPtr - eventPtr;
return 0;
}
-const char * XML_GetInputContext(XML_Parser parser, int *offset, int *size)
+const char *
+XML_GetInputContext(XML_Parser parser, int *offset, int *size)
{
#ifdef XML_CONTEXT_BYTES
if (eventPtr && buffer) {
@@ -1260,7 +1568,8 @@ const char * XML_GetInputContext(XML_Parser parser, int *offset, int *size)
return (char *) 0;
}
-int XML_GetCurrentLineNumber(XML_Parser parser)
+int
+XML_GetCurrentLineNumber(XML_Parser parser)
{
if (eventPtr) {
XmlUpdatePosition(encoding, positionPtr, eventPtr, &position);
@@ -1269,7 +1578,8 @@ int XML_GetCurrentLineNumber(XML_Parser parser)
return position.lineNumber + 1;
}
-int XML_GetCurrentColumnNumber(XML_Parser parser)
+int
+XML_GetCurrentColumnNumber(XML_Parser parser)
{
if (eventPtr) {
XmlUpdatePosition(encoding, positionPtr, eventPtr, &position);
@@ -1278,59 +1588,104 @@ int XML_GetCurrentColumnNumber(XML_Parser parser)
return position.columnNumber;
}
-void XML_DefaultCurrent(XML_Parser parser)
+void
+XML_FreeContentModel(XML_Parser parser, XML_Content *model)
+{
+ FREE(model);
+}
+
+void *
+XML_MemMalloc(XML_Parser parser, size_t size)
+{
+ return MALLOC(size);
+}
+
+void *
+XML_MemRealloc(XML_Parser parser, void *ptr, size_t size)
+{
+ return REALLOC(ptr, size);
+}
+
+void
+XML_MemFree(XML_Parser parser, void *ptr)
+{
+ FREE(ptr);
+}
+
+void
+XML_DefaultCurrent(XML_Parser parser)
{
if (defaultHandler) {
if (openInternalEntities)
reportDefault(parser,
- internalEncoding,
- openInternalEntities->internalEventPtr,
- openInternalEntities->internalEventEndPtr);
+ internalEncoding,
+ openInternalEntities->internalEventPtr,
+ openInternalEntities->internalEventEndPtr);
else
reportDefault(parser, encoding, eventPtr, eventEndPtr);
}
}
-const XML_LChar *XML_ErrorString(int code)
+const XML_LChar *
+XML_ErrorString(enum XML_Error code)
{
static const XML_LChar *message[] = {
0,
- XML_T("out of memory"),
- XML_T("syntax error"),
- XML_T("no element found"),
- XML_T("not well-formed (invalid token)"),
- XML_T("unclosed token"),
- XML_T("unclosed token"),
- XML_T("mismatched tag"),
- XML_T("duplicate attribute"),
- XML_T("junk after document element"),
- XML_T("illegal parameter entity reference"),
- XML_T("undefined entity"),
- XML_T("recursive entity reference"),
- XML_T("asynchronous entity"),
- XML_T("reference to invalid character number"),
- XML_T("reference to binary entity"),
- XML_T("reference to external entity in attribute"),
- XML_T("xml processing instruction not at start of external entity"),
- XML_T("unknown encoding"),
- XML_T("encoding specified in XML declaration is incorrect"),
- XML_T("unclosed CDATA section"),
- XML_T("error in processing external entity reference"),
- XML_T("document is not standalone"),
- XML_T("unexpected parser state - please send a bug report")
+ XML_L("out of memory"),
+ XML_L("syntax error"),
+ XML_L("no element found"),
+ XML_L("not well-formed (invalid token)"),
+ XML_L("unclosed token"),
+ XML_L("partial character"),
+ XML_L("mismatched tag"),
+ XML_L("duplicate attribute"),
+ XML_L("junk after document element"),
+ XML_L("illegal parameter entity reference"),
+ XML_L("undefined entity"),
+ XML_L("recursive entity reference"),
+ XML_L("asynchronous entity"),
+ XML_L("reference to invalid character number"),
+ XML_L("reference to binary entity"),
+ XML_L("reference to external entity in attribute"),
+ XML_L("xml declaration not at start of external entity"),
+ XML_L("unknown encoding"),
+ XML_L("encoding specified in XML declaration is incorrect"),
+ XML_L("unclosed CDATA section"),
+ XML_L("error in processing external entity reference"),
+ XML_L("document is not standalone"),
+ XML_L("unexpected parser state - please send a bug report"),
+ XML_L("entity declared in parameter entity"),
+ XML_L("requested feature requires XML_DTD support in Expat"),
+ XML_L("cannot change setting once parsing has begun")
};
if (code > 0 && code < sizeof(message)/sizeof(message[0]))
return message[code];
- return 0;
+ return NULL;
}
const XML_LChar *
XML_ExpatVersion(void) {
- return VERSION;
+
+ /* V1 is used to string-ize the version number. However, it would
+ string-ize the actual version macro *names* unless we get them
+ substituted before being passed to V1. CPP is defined to expand
+ a macro, then rescan for more expansions. Thus, we use V2 to expand
+ the version macros, then CPP will expand the resulting V1() macro
+ with the correct numerals. */
+ /* ### I'm assuming cpp is portable in this respect... */
+
+#define V1(a,b,c) XML_L(#a)XML_L(".")XML_L(#b)XML_L(".")XML_L(#c)
+#define V2(a,b,c) XML_L("expat_")V1(a,b,c)
+
+ return V2(XML_MAJOR_VERSION, XML_MINOR_VERSION, XML_MICRO_VERSION);
+
+#undef V1
+#undef V2
}
XML_Expat_Version
-XML_ExpatVersionInfo(void) {
+XML_ExpatVersionInfo(void)
+{
XML_Expat_Version version;
version.major = XML_MAJOR_VERSION;
@@ -1340,20 +1695,106 @@ XML_ExpatVersionInfo(void) {
return version;
}
-static
-enum XML_Error contentProcessor(XML_Parser parser,
- const char *start,
- const char *end,
- const char **endPtr)
+const XML_Feature *
+XML_GetFeatureList(void)
{
- return doContent(parser, 0, encoding, start, end, endPtr);
+ static XML_Feature features[] = {
+ {XML_FEATURE_SIZEOF_XML_CHAR, XML_L("sizeof(XML_Char)")},
+ {XML_FEATURE_SIZEOF_XML_LCHAR, XML_L("sizeof(XML_LChar)")},
+#ifdef XML_UNICODE
+ {XML_FEATURE_UNICODE, XML_L("XML_UNICODE")},
+#endif
+#ifdef XML_UNICODE_WCHAR_T
+ {XML_FEATURE_UNICODE_WCHAR_T, XML_L("XML_UNICODE_WCHAR_T")},
+#endif
+#ifdef XML_DTD
+ {XML_FEATURE_DTD, XML_L("XML_DTD")},
+#endif
+#ifdef XML_CONTEXT_BYTES
+ {XML_FEATURE_CONTEXT_BYTES, XML_L("XML_CONTEXT_BYTES"),
+ XML_CONTEXT_BYTES},
+#endif
+#ifdef XML_MIN_SIZE
+ {XML_FEATURE_MIN_SIZE, XML_L("XML_MIN_SIZE")},
+#endif
+ {XML_FEATURE_END, NULL}
+ };
+
+ features[0].value = sizeof(XML_Char);
+ features[1].value = sizeof(XML_LChar);
+ return features;
+}
+
+/* Initially tag->rawName always points into the parse buffer;
+ for those TAG instances opened while the current parse buffer was
+ processed, and not yet closed, we need to store tag->rawName in a more
+ permanent location, since the parse buffer is about to be discarded.
+*/
+static XML_Bool
+storeRawNames(XML_Parser parser)
+{
+ TAG *tag = tagStack;
+ while (tag) {
+ int bufSize;
+ int nameLen = sizeof(XML_Char) * (tag->name.strLen + 1);
+ char *rawNameBuf = tag->buf + nameLen;
+ /* Stop if already stored. Since tagStack is a stack, we can stop
+ at the first entry that has already been copied; everything
+ below it in the stack is already been accounted for in a
+ previous call to this function.
+ */
+ if (tag->rawName == rawNameBuf)
+ break;
+ /* For re-use purposes we need to ensure that the
+ size of tag->buf is a multiple of sizeof(XML_Char).
+ */
+ bufSize = nameLen + ROUND_UP(tag->rawNameLength, sizeof(XML_Char));
+ if (bufSize > tag->bufEnd - tag->buf) {
+ char *temp = (char *)REALLOC(tag->buf, bufSize);
+ if (temp == NULL)
+ return XML_FALSE;
+ /* if tag->name.str points to tag->buf (only when namespace
+ processing is off) then we have to update it
+ */
+ if (tag->name.str == (XML_Char *)tag->buf)
+ tag->name.str = (XML_Char *)temp;
+ /* if tag->name.localPart is set (when namespace processing is on)
+ then update it as well, since it will always point into tag->buf
+ */
+ if (tag->name.localPart)
+ tag->name.localPart = (XML_Char *)temp + (tag->name.localPart -
+ (XML_Char *)tag->buf);
+ tag->buf = temp;
+ tag->bufEnd = temp + bufSize;
+ rawNameBuf = temp + nameLen;
+ }
+ memcpy(rawNameBuf, tag->rawName, tag->rawNameLength);
+ tag->rawName = rawNameBuf;
+ tag = tag->parent;
+ }
+ return XML_TRUE;
+}
+
+static enum XML_Error PTRCALL
+contentProcessor(XML_Parser parser,
+ const char *start,
+ const char *end,
+ const char **endPtr)
+{
+ enum XML_Error result =
+ doContent(parser, 0, encoding, start, end, endPtr);
+ if (result != XML_ERROR_NONE)
+ return result;
+ if (!storeRawNames(parser))
+ return XML_ERROR_NO_MEMORY;
+ return result;
}
-static
-enum XML_Error externalEntityInitProcessor(XML_Parser parser,
- const char *start,
- const char *end,
- const char **endPtr)
+static enum XML_Error PTRCALL
+externalEntityInitProcessor(XML_Parser parser,
+ const char *start,
+ const char *end,
+ const char **endPtr)
{
enum XML_Error result = initializeEncoding(parser);
if (result != XML_ERROR_NONE)
@@ -1362,16 +1803,25 @@ enum XML_Error externalEntityInitProcessor(XML_Parser parser,
return externalEntityInitProcessor2(parser, start, end, endPtr);
}
-static
-enum XML_Error externalEntityInitProcessor2(XML_Parser parser,
- const char *start,
- const char *end,
- const char **endPtr)
+static enum XML_Error PTRCALL
+externalEntityInitProcessor2(XML_Parser parser,
+ const char *start,
+ const char *end,
+ const char **endPtr)
{
- const char *next;
+ const char *next = start; /* XmlContentTok doesn't always set the last arg */
int tok = XmlContentTok(encoding, start, end, &next);
switch (tok) {
case XML_TOK_BOM:
+ /* If we are at the end of the buffer, this would cause the next stage,
+ i.e. externalEntityInitProcessor3, to pass control directly to
+ doContent (by detecting XML_TOK_NONE) without processing any xml text
+ declaration - causing the error XML_ERROR_MISPLACED_XML_PI in doContent.
+ */
+ if (next == end && endPtr) {
+ *endPtr = next;
+ return XML_ERROR_NONE;
+ }
start = next;
break;
case XML_TOK_PARTIAL:
@@ -1393,20 +1843,20 @@ enum XML_Error externalEntityInitProcessor2(XML_Parser parser,
return externalEntityInitProcessor3(parser, start, end, endPtr);
}
-static
-enum XML_Error externalEntityInitProcessor3(XML_Parser parser,
- const char *start,
- const char *end,
- const char **endPtr)
+static enum XML_Error PTRCALL
+externalEntityInitProcessor3(XML_Parser parser,
+ const char *start,
+ const char *end,
+ const char **endPtr)
{
- const char *next;
+ const char *next = start; /* XmlContentTok doesn't always set the last arg */
int tok = XmlContentTok(encoding, start, end, &next);
switch (tok) {
case XML_TOK_XML_DECL:
{
enum XML_Error result = processXmlDecl(parser, 1, start, next);
if (result != XML_ERROR_NONE)
- return result;
+ return result;
start = next;
}
break;
@@ -1427,26 +1877,33 @@ enum XML_Error externalEntityInitProcessor3(XML_Parser parser,
}
processor = externalEntityContentProcessor;
tagLevel = 1;
- return doContent(parser, 1, encoding, start, end, endPtr);
+ return externalEntityContentProcessor(parser, start, end, endPtr);
}
-static
-enum XML_Error externalEntityContentProcessor(XML_Parser parser,
- const char *start,
- const char *end,
- const char **endPtr)
+static enum XML_Error PTRCALL
+externalEntityContentProcessor(XML_Parser parser,
+ const char *start,
+ const char *end,
+ const char **endPtr)
{
- return doContent(parser, 1, encoding, start, end, endPtr);
+ enum XML_Error result =
+ doContent(parser, 1, encoding, start, end, endPtr);
+ if (result != XML_ERROR_NONE)
+ return result;
+ if (!storeRawNames(parser))
+ return XML_ERROR_NO_MEMORY;
+ return result;
}
static enum XML_Error
doContent(XML_Parser parser,
- int startTagLevel,
- const ENCODING *enc,
- const char *s,
- const char *end,
- const char **nextPtr)
+ int startTagLevel,
+ const ENCODING *enc,
+ const char *s,
+ const char *end,
+ const char **nextPtr)
{
+ DTD * const dtd = _dtd; /* save one level of indirection */
const char **eventPP;
const char **eventEndPP;
if (enc == encoding) {
@@ -1465,30 +1922,30 @@ doContent(XML_Parser parser,
switch (tok) {
case XML_TOK_TRAILING_CR:
if (nextPtr) {
- *nextPtr = s;
- return XML_ERROR_NONE;
+ *nextPtr = s;
+ return XML_ERROR_NONE;
}
*eventEndPP = end;
if (characterDataHandler) {
- XML_Char c = 0xA;
- characterDataHandler(handlerArg, &c, 1);
+ XML_Char c = 0xA;
+ characterDataHandler(handlerArg, &c, 1);
}
else if (defaultHandler)
- reportDefault(parser, enc, s, end);
+ reportDefault(parser, enc, s, end);
if (startTagLevel == 0)
- return XML_ERROR_NO_ELEMENTS;
+ return XML_ERROR_NO_ELEMENTS;
if (tagLevel != startTagLevel)
- return XML_ERROR_ASYNC_ENTITY;
+ return XML_ERROR_ASYNC_ENTITY;
return XML_ERROR_NONE;
case XML_TOK_NONE:
if (nextPtr) {
- *nextPtr = s;
- return XML_ERROR_NONE;
+ *nextPtr = s;
+ return XML_ERROR_NONE;
}
if (startTagLevel > 0) {
- if (tagLevel != startTagLevel)
- return XML_ERROR_ASYNC_ENTITY;
- return XML_ERROR_NONE;
+ if (tagLevel != startTagLevel)
+ return XML_ERROR_ASYNC_ENTITY;
+ return XML_ERROR_NONE;
}
return XML_ERROR_NO_ELEMENTS;
case XML_TOK_INVALID:
@@ -1496,374 +1953,401 @@ doContent(XML_Parser parser,
return XML_ERROR_INVALID_TOKEN;
case XML_TOK_PARTIAL:
if (nextPtr) {
- *nextPtr = s;
- return XML_ERROR_NONE;
+ *nextPtr = s;
+ return XML_ERROR_NONE;
}
return XML_ERROR_UNCLOSED_TOKEN;
case XML_TOK_PARTIAL_CHAR:
if (nextPtr) {
- *nextPtr = s;
- return XML_ERROR_NONE;
+ *nextPtr = s;
+ return XML_ERROR_NONE;
}
return XML_ERROR_PARTIAL_CHAR;
case XML_TOK_ENTITY_REF:
{
- const XML_Char *name;
- ENTITY *entity;
- XML_Char ch = XmlPredefinedEntityName(enc,
- s + enc->minBytesPerChar,
- next - enc->minBytesPerChar);
- if (ch) {
- if (characterDataHandler)
- characterDataHandler(handlerArg, &ch, 1);
- else if (defaultHandler)
- reportDefault(parser, enc, s, next);
- break;
- }
- name = poolStoreString(&dtd.pool, enc,
- s + enc->minBytesPerChar,
- next - enc->minBytesPerChar);
- if (!name)
- return XML_ERROR_NO_MEMORY;
- entity = (ENTITY *)lookup(&dtd.generalEntities, name, 0);
- poolDiscard(&dtd.pool);
- if (!entity) {
- if (dtd.complete || dtd.standalone)
- return XML_ERROR_UNDEFINED_ENTITY;
- if (defaultHandler)
- reportDefault(parser, enc, s, next);
- break;
- }
- if (entity->open)
- return XML_ERROR_RECURSIVE_ENTITY_REF;
- if (entity->notation)
- return XML_ERROR_BINARY_ENTITY_REF;
- if (entity) {
- if (entity->textPtr) {
- enum XML_Error result;
- OPEN_INTERNAL_ENTITY openEntity;
- if (defaultHandler && !defaultExpandInternalEntities) {
- reportDefault(parser, enc, s, next);
- break;
- }
- entity->open = 1;
- openEntity.next = openInternalEntities;
- openInternalEntities = &openEntity;
- openEntity.entity = entity;
- openEntity.internalEventPtr = 0;
- openEntity.internalEventEndPtr = 0;
- result = doContent(parser,
- tagLevel,
- internalEncoding,
- (char *)entity->textPtr,
- (char *)(entity->textPtr + entity->textLen),
- 0);
- entity->open = 0;
- openInternalEntities = openEntity.next;
- if (result)
- return result;
- }
- else if (externalEntityRefHandler) {
- const XML_Char *context;
- entity->open = 1;
- context = getContext(parser);
- entity->open = 0;
- if (!context)
- return XML_ERROR_NO_MEMORY;
- if (!externalEntityRefHandler(externalEntityRefHandlerArg,
- context,
- entity->base,
- entity->systemId,
- entity->publicId))
- return XML_ERROR_EXTERNAL_ENTITY_HANDLING;
- poolDiscard(&tempPool);
- }
- else if (defaultHandler)
- reportDefault(parser, enc, s, next);
- }
- break;
- }
- case XML_TOK_START_TAG_WITH_ATTS:
- if (!startElementHandler) {
- enum XML_Error result = storeAtts(parser, enc, s, 0, 0);
- if (result)
- return result;
+ const XML_Char *name;
+ ENTITY *entity;
+ XML_Char ch = (XML_Char) XmlPredefinedEntityName(enc,
+ s + enc->minBytesPerChar,
+ next - enc->minBytesPerChar);
+ if (ch) {
+ if (characterDataHandler)
+ characterDataHandler(handlerArg, &ch, 1);
+ else if (defaultHandler)
+ reportDefault(parser, enc, s, next);
+ break;
+ }
+ name = poolStoreString(&dtd->pool, enc,
+ s + enc->minBytesPerChar,
+ next - enc->minBytesPerChar);
+ if (!name)
+ return XML_ERROR_NO_MEMORY;
+ entity = (ENTITY *)lookup(&dtd->generalEntities, name, 0);
+ poolDiscard(&dtd->pool);
+ /* First, determine if a check for an existing declaration is needed;
+ if yes, check that the entity exists, and that it is internal,
+ otherwise call the skipped entity or default handler.
+ */
+ if (!dtd->hasParamEntityRefs || dtd->standalone) {
+ if (!entity)
+ return XML_ERROR_UNDEFINED_ENTITY;
+ else if (!entity->is_internal)
+ return XML_ERROR_ENTITY_DECLARED_IN_PE;
+ }
+ else if (!entity) {
+ if (skippedEntityHandler)
+ skippedEntityHandler(handlerArg, name, 0);
+ else if (defaultHandler)
+ reportDefault(parser, enc, s, next);
+ break;
+ }
+ if (entity->open)
+ return XML_ERROR_RECURSIVE_ENTITY_REF;
+ if (entity->notation)
+ return XML_ERROR_BINARY_ENTITY_REF;
+ if (entity->textPtr) {
+ enum XML_Error result;
+ OPEN_INTERNAL_ENTITY openEntity;
+ if (!defaultExpandInternalEntities) {
+ if (skippedEntityHandler)
+ skippedEntityHandler(handlerArg, entity->name, 0);
+ else if (defaultHandler)
+ reportDefault(parser, enc, s, next);
+ break;
+ }
+ entity->open = XML_TRUE;
+ openEntity.next = openInternalEntities;
+ openInternalEntities = &openEntity;
+ openEntity.entity = entity;
+ openEntity.internalEventPtr = NULL;
+ openEntity.internalEventEndPtr = NULL;
+ result = doContent(parser,
+ tagLevel,
+ internalEncoding,
+ (char *)entity->textPtr,
+ (char *)(entity->textPtr + entity->textLen),
+ 0);
+ entity->open = XML_FALSE;
+ openInternalEntities = openEntity.next;
+ if (result)
+ return result;
+ }
+ else if (externalEntityRefHandler) {
+ const XML_Char *context;
+ entity->open = XML_TRUE;
+ context = getContext(parser);
+ entity->open = XML_FALSE;
+ if (!context)
+ return XML_ERROR_NO_MEMORY;
+ if (!externalEntityRefHandler((XML_Parser)externalEntityRefHandlerArg,
+ context,
+ entity->base,
+ entity->systemId,
+ entity->publicId))
+ return XML_ERROR_EXTERNAL_ENTITY_HANDLING;
+ poolDiscard(&tempPool);
+ }
+ else if (defaultHandler)
+ reportDefault(parser, enc, s, next);
+ break;
}
- /* fall through */
case XML_TOK_START_TAG_NO_ATTS:
+ /* fall through */
+ case XML_TOK_START_TAG_WITH_ATTS:
{
- TAG *tag;
- if (freeTagList) {
- tag = freeTagList;
- freeTagList = freeTagList->parent;
- }
- else {
- tag = MALLOC(sizeof(TAG));
- if (!tag)
- return XML_ERROR_NO_MEMORY;
- tag->buf = MALLOC(INIT_TAG_BUF_SIZE);
- if (!tag->buf)
- return XML_ERROR_NO_MEMORY;
- tag->bufEnd = tag->buf + INIT_TAG_BUF_SIZE;
- }
- tag->bindings = 0;
- tag->parent = tagStack;
- tagStack = tag;
- tag->name.localPart = 0;
- tag->rawName = s + enc->minBytesPerChar;
- tag->rawNameLength = XmlNameLength(enc, tag->rawName);
- if (nextPtr) {
- /* Need to guarantee that:
- tag->buf + ROUND_UP(tag->rawNameLength, sizeof(XML_Char)) <= tag->bufEnd - sizeof(XML_Char) */
- if (tag->rawNameLength + (int)(sizeof(XML_Char) - 1) + (int)sizeof(XML_Char) > tag->bufEnd - tag->buf) {
- int bufSize = tag->rawNameLength * 4;
- bufSize = ROUND_UP(bufSize, sizeof(XML_Char));
- tag->buf = REALLOC(tag->buf, bufSize);
- if (!tag->buf)
- return XML_ERROR_NO_MEMORY;
- tag->bufEnd = tag->buf + bufSize;
- }
- memcpy(tag->buf, tag->rawName, tag->rawNameLength);
- tag->rawName = tag->buf;
- }
- ++tagLevel;
- if (startElementHandler) {
- enum XML_Error result;
- XML_Char *toPtr;
- for (;;) {
- const char *rawNameEnd = tag->rawName + tag->rawNameLength;
- const char *fromPtr = tag->rawName;
- int bufSize;
- if (nextPtr)
- toPtr = (XML_Char *)(tag->buf + ROUND_UP(tag->rawNameLength, sizeof(XML_Char)));
- else
- toPtr = (XML_Char *)tag->buf;
- tag->name.str = toPtr;
- XmlConvert(enc,
- &fromPtr, rawNameEnd,
- (ICHAR **)&toPtr, (ICHAR *)tag->bufEnd - 1);
- if (fromPtr == rawNameEnd)
- break;
- bufSize = (tag->bufEnd - tag->buf) << 1;
- tag->buf = REALLOC(tag->buf, bufSize);
- if (!tag->buf)
- return XML_ERROR_NO_MEMORY;
- tag->bufEnd = tag->buf + bufSize;
- if (nextPtr)
- tag->rawName = tag->buf;
- }
- *toPtr = XML_T('\0');
- result = storeAtts(parser, enc, s, &(tag->name), &(tag->bindings));
- if (result)
- return result;
- startElementHandler(handlerArg, tag->name.str, (const XML_Char **)atts);
- poolClear(&tempPool);
- }
- else {
- tag->name.str = 0;
- if (defaultHandler)
- reportDefault(parser, enc, s, next);
- }
- break;
+ TAG *tag;
+ enum XML_Error result;
+ XML_Char *toPtr;
+ if (freeTagList) {
+ tag = freeTagList;
+ freeTagList = freeTagList->parent;
+ }
+ else {
+ tag = (TAG *)MALLOC(sizeof(TAG));
+ if (!tag)
+ return XML_ERROR_NO_MEMORY;
+ tag->buf = (char *)MALLOC(INIT_TAG_BUF_SIZE);
+ if (!tag->buf) {
+ FREE(tag);
+ return XML_ERROR_NO_MEMORY;
+ }
+ tag->bufEnd = tag->buf + INIT_TAG_BUF_SIZE;
+ }
+ tag->bindings = NULL;
+ tag->parent = tagStack;
+ tagStack = tag;
+ tag->name.localPart = NULL;
+ tag->name.prefix = NULL;
+ tag->rawName = s + enc->minBytesPerChar;
+ tag->rawNameLength = XmlNameLength(enc, tag->rawName);
+ ++tagLevel;
+ {
+ const char *rawNameEnd = tag->rawName + tag->rawNameLength;
+ const char *fromPtr = tag->rawName;
+ toPtr = (XML_Char *)tag->buf;
+ for (;;) {
+ int bufSize;
+ int convLen;
+ XmlConvert(enc,
+ &fromPtr, rawNameEnd,
+ (ICHAR **)&toPtr, (ICHAR *)tag->bufEnd - 1);
+ convLen = toPtr - (XML_Char *)tag->buf;
+ if (fromPtr == rawNameEnd) {
+ tag->name.strLen = convLen;
+ break;
+ }
+ bufSize = (tag->bufEnd - tag->buf) << 1;
+ {
+ char *temp = (char *)REALLOC(tag->buf, bufSize);
+ if (temp == NULL)
+ return XML_ERROR_NO_MEMORY;
+ tag->buf = temp;
+ tag->bufEnd = temp + bufSize;
+ toPtr = (XML_Char *)temp + convLen;
+ }
+ }
+ }
+ tag->name.str = (XML_Char *)tag->buf;
+ *toPtr = XML_T('\0');
+ if (!startElementHandler && (tok == XML_TOK_START_TAG_NO_ATTS)) {
+ if (defaultHandler)
+ reportDefault(parser, enc, s, next);
+ break;
+ }
+ result = storeAtts(parser, enc, s, &(tag->name), &(tag->bindings));
+ if (result)
+ return result;
+ if (startElementHandler)
+ startElementHandler(handlerArg, tag->name.str,
+ (const XML_Char **)atts);
+ else if (defaultHandler)
+ reportDefault(parser, enc, s, next);
+ poolClear(&tempPool);
+ break;
}
- case XML_TOK_EMPTY_ELEMENT_WITH_ATTS:
- if (!startElementHandler) {
- enum XML_Error result = storeAtts(parser, enc, s, 0, 0);
- if (result)
- return result;
+ case XML_TOK_EMPTY_ELEMENT_NO_ATTS:
+ if (!startElementHandler && !endElementHandler) {
+ if (defaultHandler)
+ reportDefault(parser, enc, s, next);
+ if (tagLevel == 0)
+ return epilogProcessor(parser, next, end, nextPtr);
+ break;
}
/* fall through */
- case XML_TOK_EMPTY_ELEMENT_NO_ATTS:
- if (startElementHandler || endElementHandler) {
- const char *rawName = s + enc->minBytesPerChar;
- enum XML_Error result;
- BINDING *bindings = 0;
- TAG_NAME name;
- name.str = poolStoreString(&tempPool, enc, rawName,
- rawName + XmlNameLength(enc, rawName));
- if (!name.str)
- return XML_ERROR_NO_MEMORY;
- poolFinish(&tempPool);
- result = storeAtts(parser, enc, s, &name, &bindings);
- if (result)
- return result;
- poolFinish(&tempPool);
- if (startElementHandler)
- startElementHandler(handlerArg, name.str, (const XML_Char **)atts);
- if (endElementHandler) {
- if (startElementHandler)
- *eventPP = *eventEndPP;
- endElementHandler(handlerArg, name.str);
- }
- poolClear(&tempPool);
- while (bindings) {
- BINDING *b = bindings;
- if (endNamespaceDeclHandler)
- endNamespaceDeclHandler(handlerArg, b->prefix->name);
- bindings = bindings->nextTagBinding;
- b->nextTagBinding = freeBindingList;
- freeBindingList = b;
- b->prefix->binding = b->prevPrefixBinding;
- }
+ case XML_TOK_EMPTY_ELEMENT_WITH_ATTS:
+ {
+ const char *rawName = s + enc->minBytesPerChar;
+ enum XML_Error result;
+ BINDING *bindings = NULL;
+ XML_Bool noElmHandlers = XML_TRUE;
+ TAG_NAME name;
+ name.str = poolStoreString(&tempPool, enc, rawName,
+ rawName + XmlNameLength(enc, rawName));
+ if (!name.str)
+ return XML_ERROR_NO_MEMORY;
+ poolFinish(&tempPool);
+ if (startElementHandler ||
+ (tok == XML_TOK_EMPTY_ELEMENT_WITH_ATTS)) {
+ result = storeAtts(parser, enc, s, &name, &bindings);
+ if (result)
+ return result;
+ poolFinish(&tempPool);
+ }
+ if (startElementHandler) {
+ startElementHandler(handlerArg, name.str, (const XML_Char **)atts);
+ noElmHandlers = XML_FALSE;
+ }
+ if (endElementHandler) {
+ if (startElementHandler)
+ *eventPP = *eventEndPP;
+ endElementHandler(handlerArg, name.str);
+ noElmHandlers = XML_FALSE;
+ }
+ if (noElmHandlers && defaultHandler)
+ reportDefault(parser, enc, s, next);
+ poolClear(&tempPool);
+ while (bindings) {
+ BINDING *b = bindings;
+ if (endNamespaceDeclHandler)
+ endNamespaceDeclHandler(handlerArg, b->prefix->name);
+ bindings = bindings->nextTagBinding;
+ b->nextTagBinding = freeBindingList;
+ freeBindingList = b;
+ b->prefix->binding = b->prevPrefixBinding;
+ }
}
- else if (defaultHandler)
- reportDefault(parser, enc, s, next);
if (tagLevel == 0)
- return epilogProcessor(parser, next, end, nextPtr);
+ return epilogProcessor(parser, next, end, nextPtr);
break;
case XML_TOK_END_TAG:
if (tagLevel == startTagLevel)
return XML_ERROR_ASYNC_ENTITY;
else {
- int len;
- const char *rawName;
- TAG *tag = tagStack;
- tagStack = tag->parent;
- tag->parent = freeTagList;
- freeTagList = tag;
- rawName = s + enc->minBytesPerChar*2;
- len = XmlNameLength(enc, rawName);
- if (len != tag->rawNameLength
- || memcmp(tag->rawName, rawName, len) != 0) {
- *eventPP = rawName;
- return XML_ERROR_TAG_MISMATCH;
- }
- --tagLevel;
- if (endElementHandler && tag->name.str) {
- if (tag->name.localPart) {
- XML_Char *to = (XML_Char *)tag->name.str + tag->name.uriLen;
- const XML_Char *from = tag->name.localPart;
- while ((*to++ = *from++) != 0)
- ;
- }
- endElementHandler(handlerArg, tag->name.str);
- }
- else if (defaultHandler)
- reportDefault(parser, enc, s, next);
- while (tag->bindings) {
- BINDING *b = tag->bindings;
- if (endNamespaceDeclHandler)
- endNamespaceDeclHandler(handlerArg, b->prefix->name);
- tag->bindings = tag->bindings->nextTagBinding;
- b->nextTagBinding = freeBindingList;
- freeBindingList = b;
- b->prefix->binding = b->prevPrefixBinding;
- }
- if (tagLevel == 0)
- return epilogProcessor(parser, next, end, nextPtr);
+ int len;
+ const char *rawName;
+ TAG *tag = tagStack;
+ tagStack = tag->parent;
+ tag->parent = freeTagList;
+ freeTagList = tag;
+ rawName = s + enc->minBytesPerChar*2;
+ len = XmlNameLength(enc, rawName);
+ if (len != tag->rawNameLength
+ || memcmp(tag->rawName, rawName, len) != 0) {
+ *eventPP = rawName;
+ return XML_ERROR_TAG_MISMATCH;
+ }
+ --tagLevel;
+ if (endElementHandler) {
+ const XML_Char *localPart;
+ const XML_Char *prefix;
+ XML_Char *uri;
+ localPart = tag->name.localPart;
+ if (ns && localPart) {
+ /* localPart and prefix may have been overwritten in
+ tag->name.str, since this points to the binding->uri
+ buffer which gets re-used; so we have to add them again
+ */
+ uri = (XML_Char *)tag->name.str + tag->name.uriLen;
+ /* don't need to check for space - already done in storeAtts() */
+ while (*localPart) *uri++ = *localPart++;
+ prefix = (XML_Char *)tag->name.prefix;
+ if (ns_triplets && prefix) {
+ *uri++ = namespaceSeparator;
+ while (*prefix) *uri++ = *prefix++;
+ }
+ *uri = XML_T('\0');
+ }
+ endElementHandler(handlerArg, tag->name.str);
+ }
+ else if (defaultHandler)
+ reportDefault(parser, enc, s, next);
+ while (tag->bindings) {
+ BINDING *b = tag->bindings;
+ if (endNamespaceDeclHandler)
+ endNamespaceDeclHandler(handlerArg, b->prefix->name);
+ tag->bindings = tag->bindings->nextTagBinding;
+ b->nextTagBinding = freeBindingList;
+ freeBindingList = b;
+ b->prefix->binding = b->prevPrefixBinding;
+ }
+ if (tagLevel == 0)
+ return epilogProcessor(parser, next, end, nextPtr);
}
break;
case XML_TOK_CHAR_REF:
{
- int n = XmlCharRefNumber(enc, s);
- if (n < 0)
- return XML_ERROR_BAD_CHAR_REF;
- if (characterDataHandler) {
- XML_Char buf[XML_ENCODE_MAX];
- characterDataHandler(handlerArg, buf, XmlEncode(n, (ICHAR *)buf));
- }
- else if (defaultHandler)
- reportDefault(parser, enc, s, next);
+ int n = XmlCharRefNumber(enc, s);
+ if (n < 0)
+ return XML_ERROR_BAD_CHAR_REF;
+ if (characterDataHandler) {
+ XML_Char buf[XML_ENCODE_MAX];
+ characterDataHandler(handlerArg, buf, XmlEncode(n, (ICHAR *)buf));
+ }
+ else if (defaultHandler)
+ reportDefault(parser, enc, s, next);
}
break;
case XML_TOK_XML_DECL:
return XML_ERROR_MISPLACED_XML_PI;
case XML_TOK_DATA_NEWLINE:
if (characterDataHandler) {
- XML_Char c = 0xA;
- characterDataHandler(handlerArg, &c, 1);
+ XML_Char c = 0xA;
+ characterDataHandler(handlerArg, &c, 1);
}
else if (defaultHandler)
- reportDefault(parser, enc, s, next);
+ reportDefault(parser, enc, s, next);
break;
case XML_TOK_CDATA_SECT_OPEN:
{
- enum XML_Error result;
- if (startCdataSectionHandler)
- startCdataSectionHandler(handlerArg);
+ enum XML_Error result;
+ if (startCdataSectionHandler)
+ startCdataSectionHandler(handlerArg);
#if 0
- /* Suppose you doing a transformation on a document that involves
- changing only the character data. You set up a defaultHandler
- and a characterDataHandler. The defaultHandler simply copies
- characters through. The characterDataHandler does the transformation
- and writes the characters out escaping them as necessary. This case
- will fail to work if we leave out the following two lines (because &
- and < inside CDATA sections will be incorrectly escaped).
-
- However, now we have a start/endCdataSectionHandler, so it seems
- easier to let the user deal with this. */
-
- else if (characterDataHandler)
- characterDataHandler(handlerArg, dataBuf, 0);
+ /* Suppose you doing a transformation on a document that involves
+ changing only the character data. You set up a defaultHandler
+ and a characterDataHandler. The defaultHandler simply copies
+ characters through. The characterDataHandler does the
+ transformation and writes the characters out escaping them as
+ necessary. This case will fail to work if we leave out the
+ following two lines (because & and < inside CDATA sections will
+ be incorrectly escaped).
+
+ However, now we have a start/endCdataSectionHandler, so it seems
+ easier to let the user deal with this.
+ */
+ else if (characterDataHandler)
+ characterDataHandler(handlerArg, dataBuf, 0);
#endif
- else if (defaultHandler)
- reportDefault(parser, enc, s, next);
- result = doCdataSection(parser, enc, &next, end, nextPtr);
- if (!next) {
- processor = cdataSectionProcessor;
- return result;
- }
+ else if (defaultHandler)
+ reportDefault(parser, enc, s, next);
+ result = doCdataSection(parser, enc, &next, end, nextPtr);
+ if (!next) {
+ processor = cdataSectionProcessor;
+ return result;
+ }
}
break;
case XML_TOK_TRAILING_RSQB:
if (nextPtr) {
- *nextPtr = s;
- return XML_ERROR_NONE;
+ *nextPtr = s;
+ return XML_ERROR_NONE;
}
if (characterDataHandler) {
- if (MUST_CONVERT(enc, s)) {
- ICHAR *dataPtr = (ICHAR *)dataBuf;
- XmlConvert(enc, &s, end, &dataPtr, (ICHAR *)dataBufEnd);
- characterDataHandler(handlerArg, dataBuf, dataPtr - (ICHAR *)dataBuf);
- }
- else
- characterDataHandler(handlerArg,
- (XML_Char *)s,
- (XML_Char *)end - (XML_Char *)s);
+ if (MUST_CONVERT(enc, s)) {
+ ICHAR *dataPtr = (ICHAR *)dataBuf;
+ XmlConvert(enc, &s, end, &dataPtr, (ICHAR *)dataBufEnd);
+ characterDataHandler(handlerArg, dataBuf,
+ dataPtr - (ICHAR *)dataBuf);
+ }
+ else
+ characterDataHandler(handlerArg,
+ (XML_Char *)s,
+ (XML_Char *)end - (XML_Char *)s);
}
else if (defaultHandler)
- reportDefault(parser, enc, s, end);
+ reportDefault(parser, enc, s, end);
if (startTagLevel == 0) {
*eventPP = end;
- return XML_ERROR_NO_ELEMENTS;
+ return XML_ERROR_NO_ELEMENTS;
}
if (tagLevel != startTagLevel) {
- *eventPP = end;
- return XML_ERROR_ASYNC_ENTITY;
+ *eventPP = end;
+ return XML_ERROR_ASYNC_ENTITY;
}
return XML_ERROR_NONE;
case XML_TOK_DATA_CHARS:
if (characterDataHandler) {
- if (MUST_CONVERT(enc, s)) {
- for (;;) {
- ICHAR *dataPtr = (ICHAR *)dataBuf;
- XmlConvert(enc, &s, next, &dataPtr, (ICHAR *)dataBufEnd);
- *eventEndPP = s;
- characterDataHandler(handlerArg, dataBuf, dataPtr - (ICHAR *)dataBuf);
- if (s == next)
- break;
- *eventPP = s;
- }
- }
- else
- characterDataHandler(handlerArg,
- (XML_Char *)s,
- (XML_Char *)next - (XML_Char *)s);
+ if (MUST_CONVERT(enc, s)) {
+ for (;;) {
+ ICHAR *dataPtr = (ICHAR *)dataBuf;
+ XmlConvert(enc, &s, next, &dataPtr, (ICHAR *)dataBufEnd);
+ *eventEndPP = s;
+ characterDataHandler(handlerArg, dataBuf,
+ dataPtr - (ICHAR *)dataBuf);
+ if (s == next)
+ break;
+ *eventPP = s;
+ }
+ }
+ else
+ characterDataHandler(handlerArg,
+ (XML_Char *)s,
+ (XML_Char *)next - (XML_Char *)s);
}
else if (defaultHandler)
- reportDefault(parser, enc, s, next);
+ reportDefault(parser, enc, s, next);
break;
case XML_TOK_PI:
if (!reportProcessingInstruction(parser, enc, s, next))
- return XML_ERROR_NO_MEMORY;
+ return XML_ERROR_NO_MEMORY;
break;
case XML_TOK_COMMENT:
if (!reportComment(parser, enc, s, next))
- return XML_ERROR_NO_MEMORY;
+ return XML_ERROR_NO_MEMORY;
break;
default:
if (defaultHandler)
- reportDefault(parser, enc, s, next);
+ reportDefault(parser, enc, s, next);
break;
}
*eventPP = s = next;
@@ -1872,30 +2356,35 @@ doContent(XML_Parser parser,
}
/* If tagNamePtr is non-null, build a real list of attributes,
-otherwise just check the attributes for well-formedness. */
-
-static enum XML_Error storeAtts(XML_Parser parser, const ENCODING *enc,
- const char *attStr, TAG_NAME *tagNamePtr,
- BINDING **bindingsPtr)
+ otherwise just check the attributes for well-formedness.
+*/
+static enum XML_Error
+storeAtts(XML_Parser parser, const ENCODING *enc,
+ const char *attStr, TAG_NAME *tagNamePtr,
+ BINDING **bindingsPtr)
{
- ELEMENT_TYPE *elementType = 0;
+ DTD * const dtd = _dtd; /* save one level of indirection */
+ ELEMENT_TYPE *elementType = NULL;
int nDefaultAtts = 0;
- const XML_Char **appAtts; /* the attribute list to pass to the application */
+ const XML_Char **appAtts; /* the attribute list for the application */
int attIndex = 0;
+ int prefixLen;
int i;
int n;
+ XML_Char *uri;
int nPrefixes = 0;
BINDING *binding;
const XML_Char *localPart;
/* lookup the element type name */
if (tagNamePtr) {
- elementType = (ELEMENT_TYPE *)lookup(&dtd.elementTypes, tagNamePtr->str,0);
+ elementType = (ELEMENT_TYPE *)lookup(&dtd->elementTypes, tagNamePtr->str,0);
if (!elementType) {
- tagNamePtr->str = poolCopyString(&dtd.pool, tagNamePtr->str);
- if (!tagNamePtr->str)
- return XML_ERROR_NO_MEMORY;
- elementType = (ELEMENT_TYPE *)lookup(&dtd.elementTypes, tagNamePtr->str, sizeof(ELEMENT_TYPE));
+ const XML_Char *name = poolCopyString(&dtd->pool, tagNamePtr->str);
+ if (!name)
+ return XML_ERROR_NO_MEMORY;
+ elementType = (ELEMENT_TYPE *)lookup(&dtd->elementTypes, name,
+ sizeof(ELEMENT_TYPE));
if (!elementType)
return XML_ERROR_NO_MEMORY;
if (ns && !setElementTypePrefix(parser, elementType))
@@ -1907,10 +2396,12 @@ static enum XML_Error storeAtts(XML_Parser parser, const ENCODING *enc,
n = XmlGetAttributes(enc, attStr, attsSize, atts);
if (n + nDefaultAtts > attsSize) {
int oldAttsSize = attsSize;
+ ATTRIBUTE *temp;
attsSize = n + nDefaultAtts + INIT_ATTS_SIZE;
- atts = REALLOC((void *)atts, attsSize * sizeof(ATTRIBUTE));
- if (!atts)
+ temp = (ATTRIBUTE *)REALLOC((void *)atts, attsSize * sizeof(ATTRIBUTE));
+ if (temp == NULL)
return XML_ERROR_NO_MEMORY;
+ atts = temp;
if (n > oldAttsSize)
XmlGetAttributes(enc, attStr, n, atts);
}
@@ -1918,63 +2409,66 @@ static enum XML_Error storeAtts(XML_Parser parser, const ENCODING *enc,
for (i = 0; i < n; i++) {
/* add the name and value to the attribute list */
ATTRIBUTE_ID *attId = getAttributeId(parser, enc, atts[i].name,
- atts[i].name
- + XmlNameLength(enc, atts[i].name));
+ atts[i].name
+ + XmlNameLength(enc, atts[i].name));
if (!attId)
return XML_ERROR_NO_MEMORY;
/* detect duplicate attributes */
if ((attId->name)[-1]) {
if (enc == encoding)
- eventPtr = atts[i].name;
+ eventPtr = atts[i].name;
return XML_ERROR_DUPLICATE_ATTRIBUTE;
}
(attId->name)[-1] = 1;
appAtts[attIndex++] = attId->name;
if (!atts[i].normalized) {
enum XML_Error result;
- int isCdata = 1;
+ XML_Bool isCdata = XML_TRUE;
/* figure out whether declared as other than CDATA */
if (attId->maybeTokenized) {
- int j;
- for (j = 0; j < nDefaultAtts; j++) {
- if (attId == elementType->defaultAtts[j].id) {
- isCdata = elementType->defaultAtts[j].isCdata;
- break;
- }
- }
+ int j;
+ for (j = 0; j < nDefaultAtts; j++) {
+ if (attId == elementType->defaultAtts[j].id) {
+ isCdata = elementType->defaultAtts[j].isCdata;
+ break;
+ }
+ }
}
/* normalize the attribute value */
result = storeAttributeValue(parser, enc, isCdata,
- atts[i].valuePtr, atts[i].valueEnd,
- &tempPool);
+ atts[i].valuePtr, atts[i].valueEnd,
+ &tempPool);
if (result)
- return result;
+ return result;
if (tagNamePtr) {
- appAtts[attIndex] = poolStart(&tempPool);
- poolFinish(&tempPool);
+ appAtts[attIndex] = poolStart(&tempPool);
+ poolFinish(&tempPool);
}
else
- poolDiscard(&tempPool);
+ poolDiscard(&tempPool);
}
else if (tagNamePtr) {
/* the value did not need normalizing */
- appAtts[attIndex] = poolStoreString(&tempPool, enc, atts[i].valuePtr, atts[i].valueEnd);
+ appAtts[attIndex] = poolStoreString(&tempPool, enc, atts[i].valuePtr,
+ atts[i].valueEnd);
if (appAtts[attIndex] == 0)
- return XML_ERROR_NO_MEMORY;
+ return XML_ERROR_NO_MEMORY;
poolFinish(&tempPool);
}
/* handle prefixed attribute names */
if (attId->prefix && tagNamePtr) {
if (attId->xmlns) {
- /* deal with namespace declarations here */
- if (!addBinding(parser, attId->prefix, attId, appAtts[attIndex], bindingsPtr))
- return XML_ERROR_NO_MEMORY;
+ /* deal with namespace declarations here */
+ enum XML_Error result = addBinding(parser, attId->prefix, attId,
+ appAtts[attIndex], bindingsPtr);
+ if (result)
+ return result;
--attIndex;
}
else {
- /* deal with other prefixed names later */
+ /* deal with other prefixed names later */
attIndex++;
nPrefixes++;
(attId->name)[-1] = 2;
@@ -1988,10 +2482,10 @@ static enum XML_Error storeAtts(XML_Parser parser, const ENCODING *enc,
nSpecifiedAtts = attIndex;
if (elementType->idAtt && (elementType->idAtt->name)[-1]) {
for (i = 0; i < attIndex; i += 2)
- if (appAtts[i] == elementType->idAtt->name) {
- idAttIndex = i;
- break;
- }
+ if (appAtts[i] == elementType->idAtt->name) {
+ idAttIndex = i;
+ break;
+ }
}
else
idAttIndex = -1;
@@ -2001,21 +2495,23 @@ static enum XML_Error storeAtts(XML_Parser parser, const ENCODING *enc,
if (!(da->id->name)[-1] && da->value) {
if (da->id->prefix) {
if (da->id->xmlns) {
- if (!addBinding(parser, da->id->prefix, da->id, da->value, bindingsPtr))
- return XML_ERROR_NO_MEMORY;
- }
+ enum XML_Error result = addBinding(parser, da->id->prefix, da->id,
+ da->value, bindingsPtr);
+ if (result)
+ return result;
+ }
else {
- (da->id->name)[-1] = 2;
- nPrefixes++;
- appAtts[attIndex++] = da->id->name;
- appAtts[attIndex++] = da->value;
- }
- }
- else {
- (da->id->name)[-1] = 1;
- appAtts[attIndex++] = da->id->name;
- appAtts[attIndex++] = da->value;
- }
+ (da->id->name)[-1] = 2;
+ nPrefixes++;
+ appAtts[attIndex++] = da->id->name;
+ appAtts[attIndex++] = da->value;
+ }
+ }
+ else {
+ (da->id->name)[-1] = 1;
+ appAtts[attIndex++] = da->id->name;
+ appAtts[attIndex++] = da->value;
+ }
}
}
appAtts[attIndex] = 0;
@@ -2027,38 +2523,38 @@ static enum XML_Error storeAtts(XML_Parser parser, const ENCODING *enc,
if (appAtts[i][-1] == 2) {
ATTRIBUTE_ID *id;
((XML_Char *)(appAtts[i]))[-1] = 0;
- id = (ATTRIBUTE_ID *)lookup(&dtd.attributeIds, appAtts[i], 0);
- if (id->prefix->binding) {
- int j;
- const BINDING *b = id->prefix->binding;
- const XML_Char *s = appAtts[i];
- for (j = 0; j < b->uriLen; j++) {
- if (!poolAppendChar(&tempPool, b->uri[j]))
- return XML_ERROR_NO_MEMORY;
- }
- while (*s++ != ':')
- ;
- do {
- if (!poolAppendChar(&tempPool, *s))
- return XML_ERROR_NO_MEMORY;
- } while (*s++);
- if (ns_triplets) {
- tempPool.ptr[-1] = namespaceSeparator;
- s = b->prefix->name;
- do {
- if (!poolAppendChar(&tempPool, *s))
- return XML_ERROR_NO_MEMORY;
- } while (*s++);
- }
-
- appAtts[i] = poolStart(&tempPool);
- poolFinish(&tempPool);
- }
- if (!--nPrefixes)
- break;
+ id = (ATTRIBUTE_ID *)lookup(&dtd->attributeIds, appAtts[i], 0);
+ if (id->prefix->binding) {
+ int j;
+ const BINDING *b = id->prefix->binding;
+ const XML_Char *s = appAtts[i];
+ for (j = 0; j < b->uriLen; j++) {
+ if (!poolAppendChar(&tempPool, b->uri[j]))
+ return XML_ERROR_NO_MEMORY;
+ }
+ while (*s++ != XML_T(':'))
+ ;
+ do {
+ if (!poolAppendChar(&tempPool, *s))
+ return XML_ERROR_NO_MEMORY;
+ } while (*s++);
+ if (ns_triplets) {
+ tempPool.ptr[-1] = namespaceSeparator;
+ s = b->prefix->name;
+ do {
+ if (!poolAppendChar(&tempPool, *s))
+ return XML_ERROR_NO_MEMORY;
+ } while (*s++);
+ }
+
+ appAtts[i] = poolStart(&tempPool);
+ poolFinish(&tempPool);
+ }
+ if (!--nPrefixes)
+ break;
}
else
- ((XML_Char *)(appAtts[i]))[-1] = 0;
+ ((XML_Char *)(appAtts[i]))[-1] = 0;
}
}
/* clear the flags that say whether attributes were specified */
@@ -2077,40 +2573,62 @@ static enum XML_Error storeAtts(XML_Parser parser, const ENCODING *enc,
while (*localPart++ != XML_T(':'))
;
}
- else if (dtd.defaultPrefix.binding) {
- binding = dtd.defaultPrefix.binding;
+ else if (dtd->defaultPrefix.binding) {
+ binding = dtd->defaultPrefix.binding;
localPart = tagNamePtr->str;
}
else
return XML_ERROR_NONE;
+ prefixLen = 0;
+ if (ns && ns_triplets && binding->prefix->name) {
+ for (; binding->prefix->name[prefixLen++];)
+ ;
+ }
tagNamePtr->localPart = localPart;
tagNamePtr->uriLen = binding->uriLen;
+ tagNamePtr->prefix = binding->prefix->name;
+ tagNamePtr->prefixLen = prefixLen;
for (i = 0; localPart[i++];)
;
- n = i + binding->uriLen;
+ n = i + binding->uriLen + prefixLen;
if (n > binding->uriAlloc) {
TAG *p;
- XML_Char *uri = MALLOC((n + EXPAND_SPARE) * sizeof(XML_Char));
+ uri = (XML_Char *)MALLOC((n + EXPAND_SPARE) * sizeof(XML_Char));
if (!uri)
return XML_ERROR_NO_MEMORY;
binding->uriAlloc = n + EXPAND_SPARE;
memcpy(uri, binding->uri, binding->uriLen * sizeof(XML_Char));
for (p = tagStack; p; p = p->parent)
if (p->name.str == binding->uri)
- p->name.str = uri;
+ p->name.str = uri;
FREE(binding->uri);
binding->uri = uri;
}
- memcpy(binding->uri + binding->uriLen, localPart, i * sizeof(XML_Char));
+ uri = binding->uri + binding->uriLen;
+ memcpy(uri, localPart, i * sizeof(XML_Char));
+ if (prefixLen) {
+ uri = uri + (i - 1);
+ if (namespaceSeparator) { *(uri) = namespaceSeparator; }
+ memcpy(uri + 1, binding->prefix->name, prefixLen * sizeof(XML_Char));
+ }
tagNamePtr->str = binding->uri;
return XML_ERROR_NONE;
}
-static
-int addBinding(XML_Parser parser, PREFIX *prefix, const ATTRIBUTE_ID *attId, const XML_Char *uri, BINDING **bindingsPtr)
+/* addBinding() overwrites the value of prefix->binding without checking.
+ Therefore one must keep track of the old value outside of addBinding().
+*/
+static enum XML_Error
+addBinding(XML_Parser parser, PREFIX *prefix, const ATTRIBUTE_ID *attId,
+ const XML_Char *uri, BINDING **bindingsPtr)
{
BINDING *b;
int len;
+
+ /* empty string is only valid when there is no prefix per XML NS 1.0 */
+ if (*uri == XML_T('\0') && prefix->name)
+ return XML_ERROR_SYNTAX;
+
for (len = 0; uri[len]; len++)
;
if (namespaceSeparator)
@@ -2118,21 +2636,23 @@ int addBinding(XML_Parser parser, PREFIX *prefix, const ATTRIBUTE_ID *attId, con
if (freeBindingList) {
b = freeBindingList;
if (len > b->uriAlloc) {
- b->uri = REALLOC(b->uri, sizeof(XML_Char) * (len + EXPAND_SPARE));
- if (!b->uri)
- return 0;
+ XML_Char *temp = (XML_Char *)REALLOC(b->uri,
+ sizeof(XML_Char) * (len + EXPAND_SPARE));
+ if (temp == NULL)
+ return XML_ERROR_NO_MEMORY;
+ b->uri = temp;
b->uriAlloc = len + EXPAND_SPARE;
}
freeBindingList = b->nextTagBinding;
}
else {
- b = MALLOC(sizeof(BINDING));
+ b = (BINDING *)MALLOC(sizeof(BINDING));
if (!b)
- return 0;
- b->uri = MALLOC(sizeof(XML_Char) * (len + EXPAND_SPARE));
+ return XML_ERROR_NO_MEMORY;
+ b->uri = (XML_Char *)MALLOC(sizeof(XML_Char) * (len + EXPAND_SPARE));
if (!b->uri) {
FREE(b);
- return 0;
+ return XML_ERROR_NO_MEMORY;
}
b->uriAlloc = len + EXPAND_SPARE;
}
@@ -2143,44 +2663,51 @@ int addBinding(XML_Parser parser, PREFIX *prefix, const ATTRIBUTE_ID *attId, con
b->prefix = prefix;
b->attId = attId;
b->prevPrefixBinding = prefix->binding;
- if (*uri == XML_T('\0') && prefix == &dtd.defaultPrefix)
- prefix->binding = 0;
+ if (*uri == XML_T('\0') && prefix == &_dtd->defaultPrefix)
+ prefix->binding = NULL;
else
prefix->binding = b;
b->nextTagBinding = *bindingsPtr;
*bindingsPtr = b;
if (startNamespaceDeclHandler)
startNamespaceDeclHandler(handlerArg, prefix->name,
- prefix->binding ? uri : 0);
- return 1;
+ prefix->binding ? uri : 0);
+ return XML_ERROR_NONE;
}
/* The idea here is to avoid using stack for each CDATA section when
-the whole file is parsed with one call. */
-
-static
-enum XML_Error cdataSectionProcessor(XML_Parser parser,
- const char *start,
- const char *end,
- const char **endPtr)
+ the whole file is parsed with one call.
+*/
+static enum XML_Error PTRCALL
+cdataSectionProcessor(XML_Parser parser,
+ const char *start,
+ const char *end,
+ const char **endPtr)
{
- enum XML_Error result = doCdataSection(parser, encoding, &start, end, endPtr);
+ enum XML_Error result = doCdataSection(parser, encoding, &start,
+ end, endPtr);
if (start) {
- processor = contentProcessor;
- return contentProcessor(parser, start, end, endPtr);
+ if (parentParser) { /* we are parsing an external entity */
+ processor = externalEntityContentProcessor;
+ return externalEntityContentProcessor(parser, start, end, endPtr);
+ }
+ else {
+ processor = contentProcessor;
+ return contentProcessor(parser, start, end, endPtr);
+ }
}
return result;
}
/* startPtr gets set to non-null is the section is closed, and to null if
-the section is not yet closed. */
-
-static
-enum XML_Error doCdataSection(XML_Parser parser,
- const ENCODING *enc,
- const char **startPtr,
- const char *end,
- const char **nextPtr)
+ the section is not yet closed.
+*/
+static enum XML_Error
+doCdataSection(XML_Parser parser,
+ const ENCODING *enc,
+ const char **startPtr,
+ const char *end,
+ const char **nextPtr)
{
const char *s = *startPtr;
const char **eventPP;
@@ -2195,7 +2722,7 @@ enum XML_Error doCdataSection(XML_Parser parser,
eventEndPP = &(openInternalEntities->internalEventEndPtr);
}
*eventPP = s;
- *startPtr = 0;
+ *startPtr = NULL;
for (;;) {
const char *next;
int tok = XmlCdataSectionTok(enc, s, end, &next);
@@ -2203,59 +2730,60 @@ enum XML_Error doCdataSection(XML_Parser parser,
switch (tok) {
case XML_TOK_CDATA_SECT_CLOSE:
if (endCdataSectionHandler)
- endCdataSectionHandler(handlerArg);
+ endCdataSectionHandler(handlerArg);
#if 0
/* see comment under XML_TOK_CDATA_SECT_OPEN */
else if (characterDataHandler)
- characterDataHandler(handlerArg, dataBuf, 0);
+ characterDataHandler(handlerArg, dataBuf, 0);
#endif
else if (defaultHandler)
- reportDefault(parser, enc, s, next);
+ reportDefault(parser, enc, s, next);
*startPtr = next;
return XML_ERROR_NONE;
case XML_TOK_DATA_NEWLINE:
if (characterDataHandler) {
- XML_Char c = 0xA;
- characterDataHandler(handlerArg, &c, 1);
+ XML_Char c = 0xA;
+ characterDataHandler(handlerArg, &c, 1);
}
else if (defaultHandler)
- reportDefault(parser, enc, s, next);
+ reportDefault(parser, enc, s, next);
break;
case XML_TOK_DATA_CHARS:
if (characterDataHandler) {
- if (MUST_CONVERT(enc, s)) {
- for (;;) {
- ICHAR *dataPtr = (ICHAR *)dataBuf;
- XmlConvert(enc, &s, next, &dataPtr, (ICHAR *)dataBufEnd);
- *eventEndPP = next;
- characterDataHandler(handlerArg, dataBuf, dataPtr - (ICHAR *)dataBuf);
- if (s == next)
- break;
- *eventPP = s;
- }
- }
- else
- characterDataHandler(handlerArg,
- (XML_Char *)s,
- (XML_Char *)next - (XML_Char *)s);
+ if (MUST_CONVERT(enc, s)) {
+ for (;;) {
+ ICHAR *dataPtr = (ICHAR *)dataBuf;
+ XmlConvert(enc, &s, next, &dataPtr, (ICHAR *)dataBufEnd);
+ *eventEndPP = next;
+ characterDataHandler(handlerArg, dataBuf,
+ dataPtr - (ICHAR *)dataBuf);
+ if (s == next)
+ break;
+ *eventPP = s;
+ }
+ }
+ else
+ characterDataHandler(handlerArg,
+ (XML_Char *)s,
+ (XML_Char *)next - (XML_Char *)s);
}
else if (defaultHandler)
- reportDefault(parser, enc, s, next);
+ reportDefault(parser, enc, s, next);
break;
case XML_TOK_INVALID:
*eventPP = next;
return XML_ERROR_INVALID_TOKEN;
case XML_TOK_PARTIAL_CHAR:
if (nextPtr) {
- *nextPtr = s;
- return XML_ERROR_NONE;
+ *nextPtr = s;
+ return XML_ERROR_NONE;
}
return XML_ERROR_PARTIAL_CHAR;
case XML_TOK_PARTIAL:
case XML_TOK_NONE:
if (nextPtr) {
- *nextPtr = s;
- return XML_ERROR_NONE;
+ *nextPtr = s;
+ return XML_ERROR_NONE;
}
return XML_ERROR_UNCLOSED_CDATA_SECTION;
default:
@@ -2270,15 +2798,16 @@ enum XML_Error doCdataSection(XML_Parser parser,
#ifdef XML_DTD
/* The idea here is to avoid using stack for each IGNORE section when
-the whole file is parsed with one call. */
-
-static
-enum XML_Error ignoreSectionProcessor(XML_Parser parser,
- const char *start,
- const char *end,
- const char **endPtr)
+ the whole file is parsed with one call.
+*/
+static enum XML_Error PTRCALL
+ignoreSectionProcessor(XML_Parser parser,
+ const char *start,
+ const char *end,
+ const char **endPtr)
{
- enum XML_Error result = doIgnoreSection(parser, encoding, &start, end, endPtr);
+ enum XML_Error result = doIgnoreSection(parser, encoding, &start,
+ end, endPtr);
if (start) {
processor = prologProcessor;
return prologProcessor(parser, start, end, endPtr);
@@ -2286,15 +2815,15 @@ enum XML_Error ignoreSectionProcessor(XML_Parser parser,
return result;
}
-/* startPtr gets set to non-null is the section is closed, and to null if
-the section is not yet closed. */
-
-static
-enum XML_Error doIgnoreSection(XML_Parser parser,
- const ENCODING *enc,
- const char **startPtr,
- const char *end,
- const char **nextPtr)
+/* startPtr gets set to non-null is the section is closed, and to null
+ if the section is not yet closed.
+*/
+static enum XML_Error
+doIgnoreSection(XML_Parser parser,
+ const ENCODING *enc,
+ const char **startPtr,
+ const char *end,
+ const char **nextPtr)
{
const char *next;
int tok;
@@ -2311,7 +2840,7 @@ enum XML_Error doIgnoreSection(XML_Parser parser,
eventEndPP = &(openInternalEntities->internalEventEndPtr);
}
*eventPP = s;
- *startPtr = 0;
+ *startPtr = NULL;
tok = XmlIgnoreSectionTok(enc, s, end, &next);
*eventEndPP = next;
switch (tok) {
@@ -2352,14 +2881,14 @@ initializeEncoding(XML_Parser parser)
#ifdef XML_UNICODE
char encodingBuf[128];
if (!protocolEncodingName)
- s = 0;
+ s = NULL;
else {
int i;
for (i = 0; protocolEncodingName[i]; i++) {
if (i == sizeof(encodingBuf) - 1
- || (protocolEncodingName[i] & ~0x7f) != 0) {
- encodingBuf[0] = '\0';
- break;
+ || (protocolEncodingName[i] & ~0x7f) != 0) {
+ encodingBuf[0] = '\0';
+ break;
}
encodingBuf[i] = (char)protocolEncodingName[i];
}
@@ -2376,81 +2905,79 @@ initializeEncoding(XML_Parser parser)
static enum XML_Error
processXmlDecl(XML_Parser parser, int isGeneralTextEntity,
- const char *s, const char *next)
+ const char *s, const char *next)
{
- const char *encodingName = 0;
- const char *storedEncName = 0;
- const ENCODING *newEncoding = 0;
- const char *version = 0;
+ const char *encodingName = NULL;
+ const XML_Char *storedEncName = NULL;
+ const ENCODING *newEncoding = NULL;
+ const char *version = NULL;
const char *versionend;
- const char *storedversion = 0;
+ const XML_Char *storedversion = NULL;
int standalone = -1;
if (!(ns
? XmlParseXmlDeclNS
- : XmlParseXmlDecl)(isGeneralTextEntity,
- encoding,
- s,
- next,
- &eventPtr,
- &version,
- &versionend,
- &encodingName,
- &newEncoding,
- &standalone))
+ : XmlParseXmlDecl)(isGeneralTextEntity,
+ encoding,
+ s,
+ next,
+ &eventPtr,
+ &version,
+ &versionend,
+ &encodingName,
+ &newEncoding,
+ &standalone))
return XML_ERROR_SYNTAX;
if (!isGeneralTextEntity && standalone == 1) {
- dtd.standalone = 1;
+ _dtd->standalone = XML_TRUE;
#ifdef XML_DTD
if (paramEntityParsing == XML_PARAM_ENTITY_PARSING_UNLESS_STANDALONE)
paramEntityParsing = XML_PARAM_ENTITY_PARSING_NEVER;
#endif /* XML_DTD */
}
if (xmlDeclHandler) {
- if (encodingName) {
+ if (encodingName != NULL) {
storedEncName = poolStoreString(&temp2Pool,
- encoding,
- encodingName,
- encodingName
- + XmlNameLength(encoding, encodingName));
- if (! storedEncName)
- return XML_ERROR_NO_MEMORY;
+ encoding,
+ encodingName,
+ encodingName
+ + XmlNameLength(encoding, encodingName));
+ if (!storedEncName)
+ return XML_ERROR_NO_MEMORY;
poolFinish(&temp2Pool);
}
if (version) {
storedversion = poolStoreString(&temp2Pool,
- encoding,
- version,
- versionend - encoding->minBytesPerChar);
- if (! storedversion)
- return XML_ERROR_NO_MEMORY;
+ encoding,
+ version,
+ versionend - encoding->minBytesPerChar);
+ if (!storedversion)
+ return XML_ERROR_NO_MEMORY;
}
xmlDeclHandler(handlerArg, storedversion, storedEncName, standalone);
}
else if (defaultHandler)
reportDefault(parser, encoding, s, next);
- if (!protocolEncodingName) {
+ if (protocolEncodingName == NULL) {
if (newEncoding) {
if (newEncoding->minBytesPerChar != encoding->minBytesPerChar) {
- eventPtr = encodingName;
- return XML_ERROR_INCORRECT_ENCODING;
+ eventPtr = encodingName;
+ return XML_ERROR_INCORRECT_ENCODING;
}
encoding = newEncoding;
}
else if (encodingName) {
enum XML_Error result;
- if (! storedEncName) {
- storedEncName = poolStoreString(&temp2Pool,
- encoding,
- encodingName,
- encodingName
- + XmlNameLength(encoding, encodingName));
- if (! storedEncName)
- return XML_ERROR_NO_MEMORY;
+ if (!storedEncName) {
+ storedEncName = poolStoreString(
+ &temp2Pool, encoding, encodingName,
+ encodingName + XmlNameLength(encoding, encodingName));
+ if (!storedEncName)
+ return XML_ERROR_NO_MEMORY;
}
result = handleUnknownEncoding(parser, storedEncName);
- poolClear(&tempPool);
+ poolClear(&temp2Pool);
if (result == XML_ERROR_UNKNOWN_ENCODING)
- eventPtr = encodingName;
+ eventPtr = encodingName;
return result;
}
}
@@ -2469,41 +2996,42 @@ handleUnknownEncoding(XML_Parser parser, const XML_Char *encodingName)
int i;
for (i = 0; i < 256; i++)
info.map[i] = -1;
- info.convert = 0;
- info.data = 0;
- info.release = 0;
- if (unknownEncodingHandler(unknownEncodingHandlerData, encodingName, &info)) {
+ info.convert = NULL;
+ info.data = NULL;
+ info.release = NULL;
+ if (unknownEncodingHandler(unknownEncodingHandlerData, encodingName,
+ &info)) {
ENCODING *enc;
unknownEncodingMem = MALLOC(XmlSizeOfUnknownEncoding());
if (!unknownEncodingMem) {
- if (info.release)
- info.release(info.data);
- return XML_ERROR_NO_MEMORY;
+ if (info.release)
+ info.release(info.data);
+ return XML_ERROR_NO_MEMORY;
}
enc = (ns
- ? XmlInitUnknownEncodingNS
- : XmlInitUnknownEncoding)(unknownEncodingMem,
- info.map,
- info.convert,
- info.data);
+ ? XmlInitUnknownEncodingNS
+ : XmlInitUnknownEncoding)(unknownEncodingMem,
+ info.map,
+ info.convert,
+ info.data);
if (enc) {
- unknownEncodingData = info.data;
- unknownEncodingRelease = info.release;
- encoding = enc;
- return XML_ERROR_NONE;
+ unknownEncodingData = info.data;
+ unknownEncodingRelease = info.release;
+ encoding = enc;
+ return XML_ERROR_NONE;
}
}
- if (info.release)
+ if (info.release != NULL)
info.release(info.data);
}
return XML_ERROR_UNKNOWN_ENCODING;
}
-static enum XML_Error
+static enum XML_Error PTRCALL
prologInitProcessor(XML_Parser parser,
- const char *s,
- const char *end,
- const char **nextPtr)
+ const char *s,
+ const char *end,
+ const char **nextPtr)
{
enum XML_Error result = initializeEncoding(parser);
if (result != XML_ERROR_NONE)
@@ -2512,29 +3040,204 @@ prologInitProcessor(XML_Parser parser,
return prologProcessor(parser, s, end, nextPtr);
}
-static enum XML_Error
+#ifdef XML_DTD
+
+static enum XML_Error PTRCALL
+externalParEntInitProcessor(XML_Parser parser,
+ const char *s,
+ const char *end,
+ const char **nextPtr)
+{
+ enum XML_Error result = initializeEncoding(parser);
+ if (result != XML_ERROR_NONE)
+ return result;
+
+ /* we know now that XML_Parse(Buffer) has been called,
+ so we consider the external parameter entity read */
+ _dtd->paramEntityRead = XML_TRUE;
+
+ if (prologState.inEntityValue) {
+ processor = entityValueInitProcessor;
+ return entityValueInitProcessor(parser, s, end, nextPtr);
+ }
+ else {
+ processor = externalParEntProcessor;
+ return externalParEntProcessor(parser, s, end, nextPtr);
+ }
+}
+
+static enum XML_Error PTRCALL
+entityValueInitProcessor(XML_Parser parser,
+ const char *s,
+ const char *end,
+ const char **nextPtr)
+{
+ const char *start = s;
+ const char *next = s;
+ int tok;
+
+ for (;;) {
+ tok = XmlPrologTok(encoding, start, end, &next);
+ if (tok <= 0) {
+ if (nextPtr != 0 && tok != XML_TOK_INVALID) {
+ *nextPtr = s;
+ return XML_ERROR_NONE;
+ }
+ switch (tok) {
+ case XML_TOK_INVALID:
+ return XML_ERROR_INVALID_TOKEN;
+ case XML_TOK_PARTIAL:
+ return XML_ERROR_UNCLOSED_TOKEN;
+ case XML_TOK_PARTIAL_CHAR:
+ return XML_ERROR_PARTIAL_CHAR;
+ case XML_TOK_NONE: /* start == end */
+ default:
+ break;
+ }
+ return storeEntityValue(parser, encoding, s, end);
+ }
+ else if (tok == XML_TOK_XML_DECL) {
+ enum XML_Error result = processXmlDecl(parser, 0, start, next);
+ if (result != XML_ERROR_NONE)
+ return result;
+ if (nextPtr) *nextPtr = next;
+ /* stop scanning for text declaration - we found one */
+ processor = entityValueProcessor;
+ return entityValueProcessor(parser, next, end, nextPtr);
+ }
+ /* If we are at the end of the buffer, this would cause XmlPrologTok to
+ return XML_TOK_NONE on the next call, which would then cause the
+ function to exit with *nextPtr set to s - that is what we want for other
+ tokens, but not for the BOM - we would rather like to skip it;
+ then, when this routine is entered the next time, XmlPrologTok will
+ return XML_TOK_INVALID, since the BOM is still in the buffer
+ */
+ else if (tok == XML_TOK_BOM && next == end && nextPtr) {
+ *nextPtr = next;
+ return XML_ERROR_NONE;
+ }
+ start = next;
+ }
+}
+
+static enum XML_Error PTRCALL
+externalParEntProcessor(XML_Parser parser,
+ const char *s,
+ const char *end,
+ const char **nextPtr)
+{
+ const char *start = s;
+ const char *next = s;
+ int tok;
+
+ tok = XmlPrologTok(encoding, start, end, &next);
+ if (tok <= 0) {
+ if (nextPtr != 0 && tok != XML_TOK_INVALID) {
+ *nextPtr = s;
+ return XML_ERROR_NONE;
+ }
+ switch (tok) {
+ case XML_TOK_INVALID:
+ return XML_ERROR_INVALID_TOKEN;
+ case XML_TOK_PARTIAL:
+ return XML_ERROR_UNCLOSED_TOKEN;
+ case XML_TOK_PARTIAL_CHAR:
+ return XML_ERROR_PARTIAL_CHAR;
+ case XML_TOK_NONE: /* start == end */
+ default:
+ break;
+ }
+ }
+ /* This would cause the next stage, i.e. doProlog to be passed XML_TOK_BOM.
+ However, when parsing an external subset, doProlog will not accept a BOM
+ as valid, and report a syntax error, so we have to skip the BOM
+ */
+ else if (tok == XML_TOK_BOM) {
+ s = next;
+ tok = XmlPrologTok(encoding, s, end, &next);
+ }
+
+ processor = prologProcessor;
+ return doProlog(parser, encoding, s, end, tok, next, nextPtr);
+}
+
+static enum XML_Error PTRCALL
+entityValueProcessor(XML_Parser parser,
+ const char *s,
+ const char *end,
+ const char **nextPtr)
+{
+ const char *start = s;
+ const char *next = s;
+ const ENCODING *enc = encoding;
+ int tok;
+
+ for (;;) {
+ tok = XmlPrologTok(enc, start, end, &next);
+ if (tok <= 0) {
+ if (nextPtr != 0 && tok != XML_TOK_INVALID) {
+ *nextPtr = s;
+ return XML_ERROR_NONE;
+ }
+ switch (tok) {
+ case XML_TOK_INVALID:
+ return XML_ERROR_INVALID_TOKEN;
+ case XML_TOK_PARTIAL:
+ return XML_ERROR_UNCLOSED_TOKEN;
+ case XML_TOK_PARTIAL_CHAR:
+ return XML_ERROR_PARTIAL_CHAR;
+ case XML_TOK_NONE: /* start == end */
+ default:
+ break;
+ }
+ return storeEntityValue(parser, enc, s, end);
+ }
+ start = next;
+ }
+}
+
+#endif /* XML_DTD */
+
+static enum XML_Error PTRCALL
prologProcessor(XML_Parser parser,
- const char *s,
- const char *end,
- const char **nextPtr)
+ const char *s,
+ const char *end,
+ const char **nextPtr)
{
- const char *next;
+ const char *next = s;
int tok = XmlPrologTok(encoding, s, end, &next);
return doProlog(parser, encoding, s, end, tok, next, nextPtr);
}
static enum XML_Error
doProlog(XML_Parser parser,
- const ENCODING *enc,
- const char *s,
- const char *end,
- int tok,
- const char *next,
- const char **nextPtr)
+ const ENCODING *enc,
+ const char *s,
+ const char *end,
+ int tok,
+ const char *next,
+ const char **nextPtr)
{
#ifdef XML_DTD
static const XML_Char externalSubsetName[] = { '#' , '\0' };
#endif /* XML_DTD */
+ static const XML_Char atypeCDATA[] = { 'C', 'D', 'A', 'T', 'A', '\0' };
+ static const XML_Char atypeID[] = { 'I', 'D', '\0' };
+ static const XML_Char atypeIDREF[] = { 'I', 'D', 'R', 'E', 'F', '\0' };
+ static const XML_Char atypeIDREFS[] = { 'I', 'D', 'R', 'E', 'F', 'S', '\0' };
+ static const XML_Char atypeENTITY[] = { 'E', 'N', 'T', 'I', 'T', 'Y', '\0' };
+ static const XML_Char atypeENTITIES[] =
+ { 'E', 'N', 'T', 'I', 'T', 'I', 'E', 'S', '\0' };
+ static const XML_Char atypeNMTOKEN[] = {
+ 'N', 'M', 'T', 'O', 'K', 'E', 'N', '\0' };
+ static const XML_Char atypeNMTOKENS[] = {
+ 'N', 'M', 'T', 'O', 'K', 'E', 'N', 'S', '\0' };
+ static const XML_Char notationPrefix[] = {
+ 'N', 'O', 'T', 'A', 'T', 'I', 'O', 'N', '(', '\0' };
+ static const XML_Char enumValueSep[] = { '|', '\0' };
+ static const XML_Char enumValueStart[] = { '(', '\0' };
+
+ DTD * const dtd = _dtd; /* save one level of indirection */
const char **eventPP;
const char **eventEndPP;
@@ -2550,624 +3253,777 @@ doProlog(XML_Parser parser,
}
for (;;) {
int role;
+ XML_Bool handleDefault = XML_TRUE;
*eventPP = s;
*eventEndPP = next;
if (tok <= 0) {
if (nextPtr != 0 && tok != XML_TOK_INVALID) {
- *nextPtr = s;
- return XML_ERROR_NONE;
+ *nextPtr = s;
+ return XML_ERROR_NONE;
}
switch (tok) {
case XML_TOK_INVALID:
- *eventPP = next;
- return XML_ERROR_INVALID_TOKEN;
+ *eventPP = next;
+ return XML_ERROR_INVALID_TOKEN;
case XML_TOK_PARTIAL:
- return XML_ERROR_UNCLOSED_TOKEN;
+ return XML_ERROR_UNCLOSED_TOKEN;
case XML_TOK_PARTIAL_CHAR:
- return XML_ERROR_PARTIAL_CHAR;
+ return XML_ERROR_PARTIAL_CHAR;
case XML_TOK_NONE:
#ifdef XML_DTD
- if (enc != encoding)
- return XML_ERROR_NONE;
- if (parentParser) {
- if (XmlTokenRole(&prologState, XML_TOK_NONE, end, end, enc)
- == XML_ROLE_ERROR)
- return XML_ERROR_SYNTAX;
- hadExternalDoctype = 0;
- return XML_ERROR_NONE;
- }
+ if (enc != encoding)
+ return XML_ERROR_NONE;
+ if (isParamEntity) {
+ if (XmlTokenRole(&prologState, XML_TOK_NONE, end, end, enc)
+ == XML_ROLE_ERROR)
+ return XML_ERROR_SYNTAX;
+ return XML_ERROR_NONE;
+ }
#endif /* XML_DTD */
- return XML_ERROR_NO_ELEMENTS;
+ return XML_ERROR_NO_ELEMENTS;
default:
- tok = -tok;
- next = end;
- break;
+ tok = -tok;
+ next = end;
+ break;
}
}
role = XmlTokenRole(&prologState, tok, s, next, enc);
switch (role) {
case XML_ROLE_XML_DECL:
{
- enum XML_Error result = processXmlDecl(parser, 0, s, next);
- if (result != XML_ERROR_NONE)
- return result;
- enc = encoding;
+ enum XML_Error result = processXmlDecl(parser, 0, s, next);
+ if (result != XML_ERROR_NONE)
+ return result;
+ enc = encoding;
+ handleDefault = XML_FALSE;
}
break;
case XML_ROLE_DOCTYPE_NAME:
if (startDoctypeDeclHandler) {
- doctypeName = poolStoreString(&tempPool, enc, s, next);
- if (! doctypeName)
- return XML_ERROR_NO_MEMORY;
- poolFinish(&tempPool);
- doctypeSysid = 0;
- doctypePubid = 0;
+ doctypeName = poolStoreString(&tempPool, enc, s, next);
+ if (!doctypeName)
+ return XML_ERROR_NO_MEMORY;
+ poolFinish(&tempPool);
+ doctypePubid = NULL;
+ handleDefault = XML_FALSE;
}
+ doctypeSysid = NULL; /* always initialize to NULL */
break;
case XML_ROLE_DOCTYPE_INTERNAL_SUBSET:
if (startDoctypeDeclHandler) {
- startDoctypeDeclHandler(handlerArg, doctypeName, doctypeSysid,
- doctypePubid, 1);
- doctypeName = 0;
- poolClear(&tempPool);
+ startDoctypeDeclHandler(handlerArg, doctypeName, doctypeSysid,
+ doctypePubid, 1);
+ doctypeName = NULL;
+ poolClear(&tempPool);
+ handleDefault = XML_FALSE;
}
break;
#ifdef XML_DTD
case XML_ROLE_TEXT_DECL:
{
- enum XML_Error result = processXmlDecl(parser, 1, s, next);
- if (result != XML_ERROR_NONE)
- return result;
- enc = encoding;
+ enum XML_Error result = processXmlDecl(parser, 1, s, next);
+ if (result != XML_ERROR_NONE)
+ return result;
+ enc = encoding;
+ handleDefault = XML_FALSE;
}
break;
#endif /* XML_DTD */
case XML_ROLE_DOCTYPE_PUBLIC_ID:
+#ifdef XML_DTD
+ useForeignDTD = XML_FALSE;
+#endif /* XML_DTD */
+ dtd->hasParamEntityRefs = XML_TRUE;
if (startDoctypeDeclHandler) {
- doctypePubid = poolStoreString(&tempPool, enc, s + 1, next - 1);
- if (! doctypePubid)
- return XML_ERROR_NO_MEMORY;
- poolFinish(&tempPool);
+ doctypePubid = poolStoreString(&tempPool, enc,
+ s + enc->minBytesPerChar,
+ next - enc->minBytesPerChar);
+ if (!doctypePubid)
+ return XML_ERROR_NO_MEMORY;
+ poolFinish(&tempPool);
+ handleDefault = XML_FALSE;
}
#ifdef XML_DTD
- declEntity = (ENTITY *)lookup(&dtd.paramEntities,
- externalSubsetName,
- sizeof(ENTITY));
+ declEntity = (ENTITY *)lookup(&dtd->paramEntities,
+ externalSubsetName,
+ sizeof(ENTITY));
if (!declEntity)
- return XML_ERROR_NO_MEMORY;
+ return XML_ERROR_NO_MEMORY;
#endif /* XML_DTD */
/* fall through */
case XML_ROLE_ENTITY_PUBLIC_ID:
if (!XmlIsPublicId(enc, s, next, eventPP))
- return XML_ERROR_SYNTAX;
- if (declEntity) {
- XML_Char *tem = poolStoreString(&dtd.pool,
- enc,
- s + enc->minBytesPerChar,
- next - enc->minBytesPerChar);
- if (!tem)
- return XML_ERROR_NO_MEMORY;
- normalizePublicId(tem);
- declEntity->publicId = tem;
- poolFinish(&dtd.pool);
+ return XML_ERROR_SYNTAX;
+ if (dtd->keepProcessing && declEntity) {
+ XML_Char *tem = poolStoreString(&dtd->pool,
+ enc,
+ s + enc->minBytesPerChar,
+ next - enc->minBytesPerChar);
+ if (!tem)
+ return XML_ERROR_NO_MEMORY;
+ normalizePublicId(tem);
+ declEntity->publicId = tem;
+ poolFinish(&dtd->pool);
+ if (entityDeclHandler)
+ handleDefault = XML_FALSE;
}
break;
case XML_ROLE_DOCTYPE_CLOSE:
if (doctypeName) {
- startDoctypeDeclHandler(handlerArg, doctypeName,
- doctypeSysid, doctypePubid, 0);
- poolClear(&tempPool);
+ startDoctypeDeclHandler(handlerArg, doctypeName,
+ doctypeSysid, doctypePubid, 0);
+ poolClear(&tempPool);
+ handleDefault = XML_FALSE;
}
- if (dtd.complete && hadExternalDoctype) {
- dtd.complete = 0;
+ /* doctypeSysid will be non-NULL in the case of a previous
+ XML_ROLE_DOCTYPE_SYSTEM_ID, even if startDoctypeDeclHandler
+ was not set, indicating an external subset
+ */
#ifdef XML_DTD
- if (paramEntityParsing && externalEntityRefHandler) {
- ENTITY *entity = (ENTITY *)lookup(&dtd.paramEntities,
- externalSubsetName,
- 0);
- if (!externalEntityRefHandler(externalEntityRefHandlerArg,
- 0,
- entity->base,
- entity->systemId,
- entity->publicId))
- return XML_ERROR_EXTERNAL_ENTITY_HANDLING;
- }
+ if (doctypeSysid || useForeignDTD) {
+ dtd->hasParamEntityRefs = XML_TRUE; /* when docTypeSysid == NULL */
+ if (paramEntityParsing && externalEntityRefHandler) {
+ ENTITY *entity = (ENTITY *)lookup(&dtd->paramEntities,
+ externalSubsetName,
+ sizeof(ENTITY));
+ if (!entity)
+ return XML_ERROR_NO_MEMORY;
+ if (useForeignDTD)
+ entity->base = curBase;
+ dtd->paramEntityRead = XML_FALSE;
+ if (!externalEntityRefHandler(externalEntityRefHandlerArg,
+ 0,
+ entity->base,
+ entity->systemId,
+ entity->publicId))
+ return XML_ERROR_EXTERNAL_ENTITY_HANDLING;
+ if (dtd->paramEntityRead &&
+ !dtd->standalone &&
+ notStandaloneHandler &&
+ !notStandaloneHandler(handlerArg))
+ return XML_ERROR_NOT_STANDALONE;
+ /* end of DTD - no need to update dtd->keepProcessing */
+ }
+ useForeignDTD = XML_FALSE;
+ }
#endif /* XML_DTD */
- if (!dtd.complete
- && !dtd.standalone
- && notStandaloneHandler
- && !notStandaloneHandler(handlerArg))
- return XML_ERROR_NOT_STANDALONE;
+ if (endDoctypeDeclHandler) {
+ endDoctypeDeclHandler(handlerArg);
+ handleDefault = XML_FALSE;
}
- if (endDoctypeDeclHandler)
- endDoctypeDeclHandler(handlerArg);
break;
case XML_ROLE_INSTANCE_START:
+#ifdef XML_DTD
+ /* if there is no DOCTYPE declaration then now is the
+ last chance to read the foreign DTD
+ */
+ if (useForeignDTD) {
+ dtd->hasParamEntityRefs = XML_TRUE;
+ if (paramEntityParsing && externalEntityRefHandler) {
+ ENTITY *entity = (ENTITY *)lookup(&dtd->paramEntities,
+ externalSubsetName,
+ sizeof(ENTITY));
+ if (!entity)
+ return XML_ERROR_NO_MEMORY;
+ entity->base = curBase;
+ dtd->paramEntityRead = XML_FALSE;
+ if (!externalEntityRefHandler(externalEntityRefHandlerArg,
+ 0,
+ entity->base,
+ entity->systemId,
+ entity->publicId))
+ return XML_ERROR_EXTERNAL_ENTITY_HANDLING;
+ if (dtd->paramEntityRead &&
+ !dtd->standalone &&
+ notStandaloneHandler &&
+ !notStandaloneHandler(handlerArg))
+ return XML_ERROR_NOT_STANDALONE;
+ /* end of DTD - no need to update dtd->keepProcessing */
+ }
+ }
+#endif /* XML_DTD */
processor = contentProcessor;
return contentProcessor(parser, s, end, nextPtr);
case XML_ROLE_ATTLIST_ELEMENT_NAME:
declElementType = getElementType(parser, enc, s, next);
if (!declElementType)
- return XML_ERROR_NO_MEMORY;
- break;
+ return XML_ERROR_NO_MEMORY;
+ goto checkAttListDeclHandler;
case XML_ROLE_ATTRIBUTE_NAME:
declAttributeId = getAttributeId(parser, enc, s, next);
if (!declAttributeId)
- return XML_ERROR_NO_MEMORY;
- declAttributeIsCdata = 0;
- declAttributeType = 0;
- declAttributeIsId = 0;
- break;
+ return XML_ERROR_NO_MEMORY;
+ declAttributeIsCdata = XML_FALSE;
+ declAttributeType = NULL;
+ declAttributeIsId = XML_FALSE;
+ goto checkAttListDeclHandler;
case XML_ROLE_ATTRIBUTE_TYPE_CDATA:
- declAttributeIsCdata = 1;
- declAttributeType = "CDATA";
- break;
+ declAttributeIsCdata = XML_TRUE;
+ declAttributeType = atypeCDATA;
+ goto checkAttListDeclHandler;
case XML_ROLE_ATTRIBUTE_TYPE_ID:
- declAttributeIsId = 1;
- declAttributeType = "ID";
- break;
+ declAttributeIsId = XML_TRUE;
+ declAttributeType = atypeID;
+ goto checkAttListDeclHandler;
case XML_ROLE_ATTRIBUTE_TYPE_IDREF:
- declAttributeType = "IDREF";
- break;
+ declAttributeType = atypeIDREF;
+ goto checkAttListDeclHandler;
case XML_ROLE_ATTRIBUTE_TYPE_IDREFS:
- declAttributeType = "IDREFS";
- break;
+ declAttributeType = atypeIDREFS;
+ goto checkAttListDeclHandler;
case XML_ROLE_ATTRIBUTE_TYPE_ENTITY:
- declAttributeType = "ENTITY";
- break;
+ declAttributeType = atypeENTITY;
+ goto checkAttListDeclHandler;
case XML_ROLE_ATTRIBUTE_TYPE_ENTITIES:
- declAttributeType = "ENTITIES";
- break;
+ declAttributeType = atypeENTITIES;
+ goto checkAttListDeclHandler;
case XML_ROLE_ATTRIBUTE_TYPE_NMTOKEN:
- declAttributeType = "NMTOKEN";
- break;
+ declAttributeType = atypeNMTOKEN;
+ goto checkAttListDeclHandler;
case XML_ROLE_ATTRIBUTE_TYPE_NMTOKENS:
- declAttributeType = "NMTOKENS";
+ declAttributeType = atypeNMTOKENS;
+ checkAttListDeclHandler:
+ if (dtd->keepProcessing && attlistDeclHandler)
+ handleDefault = XML_FALSE;
break;
-
case XML_ROLE_ATTRIBUTE_ENUM_VALUE:
case XML_ROLE_ATTRIBUTE_NOTATION_VALUE:
- if (attlistDeclHandler)
- {
- char *prefix;
- if (declAttributeType) {
- prefix = "|";
- }
- else {
- prefix = (role == XML_ROLE_ATTRIBUTE_NOTATION_VALUE
- ? "NOTATION("
- : "(");
- }
- if (! poolAppendString(&tempPool, prefix))
- return XML_ERROR_NO_MEMORY;
- if (! poolAppend(&tempPool, enc, s, next))
- return XML_ERROR_NO_MEMORY;
- declAttributeType = tempPool.start;
+ if (dtd->keepProcessing && attlistDeclHandler) {
+ const XML_Char *prefix;
+ if (declAttributeType) {
+ prefix = enumValueSep;
+ }
+ else {
+ prefix = (role == XML_ROLE_ATTRIBUTE_NOTATION_VALUE
+ ? notationPrefix
+ : enumValueStart);
+ }
+ if (!poolAppendString(&tempPool, prefix))
+ return XML_ERROR_NO_MEMORY;
+ if (!poolAppend(&tempPool, enc, s, next))
+ return XML_ERROR_NO_MEMORY;
+ declAttributeType = tempPool.start;
+ handleDefault = XML_FALSE;
}
break;
case XML_ROLE_IMPLIED_ATTRIBUTE_VALUE:
case XML_ROLE_REQUIRED_ATTRIBUTE_VALUE:
- if (dtd.complete
- && !defineAttribute(declElementType, declAttributeId,
- declAttributeIsCdata, declAttributeIsId, 0,
- parser))
- return XML_ERROR_NO_MEMORY;
- if (attlistDeclHandler && declAttributeType) {
- if (*declAttributeType == '('
- || (*declAttributeType == 'N' && declAttributeType[1] == 'O')) {
- /* Enumerated or Notation type */
- if (! poolAppendChar(&tempPool, ')')
- || ! poolAppendChar(&tempPool, '\0'))
- return XML_ERROR_NO_MEMORY;
- declAttributeType = tempPool.start;
- poolFinish(&tempPool);
- }
- *eventEndPP = s;
- attlistDeclHandler(handlerArg, declElementType->name,
- declAttributeId->name, declAttributeType,
- 0, role == XML_ROLE_REQUIRED_ATTRIBUTE_VALUE);
- poolClear(&tempPool);
+ if (dtd->keepProcessing) {
+ if (!defineAttribute(declElementType, declAttributeId,
+ declAttributeIsCdata, declAttributeIsId, 0,
+ parser))
+ return XML_ERROR_NO_MEMORY;
+ if (attlistDeclHandler && declAttributeType) {
+ if (*declAttributeType == XML_T('(')
+ || (*declAttributeType == XML_T('N')
+ && declAttributeType[1] == XML_T('O'))) {
+ /* Enumerated or Notation type */
+ if (!poolAppendChar(&tempPool, XML_T(')'))
+ || !poolAppendChar(&tempPool, XML_T('\0')))
+ return XML_ERROR_NO_MEMORY;
+ declAttributeType = tempPool.start;
+ poolFinish(&tempPool);
+ }
+ *eventEndPP = s;
+ attlistDeclHandler(handlerArg, declElementType->name,
+ declAttributeId->name, declAttributeType,
+ 0, role == XML_ROLE_REQUIRED_ATTRIBUTE_VALUE);
+ poolClear(&tempPool);
+ handleDefault = XML_FALSE;
+ }
}
break;
case XML_ROLE_DEFAULT_ATTRIBUTE_VALUE:
case XML_ROLE_FIXED_ATTRIBUTE_VALUE:
- {
- const XML_Char *attVal;
- enum XML_Error result
- = storeAttributeValue(parser, enc, declAttributeIsCdata,
- s + enc->minBytesPerChar,
- next - enc->minBytesPerChar,
- &dtd.pool);
- if (result)
- return result;
- attVal = poolStart(&dtd.pool);
- poolFinish(&dtd.pool);
- if (dtd.complete
- /* ID attributes aren't allowed to have a default */
- && !defineAttribute(declElementType, declAttributeId, declAttributeIsCdata, 0, attVal, parser))
- return XML_ERROR_NO_MEMORY;
- if (attlistDeclHandler && declAttributeType) {
- if (*declAttributeType == '('
- || (*declAttributeType == 'N' && declAttributeType[1] == 'O')) {
- /* Enumerated or Notation type */
- if (! poolAppendChar(&tempPool, ')')
- || ! poolAppendChar(&tempPool, '\0'))
- return XML_ERROR_NO_MEMORY;
- declAttributeType = tempPool.start;
- poolFinish(&tempPool);
- }
- *eventEndPP = s;
- attlistDeclHandler(handlerArg, declElementType->name,
- declAttributeId->name, declAttributeType,
- attVal,
- role == XML_ROLE_FIXED_ATTRIBUTE_VALUE);
- poolClear(&tempPool);
- }
- break;
+ if (dtd->keepProcessing) {
+ const XML_Char *attVal;
+ enum XML_Error result
+ = storeAttributeValue(parser, enc, declAttributeIsCdata,
+ s + enc->minBytesPerChar,
+ next - enc->minBytesPerChar,
+ &dtd->pool);
+ if (result)
+ return result;
+ attVal = poolStart(&dtd->pool);
+ poolFinish(&dtd->pool);
+ /* ID attributes aren't allowed to have a default */
+ if (!defineAttribute(declElementType, declAttributeId,
+ declAttributeIsCdata, XML_FALSE, attVal, parser))
+ return XML_ERROR_NO_MEMORY;
+ if (attlistDeclHandler && declAttributeType) {
+ if (*declAttributeType == XML_T('(')
+ || (*declAttributeType == XML_T('N')
+ && declAttributeType[1] == XML_T('O'))) {
+ /* Enumerated or Notation type */
+ if (!poolAppendChar(&tempPool, XML_T(')'))
+ || !poolAppendChar(&tempPool, XML_T('\0')))
+ return XML_ERROR_NO_MEMORY;
+ declAttributeType = tempPool.start;
+ poolFinish(&tempPool);
+ }
+ *eventEndPP = s;
+ attlistDeclHandler(handlerArg, declElementType->name,
+ declAttributeId->name, declAttributeType,
+ attVal,
+ role == XML_ROLE_FIXED_ATTRIBUTE_VALUE);
+ poolClear(&tempPool);
+ handleDefault = XML_FALSE;
+ }
}
+ break;
case XML_ROLE_ENTITY_VALUE:
- {
- enum XML_Error result = storeEntityValue(parser, enc,
- s + enc->minBytesPerChar,
- next - enc->minBytesPerChar);
- if (declEntity) {
- declEntity->textPtr = poolStart(&dtd.pool);
- declEntity->textLen = poolLength(&dtd.pool);
- poolFinish(&dtd.pool);
- if (entityDeclHandler) {
- *eventEndPP = s;
- entityDeclHandler(handlerArg,
- declEntity->name,
- declEntity->is_param,
- declEntity->textPtr,
- declEntity->textLen,
- curBase, 0, 0, 0);
- }
- }
- else
- poolDiscard(&dtd.pool);
- if (result != XML_ERROR_NONE)
- return result;
+ if (dtd->keepProcessing) {
+ enum XML_Error result = storeEntityValue(parser, enc,
+ s + enc->minBytesPerChar,
+ next - enc->minBytesPerChar);
+ if (declEntity) {
+ declEntity->textPtr = poolStart(&dtd->entityValuePool);
+ declEntity->textLen = poolLength(&dtd->entityValuePool);
+ poolFinish(&dtd->entityValuePool);
+ if (entityDeclHandler) {
+ *eventEndPP = s;
+ entityDeclHandler(handlerArg,
+ declEntity->name,
+ declEntity->is_param,
+ declEntity->textPtr,
+ declEntity->textLen,
+ curBase, 0, 0, 0);
+ handleDefault = XML_FALSE;
+ }
+ }
+ else
+ poolDiscard(&dtd->entityValuePool);
+ if (result != XML_ERROR_NONE)
+ return result;
}
break;
case XML_ROLE_DOCTYPE_SYSTEM_ID:
+#ifdef XML_DTD
+ useForeignDTD = XML_FALSE;
+#endif /* XML_DTD */
+ dtd->hasParamEntityRefs = XML_TRUE;
if (startDoctypeDeclHandler) {
- doctypeSysid = poolStoreString(&tempPool, enc, s + 1, next - 1);
- if (! doctypeSysid)
- return XML_ERROR_NO_MEMORY;
- poolFinish(&tempPool);
+ doctypeSysid = poolStoreString(&tempPool, enc,
+ s + enc->minBytesPerChar,
+ next - enc->minBytesPerChar);
+ if (doctypeSysid == NULL)
+ return XML_ERROR_NO_MEMORY;
+ poolFinish(&tempPool);
+ handleDefault = XML_FALSE;
}
- if (!dtd.standalone
#ifdef XML_DTD
- && !paramEntityParsing
+ else
+ /* use externalSubsetName to make doctypeSysid non-NULL
+ for the case where no startDoctypeDeclHandler is set */
+ doctypeSysid = externalSubsetName;
+#endif /* XML_DTD */
+ if (!dtd->standalone
+#ifdef XML_DTD
+ && !paramEntityParsing
#endif /* XML_DTD */
- && notStandaloneHandler
- && !notStandaloneHandler(handlerArg))
- return XML_ERROR_NOT_STANDALONE;
- hadExternalDoctype = 1;
+ && notStandaloneHandler
+ && !notStandaloneHandler(handlerArg))
+ return XML_ERROR_NOT_STANDALONE;
#ifndef XML_DTD
break;
#else /* XML_DTD */
if (!declEntity) {
- declEntity = (ENTITY *)lookup(&dtd.paramEntities,
- externalSubsetName,
- sizeof(ENTITY));
- declEntity->publicId = 0;
- if (!declEntity)
- return XML_ERROR_NO_MEMORY;
+ declEntity = (ENTITY *)lookup(&dtd->paramEntities,
+ externalSubsetName,
+ sizeof(ENTITY));
+ if (!declEntity)
+ return XML_ERROR_NO_MEMORY;
+ declEntity->publicId = NULL;
}
/* fall through */
#endif /* XML_DTD */
case XML_ROLE_ENTITY_SYSTEM_ID:
- if (declEntity) {
- declEntity->systemId = poolStoreString(&dtd.pool, enc,
- s + enc->minBytesPerChar,
- next - enc->minBytesPerChar);
- if (!declEntity->systemId)
- return XML_ERROR_NO_MEMORY;
- declEntity->base = curBase;
- poolFinish(&dtd.pool);
+ if (dtd->keepProcessing && declEntity) {
+ declEntity->systemId = poolStoreString(&dtd->pool, enc,
+ s + enc->minBytesPerChar,
+ next - enc->minBytesPerChar);
+ if (!declEntity->systemId)
+ return XML_ERROR_NO_MEMORY;
+ declEntity->base = curBase;
+ poolFinish(&dtd->pool);
+ if (entityDeclHandler)
+ handleDefault = XML_FALSE;
}
break;
case XML_ROLE_ENTITY_COMPLETE:
- if (declEntity && entityDeclHandler) {
- *eventEndPP = s;
- entityDeclHandler(handlerArg,
- declEntity->name,
- 0,0,0,
- declEntity->base,
- declEntity->systemId,
- declEntity->publicId,
- 0);
+ if (dtd->keepProcessing && declEntity && entityDeclHandler) {
+ *eventEndPP = s;
+ entityDeclHandler(handlerArg,
+ declEntity->name,
+ declEntity->is_param,
+ 0,0,
+ declEntity->base,
+ declEntity->systemId,
+ declEntity->publicId,
+ 0);
+ handleDefault = XML_FALSE;
}
break;
case XML_ROLE_ENTITY_NOTATION_NAME:
- if (declEntity) {
- declEntity->notation = poolStoreString(&dtd.pool, enc, s, next);
- if (!declEntity->notation)
- return XML_ERROR_NO_MEMORY;
- poolFinish(&dtd.pool);
- if (unparsedEntityDeclHandler) {
- *eventEndPP = s;
- unparsedEntityDeclHandler(handlerArg,
- declEntity->name,
- declEntity->base,
- declEntity->systemId,
- declEntity->publicId,
- declEntity->notation);
- }
- else if (entityDeclHandler) {
- *eventEndPP = s;
- entityDeclHandler(handlerArg,
- declEntity->name,
- 0,0,0,
- declEntity->base,
- declEntity->systemId,
- declEntity->publicId,
- declEntity->notation);
- }
+ if (dtd->keepProcessing && declEntity) {
+ declEntity->notation = poolStoreString(&dtd->pool, enc, s, next);
+ if (!declEntity->notation)
+ return XML_ERROR_NO_MEMORY;
+ poolFinish(&dtd->pool);
+ if (unparsedEntityDeclHandler) {
+ *eventEndPP = s;
+ unparsedEntityDeclHandler(handlerArg,
+ declEntity->name,
+ declEntity->base,
+ declEntity->systemId,
+ declEntity->publicId,
+ declEntity->notation);
+ handleDefault = XML_FALSE;
+ }
+ else if (entityDeclHandler) {
+ *eventEndPP = s;
+ entityDeclHandler(handlerArg,
+ declEntity->name,
+ 0,0,0,
+ declEntity->base,
+ declEntity->systemId,
+ declEntity->publicId,
+ declEntity->notation);
+ handleDefault = XML_FALSE;
+ }
}
break;
case XML_ROLE_GENERAL_ENTITY_NAME:
{
- const XML_Char *name;
- if (XmlPredefinedEntityName(enc, s, next)) {
- declEntity = 0;
- break;
- }
- name = poolStoreString(&dtd.pool, enc, s, next);
- if (!name)
- return XML_ERROR_NO_MEMORY;
- if (dtd.complete) {
- declEntity = (ENTITY *)lookup(&dtd.generalEntities, name, sizeof(ENTITY));
- if (!declEntity)
- return XML_ERROR_NO_MEMORY;
- if (declEntity->name != name) {
- poolDiscard(&dtd.pool);
- declEntity = 0;
- }
- else {
- poolFinish(&dtd.pool);
- declEntity->publicId = 0;
- declEntity->is_param = 0;
- }
- }
- else {
- poolDiscard(&dtd.pool);
- declEntity = 0;
- }
+ if (XmlPredefinedEntityName(enc, s, next)) {
+ declEntity = NULL;
+ break;
+ }
+ if (dtd->keepProcessing) {
+ const XML_Char *name = poolStoreString(&dtd->pool, enc, s, next);
+ if (!name)
+ return XML_ERROR_NO_MEMORY;
+ declEntity = (ENTITY *)lookup(&dtd->generalEntities, name,
+ sizeof(ENTITY));
+ if (!declEntity)
+ return XML_ERROR_NO_MEMORY;
+ if (declEntity->name != name) {
+ poolDiscard(&dtd->pool);
+ declEntity = NULL;
+ }
+ else {
+ poolFinish(&dtd->pool);
+ declEntity->publicId = NULL;
+ declEntity->is_param = XML_FALSE;
+ /* if we have a parent parser or are reading an internal parameter
+ entity, then the entity declaration is not considered "internal"
+ */
+ declEntity->is_internal = !(parentParser || openInternalEntities);
+ if (entityDeclHandler)
+ handleDefault = XML_FALSE;
+ }
+ }
+ else {
+ poolDiscard(&dtd->pool);
+ declEntity = NULL;
+ }
}
break;
case XML_ROLE_PARAM_ENTITY_NAME:
#ifdef XML_DTD
- if (dtd.complete) {
- const XML_Char *name = poolStoreString(&dtd.pool, enc, s, next);
- if (!name)
- return XML_ERROR_NO_MEMORY;
- declEntity = (ENTITY *)lookup(&dtd.paramEntities,
- name, sizeof(ENTITY));
- if (!declEntity)
- return XML_ERROR_NO_MEMORY;
- if (declEntity->name != name) {
- poolDiscard(&dtd.pool);
- declEntity = 0;
- }
- else {
- poolFinish(&dtd.pool);
- declEntity->publicId = 0;
- declEntity->is_param = 1;
- }
+ if (dtd->keepProcessing) {
+ const XML_Char *name = poolStoreString(&dtd->pool, enc, s, next);
+ if (!name)
+ return XML_ERROR_NO_MEMORY;
+ declEntity = (ENTITY *)lookup(&dtd->paramEntities,
+ name, sizeof(ENTITY));
+ if (!declEntity)
+ return XML_ERROR_NO_MEMORY;
+ if (declEntity->name != name) {
+ poolDiscard(&dtd->pool);
+ declEntity = NULL;
+ }
+ else {
+ poolFinish(&dtd->pool);
+ declEntity->publicId = NULL;
+ declEntity->is_param = XML_TRUE;
+ /* if we have a parent parser or are reading an internal parameter
+ entity, then the entity declaration is not considered "internal"
+ */
+ declEntity->is_internal = !(parentParser || openInternalEntities);
+ if (entityDeclHandler)
+ handleDefault = XML_FALSE;
+ }
+ }
+ else {
+ poolDiscard(&dtd->pool);
+ declEntity = NULL;
}
#else /* not XML_DTD */
- declEntity = 0;
-#endif /* not XML_DTD */
+ declEntity = NULL;
+#endif /* XML_DTD */
break;
case XML_ROLE_NOTATION_NAME:
- declNotationPublicId = 0;
- declNotationName = 0;
+ declNotationPublicId = NULL;
+ declNotationName = NULL;
if (notationDeclHandler) {
- declNotationName = poolStoreString(&tempPool, enc, s, next);
- if (!declNotationName)
- return XML_ERROR_NO_MEMORY;
- poolFinish(&tempPool);
+ declNotationName = poolStoreString(&tempPool, enc, s, next);
+ if (!declNotationName)
+ return XML_ERROR_NO_MEMORY;
+ poolFinish(&tempPool);
+ handleDefault = XML_FALSE;
}
break;
case XML_ROLE_NOTATION_PUBLIC_ID:
if (!XmlIsPublicId(enc, s, next, eventPP))
- return XML_ERROR_SYNTAX;
- if (declNotationName) {
- XML_Char *tem = poolStoreString(&tempPool,
- enc,
- s + enc->minBytesPerChar,
- next - enc->minBytesPerChar);
- if (!tem)
- return XML_ERROR_NO_MEMORY;
- normalizePublicId(tem);
- declNotationPublicId = tem;
- poolFinish(&tempPool);
+ return XML_ERROR_SYNTAX;
+ if (declNotationName) { /* means notationDeclHandler != NULL */
+ XML_Char *tem = poolStoreString(&tempPool,
+ enc,
+ s + enc->minBytesPerChar,
+ next - enc->minBytesPerChar);
+ if (!tem)
+ return XML_ERROR_NO_MEMORY;
+ normalizePublicId(tem);
+ declNotationPublicId = tem;
+ poolFinish(&tempPool);
+ handleDefault = XML_FALSE;
}
break;
case XML_ROLE_NOTATION_SYSTEM_ID:
if (declNotationName && notationDeclHandler) {
- const XML_Char *systemId
- = poolStoreString(&tempPool, enc,
- s + enc->minBytesPerChar,
- next - enc->minBytesPerChar);
- if (!systemId)
- return XML_ERROR_NO_MEMORY;
- *eventEndPP = s;
- notationDeclHandler(handlerArg,
- declNotationName,
- curBase,
- systemId,
- declNotationPublicId);
+ const XML_Char *systemId
+ = poolStoreString(&tempPool, enc,
+ s + enc->minBytesPerChar,
+ next - enc->minBytesPerChar);
+ if (!systemId)
+ return XML_ERROR_NO_MEMORY;
+ *eventEndPP = s;
+ notationDeclHandler(handlerArg,
+ declNotationName,
+ curBase,
+ systemId,
+ declNotationPublicId);
+ handleDefault = XML_FALSE;
}
poolClear(&tempPool);
break;
case XML_ROLE_NOTATION_NO_SYSTEM_ID:
if (declNotationPublicId && notationDeclHandler) {
- *eventEndPP = s;
- notationDeclHandler(handlerArg,
- declNotationName,
- curBase,
- 0,
- declNotationPublicId);
+ *eventEndPP = s;
+ notationDeclHandler(handlerArg,
+ declNotationName,
+ curBase,
+ 0,
+ declNotationPublicId);
+ handleDefault = XML_FALSE;
}
poolClear(&tempPool);
break;
case XML_ROLE_ERROR:
switch (tok) {
case XML_TOK_PARAM_ENTITY_REF:
- return XML_ERROR_PARAM_ENTITY_REF;
+ return XML_ERROR_PARAM_ENTITY_REF;
case XML_TOK_XML_DECL:
- return XML_ERROR_MISPLACED_XML_PI;
+ return XML_ERROR_MISPLACED_XML_PI;
default:
- return XML_ERROR_SYNTAX;
+ return XML_ERROR_SYNTAX;
}
#ifdef XML_DTD
case XML_ROLE_IGNORE_SECT:
{
- enum XML_Error result;
- if (defaultHandler)
- reportDefault(parser, enc, s, next);
- result = doIgnoreSection(parser, enc, &next, end, nextPtr);
- if (!next) {
- processor = ignoreSectionProcessor;
- return result;
- }
+ enum XML_Error result;
+ if (defaultHandler)
+ reportDefault(parser, enc, s, next);
+ handleDefault = XML_FALSE;
+ result = doIgnoreSection(parser, enc, &next, end, nextPtr);
+ if (!next) {
+ processor = ignoreSectionProcessor;
+ return result;
+ }
}
break;
#endif /* XML_DTD */
case XML_ROLE_GROUP_OPEN:
if (prologState.level >= groupSize) {
- if (groupSize) {
- groupConnector = REALLOC(groupConnector, groupSize *= 2);
- if (dtd.scaffIndex)
- dtd.scaffIndex = REALLOC(dtd.scaffIndex, groupSize * sizeof(int));
- }
- else
- groupConnector = MALLOC(groupSize = 32);
- if (!groupConnector)
- return XML_ERROR_NO_MEMORY;
+ if (groupSize) {
+ char *temp = (char *)REALLOC(groupConnector, groupSize *= 2);
+ if (temp == NULL)
+ return XML_ERROR_NO_MEMORY;
+ groupConnector = temp;
+ if (dtd->scaffIndex) {
+ int *temp = (int *)REALLOC(dtd->scaffIndex,
+ groupSize * sizeof(int));
+ if (temp == NULL)
+ return XML_ERROR_NO_MEMORY;
+ dtd->scaffIndex = temp;
+ }
+ }
+ else {
+ groupConnector = (char *)MALLOC(groupSize = 32);
+ if (!groupConnector)
+ return XML_ERROR_NO_MEMORY;
+ }
}
groupConnector[prologState.level] = 0;
- if (dtd.in_eldecl) {
- int myindex = nextScaffoldPart(parser);
- if (myindex < 0)
- return XML_ERROR_NO_MEMORY;
- dtd.scaffIndex[dtd.scaffLevel] = myindex;
- dtd.scaffLevel++;
- dtd.scaffold[myindex].type = XML_CTYPE_SEQ;
+ if (dtd->in_eldecl) {
+ int myindex = nextScaffoldPart(parser);
+ if (myindex < 0)
+ return XML_ERROR_NO_MEMORY;
+ dtd->scaffIndex[dtd->scaffLevel] = myindex;
+ dtd->scaffLevel++;
+ dtd->scaffold[myindex].type = XML_CTYPE_SEQ;
+ if (elementDeclHandler)
+ handleDefault = XML_FALSE;
}
break;
case XML_ROLE_GROUP_SEQUENCE:
if (groupConnector[prologState.level] == '|')
- return XML_ERROR_SYNTAX;
+ return XML_ERROR_SYNTAX;
groupConnector[prologState.level] = ',';
+ if (dtd->in_eldecl && elementDeclHandler)
+ handleDefault = XML_FALSE;
break;
case XML_ROLE_GROUP_CHOICE:
if (groupConnector[prologState.level] == ',')
- return XML_ERROR_SYNTAX;
- if (dtd.in_eldecl
- && ! groupConnector[prologState.level]
- && dtd.scaffold[dtd.scaffIndex[dtd.scaffLevel - 1]].type != XML_CTYPE_MIXED
- ) {
- dtd.scaffold[dtd.scaffIndex[dtd.scaffLevel - 1]].type = XML_CTYPE_CHOICE;
+ return XML_ERROR_SYNTAX;
+ if (dtd->in_eldecl
+ && !groupConnector[prologState.level]
+ && (dtd->scaffold[dtd->scaffIndex[dtd->scaffLevel - 1]].type
+ != XML_CTYPE_MIXED)
+ ) {
+ dtd->scaffold[dtd->scaffIndex[dtd->scaffLevel - 1]].type
+ = XML_CTYPE_CHOICE;
+ if (elementDeclHandler)
+ handleDefault = XML_FALSE;
}
groupConnector[prologState.level] = '|';
break;
case XML_ROLE_PARAM_ENTITY_REF:
#ifdef XML_DTD
case XML_ROLE_INNER_PARAM_ENTITY_REF:
- if (paramEntityParsing
- && (dtd.complete || role == XML_ROLE_INNER_PARAM_ENTITY_REF)) {
- const XML_Char *name;
- ENTITY *entity;
- name = poolStoreString(&dtd.pool, enc,
- s + enc->minBytesPerChar,
- next - enc->minBytesPerChar);
- if (!name)
- return XML_ERROR_NO_MEMORY;
- entity = (ENTITY *)lookup(&dtd.paramEntities, name, 0);
- poolDiscard(&dtd.pool);
- if (!entity) {
- /* FIXME what to do if !dtd.complete? */
- return XML_ERROR_UNDEFINED_ENTITY;
- }
- if (entity->open)
- return XML_ERROR_RECURSIVE_ENTITY_REF;
- if (entity->textPtr) {
- enum XML_Error result;
- result = processInternalParamEntity(parser, entity);
- if (result != XML_ERROR_NONE)
- return result;
- break;
- }
- if (role == XML_ROLE_INNER_PARAM_ENTITY_REF)
- return XML_ERROR_PARAM_ENTITY_REF;
- if (externalEntityRefHandler) {
- dtd.complete = 0;
- entity->open = 1;
- if (!externalEntityRefHandler(externalEntityRefHandlerArg,
- 0,
- entity->base,
- entity->systemId,
- entity->publicId)) {
- entity->open = 0;
- return XML_ERROR_EXTERNAL_ENTITY_HANDLING;
- }
- entity->open = 0;
- if (dtd.complete)
- break;
- }
+ /* PE references in internal subset are
+ not allowed within declarations */
+ if (prologState.documentEntity &&
+ role == XML_ROLE_INNER_PARAM_ENTITY_REF)
+ return XML_ERROR_PARAM_ENTITY_REF;
+ dtd->hasParamEntityRefs = XML_TRUE;
+ if (!paramEntityParsing)
+ dtd->keepProcessing = dtd->standalone;
+ else {
+ const XML_Char *name;
+ ENTITY *entity;
+ name = poolStoreString(&dtd->pool, enc,
+ s + enc->minBytesPerChar,
+ next - enc->minBytesPerChar);
+ if (!name)
+ return XML_ERROR_NO_MEMORY;
+ entity = (ENTITY *)lookup(&dtd->paramEntities, name, 0);
+ poolDiscard(&dtd->pool);
+ /* first, determine if a check for an existing declaration is needed;
+ if yes, check that the entity exists, and that it is internal,
+ otherwise call the skipped entity handler
+ */
+ if (prologState.documentEntity &&
+ (dtd->standalone
+ ? !openInternalEntities
+ : !dtd->hasParamEntityRefs)) {
+ if (!entity)
+ return XML_ERROR_UNDEFINED_ENTITY;
+ else if (!entity->is_internal)
+ return XML_ERROR_ENTITY_DECLARED_IN_PE;
+ }
+ else if (!entity) {
+ dtd->keepProcessing = dtd->standalone;
+ /* cannot report skipped entities in declarations */
+ if ((role == XML_ROLE_PARAM_ENTITY_REF) && skippedEntityHandler) {
+ skippedEntityHandler(handlerArg, name, 1);
+ handleDefault = XML_FALSE;
+ }
+ break;
+ }
+ if (entity->open)
+ return XML_ERROR_RECURSIVE_ENTITY_REF;
+ if (entity->textPtr) {
+ enum XML_Error result;
+ result = processInternalParamEntity(parser, entity);
+ if (result != XML_ERROR_NONE)
+ return result;
+ handleDefault = XML_FALSE;
+ break;
+ }
+ if (externalEntityRefHandler) {
+ dtd->paramEntityRead = XML_FALSE;
+ entity->open = XML_TRUE;
+ if (!externalEntityRefHandler(externalEntityRefHandlerArg,
+ 0,
+ entity->base,
+ entity->systemId,
+ entity->publicId)) {
+ entity->open = XML_FALSE;
+ return XML_ERROR_EXTERNAL_ENTITY_HANDLING;
+ }
+ entity->open = XML_FALSE;
+ handleDefault = XML_FALSE;
+ if (!dtd->paramEntityRead) {
+ dtd->keepProcessing = dtd->standalone;
+ break;
+ }
+ }
+ else {
+ dtd->keepProcessing = dtd->standalone;
+ break;
+ }
}
#endif /* XML_DTD */
- if (!dtd.standalone
- && notStandaloneHandler
- && !notStandaloneHandler(handlerArg))
- return XML_ERROR_NOT_STANDALONE;
- dtd.complete = 0;
- if (defaultHandler)
- reportDefault(parser, enc, s, next);
+ if (!dtd->standalone &&
+ notStandaloneHandler &&
+ !notStandaloneHandler(handlerArg))
+ return XML_ERROR_NOT_STANDALONE;
break;
- /* Element declaration stuff */
+ /* Element declaration stuff */
case XML_ROLE_ELEMENT_NAME:
if (elementDeclHandler) {
- declElementType = getElementType(parser, enc, s, next);
- if (! declElementType)
- return XML_ERROR_NO_MEMORY;
- dtd.scaffLevel = 0;
- dtd.scaffCount = 0;
- dtd.in_eldecl = 1;
+ declElementType = getElementType(parser, enc, s, next);
+ if (!declElementType)
+ return XML_ERROR_NO_MEMORY;
+ dtd->scaffLevel = 0;
+ dtd->scaffCount = 0;
+ dtd->in_eldecl = XML_TRUE;
+ handleDefault = XML_FALSE;
}
break;
case XML_ROLE_CONTENT_ANY:
case XML_ROLE_CONTENT_EMPTY:
- if (dtd.in_eldecl) {
- if (elementDeclHandler) {
- XML_Content * content = (XML_Content *) MALLOC(sizeof(XML_Content));
- if (! content)
- return XML_ERROR_NO_MEMORY;
- content->quant = XML_CQUANT_NONE;
- content->name = 0;
- content->numchildren = 0;
- content->children = 0;
- content->type = ((role == XML_ROLE_CONTENT_ANY) ?
- XML_CTYPE_ANY :
- XML_CTYPE_EMPTY);
- *eventEndPP = s;
- elementDeclHandler(handlerArg, declElementType->name, content);
- }
- dtd.in_eldecl = 0;
+ if (dtd->in_eldecl) {
+ if (elementDeclHandler) {
+ XML_Content * content = (XML_Content *) MALLOC(sizeof(XML_Content));
+ if (!content)
+ return XML_ERROR_NO_MEMORY;
+ content->quant = XML_CQUANT_NONE;
+ content->name = NULL;
+ content->numchildren = 0;
+ content->children = NULL;
+ content->type = ((role == XML_ROLE_CONTENT_ANY) ?
+ XML_CTYPE_ANY :
+ XML_CTYPE_EMPTY);
+ *eventEndPP = s;
+ elementDeclHandler(handlerArg, declElementType->name, content);
+ handleDefault = XML_FALSE;
+ }
+ dtd->in_eldecl = XML_FALSE;
}
break;
-
+
case XML_ROLE_CONTENT_PCDATA:
- if (dtd.in_eldecl) {
- dtd.scaffold[dtd.scaffIndex[dtd.scaffLevel - 1]].type = XML_CTYPE_MIXED;
+ if (dtd->in_eldecl) {
+ dtd->scaffold[dtd->scaffIndex[dtd->scaffLevel - 1]].type
+ = XML_CTYPE_MIXED;
+ if (elementDeclHandler)
+ handleDefault = XML_FALSE;
}
break;
@@ -3183,21 +4039,29 @@ doProlog(XML_Parser parser,
case XML_ROLE_CONTENT_ELEMENT_PLUS:
quant = XML_CQUANT_PLUS;
elementContent:
- if (dtd.in_eldecl)
- {
- ELEMENT_TYPE *el;
- const char *nxt = quant == XML_CQUANT_NONE ? next : next - 1;
- int myindex = nextScaffoldPart(parser);
- if (myindex < 0)
- return XML_ERROR_NO_MEMORY;
- dtd.scaffold[myindex].type = XML_CTYPE_NAME;
- dtd.scaffold[myindex].quant = quant;
- el = getElementType(parser, enc, s, nxt);
- if (! el)
- return XML_ERROR_NO_MEMORY;
- dtd.scaffold[myindex].name = el->name;
- dtd.contentStringLen += nxt - s + 1;
- }
+ if (dtd->in_eldecl) {
+ ELEMENT_TYPE *el;
+ const XML_Char *name;
+ int nameLen;
+ const char *nxt = (quant == XML_CQUANT_NONE
+ ? next
+ : next - enc->minBytesPerChar);
+ int myindex = nextScaffoldPart(parser);
+ if (myindex < 0)
+ return XML_ERROR_NO_MEMORY;
+ dtd->scaffold[myindex].type = XML_CTYPE_NAME;
+ dtd->scaffold[myindex].quant = quant;
+ el = getElementType(parser, enc, s, nxt);
+ if (!el)
+ return XML_ERROR_NO_MEMORY;
+ name = el->name;
+ dtd->scaffold[myindex].name = name;
+ nameLen = 0;
+ for (; name[nameLen++]; );
+ dtd->contentStringLen += nameLen;
+ if (elementDeclHandler)
+ handleDefault = XML_FALSE;
+ }
break;
case XML_ROLE_GROUP_CLOSE:
@@ -3212,109 +4076,125 @@ doProlog(XML_Parser parser,
case XML_ROLE_GROUP_CLOSE_PLUS:
quant = XML_CQUANT_PLUS;
closeGroup:
- if (dtd.in_eldecl) {
- dtd.scaffLevel--;
- dtd.scaffold[dtd.scaffIndex[dtd.scaffLevel]].quant = quant;
- if (dtd.scaffLevel == 0) {
- if (elementDeclHandler) {
- XML_Content *model = build_model(parser);
- if (! model)
- return XML_ERROR_NO_MEMORY;
- *eventEndPP = s;
- elementDeclHandler(handlerArg, declElementType->name, model);
- }
- dtd.in_eldecl = 0;
- dtd.contentStringLen = 0;
- }
+ if (dtd->in_eldecl) {
+ if (elementDeclHandler)
+ handleDefault = XML_FALSE;
+ dtd->scaffLevel--;
+ dtd->scaffold[dtd->scaffIndex[dtd->scaffLevel]].quant = quant;
+ if (dtd->scaffLevel == 0) {
+ if (!handleDefault) {
+ XML_Content *model = build_model(parser);
+ if (!model)
+ return XML_ERROR_NO_MEMORY;
+ *eventEndPP = s;
+ elementDeclHandler(handlerArg, declElementType->name, model);
+ }
+ dtd->in_eldecl = XML_FALSE;
+ dtd->contentStringLen = 0;
+ }
}
break;
/* End element declaration stuff */
- case XML_ROLE_NONE:
- switch (tok) {
- case XML_TOK_PI:
- if (!reportProcessingInstruction(parser, enc, s, next))
- return XML_ERROR_NO_MEMORY;
- break;
- case XML_TOK_COMMENT:
- if (!reportComment(parser, enc, s, next))
- return XML_ERROR_NO_MEMORY;
- break;
- }
+ case XML_ROLE_PI:
+ if (!reportProcessingInstruction(parser, enc, s, next))
+ return XML_ERROR_NO_MEMORY;
+ handleDefault = XML_FALSE;
break;
- }
- if (defaultHandler) {
+ case XML_ROLE_COMMENT:
+ if (!reportComment(parser, enc, s, next))
+ return XML_ERROR_NO_MEMORY;
+ handleDefault = XML_FALSE;
+ break;
+ case XML_ROLE_NONE:
switch (tok) {
- case XML_TOK_PI:
- case XML_TOK_COMMENT:
case XML_TOK_BOM:
- case XML_TOK_XML_DECL:
-#ifdef XML_DTD
- case XML_TOK_IGNORE_SECT:
-#endif /* XML_DTD */
- case XML_TOK_PARAM_ENTITY_REF:
- break;
- default:
-#ifdef XML_DTD
- if (role != XML_ROLE_IGNORE_SECT)
-#endif /* XML_DTD */
- reportDefault(parser, enc, s, next);
+ handleDefault = XML_FALSE;
+ break;
}
- }
+ break;
+ case XML_ROLE_DOCTYPE_NONE:
+ if (startDoctypeDeclHandler)
+ handleDefault = XML_FALSE;
+ break;
+ case XML_ROLE_ENTITY_NONE:
+ if (dtd->keepProcessing && entityDeclHandler)
+ handleDefault = XML_FALSE;
+ break;
+ case XML_ROLE_NOTATION_NONE:
+ if (notationDeclHandler)
+ handleDefault = XML_FALSE;
+ break;
+ case XML_ROLE_ATTLIST_NONE:
+ if (dtd->keepProcessing && attlistDeclHandler)
+ handleDefault = XML_FALSE;
+ break;
+ case XML_ROLE_ELEMENT_NONE:
+ if (elementDeclHandler)
+ handleDefault = XML_FALSE;
+ break;
+ } /* end of big switch */
+
+ if (handleDefault && defaultHandler)
+ reportDefault(parser, enc, s, next);
+
s = next;
tok = XmlPrologTok(enc, s, end, &next);
}
/* not reached */
}
-static
-enum XML_Error epilogProcessor(XML_Parser parser,
- const char *s,
- const char *end,
- const char **nextPtr)
+static enum XML_Error PTRCALL
+epilogProcessor(XML_Parser parser,
+ const char *s,
+ const char *end,
+ const char **nextPtr)
{
processor = epilogProcessor;
eventPtr = s;
for (;;) {
- const char *next;
+ const char *next = NULL;
int tok = XmlPrologTok(encoding, s, end, &next);
eventEndPtr = next;
switch (tok) {
+ /* report partial linebreak - it might be the last token */
case -XML_TOK_PROLOG_S:
if (defaultHandler) {
- eventEndPtr = end;
- reportDefault(parser, encoding, s, end);
+ eventEndPtr = next;
+ reportDefault(parser, encoding, s, next);
}
- /* fall through */
+ if (nextPtr)
+ *nextPtr = next;
+ return XML_ERROR_NONE;
case XML_TOK_NONE:
if (nextPtr)
- *nextPtr = end;
+ *nextPtr = s;
return XML_ERROR_NONE;
case XML_TOK_PROLOG_S:
if (defaultHandler)
- reportDefault(parser, encoding, s, next);
+ reportDefault(parser, encoding, s, next);
break;
case XML_TOK_PI:
if (!reportProcessingInstruction(parser, encoding, s, next))
- return XML_ERROR_NO_MEMORY;
+ return XML_ERROR_NO_MEMORY;
break;
case XML_TOK_COMMENT:
if (!reportComment(parser, encoding, s, next))
- return XML_ERROR_NO_MEMORY;
+ return XML_ERROR_NO_MEMORY;
break;
case XML_TOK_INVALID:
eventPtr = next;
return XML_ERROR_INVALID_TOKEN;
case XML_TOK_PARTIAL:
if (nextPtr) {
- *nextPtr = s;
- return XML_ERROR_NONE;
+ *nextPtr = s;
+ return XML_ERROR_NONE;
}
return XML_ERROR_UNCLOSED_TOKEN;
case XML_TOK_PARTIAL_CHAR:
if (nextPtr) {
- *nextPtr = s;
- return XML_ERROR_NONE;
+ *nextPtr = s;
+ return XML_ERROR_NONE;
}
return XML_ERROR_PARTIAL_CHAR;
default:
@@ -3333,38 +4213,39 @@ processInternalParamEntity(XML_Parser parser, ENTITY *entity)
int tok;
enum XML_Error result;
OPEN_INTERNAL_ENTITY openEntity;
- entity->open = 1;
+ entity->open = XML_TRUE;
openEntity.next = openInternalEntities;
openInternalEntities = &openEntity;
openEntity.entity = entity;
- openEntity.internalEventPtr = 0;
- openEntity.internalEventEndPtr = 0;
+ openEntity.internalEventPtr = NULL;
+ openEntity.internalEventEndPtr = NULL;
s = (char *)entity->textPtr;
end = (char *)(entity->textPtr + entity->textLen);
tok = XmlPrologTok(internalEncoding, s, end, &next);
result = doProlog(parser, internalEncoding, s, end, tok, next, 0);
- entity->open = 0;
+ entity->open = XML_FALSE;
openInternalEntities = openEntity.next;
return result;
}
#endif /* XML_DTD */
-static
-enum XML_Error errorProcessor(XML_Parser parser,
- const char *s,
- const char *end,
- const char **nextPtr)
+static enum XML_Error PTRCALL
+errorProcessor(XML_Parser parser,
+ const char *s,
+ const char *end,
+ const char **nextPtr)
{
return errorCode;
}
static enum XML_Error
-storeAttributeValue(XML_Parser parser, const ENCODING *enc, int isCdata,
- const char *ptr, const char *end,
- STRING_POOL *pool)
+storeAttributeValue(XML_Parser parser, const ENCODING *enc, XML_Bool isCdata,
+ const char *ptr, const char *end,
+ STRING_POOL *pool)
{
- enum XML_Error result = appendAttributeValue(parser, enc, isCdata, ptr, end, pool);
+ enum XML_Error result = appendAttributeValue(parser, enc, isCdata, ptr,
+ end, pool);
if (result)
return result;
if (!isCdata && poolLength(pool) && poolLastChar(pool) == 0x20)
@@ -3375,10 +4256,11 @@ storeAttributeValue(XML_Parser parser, const ENCODING *enc, int isCdata,
}
static enum XML_Error
-appendAttributeValue(XML_Parser parser, const ENCODING *enc, int isCdata,
- const char *ptr, const char *end,
- STRING_POOL *pool)
+appendAttributeValue(XML_Parser parser, const ENCODING *enc, XML_Bool isCdata,
+ const char *ptr, const char *end,
+ STRING_POOL *pool)
{
+ DTD * const dtd = _dtd; /* save one level of indirection */
for (;;) {
const char *next;
int tok = XmlAttributeValueTok(enc, ptr, end, &next);
@@ -3387,42 +4269,41 @@ appendAttributeValue(XML_Parser parser, const ENCODING *enc, int isCdata,
return XML_ERROR_NONE;
case XML_TOK_INVALID:
if (enc == encoding)
- eventPtr = next;
+ eventPtr = next;
return XML_ERROR_INVALID_TOKEN;
case XML_TOK_PARTIAL:
if (enc == encoding)
- eventPtr = ptr;
+ eventPtr = ptr;
return XML_ERROR_INVALID_TOKEN;
case XML_TOK_CHAR_REF:
{
- XML_Char buf[XML_ENCODE_MAX];
- int i;
- int n = XmlCharRefNumber(enc, ptr);
- if (n < 0) {
- if (enc == encoding)
- eventPtr = ptr;
- return XML_ERROR_BAD_CHAR_REF;
- }
- if (!isCdata
- && n == 0x20 /* space */
- && (poolLength(pool) == 0 || poolLastChar(pool) == 0x20))
- break;
- n = XmlEncode(n, (ICHAR *)buf);
- if (!n) {
- if (enc == encoding)
- eventPtr = ptr;
- return XML_ERROR_BAD_CHAR_REF;
- }
- for (i = 0; i < n; i++) {
- if (!poolAppendChar(pool, buf[i]))
- return XML_ERROR_NO_MEMORY;
- }
+ XML_Char buf[XML_ENCODE_MAX];
+ int i;
+ int n = XmlCharRefNumber(enc, ptr);
+ if (n < 0) {
+ if (enc == encoding)
+ eventPtr = ptr;
+ return XML_ERROR_BAD_CHAR_REF;
+ }
+ if (!isCdata
+ && n == 0x20 /* space */
+ && (poolLength(pool) == 0 || poolLastChar(pool) == 0x20))
+ break;
+ n = XmlEncode(n, (ICHAR *)buf);
+ if (!n) {
+ if (enc == encoding)
+ eventPtr = ptr;
+ return XML_ERROR_BAD_CHAR_REF;
+ }
+ for (i = 0; i < n; i++) {
+ if (!poolAppendChar(pool, buf[i]))
+ return XML_ERROR_NO_MEMORY;
+ }
}
break;
case XML_TOK_DATA_CHARS:
if (!poolAppend(pool, enc, ptr, next))
- return XML_ERROR_NO_MEMORY;
- break;
+ return XML_ERROR_NO_MEMORY;
break;
case XML_TOK_TRAILING_CR:
next = ptr + enc->minBytesPerChar;
@@ -3430,65 +4311,91 @@ appendAttributeValue(XML_Parser parser, const ENCODING *enc, int isCdata,
case XML_TOK_ATTRIBUTE_VALUE_S:
case XML_TOK_DATA_NEWLINE:
if (!isCdata && (poolLength(pool) == 0 || poolLastChar(pool) == 0x20))
- break;
+ break;
if (!poolAppendChar(pool, 0x20))
- return XML_ERROR_NO_MEMORY;
+ return XML_ERROR_NO_MEMORY;
break;
case XML_TOK_ENTITY_REF:
{
- const XML_Char *name;
- ENTITY *entity;
- XML_Char ch = XmlPredefinedEntityName(enc,
- ptr + enc->minBytesPerChar,
- next - enc->minBytesPerChar);
- if (ch) {
- if (!poolAppendChar(pool, ch))
- return XML_ERROR_NO_MEMORY;
- break;
- }
- name = poolStoreString(&temp2Pool, enc,
- ptr + enc->minBytesPerChar,
- next - enc->minBytesPerChar);
- if (!name)
- return XML_ERROR_NO_MEMORY;
- entity = (ENTITY *)lookup(&dtd.generalEntities, name, 0);
- poolDiscard(&temp2Pool);
- if (!entity) {
- if (dtd.complete) {
- if (enc == encoding)
- eventPtr = ptr;
- return XML_ERROR_UNDEFINED_ENTITY;
- }
- }
- else if (entity->open) {
- if (enc == encoding)
- eventPtr = ptr;
- return XML_ERROR_RECURSIVE_ENTITY_REF;
- }
- else if (entity->notation) {
- if (enc == encoding)
- eventPtr = ptr;
- return XML_ERROR_BINARY_ENTITY_REF;
- }
- else if (!entity->textPtr) {
- if (enc == encoding)
- eventPtr = ptr;
- return XML_ERROR_ATTRIBUTE_EXTERNAL_ENTITY_REF;
- }
- else {
- enum XML_Error result;
- const XML_Char *textEnd = entity->textPtr + entity->textLen;
- entity->open = 1;
- result = appendAttributeValue(parser, internalEncoding, isCdata, (char *)entity->textPtr, (char *)textEnd, pool);
- entity->open = 0;
- if (result)
- return result;
- }
+ const XML_Char *name;
+ ENTITY *entity;
+ char checkEntityDecl;
+ XML_Char ch = (XML_Char) XmlPredefinedEntityName(enc,
+ ptr + enc->minBytesPerChar,
+ next - enc->minBytesPerChar);
+ if (ch) {
+ if (!poolAppendChar(pool, ch))
+ return XML_ERROR_NO_MEMORY;
+ break;
+ }
+ name = poolStoreString(&temp2Pool, enc,
+ ptr + enc->minBytesPerChar,
+ next - enc->minBytesPerChar);
+ if (!name)
+ return XML_ERROR_NO_MEMORY;
+ entity = (ENTITY *)lookup(&dtd->generalEntities, name, 0);
+ poolDiscard(&temp2Pool);
+ /* first, determine if a check for an existing declaration is needed;
+ if yes, check that the entity exists, and that it is internal,
+ otherwise call the default handler (if called from content)
+ */
+ if (pool == &dtd->pool) /* are we called from prolog? */
+ checkEntityDecl =
+#ifdef XML_DTD
+ prologState.documentEntity &&
+#endif /* XML_DTD */
+ (dtd->standalone
+ ? !openInternalEntities
+ : !dtd->hasParamEntityRefs);
+ else /* if (pool == &tempPool): we are called from content */
+ checkEntityDecl = !dtd->hasParamEntityRefs || dtd->standalone;
+ if (checkEntityDecl) {
+ if (!entity)
+ return XML_ERROR_UNDEFINED_ENTITY;
+ else if (!entity->is_internal)
+ return XML_ERROR_ENTITY_DECLARED_IN_PE;
+ }
+ else if (!entity) {
+ /* cannot report skipped entity here - see comments on
+ skippedEntityHandler
+ if (skippedEntityHandler)
+ skippedEntityHandler(handlerArg, name, 0);
+ */
+ if ((pool == &tempPool) && defaultHandler)
+ reportDefault(parser, enc, ptr, next);
+ break;
+ }
+ if (entity->open) {
+ if (enc == encoding)
+ eventPtr = ptr;
+ return XML_ERROR_RECURSIVE_ENTITY_REF;
+ }
+ if (entity->notation) {
+ if (enc == encoding)
+ eventPtr = ptr;
+ return XML_ERROR_BINARY_ENTITY_REF;
+ }
+ if (!entity->textPtr) {
+ if (enc == encoding)
+ eventPtr = ptr;
+ return XML_ERROR_ATTRIBUTE_EXTERNAL_ENTITY_REF;
+ }
+ else {
+ enum XML_Error result;
+ const XML_Char *textEnd = entity->textPtr + entity->textLen;
+ entity->open = XML_TRUE;
+ result = appendAttributeValue(parser, internalEncoding, isCdata,
+ (char *)entity->textPtr,
+ (char *)textEnd, pool);
+ entity->open = XML_FALSE;
+ if (result)
+ return result;
+ }
}
break;
default:
if (enc == encoding)
- eventPtr = ptr;
+ eventPtr = ptr;
return XML_ERROR_UNEXPECTED_STATE;
}
ptr = next;
@@ -3496,115 +4403,173 @@ appendAttributeValue(XML_Parser parser, const ENCODING *enc, int isCdata,
/* not reached */
}
-static
-enum XML_Error storeEntityValue(XML_Parser parser,
- const ENCODING *enc,
- const char *entityTextPtr,
- const char *entityTextEnd)
+static enum XML_Error
+storeEntityValue(XML_Parser parser,
+ const ENCODING *enc,
+ const char *entityTextPtr,
+ const char *entityTextEnd)
{
- STRING_POOL *pool = &(dtd.pool);
+ DTD * const dtd = _dtd; /* save one level of indirection */
+ STRING_POOL *pool = &(dtd->entityValuePool);
+ enum XML_Error result = XML_ERROR_NONE;
+#ifdef XML_DTD
+ int oldInEntityValue = prologState.inEntityValue;
+ prologState.inEntityValue = 1;
+#endif /* XML_DTD */
+ /* never return Null for the value argument in EntityDeclHandler,
+ since this would indicate an external entity; therefore we
+ have to make sure that entityValuePool.start is not null */
+ if (!pool->blocks) {
+ if (!poolGrow(pool))
+ return XML_ERROR_NO_MEMORY;
+ }
+
for (;;) {
const char *next;
int tok = XmlEntityValueTok(enc, entityTextPtr, entityTextEnd, &next);
switch (tok) {
case XML_TOK_PARAM_ENTITY_REF:
#ifdef XML_DTD
- if (parentParser || enc != encoding) {
- enum XML_Error result;
- const XML_Char *name;
- ENTITY *entity;
- name = poolStoreString(&tempPool, enc,
- entityTextPtr + enc->minBytesPerChar,
- next - enc->minBytesPerChar);
- if (!name)
- return XML_ERROR_NO_MEMORY;
- entity = (ENTITY *)lookup(&dtd.paramEntities, name, 0);
- poolDiscard(&tempPool);
- if (!entity) {
- if (enc == encoding)
- eventPtr = entityTextPtr;
- return XML_ERROR_UNDEFINED_ENTITY;
- }
- if (entity->open) {
- if (enc == encoding)
- eventPtr = entityTextPtr;
- return XML_ERROR_RECURSIVE_ENTITY_REF;
- }
- if (entity->systemId) {
- if (enc == encoding)
- eventPtr = entityTextPtr;
- return XML_ERROR_PARAM_ENTITY_REF;
- }
- entity->open = 1;
- result = storeEntityValue(parser,
- internalEncoding,
- (char *)entity->textPtr,
- (char *)(entity->textPtr + entity->textLen));
- entity->open = 0;
- if (result)
- return result;
- break;
+ if (isParamEntity || enc != encoding) {
+ const XML_Char *name;
+ ENTITY *entity;
+ name = poolStoreString(&tempPool, enc,
+ entityTextPtr + enc->minBytesPerChar,
+ next - enc->minBytesPerChar);
+ if (!name) {
+ result = XML_ERROR_NO_MEMORY;
+ goto endEntityValue;
+ }
+ entity = (ENTITY *)lookup(&dtd->paramEntities, name, 0);
+ poolDiscard(&tempPool);
+ if (!entity) {
+ /* not a well-formedness error - see XML 1.0: WFC Entity Declared */
+ /* cannot report skipped entity here - see comments on
+ skippedEntityHandler
+ if (skippedEntityHandler)
+ skippedEntityHandler(handlerArg, name, 0);
+ */
+ dtd->keepProcessing = dtd->standalone;
+ goto endEntityValue;
+ }
+ if (entity->open) {
+ if (enc == encoding)
+ eventPtr = entityTextPtr;
+ result = XML_ERROR_RECURSIVE_ENTITY_REF;
+ goto endEntityValue;
+ }
+ if (entity->systemId) {
+ if (externalEntityRefHandler) {
+ dtd->paramEntityRead = XML_FALSE;
+ entity->open = XML_TRUE;
+ if (!externalEntityRefHandler(externalEntityRefHandlerArg,
+ 0,
+ entity->base,
+ entity->systemId,
+ entity->publicId)) {
+ entity->open = XML_FALSE;
+ result = XML_ERROR_EXTERNAL_ENTITY_HANDLING;
+ goto endEntityValue;
+ }
+ entity->open = XML_FALSE;
+ if (!dtd->paramEntityRead)
+ dtd->keepProcessing = dtd->standalone;
+ }
+ else
+ dtd->keepProcessing = dtd->standalone;
+ }
+ else {
+ entity->open = XML_TRUE;
+ result = storeEntityValue(parser,
+ internalEncoding,
+ (char *)entity->textPtr,
+ (char *)(entity->textPtr
+ + entity->textLen));
+ entity->open = XML_FALSE;
+ if (result)
+ goto endEntityValue;
+ }
+ break;
}
#endif /* XML_DTD */
+ /* in the internal subset, PE references are not legal
+ within markup declarations, e.g entity values in this case */
eventPtr = entityTextPtr;
- return XML_ERROR_SYNTAX;
+ result = XML_ERROR_PARAM_ENTITY_REF;
+ goto endEntityValue;
case XML_TOK_NONE:
- return XML_ERROR_NONE;
+ result = XML_ERROR_NONE;
+ goto endEntityValue;
case XML_TOK_ENTITY_REF:
case XML_TOK_DATA_CHARS:
- if (!poolAppend(pool, enc, entityTextPtr, next))
- return XML_ERROR_NO_MEMORY;
+ if (!poolAppend(pool, enc, entityTextPtr, next)) {
+ result = XML_ERROR_NO_MEMORY;
+ goto endEntityValue;
+ }
break;
case XML_TOK_TRAILING_CR:
next = entityTextPtr + enc->minBytesPerChar;
/* fall through */
case XML_TOK_DATA_NEWLINE:
- if (pool->end == pool->ptr && !poolGrow(pool))
- return XML_ERROR_NO_MEMORY;
+ if (pool->end == pool->ptr && !poolGrow(pool)) {
+ result = XML_ERROR_NO_MEMORY;
+ goto endEntityValue;
+ }
*(pool->ptr)++ = 0xA;
break;
case XML_TOK_CHAR_REF:
{
- XML_Char buf[XML_ENCODE_MAX];
- int i;
- int n = XmlCharRefNumber(enc, entityTextPtr);
- if (n < 0) {
- if (enc == encoding)
- eventPtr = entityTextPtr;
- return XML_ERROR_BAD_CHAR_REF;
- }
- n = XmlEncode(n, (ICHAR *)buf);
- if (!n) {
- if (enc == encoding)
- eventPtr = entityTextPtr;
- return XML_ERROR_BAD_CHAR_REF;
- }
- for (i = 0; i < n; i++) {
- if (pool->end == pool->ptr && !poolGrow(pool))
- return XML_ERROR_NO_MEMORY;
- *(pool->ptr)++ = buf[i];
- }
+ XML_Char buf[XML_ENCODE_MAX];
+ int i;
+ int n = XmlCharRefNumber(enc, entityTextPtr);
+ if (n < 0) {
+ if (enc == encoding)
+ eventPtr = entityTextPtr;
+ result = XML_ERROR_BAD_CHAR_REF;
+ goto endEntityValue;
+ }
+ n = XmlEncode(n, (ICHAR *)buf);
+ if (!n) {
+ if (enc == encoding)
+ eventPtr = entityTextPtr;
+ result = XML_ERROR_BAD_CHAR_REF;
+ goto endEntityValue;
+ }
+ for (i = 0; i < n; i++) {
+ if (pool->end == pool->ptr && !poolGrow(pool)) {
+ result = XML_ERROR_NO_MEMORY;
+ goto endEntityValue;
+ }
+ *(pool->ptr)++ = buf[i];
+ }
}
break;
case XML_TOK_PARTIAL:
if (enc == encoding)
- eventPtr = entityTextPtr;
- return XML_ERROR_INVALID_TOKEN;
+ eventPtr = entityTextPtr;
+ result = XML_ERROR_INVALID_TOKEN;
+ goto endEntityValue;
case XML_TOK_INVALID:
if (enc == encoding)
- eventPtr = next;
- return XML_ERROR_INVALID_TOKEN;
+ eventPtr = next;
+ result = XML_ERROR_INVALID_TOKEN;
+ goto endEntityValue;
default:
if (enc == encoding)
- eventPtr = entityTextPtr;
- return XML_ERROR_UNEXPECTED_STATE;
+ eventPtr = entityTextPtr;
+ result = XML_ERROR_UNEXPECTED_STATE;
+ goto endEntityValue;
}
entityTextPtr = next;
}
- /* not reached */
+endEntityValue:
+#ifdef XML_DTD
+ prologState.inEntityValue = oldInEntityValue;
+#endif /* XML_DTD */
+ return result;
}
-static void
+static void FASTCALL
normalizeLines(XML_Char *s)
{
XML_Char *p;
@@ -3628,7 +4593,8 @@ normalizeLines(XML_Char *s)
}
static int
-reportProcessingInstruction(XML_Parser parser, const ENCODING *enc, const char *start, const char *end)
+reportProcessingInstruction(XML_Parser parser, const ENCODING *enc,
+ const char *start, const char *end)
{
const XML_Char *target;
XML_Char *data;
@@ -3645,8 +4611,8 @@ reportProcessingInstruction(XML_Parser parser, const ENCODING *enc, const char *
return 0;
poolFinish(&tempPool);
data = poolStoreString(&tempPool, enc,
- XmlSkipS(enc, tem),
- end - enc->minBytesPerChar*2);
+ XmlSkipS(enc, tem),
+ end - enc->minBytesPerChar*2);
if (!data)
return 0;
normalizeLines(data);
@@ -3656,7 +4622,8 @@ reportProcessingInstruction(XML_Parser parser, const ENCODING *enc, const char *
}
static int
-reportComment(XML_Parser parser, const ENCODING *enc, const char *start, const char *end)
+reportComment(XML_Parser parser, const ENCODING *enc,
+ const char *start, const char *end)
{
XML_Char *data;
if (!commentHandler) {
@@ -3666,8 +4633,8 @@ reportComment(XML_Parser parser, const ENCODING *enc, const char *start, const c
}
data = poolStoreString(&tempPool,
enc,
- start + enc->minBytesPerChar * 4,
- end - enc->minBytesPerChar * 3);
+ start + enc->minBytesPerChar * 4,
+ end - enc->minBytesPerChar * 3);
if (!data)
return 0;
normalizeLines(data);
@@ -3677,7 +4644,8 @@ reportComment(XML_Parser parser, const ENCODING *enc, const char *start, const c
}
static void
-reportDefault(XML_Parser parser, const ENCODING *enc, const char *s, const char *end)
+reportDefault(XML_Parser parser, const ENCODING *enc,
+ const char *s, const char *end)
{
if (MUST_CONVERT(enc, s)) {
const char **eventPP;
@@ -3704,8 +4672,8 @@ reportDefault(XML_Parser parser, const ENCODING *enc, const char *s, const char
static int
-defineAttribute(ELEMENT_TYPE *type, ATTRIBUTE_ID *attId, int isCdata,
- int isId, const XML_Char *value, XML_Parser parser)
+defineAttribute(ELEMENT_TYPE *type, ATTRIBUTE_ID *attId, XML_Bool isCdata,
+ XML_Bool isId, const XML_Char *value, XML_Parser parser)
{
DEFAULT_ATTRIBUTE *att;
if (value || isId) {
@@ -3714,53 +4682,62 @@ defineAttribute(ELEMENT_TYPE *type, ATTRIBUTE_ID *attId, int isCdata,
int i;
for (i = 0; i < type->nDefaultAtts; i++)
if (attId == type->defaultAtts[i].id)
- return 1;
+ return 1;
if (isId && !type->idAtt && !attId->xmlns)
type->idAtt = attId;
}
if (type->nDefaultAtts == type->allocDefaultAtts) {
if (type->allocDefaultAtts == 0) {
type->allocDefaultAtts = 8;
- type->defaultAtts = MALLOC(type->allocDefaultAtts*sizeof(DEFAULT_ATTRIBUTE));
+ type->defaultAtts = (DEFAULT_ATTRIBUTE *)MALLOC(type->allocDefaultAtts
+ * sizeof(DEFAULT_ATTRIBUTE));
+ if (!type->defaultAtts)
+ return 0;
}
else {
- type->allocDefaultAtts *= 2;
- type->defaultAtts = REALLOC(type->defaultAtts,
- type->allocDefaultAtts*sizeof(DEFAULT_ATTRIBUTE));
+ DEFAULT_ATTRIBUTE *temp;
+ int count = type->allocDefaultAtts * 2;
+ temp = (DEFAULT_ATTRIBUTE *)
+ REALLOC(type->defaultAtts, (count * sizeof(DEFAULT_ATTRIBUTE)));
+ if (temp == NULL)
+ return 0;
+ type->allocDefaultAtts = count;
+ type->defaultAtts = temp;
}
- if (!type->defaultAtts)
- return 0;
}
att = type->defaultAtts + type->nDefaultAtts;
att->id = attId;
att->value = value;
att->isCdata = isCdata;
if (!isCdata)
- attId->maybeTokenized = 1;
+ attId->maybeTokenized = XML_TRUE;
type->nDefaultAtts += 1;
return 1;
}
-static int setElementTypePrefix(XML_Parser parser, ELEMENT_TYPE *elementType)
+static int
+setElementTypePrefix(XML_Parser parser, ELEMENT_TYPE *elementType)
{
+ DTD * const dtd = _dtd; /* save one level of indirection */
const XML_Char *name;
for (name = elementType->name; *name; name++) {
if (*name == XML_T(':')) {
PREFIX *prefix;
const XML_Char *s;
for (s = elementType->name; s != name; s++) {
- if (!poolAppendChar(&dtd.pool, *s))
- return 0;
+ if (!poolAppendChar(&dtd->pool, *s))
+ return 0;
}
- if (!poolAppendChar(&dtd.pool, XML_T('\0')))
- return 0;
- prefix = (PREFIX *)lookup(&dtd.prefixes, poolStart(&dtd.pool), sizeof(PREFIX));
+ if (!poolAppendChar(&dtd->pool, XML_T('\0')))
+ return 0;
+ prefix = (PREFIX *)lookup(&dtd->prefixes, poolStart(&dtd->pool),
+ sizeof(PREFIX));
if (!prefix)
- return 0;
- if (prefix->name == poolStart(&dtd.pool))
- poolFinish(&dtd.pool);
+ return 0;
+ if (prefix->name == poolStart(&dtd->pool))
+ poolFinish(&dtd->pool);
else
- poolDiscard(&dtd.pool);
+ poolDiscard(&dtd->pool);
elementType->prefix = prefix;
}
@@ -3769,55 +4746,58 @@ static int setElementTypePrefix(XML_Parser parser, ELEMENT_TYPE *elementType)
}
static ATTRIBUTE_ID *
-getAttributeId(XML_Parser parser, const ENCODING *enc, const char *start, const char *end)
+getAttributeId(XML_Parser parser, const ENCODING *enc,
+ const char *start, const char *end)
{
+ DTD * const dtd = _dtd; /* save one level of indirection */
ATTRIBUTE_ID *id;
const XML_Char *name;
- if (!poolAppendChar(&dtd.pool, XML_T('\0')))
- return 0;
- name = poolStoreString(&dtd.pool, enc, start, end);
+ if (!poolAppendChar(&dtd->pool, XML_T('\0')))
+ return NULL;
+ name = poolStoreString(&dtd->pool, enc, start, end);
if (!name)
- return 0;
+ return NULL;
++name;
- id = (ATTRIBUTE_ID *)lookup(&dtd.attributeIds, name, sizeof(ATTRIBUTE_ID));
+ id = (ATTRIBUTE_ID *)lookup(&dtd->attributeIds, name, sizeof(ATTRIBUTE_ID));
if (!id)
- return 0;
+ return NULL;
if (id->name != name)
- poolDiscard(&dtd.pool);
+ poolDiscard(&dtd->pool);
else {
- poolFinish(&dtd.pool);
+ poolFinish(&dtd->pool);
if (!ns)
;
- else if (name[0] == 'x'
- && name[1] == 'm'
- && name[2] == 'l'
- && name[3] == 'n'
- && name[4] == 's'
- && (name[5] == XML_T('\0') || name[5] == XML_T(':'))) {
- if (name[5] == '\0')
- id->prefix = &dtd.defaultPrefix;
+ else if (name[0] == XML_T('x')
+ && name[1] == XML_T('m')
+ && name[2] == XML_T('l')
+ && name[3] == XML_T('n')
+ && name[4] == XML_T('s')
+ && (name[5] == XML_T('\0') || name[5] == XML_T(':'))) {
+ if (name[5] == XML_T('\0'))
+ id->prefix = &dtd->defaultPrefix;
else
- id->prefix = (PREFIX *)lookup(&dtd.prefixes, name + 6, sizeof(PREFIX));
- id->xmlns = 1;
+ id->prefix = (PREFIX *)lookup(&dtd->prefixes, name + 6, sizeof(PREFIX));
+ id->xmlns = XML_TRUE;
}
else {
int i;
for (i = 0; name[i]; i++) {
- if (name[i] == XML_T(':')) {
- int j;
- for (j = 0; j < i; j++) {
- if (!poolAppendChar(&dtd.pool, name[j]))
- return 0;
- }
- if (!poolAppendChar(&dtd.pool, XML_T('\0')))
- return 0;
- id->prefix = (PREFIX *)lookup(&dtd.prefixes, poolStart(&dtd.pool), sizeof(PREFIX));
- if (id->prefix->name == poolStart(&dtd.pool))
- poolFinish(&dtd.pool);
- else
- poolDiscard(&dtd.pool);
- break;
- }
+ if (name[i] == XML_T(':')) {
+ int j;
+ for (j = 0; j < i; j++) {
+ if (!poolAppendChar(&dtd->pool, name[j]))
+ return NULL;
+ }
+ if (!poolAppendChar(&dtd->pool, XML_T('\0')))
+ return NULL;
+ id->prefix = (PREFIX *)lookup(&dtd->prefixes, poolStart(&dtd->pool),
+ sizeof(PREFIX));
+ if (id->prefix->name == poolStart(&dtd->pool))
+ poolFinish(&dtd->pool);
+ else
+ poolDiscard(&dtd->pool);
+ break;
+ }
}
}
}
@@ -3826,27 +4806,28 @@ getAttributeId(XML_Parser parser, const ENCODING *enc, const char *start, const
#define CONTEXT_SEP XML_T('\f')
-static
-const XML_Char *getContext(XML_Parser parser)
+static const XML_Char *
+getContext(XML_Parser parser)
{
+ DTD * const dtd = _dtd; /* save one level of indirection */
HASH_TABLE_ITER iter;
- int needSep = 0;
+ XML_Bool needSep = XML_FALSE;
- if (dtd.defaultPrefix.binding) {
+ if (dtd->defaultPrefix.binding) {
int i;
int len;
if (!poolAppendChar(&tempPool, XML_T('=')))
- return 0;
- len = dtd.defaultPrefix.binding->uriLen;
+ return NULL;
+ len = dtd->defaultPrefix.binding->uriLen;
if (namespaceSeparator != XML_T('\0'))
len--;
for (i = 0; i < len; i++)
- if (!poolAppendChar(&tempPool, dtd.defaultPrefix.binding->uri[i]))
- return 0;
- needSep = 1;
+ if (!poolAppendChar(&tempPool, dtd->defaultPrefix.binding->uri[i]))
+ return NULL;
+ needSep = XML_TRUE;
}
- hashTableIterInit(&iter, &(dtd.prefixes));
+ hashTableIterInit(&iter, &(dtd->prefixes));
for (;;) {
int i;
int len;
@@ -3857,23 +4838,23 @@ const XML_Char *getContext(XML_Parser parser)
if (!prefix->binding)
continue;
if (needSep && !poolAppendChar(&tempPool, CONTEXT_SEP))
- return 0;
+ return NULL;
for (s = prefix->name; *s; s++)
if (!poolAppendChar(&tempPool, *s))
- return 0;
+ return NULL;
if (!poolAppendChar(&tempPool, XML_T('=')))
- return 0;
+ return NULL;
len = prefix->binding->uriLen;
if (namespaceSeparator != XML_T('\0'))
len--;
for (i = 0; i < len; i++)
if (!poolAppendChar(&tempPool, prefix->binding->uri[i]))
- return 0;
- needSep = 1;
+ return NULL;
+ needSep = XML_TRUE;
}
- hashTableIterInit(&iter, &(dtd.generalEntities));
+ hashTableIterInit(&iter, &(dtd->generalEntities));
for (;;) {
const XML_Char *s;
ENTITY *e = (ENTITY *)hashTableIterNext(&iter);
@@ -3882,77 +4863,81 @@ const XML_Char *getContext(XML_Parser parser)
if (!e->open)
continue;
if (needSep && !poolAppendChar(&tempPool, CONTEXT_SEP))
- return 0;
+ return NULL;
for (s = e->name; *s; s++)
if (!poolAppendChar(&tempPool, *s))
return 0;
- needSep = 1;
+ needSep = XML_TRUE;
}
if (!poolAppendChar(&tempPool, XML_T('\0')))
- return 0;
+ return NULL;
return tempPool.start;
}
-static
-int setContext(XML_Parser parser, const XML_Char *context)
+static XML_Bool
+setContext(XML_Parser parser, const XML_Char *context)
{
+ DTD * const dtd = _dtd; /* save one level of indirection */
const XML_Char *s = context;
while (*context != XML_T('\0')) {
if (*s == CONTEXT_SEP || *s == XML_T('\0')) {
ENTITY *e;
if (!poolAppendChar(&tempPool, XML_T('\0')))
- return 0;
- e = (ENTITY *)lookup(&dtd.generalEntities, poolStart(&tempPool), 0);
+ return XML_FALSE;
+ e = (ENTITY *)lookup(&dtd->generalEntities, poolStart(&tempPool), 0);
if (e)
- e->open = 1;
+ e->open = XML_TRUE;
if (*s != XML_T('\0'))
- s++;
+ s++;
context = s;
poolDiscard(&tempPool);
}
- else if (*s == '=') {
+ else if (*s == XML_T('=')) {
PREFIX *prefix;
if (poolLength(&tempPool) == 0)
- prefix = &dtd.defaultPrefix;
+ prefix = &dtd->defaultPrefix;
else {
- if (!poolAppendChar(&tempPool, XML_T('\0')))
- return 0;
- prefix = (PREFIX *)lookup(&dtd.prefixes, poolStart(&tempPool), sizeof(PREFIX));
- if (!prefix)
- return 0;
+ if (!poolAppendChar(&tempPool, XML_T('\0')))
+ return XML_FALSE;
+ prefix = (PREFIX *)lookup(&dtd->prefixes, poolStart(&tempPool),
+ sizeof(PREFIX));
+ if (!prefix)
+ return XML_FALSE;
if (prefix->name == poolStart(&tempPool)) {
- prefix->name = poolCopyString(&dtd.pool, prefix->name);
- if (!prefix->name)
- return 0;
- }
- poolDiscard(&tempPool);
+ prefix->name = poolCopyString(&dtd->pool, prefix->name);
+ if (!prefix->name)
+ return XML_FALSE;
+ }
+ poolDiscard(&tempPool);
}
- for (context = s + 1; *context != CONTEXT_SEP && *context != XML_T('\0'); context++)
+ for (context = s + 1;
+ *context != CONTEXT_SEP && *context != XML_T('\0');
+ context++)
if (!poolAppendChar(&tempPool, *context))
- return 0;
+ return XML_FALSE;
if (!poolAppendChar(&tempPool, XML_T('\0')))
- return 0;
- if (!addBinding(parser, prefix, 0, poolStart(&tempPool), &inheritedBindings))
- return 0;
+ return XML_FALSE;
+ if (addBinding(parser, prefix, 0, poolStart(&tempPool),
+ &inheritedBindings) != XML_ERROR_NONE)
+ return XML_FALSE;
poolDiscard(&tempPool);
if (*context != XML_T('\0'))
- ++context;
+ ++context;
s = context;
}
else {
if (!poolAppendChar(&tempPool, *s))
- return 0;
+ return XML_FALSE;
s++;
}
}
- return 1;
+ return XML_TRUE;
}
-
-static
-void normalizePublicId(XML_Char *publicId)
+static void FASTCALL
+normalizePublicId(XML_Char *publicId)
{
XML_Char *p = publicId;
XML_Char *s;
@@ -3962,7 +4947,7 @@ void normalizePublicId(XML_Char *publicId)
case 0xD:
case 0xA:
if (p != publicId && p[-1] != 0x20)
- *p++ = 0x20;
+ *p++ = 0x20;
break;
default:
*p++ = *s;
@@ -3973,46 +4958,89 @@ void normalizePublicId(XML_Char *publicId)
*p = XML_T('\0');
}
-static int dtdInit(DTD *p, XML_Parser parser)
+static DTD *
+dtdCreate(const XML_Memory_Handling_Suite *ms)
{
- XML_Memory_Handling_Suite *ms = &((Parser *) parser)->m_mem;
+ DTD *p = (DTD *)ms->malloc_fcn(sizeof(DTD));
+ if (p == NULL)
+ return p;
poolInit(&(p->pool), ms);
+#ifdef XML_DTD
+ poolInit(&(p->entityValuePool), ms);
+#endif /* XML_DTD */
hashTableInit(&(p->generalEntities), ms);
hashTableInit(&(p->elementTypes), ms);
hashTableInit(&(p->attributeIds), ms);
hashTableInit(&(p->prefixes), ms);
- p->complete = 1;
- p->standalone = 0;
#ifdef XML_DTD
+ p->paramEntityRead = XML_FALSE;
hashTableInit(&(p->paramEntities), ms);
#endif /* XML_DTD */
- p->defaultPrefix.name = 0;
- p->defaultPrefix.binding = 0;
+ p->defaultPrefix.name = NULL;
+ p->defaultPrefix.binding = NULL;
- p->in_eldecl = 0;
- p->scaffIndex = 0;
+ p->in_eldecl = XML_FALSE;
+ p->scaffIndex = NULL;
+ p->scaffold = NULL;
p->scaffLevel = 0;
- p->scaffold = 0;
- p->contentStringLen = 0;
p->scaffSize = 0;
p->scaffCount = 0;
+ p->contentStringLen = 0;
- return 1;
+ p->keepProcessing = XML_TRUE;
+ p->hasParamEntityRefs = XML_FALSE;
+ p->standalone = XML_FALSE;
+ return p;
}
+static void
+dtdReset(DTD *p, const XML_Memory_Handling_Suite *ms)
+{
+ HASH_TABLE_ITER iter;
+ hashTableIterInit(&iter, &(p->elementTypes));
+ for (;;) {
+ ELEMENT_TYPE *e = (ELEMENT_TYPE *)hashTableIterNext(&iter);
+ if (!e)
+ break;
+ if (e->allocDefaultAtts != 0)
+ ms->free_fcn(e->defaultAtts);
+ }
+ hashTableClear(&(p->generalEntities));
#ifdef XML_DTD
+ p->paramEntityRead = XML_FALSE;
+ hashTableClear(&(p->paramEntities));
+#endif /* XML_DTD */
+ hashTableClear(&(p->elementTypes));
+ hashTableClear(&(p->attributeIds));
+ hashTableClear(&(p->prefixes));
+ poolClear(&(p->pool));
+#ifdef XML_DTD
+ poolClear(&(p->entityValuePool));
+#endif /* XML_DTD */
+ p->defaultPrefix.name = NULL;
+ p->defaultPrefix.binding = NULL;
-static void dtdSwap(DTD *p1, DTD *p2)
-{
- DTD tem;
- memcpy(&tem, p1, sizeof(DTD));
- memcpy(p1, p2, sizeof(DTD));
- memcpy(p2, &tem, sizeof(DTD));
-}
+ p->in_eldecl = XML_FALSE;
+ if (p->scaffIndex) {
+ ms->free_fcn(p->scaffIndex);
+ p->scaffIndex = NULL;
+ }
+ if (p->scaffold) {
+ ms->free_fcn(p->scaffold);
+ p->scaffold = NULL;
+ }
+ p->scaffLevel = 0;
+ p->scaffSize = 0;
+ p->scaffCount = 0;
+ p->contentStringLen = 0;
-#endif /* XML_DTD */
+ p->keepProcessing = XML_TRUE;
+ p->hasParamEntityRefs = XML_FALSE;
+ p->standalone = XML_FALSE;
+}
-static void dtdDestroy(DTD *p, XML_Parser parser)
+static void
+dtdDestroy(DTD *p, XML_Bool isDocEntity, const XML_Memory_Handling_Suite *ms)
{
HASH_TABLE_ITER iter;
hashTableIterInit(&iter, &(p->elementTypes));
@@ -4021,7 +5049,7 @@ static void dtdDestroy(DTD *p, XML_Parser parser)
if (!e)
break;
if (e->allocDefaultAtts != 0)
- FREE(e->defaultAtts);
+ ms->free_fcn(e->defaultAtts);
}
hashTableDestroy(&(p->generalEntities));
#ifdef XML_DTD
@@ -4031,16 +5059,23 @@ static void dtdDestroy(DTD *p, XML_Parser parser)
hashTableDestroy(&(p->attributeIds));
hashTableDestroy(&(p->prefixes));
poolDestroy(&(p->pool));
- if (p->scaffIndex)
- FREE(p->scaffIndex);
- if (p->scaffold)
- FREE(p->scaffold);
+#ifdef XML_DTD
+ poolDestroy(&(p->entityValuePool));
+#endif /* XML_DTD */
+ if (isDocEntity) {
+ if (p->scaffIndex)
+ ms->free_fcn(p->scaffIndex);
+ if (p->scaffold)
+ ms->free_fcn(p->scaffold);
+ }
+ ms->free_fcn(p);
}
-/* Do a deep copy of the DTD. Return 0 for out of memory; non-zero otherwise.
-The new DTD has already been initialized. */
-
-static int dtdCopy(DTD *newDtd, const DTD *oldDtd, XML_Parser parser)
+/* Do a deep copy of the DTD. Return 0 for out of memory, non-zero otherwise.
+ The new DTD has already been initialized.
+*/
+static int
+dtdCopy(DTD *newDtd, const DTD *oldDtd, const XML_Memory_Handling_Suite *ms)
{
HASH_TABLE_ITER iter;
@@ -4077,16 +5112,18 @@ static int dtdCopy(DTD *newDtd, const DTD *oldDtd, XML_Parser parser)
if (!name)
return 0;
++name;
- newA = (ATTRIBUTE_ID *)lookup(&(newDtd->attributeIds), name, sizeof(ATTRIBUTE_ID));
+ newA = (ATTRIBUTE_ID *)lookup(&(newDtd->attributeIds), name,
+ sizeof(ATTRIBUTE_ID));
if (!newA)
return 0;
newA->maybeTokenized = oldA->maybeTokenized;
if (oldA->prefix) {
newA->xmlns = oldA->xmlns;
if (oldA->prefix == &oldDtd->defaultPrefix)
- newA->prefix = &newDtd->defaultPrefix;
+ newA->prefix = &newDtd->defaultPrefix;
else
- newA->prefix = (PREFIX *)lookup(&(newDtd->prefixes), oldA->prefix->name, 0);
+ newA->prefix = (PREFIX *)lookup(&(newDtd->prefixes),
+ oldA->prefix->name, 0);
}
}
@@ -4104,46 +5141,56 @@ static int dtdCopy(DTD *newDtd, const DTD *oldDtd, XML_Parser parser)
name = poolCopyString(&(newDtd->pool), oldE->name);
if (!name)
return 0;
- newE = (ELEMENT_TYPE *)lookup(&(newDtd->elementTypes), name, sizeof(ELEMENT_TYPE));
+ newE = (ELEMENT_TYPE *)lookup(&(newDtd->elementTypes), name,
+ sizeof(ELEMENT_TYPE));
if (!newE)
return 0;
if (oldE->nDefaultAtts) {
- newE->defaultAtts = (DEFAULT_ATTRIBUTE *)MALLOC(oldE->nDefaultAtts * sizeof(DEFAULT_ATTRIBUTE));
- if (!newE->defaultAtts)
- return 0;
+ newE->defaultAtts = (DEFAULT_ATTRIBUTE *)
+ ms->malloc_fcn(oldE->nDefaultAtts * sizeof(DEFAULT_ATTRIBUTE));
+ if (!newE->defaultAtts) {
+ ms->free_fcn(newE);
+ return 0;
+ }
}
if (oldE->idAtt)
- newE->idAtt = (ATTRIBUTE_ID *)lookup(&(newDtd->attributeIds), oldE->idAtt->name, 0);
+ newE->idAtt = (ATTRIBUTE_ID *)
+ lookup(&(newDtd->attributeIds), oldE->idAtt->name, 0);
newE->allocDefaultAtts = newE->nDefaultAtts = oldE->nDefaultAtts;
if (oldE->prefix)
- newE->prefix = (PREFIX *)lookup(&(newDtd->prefixes), oldE->prefix->name, 0);
+ newE->prefix = (PREFIX *)lookup(&(newDtd->prefixes),
+ oldE->prefix->name, 0);
for (i = 0; i < newE->nDefaultAtts; i++) {
- newE->defaultAtts[i].id = (ATTRIBUTE_ID *)lookup(&(newDtd->attributeIds), oldE->defaultAtts[i].id->name, 0);
+ newE->defaultAtts[i].id = (ATTRIBUTE_ID *)
+ lookup(&(newDtd->attributeIds), oldE->defaultAtts[i].id->name, 0);
newE->defaultAtts[i].isCdata = oldE->defaultAtts[i].isCdata;
if (oldE->defaultAtts[i].value) {
- newE->defaultAtts[i].value = poolCopyString(&(newDtd->pool), oldE->defaultAtts[i].value);
- if (!newE->defaultAtts[i].value)
- return 0;
+ newE->defaultAtts[i].value
+ = poolCopyString(&(newDtd->pool), oldE->defaultAtts[i].value);
+ if (!newE->defaultAtts[i].value)
+ return 0;
}
else
- newE->defaultAtts[i].value = 0;
+ newE->defaultAtts[i].value = NULL;
}
}
/* Copy the entity tables. */
if (!copyEntityTable(&(newDtd->generalEntities),
- &(newDtd->pool),
- &(oldDtd->generalEntities), parser))
+ &(newDtd->pool),
+ &(oldDtd->generalEntities)))
return 0;
#ifdef XML_DTD
if (!copyEntityTable(&(newDtd->paramEntities),
- &(newDtd->pool),
- &(oldDtd->paramEntities), parser))
+ &(newDtd->pool),
+ &(oldDtd->paramEntities)))
return 0;
+ newDtd->paramEntityRead = oldDtd->paramEntityRead;
#endif /* XML_DTD */
- newDtd->complete = oldDtd->complete;
+ newDtd->keepProcessing = oldDtd->keepProcessing;
+ newDtd->hasParamEntityRefs = oldDtd->hasParamEntityRefs;
newDtd->standalone = oldDtd->standalone;
/* Don't want deep copying for scaffolding */
@@ -4157,14 +5204,14 @@ static int dtdCopy(DTD *newDtd, const DTD *oldDtd, XML_Parser parser)
return 1;
} /* End dtdCopy */
-static int copyEntityTable(HASH_TABLE *newTable,
- STRING_POOL *newPool,
- const HASH_TABLE *oldTable,
- XML_Parser parser)
+static int
+copyEntityTable(HASH_TABLE *newTable,
+ STRING_POOL *newPool,
+ const HASH_TABLE *oldTable)
{
HASH_TABLE_ITER iter;
- const XML_Char *cachedOldBase = 0;
- const XML_Char *cachedNewBase = 0;
+ const XML_Char *cachedOldBase = NULL;
+ const XML_Char *cachedNewBase = NULL;
hashTableIterInit(&iter, oldTable);
@@ -4183,41 +5230,50 @@ static int copyEntityTable(HASH_TABLE *newTable,
if (oldE->systemId) {
const XML_Char *tem = poolCopyString(newPool, oldE->systemId);
if (!tem)
- return 0;
+ return 0;
newE->systemId = tem;
if (oldE->base) {
- if (oldE->base == cachedOldBase)
- newE->base = cachedNewBase;
- else {
- cachedOldBase = oldE->base;
- tem = poolCopyString(newPool, cachedOldBase);
- if (!tem)
- return 0;
- cachedNewBase = newE->base = tem;
- }
+ if (oldE->base == cachedOldBase)
+ newE->base = cachedNewBase;
+ else {
+ cachedOldBase = oldE->base;
+ tem = poolCopyString(newPool, cachedOldBase);
+ if (!tem)
+ return 0;
+ cachedNewBase = newE->base = tem;
+ }
+ }
+ if (oldE->publicId) {
+ tem = poolCopyString(newPool, oldE->publicId);
+ if (!tem)
+ return 0;
+ newE->publicId = tem;
}
}
else {
- const XML_Char *tem = poolCopyStringN(newPool, oldE->textPtr, oldE->textLen);
+ const XML_Char *tem = poolCopyStringN(newPool, oldE->textPtr,
+ oldE->textLen);
if (!tem)
- return 0;
+ return 0;
newE->textPtr = tem;
newE->textLen = oldE->textLen;
}
if (oldE->notation) {
const XML_Char *tem = poolCopyString(newPool, oldE->notation);
if (!tem)
- return 0;
+ return 0;
newE->notation = tem;
}
+ newE->is_param = oldE->is_param;
+ newE->is_internal = oldE->is_internal;
}
return 1;
}
#define INIT_SIZE 64
-static
-int keyeq(KEY s1, KEY s2)
+static int FASTCALL
+keyeq(KEY s1, KEY s2)
{
for (; *s1 == *s2; s1++, s2++)
if (*s1 == 0)
@@ -4225,8 +5281,8 @@ int keyeq(KEY s1, KEY s2)
return 0;
}
-static
-unsigned long hash(KEY s)
+static unsigned long FASTCALL
+hash(KEY s)
{
unsigned long h = 0;
while (*s)
@@ -4234,19 +5290,19 @@ unsigned long hash(KEY s)
return h;
}
-static
-NAMED *lookup(HASH_TABLE *table, KEY name, size_t createSize)
+static NAMED *
+lookup(HASH_TABLE *table, KEY name, size_t createSize)
{
size_t i;
if (table->size == 0) {
size_t tsize;
if (!createSize)
- return 0;
+ return NULL;
tsize = INIT_SIZE * sizeof(NAMED *);
- table->v = table->mem->malloc_fcn(tsize);
+ table->v = (NAMED **)table->mem->malloc_fcn(tsize);
if (!table->v)
- return 0;
+ return NULL;
memset(table->v, 0, tsize);
table->size = INIT_SIZE;
table->usedLim = INIT_SIZE / 2;
@@ -4258,48 +5314,63 @@ NAMED *lookup(HASH_TABLE *table, KEY name, size_t createSize)
table->v[i];
i == 0 ? i = table->size - 1 : --i) {
if (keyeq(name, table->v[i]->name))
- return table->v[i];
+ return table->v[i];
}
if (!createSize)
- return 0;
+ return NULL;
if (table->used == table->usedLim) {
/* check for overflow */
size_t newSize = table->size * 2;
size_t tsize = newSize * sizeof(NAMED *);
- NAMED **newV = table->mem->malloc_fcn(tsize);
+ NAMED **newV = (NAMED **)table->mem->malloc_fcn(tsize);
if (!newV)
- return 0;
+ return NULL;
memset(newV, 0, tsize);
for (i = 0; i < table->size; i++)
- if (table->v[i]) {
- size_t j;
- for (j = hash(table->v[i]->name) & (newSize - 1);
- newV[j];
- j == 0 ? j = newSize - 1 : --j)
- ;
- newV[j] = table->v[i];
- }
+ if (table->v[i]) {
+ size_t j;
+ for (j = hash(table->v[i]->name) & (newSize - 1);
+ newV[j];
+ j == 0 ? j = newSize - 1 : --j)
+ ;
+ newV[j] = table->v[i];
+ }
table->mem->free_fcn(table->v);
table->v = newV;
table->size = newSize;
table->usedLim = newSize/2;
for (i = h & (table->size - 1);
- table->v[i];
- i == 0 ? i = table->size - 1 : --i)
- ;
+ table->v[i];
+ i == 0 ? i = table->size - 1 : --i)
+ ;
}
}
- table->v[i] = table->mem->malloc_fcn(createSize);
+ table->v[i] = (NAMED *)table->mem->malloc_fcn(createSize);
if (!table->v[i])
- return 0;
+ return NULL;
memset(table->v[i], 0, createSize);
table->v[i]->name = name;
(table->used)++;
return table->v[i];
}
-static
-void hashTableDestroy(HASH_TABLE *table)
+static void FASTCALL
+hashTableClear(HASH_TABLE *table)
+{
+ size_t i;
+ for (i = 0; i < table->size; i++) {
+ NAMED *p = table->v[i];
+ if (p) {
+ table->mem->free_fcn(p);
+ table->v[i] = NULL;
+ }
+ }
+ table->usedLim = table->size / 2;
+ table->used = 0;
+}
+
+static void FASTCALL
+hashTableDestroy(HASH_TABLE *table)
{
size_t i;
for (i = 0; i < table->size; i++) {
@@ -4311,48 +5382,47 @@ void hashTableDestroy(HASH_TABLE *table)
table->mem->free_fcn(table->v);
}
-static
-void hashTableInit(HASH_TABLE *p, XML_Memory_Handling_Suite *ms)
+static void FASTCALL
+hashTableInit(HASH_TABLE *p, const XML_Memory_Handling_Suite *ms)
{
p->size = 0;
p->usedLim = 0;
p->used = 0;
- p->v = 0;
+ p->v = NULL;
p->mem = ms;
}
-static
-void hashTableIterInit(HASH_TABLE_ITER *iter, const HASH_TABLE *table)
+static void FASTCALL
+hashTableIterInit(HASH_TABLE_ITER *iter, const HASH_TABLE *table)
{
iter->p = table->v;
iter->end = iter->p + table->size;
}
-static
-NAMED *hashTableIterNext(HASH_TABLE_ITER *iter)
+static NAMED * FASTCALL
+hashTableIterNext(HASH_TABLE_ITER *iter)
{
while (iter->p != iter->end) {
NAMED *tem = *(iter->p)++;
if (tem)
return tem;
}
- return 0;
+ return NULL;
}
-
-static
-void poolInit(STRING_POOL *pool, XML_Memory_Handling_Suite *ms)
+static void FASTCALL
+poolInit(STRING_POOL *pool, const XML_Memory_Handling_Suite *ms)
{
- pool->blocks = 0;
- pool->freeBlocks = 0;
- pool->start = 0;
- pool->ptr = 0;
- pool->end = 0;
+ pool->blocks = NULL;
+ pool->freeBlocks = NULL;
+ pool->start = NULL;
+ pool->ptr = NULL;
+ pool->end = NULL;
pool->mem = ms;
}
-static
-void poolClear(STRING_POOL *pool)
+static void FASTCALL
+poolClear(STRING_POOL *pool)
{
if (!pool->freeBlocks)
pool->freeBlocks = pool->blocks;
@@ -4365,14 +5435,14 @@ void poolClear(STRING_POOL *pool)
p = tem;
}
}
- pool->blocks = 0;
- pool->start = 0;
- pool->ptr = 0;
- pool->end = 0;
+ pool->blocks = NULL;
+ pool->start = NULL;
+ pool->ptr = NULL;
+ pool->end = NULL;
}
-static
-void poolDestroy(STRING_POOL *pool)
+static void FASTCALL
+poolDestroy(STRING_POOL *pool)
{
BLOCK *p = pool->blocks;
while (p) {
@@ -4380,113 +5450,113 @@ void poolDestroy(STRING_POOL *pool)
pool->mem->free_fcn(p);
p = tem;
}
- pool->blocks = 0;
p = pool->freeBlocks;
while (p) {
BLOCK *tem = p->next;
pool->mem->free_fcn(p);
p = tem;
}
- pool->freeBlocks = 0;
- pool->ptr = 0;
- pool->start = 0;
- pool->end = 0;
}
-static
-XML_Char *poolAppend(STRING_POOL *pool, const ENCODING *enc,
- const char *ptr, const char *end)
+static XML_Char *
+poolAppend(STRING_POOL *pool, const ENCODING *enc,
+ const char *ptr, const char *end)
{
if (!pool->ptr && !poolGrow(pool))
- return 0;
+ return NULL;
for (;;) {
XmlConvert(enc, &ptr, end, (ICHAR **)&(pool->ptr), (ICHAR *)pool->end);
if (ptr == end)
break;
if (!poolGrow(pool))
- return 0;
+ return NULL;
}
return pool->start;
}
-static const XML_Char *poolCopyString(STRING_POOL *pool, const XML_Char *s)
+static const XML_Char * FASTCALL
+poolCopyString(STRING_POOL *pool, const XML_Char *s)
{
do {
if (!poolAppendChar(pool, *s))
- return 0;
+ return NULL;
} while (*s++);
s = pool->start;
poolFinish(pool);
return s;
}
-static const XML_Char *poolCopyStringN(STRING_POOL *pool, const XML_Char *s, int n)
+static const XML_Char *
+poolCopyStringN(STRING_POOL *pool, const XML_Char *s, int n)
{
if (!pool->ptr && !poolGrow(pool))
- return 0;
+ return NULL;
for (; n > 0; --n, s++) {
if (!poolAppendChar(pool, *s))
- return 0;
-
+ return NULL;
}
s = pool->start;
poolFinish(pool);
return s;
}
-static
-const XML_Char *poolAppendString(STRING_POOL *pool, const XML_Char *s)
+static const XML_Char * FASTCALL
+poolAppendString(STRING_POOL *pool, const XML_Char *s)
{
while (*s) {
if (!poolAppendChar(pool, *s))
- return 0;
+ return NULL;
s++;
- }
+ }
return pool->start;
-} /* End poolAppendString */
+}
-static
-XML_Char *poolStoreString(STRING_POOL *pool, const ENCODING *enc,
- const char *ptr, const char *end)
+static XML_Char *
+poolStoreString(STRING_POOL *pool, const ENCODING *enc,
+ const char *ptr, const char *end)
{
if (!poolAppend(pool, enc, ptr, end))
- return 0;
+ return NULL;
if (pool->ptr == pool->end && !poolGrow(pool))
- return 0;
+ return NULL;
*(pool->ptr)++ = 0;
return pool->start;
}
-static
-int poolGrow(STRING_POOL *pool)
+static XML_Bool FASTCALL
+poolGrow(STRING_POOL *pool)
{
if (pool->freeBlocks) {
if (pool->start == 0) {
pool->blocks = pool->freeBlocks;
pool->freeBlocks = pool->freeBlocks->next;
- pool->blocks->next = 0;
+ pool->blocks->next = NULL;
pool->start = pool->blocks->s;
pool->end = pool->start + pool->blocks->size;
pool->ptr = pool->start;
- return 1;
+ return XML_TRUE;
}
if (pool->end - pool->start < pool->freeBlocks->size) {
BLOCK *tem = pool->freeBlocks->next;
pool->freeBlocks->next = pool->blocks;
pool->blocks = pool->freeBlocks;
pool->freeBlocks = tem;
- memcpy(pool->blocks->s, pool->start, (pool->end - pool->start) * sizeof(XML_Char));
+ memcpy(pool->blocks->s, pool->start,
+ (pool->end - pool->start) * sizeof(XML_Char));
pool->ptr = pool->blocks->s + (pool->ptr - pool->start);
pool->start = pool->blocks->s;
pool->end = pool->start + pool->blocks->size;
- return 1;
+ return XML_TRUE;
}
}
if (pool->blocks && pool->start == pool->blocks->s) {
int blockSize = (pool->end - pool->start)*2;
- pool->blocks = pool->mem->realloc_fcn(pool->blocks, offsetof(BLOCK, s) + blockSize * sizeof(XML_Char));
- if (!pool->blocks)
- return 0;
+ pool->blocks = (BLOCK *)
+ pool->mem->realloc_fcn(pool->blocks,
+ (offsetof(BLOCK, s)
+ + blockSize * sizeof(XML_Char)));
+ if (pool->blocks == NULL)
+ return XML_FALSE;
pool->blocks->size = blockSize;
pool->ptr = pool->blocks->s + (pool->ptr - pool->start);
pool->start = pool->blocks->s;
@@ -4499,139 +5569,151 @@ int poolGrow(STRING_POOL *pool)
blockSize = INIT_BLOCK_SIZE;
else
blockSize *= 2;
- tem = pool->mem->malloc_fcn(offsetof(BLOCK, s) + blockSize * sizeof(XML_Char));
+ tem = (BLOCK *)pool->mem->malloc_fcn(offsetof(BLOCK, s)
+ + blockSize * sizeof(XML_Char));
if (!tem)
- return 0;
+ return XML_FALSE;
tem->size = blockSize;
tem->next = pool->blocks;
pool->blocks = tem;
if (pool->ptr != pool->start)
- memcpy(tem->s, pool->start, (pool->ptr - pool->start) * sizeof(XML_Char));
+ memcpy(tem->s, pool->start,
+ (pool->ptr - pool->start) * sizeof(XML_Char));
pool->ptr = tem->s + (pool->ptr - pool->start);
pool->start = tem->s;
pool->end = tem->s + blockSize;
}
- return 1;
+ return XML_TRUE;
}
-static int
+static int FASTCALL
nextScaffoldPart(XML_Parser parser)
{
+ DTD * const dtd = _dtd; /* save one level of indirection */
CONTENT_SCAFFOLD * me;
int next;
- if (! dtd.scaffIndex) {
- dtd.scaffIndex = MALLOC(groupSize * sizeof(int));
- if (! dtd.scaffIndex)
+ if (!dtd->scaffIndex) {
+ dtd->scaffIndex = (int *)MALLOC(groupSize * sizeof(int));
+ if (!dtd->scaffIndex)
return -1;
- dtd.scaffIndex[0] = 0;
+ dtd->scaffIndex[0] = 0;
}
- if (dtd.scaffCount >= dtd.scaffSize) {
- if (dtd.scaffold) {
- dtd.scaffSize *= 2;
- dtd.scaffold = (CONTENT_SCAFFOLD *) REALLOC(dtd.scaffold,
- dtd.scaffSize * sizeof(CONTENT_SCAFFOLD));
+ if (dtd->scaffCount >= dtd->scaffSize) {
+ CONTENT_SCAFFOLD *temp;
+ if (dtd->scaffold) {
+ temp = (CONTENT_SCAFFOLD *)
+ REALLOC(dtd->scaffold, dtd->scaffSize * 2 * sizeof(CONTENT_SCAFFOLD));
+ if (temp == NULL)
+ return -1;
+ dtd->scaffSize *= 2;
}
else {
- dtd.scaffSize = 32;
- dtd.scaffold = (CONTENT_SCAFFOLD *) MALLOC(dtd.scaffSize * sizeof(CONTENT_SCAFFOLD));
+ temp = (CONTENT_SCAFFOLD *)MALLOC(INIT_SCAFFOLD_ELEMENTS
+ * sizeof(CONTENT_SCAFFOLD));
+ if (temp == NULL)
+ return -1;
+ dtd->scaffSize = INIT_SCAFFOLD_ELEMENTS;
}
- if (! dtd.scaffold)
- return -1;
+ dtd->scaffold = temp;
}
- next = dtd.scaffCount++;
- me = &dtd.scaffold[next];
- if (dtd.scaffLevel) {
- CONTENT_SCAFFOLD *parent = &dtd.scaffold[dtd.scaffIndex[dtd.scaffLevel - 1]];
+ next = dtd->scaffCount++;
+ me = &dtd->scaffold[next];
+ if (dtd->scaffLevel) {
+ CONTENT_SCAFFOLD *parent = &dtd->scaffold[dtd->scaffIndex[dtd->scaffLevel-1]];
if (parent->lastchild) {
- dtd.scaffold[parent->lastchild].nextsib = next;
+ dtd->scaffold[parent->lastchild].nextsib = next;
}
- if (! parent->childcnt)
+ if (!parent->childcnt)
parent->firstchild = next;
parent->lastchild = next;
parent->childcnt++;
}
me->firstchild = me->lastchild = me->childcnt = me->nextsib = 0;
return next;
-} /* End nextScaffoldPart */
+}
static void
-build_node (XML_Parser parser,
- int src_node,
- XML_Content *dest,
- XML_Content **contpos,
- char **strpos)
+build_node(XML_Parser parser,
+ int src_node,
+ XML_Content *dest,
+ XML_Content **contpos,
+ XML_Char **strpos)
{
- dest->type = dtd.scaffold[src_node].type;
- dest->quant = dtd.scaffold[src_node].quant;
+ DTD * const dtd = _dtd; /* save one level of indirection */
+ dest->type = dtd->scaffold[src_node].type;
+ dest->quant = dtd->scaffold[src_node].quant;
if (dest->type == XML_CTYPE_NAME) {
- const char *src;
+ const XML_Char *src;
dest->name = *strpos;
- src = dtd.scaffold[src_node].name;
+ src = dtd->scaffold[src_node].name;
for (;;) {
*(*strpos)++ = *src;
- if (! *src)
- break;
+ if (!*src)
+ break;
src++;
}
dest->numchildren = 0;
- dest->children = 0;
+ dest->children = NULL;
}
else {
unsigned int i;
int cn;
- dest->numchildren = dtd.scaffold[src_node].childcnt;
+ dest->numchildren = dtd->scaffold[src_node].childcnt;
dest->children = *contpos;
*contpos += dest->numchildren;
- for (i = 0, cn = dtd.scaffold[src_node].firstchild;
- i < dest->numchildren;
- i++, cn = dtd.scaffold[cn].nextsib) {
+ for (i = 0, cn = dtd->scaffold[src_node].firstchild;
+ i < dest->numchildren;
+ i++, cn = dtd->scaffold[cn].nextsib) {
build_node(parser, cn, &(dest->children[i]), contpos, strpos);
}
- dest->name = 0;
+ dest->name = NULL;
}
-} /* End build_node */
+}
static XML_Content *
build_model (XML_Parser parser)
{
+ DTD * const dtd = _dtd; /* save one level of indirection */
XML_Content *ret;
XML_Content *cpos;
- char * str;
- int allocsize = dtd.scaffCount * sizeof(XML_Content) + dtd.contentStringLen;
-
- ret = MALLOC(allocsize);
- if (! ret)
- return 0;
+ XML_Char * str;
+ int allocsize = (dtd->scaffCount * sizeof(XML_Content)
+ + (dtd->contentStringLen * sizeof(XML_Char)));
+
+ ret = (XML_Content *)MALLOC(allocsize);
+ if (!ret)
+ return NULL;
- str = (char *) (&ret[dtd.scaffCount]);
+ str = (XML_Char *) (&ret[dtd->scaffCount]);
cpos = &ret[1];
build_node(parser, 0, ret, &cpos, &str);
return ret;
-} /* End build_model */
+}
static ELEMENT_TYPE *
getElementType(XML_Parser parser,
- const ENCODING *enc,
- const char *ptr,
- const char *end)
+ const ENCODING *enc,
+ const char *ptr,
+ const char *end)
{
- const XML_Char *name = poolStoreString(&dtd.pool, enc, ptr, end);
+ DTD * const dtd = _dtd; /* save one level of indirection */
+ const XML_Char *name = poolStoreString(&dtd->pool, enc, ptr, end);
ELEMENT_TYPE *ret;
- if (! name)
- return 0;
- ret = (ELEMENT_TYPE *) lookup(&dtd.elementTypes, name, sizeof(ELEMENT_TYPE));
- if (! ret)
- return 0;
+ if (!name)
+ return NULL;
+ ret = (ELEMENT_TYPE *) lookup(&dtd->elementTypes, name, sizeof(ELEMENT_TYPE));
+ if (!ret)
+ return NULL;
if (ret->name != name)
- poolDiscard(&dtd.pool);
+ poolDiscard(&dtd->pool);
else {
- poolFinish(&dtd.pool);
+ poolFinish(&dtd->pool);
if (!setElementTypePrefix(parser, ret))
- return 0;
+ return NULL;
}
return ret;
-} /* End getElementType */
+}