From 6cf93fc0a1a7959987694c8f6ca1ec3e4ea79d13 Mon Sep 17 00:00:00 2001 From: "kvisco%ziplink.net" Date: Wed, 6 Sep 2000 07:22:09 +0000 Subject: [PATCH] Not part of regular build, a=leaf. Updated Expat to latest version. git-svn-id: svn://10.0.0.236/trunk@78253 18797224-902f-48f8-a5cc-f745e15eee43 --- .../source/xml/parser/xmlparse/hashtable.c | 56 +- .../source/xml/parser/xmlparse/hashtable.h | 26 +- .../source/xml/parser/xmlparse/xmlparse.c | 1171 +++++++++++++---- .../source/xml/parser/xmlparse/xmlparse.h | 140 +- .../source/xml/parser/xmltok/asciitab.h | 16 +- .../source/xml/parser/xmltok/dllmain.c | 17 +- .../source/xml/parser/xmltok/iasciitab.h | 16 +- .../source/xml/parser/xmltok/latin1tab.h | 14 +- .../source/xml/parser/xmltok/utf8tab.h | 14 +- .../source/xml/parser/xmltok/xmldef.h | 39 +- .../source/xml/parser/xmltok/xmlrole.c | 22 +- .../source/xml/parser/xmltok/xmlrole.h | 14 +- .../source/xml/parser/xmltok/xmltok.c | 862 ++++++++---- .../source/xml/parser/xmltok/xmltok.h | 49 +- .../source/xml/parser/xmltok/xmltok_impl.c | 1071 ++++++++------- .../source/xml/parser/xmltok/xmltok_impl.h | 15 +- 16 files changed, 2486 insertions(+), 1056 deletions(-) diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmlparse/hashtable.c b/mozilla/extensions/transformiix/source/xml/parser/xmlparse/hashtable.c index 27f271df8da..780a0610414 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmlparse/hashtable.c +++ b/mozilla/extensions/transformiix/source/xml/parser/xmlparse/hashtable.c @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in csompliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,39 +12,43 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): - Bob Miller, Oblix Inc. changed #define XML_UNICODE section + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ -#include -#include - #include "xmldef.h" -#include "hashtable.h" #ifdef XML_UNICODE_WCHAR_T -#define keycmp wcscmp -#else -#ifdef XML_UNICODE - static int keycmp(KEY a, KEY b) - { - for ( ; *a || *b; a++, b++) { - if (*a == *b) - continue; - return *b - *a; - } - return 0; - } -#else -#define keycmp strcmp +#ifndef XML_UNICODE +#define XML_UNICODE #endif -#endif +#endif + +#include "hashtable.h" #define INIT_SIZE 64 +static +int keyeq(KEY s1, KEY s2) +{ + for (; *s1 == *s2; s1++, s2++) + if (*s1 == 0) + return 1; + return 0; +} + static unsigned long hash(KEY s) { @@ -60,7 +64,7 @@ NAMED *lookup(HASH_TABLE *table, KEY name, size_t createSize) if (table->size == 0) { if (!createSize) return 0; - table->v = (NAMED**)calloc(INIT_SIZE, sizeof(NAMED *)); + table->v = calloc(INIT_SIZE, sizeof(NAMED *)); if (!table->v) return 0; table->size = INIT_SIZE; @@ -72,7 +76,7 @@ NAMED *lookup(HASH_TABLE *table, KEY name, size_t createSize) for (i = h & (table->size - 1); table->v[i]; i == 0 ? i = table->size - 1 : --i) { - if (keycmp(name, table->v[i]->name) == 0) + if (keyeq(name, table->v[i]->name)) return table->v[i]; } if (!createSize) @@ -80,7 +84,7 @@ NAMED *lookup(HASH_TABLE *table, KEY name, size_t createSize) if (table->used == table->usedLim) { /* check for overflow */ size_t newSize = table->size * 2; - NAMED **newV = (NAMED**)calloc(newSize, sizeof(NAMED *)); + NAMED **newV = calloc(newSize, sizeof(NAMED *)); if (!newV) return 0; for (i = 0; i < table->size; i++) @@ -102,7 +106,7 @@ NAMED *lookup(HASH_TABLE *table, KEY name, size_t createSize) ; } } - table->v[i] = (NAMED*)calloc(1, createSize); + table->v[i] = calloc(1, createSize); if (!table->v[i]) return 0; table->v[i]->name = name; diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmlparse/hashtable.h b/mozilla/extensions/transformiix/source/xml/parser/xmlparse/hashtable.h index bdb162b4fda..df8ab8a4c83 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmlparse/hashtable.h +++ b/mozilla/extensions/transformiix/source/xml/parser/xmlparse/hashtable.h @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,20 +12,38 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ #include #ifdef XML_UNICODE + +#ifdef XML_UNICODE_WCHAR_T +typedef const wchar_t *KEY; +#else /* not XML_UNICODE_WCHAR_T */ typedef const unsigned short *KEY; -#else +#endif /* not XML_UNICODE_WCHAR_T */ + +#else /* not XML_UNICODE */ + typedef const char *KEY; -#endif + +#endif /* not XML_UNICODE */ typedef struct { KEY name; diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmlparse/xmlparse.c b/mozilla/extensions/transformiix/source/xml/parser/xmlparse/xmlparse.c index f11f62c0e30..5bba88709a7 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmlparse/xmlparse.c +++ b/mozilla/extensions/transformiix/source/xml/parser/xmlparse/xmlparse.c @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,22 +12,30 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ -#include -#include -#include - #include "xmldef.h" +#include "xmlparse.h" #ifdef XML_UNICODE #define XML_ENCODE_MAX XML_UTF16_ENCODE_MAX #define XmlConvert XmlUtf16Convert #define XmlGetInternalEncoding XmlGetUtf16InternalEncoding +#define XmlGetInternalEncodingNS XmlGetUtf16InternalEncodingNS #define XmlEncode XmlUtf16Encode #define MUST_CONVERT(enc, s) (!(enc)->isUtf16 || (((unsigned long)s) & 1)) typedef unsigned short ICHAR; @@ -35,11 +43,24 @@ typedef unsigned short ICHAR; #define XML_ENCODE_MAX XML_UTF8_ENCODE_MAX #define XmlConvert XmlUtf8Convert #define XmlGetInternalEncoding XmlGetUtf8InternalEncoding +#define XmlGetInternalEncodingNS XmlGetUtf8InternalEncodingNS #define XmlEncode XmlUtf8Encode #define MUST_CONVERT(enc, s) (!(enc)->isUtf8) typedef char ICHAR; #endif + +#ifndef XML_NS + +#define XmlInitEncodingNS XmlInitEncoding +#define XmlInitUnknownEncodingNS XmlInitUnknownEncoding +#undef XmlGetInternalEncodingNS +#define XmlGetInternalEncodingNS XmlGetInternalEncoding +#define XmlParseXmlDeclNS XmlParseXmlDecl + +#endif + + #ifdef XML_UNICODE_WCHAR_T #define XML_T(x) L ## x #else @@ -49,7 +70,6 @@ typedef char ICHAR; /* 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)) -#include "xmlparse.h" #include "xmltok.h" #include "xmlrole.h" #include "hashtable.h" @@ -60,13 +80,37 @@ typedef char ICHAR; #define INIT_BLOCK_SIZE 1024 #define INIT_BUFFER_SIZE 1024 +#define EXPAND_SPARE 24 + +typedef struct binding { + struct prefix *prefix; + struct binding *nextTagBinding; + struct binding *prevPrefixBinding; + const struct attribute_id *attId; + XML_Char *uri; + int uriLen; + int uriAlloc; +} BINDING; + +typedef struct prefix { + const XML_Char *name; + BINDING *binding; +} PREFIX; + +typedef struct { + const XML_Char *str; + const XML_Char *localPart; + int uriLen; +} TAG_NAME; + typedef struct tag { struct tag *parent; const char *rawName; int rawNameLength; - const XML_Char *name; + TAG_NAME name; char *buf; char *bufEnd; + BINDING *bindings; } TAG; typedef struct { @@ -96,9 +140,11 @@ typedef struct { /* The XML_Char before the name is used to determine whether an attribute has been specified. */ -typedef struct { +typedef struct attribute_id { XML_Char *name; + PREFIX *prefix; char maybeTokenized; + char xmlns; } ATTRIBUTE_ID; typedef struct { @@ -109,6 +155,7 @@ typedef struct { typedef struct { const XML_Char *name; + PREFIX *prefix; int nDefaultAtts; int allocDefaultAtts; DEFAULT_ATTRIBUTE *defaultAtts; @@ -118,12 +165,21 @@ typedef struct { HASH_TABLE generalEntities; HASH_TABLE elementTypes; HASH_TABLE attributeIds; + HASH_TABLE prefixes; STRING_POOL pool; int complete; int standalone; const XML_Char *base; + PREFIX defaultPrefix; } DTD; +typedef struct open_internal_entity { + const char *internalEventPtr; + const char *internalEventEndPtr; + struct open_internal_entity *next; + ENTITY *entity; +} OPEN_INTERNAL_ENTITY; + typedef enum XML_Error Processor(XML_Parser parser, const char *start, const char *end, @@ -151,7 +207,10 @@ doContent(XML_Parser parser, int startTagLevel, const ENCODING *enc, 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); -static enum XML_Error storeAtts(XML_Parser parser, const ENCODING *, const XML_Char *tagName, const char *s); +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 int defineAttribute(ELEMENT_TYPE *type, ATTRIBUTE_ID *, int isCdata, const XML_Char *dfltValue); static enum XML_Error @@ -162,15 +221,18 @@ appendAttributeValue(XML_Parser parser, const ENCODING *, int isCdata, const cha 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 *); static enum XML_Error storeEntityValue(XML_Parser parser, const char *start, const char *end); static int 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); static void reportDefault(XML_Parser parser, const ENCODING *enc, const char *start, const char *end); -static const XML_Char *getOpenEntityNames(XML_Parser parser); -static int setOpenEntityNames(XML_Parser parser, const XML_Char *openEntityNames); +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 *); static void dtdDestroy(DTD *); @@ -200,112 +262,149 @@ static const XML_Char *poolCopyStringN(STRING_POOL *pool, const XML_Char *s, int typedef struct { /* The first member must be userData so that the XML_GetUserData macro works. */ - void *userData; - void *handlerArg; - char *buffer; + void *m_userData; + void *m_handlerArg; + char *m_buffer; /* first character to be parsed */ - const char *bufferPtr; + const char *m_bufferPtr; /* past last character to be parsed */ - char *bufferEnd; + char *m_bufferEnd; /* allocated end of buffer */ - const char *bufferLim; - long parseEndByteIndex; - const char *parseEndPtr; - XML_Char *dataBuf; - XML_Char *dataBufEnd; - XML_StartElementHandler startElementHandler; - XML_EndElementHandler endElementHandler; - XML_CharacterDataHandler characterDataHandler; - XML_ProcessingInstructionHandler processingInstructionHandler; - XML_DefaultHandler defaultHandler; - XML_UnparsedEntityDeclHandler unparsedEntityDeclHandler; - XML_NotationDeclHandler notationDeclHandler; - XML_ExternalEntityRefHandler externalEntityRefHandler; - XML_UnknownEncodingHandler unknownEncodingHandler; - const ENCODING *encoding; - INIT_ENCODING initEncoding; - const XML_Char *protocolEncodingName; - void *unknownEncodingMem; - void *unknownEncodingData; - void *unknownEncodingHandlerData; - void (*unknownEncodingRelease)(void *); - PROLOG_STATE prologState; - Processor *processor; - enum XML_Error errorCode; - const char *eventPtr; - const char *eventEndPtr; - const char *positionPtr; - int tagLevel; - ENTITY *declEntity; - const XML_Char *declNotationName; - const XML_Char *declNotationPublicId; - ELEMENT_TYPE *declElementType; - ATTRIBUTE_ID *declAttributeId; - char declAttributeIsCdata; - DTD dtd; - TAG *tagStack; - TAG *freeTagList; - int attsSize; - ATTRIBUTE *atts; - POSITION position; - STRING_POOL tempPool; - STRING_POOL temp2Pool; - char *groupConnector; - unsigned groupSize; - int hadExternalDoctype; + const char *m_bufferLim; + long m_parseEndByteIndex; + const char *m_parseEndPtr; + XML_Char *m_dataBuf; + XML_Char *m_dataBufEnd; + XML_StartElementHandler m_startElementHandler; + XML_EndElementHandler m_endElementHandler; + XML_CharacterDataHandler m_characterDataHandler; + XML_ProcessingInstructionHandler m_processingInstructionHandler; + XML_CommentHandler m_commentHandler; + XML_StartCdataSectionHandler m_startCdataSectionHandler; + XML_EndCdataSectionHandler m_endCdataSectionHandler; + XML_DefaultHandler m_defaultHandler; + XML_UnparsedEntityDeclHandler m_unparsedEntityDeclHandler; + XML_NotationDeclHandler m_notationDeclHandler; + XML_StartNamespaceDeclHandler m_startNamespaceDeclHandler; + XML_EndNamespaceDeclHandler m_endNamespaceDeclHandler; + XML_NotStandaloneHandler m_notStandaloneHandler; + XML_ExternalEntityRefHandler m_externalEntityRefHandler; + void *m_externalEntityRefHandlerArg; + XML_UnknownEncodingHandler m_unknownEncodingHandler; + const ENCODING *m_encoding; + INIT_ENCODING m_initEncoding; + const XML_Char *m_protocolEncodingName; + int m_ns; + void *m_unknownEncodingMem; + void *m_unknownEncodingData; + void *m_unknownEncodingHandlerData; + void (*m_unknownEncodingRelease)(void *); + PROLOG_STATE m_prologState; + Processor *m_processor; + enum XML_Error m_errorCode; + const char *m_eventPtr; + const char *m_eventEndPtr; + const char *m_positionPtr; + OPEN_INTERNAL_ENTITY *m_openInternalEntities; + int m_defaultExpandInternalEntities; + int m_tagLevel; + ENTITY *m_declEntity; + const XML_Char *m_declNotationName; + const XML_Char *m_declNotationPublicId; + ELEMENT_TYPE *m_declElementType; + ATTRIBUTE_ID *m_declAttributeId; + char m_declAttributeIsCdata; + DTD m_dtd; + TAG *m_tagStack; + TAG *m_freeTagList; + BINDING *m_inheritedBindings; + BINDING *m_freeBindingList; + int m_attsSize; + int m_nSpecifiedAtts; + ATTRIBUTE *m_atts; + POSITION m_position; + STRING_POOL m_tempPool; + STRING_POOL m_temp2Pool; + char *m_groupConnector; + unsigned m_groupSize; + int m_hadExternalDoctype; + XML_Char m_namespaceSeparator; } Parser; -#define userData (((Parser *)parser)->userData) -#define handlerArg (((Parser *)parser)->handlerArg) -#define startElementHandler (((Parser *)parser)->startElementHandler) -#define endElementHandler (((Parser *)parser)->endElementHandler) -#define characterDataHandler (((Parser *)parser)->characterDataHandler) -#define processingInstructionHandler (((Parser *)parser)->processingInstructionHandler) -#define defaultHandler (((Parser *)parser)->defaultHandler) -#define unparsedEntityDeclHandler (((Parser *)parser)->unparsedEntityDeclHandler) -#define notationDeclHandler (((Parser *)parser)->notationDeclHandler) -#define externalEntityRefHandler (((Parser *)parser)->externalEntityRefHandler) -#define unknownEncodingHandler (((Parser *)parser)->unknownEncodingHandler) -#define encoding (((Parser *)parser)->encoding) -#define initEncoding (((Parser *)parser)->initEncoding) -#define unknownEncodingMem (((Parser *)parser)->unknownEncodingMem) -#define unknownEncodingData (((Parser *)parser)->unknownEncodingData) +#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 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 unknownEncodingHandler (((Parser *)parser)->m_unknownEncodingHandler) +#define encoding (((Parser *)parser)->m_encoding) +#define initEncoding (((Parser *)parser)->m_initEncoding) +#define unknownEncodingMem (((Parser *)parser)->m_unknownEncodingMem) +#define unknownEncodingData (((Parser *)parser)->m_unknownEncodingData) #define unknownEncodingHandlerData \ - (((Parser *)parser)->unknownEncodingHandlerData) -#define unknownEncodingRelease (((Parser *)parser)->unknownEncodingRelease) -#define protocolEncodingName (((Parser *)parser)->protocolEncodingName) -#define prologState (((Parser *)parser)->prologState) -#define processor (((Parser *)parser)->processor) -#define errorCode (((Parser *)parser)->errorCode) -#define eventPtr (((Parser *)parser)->eventPtr) -#define eventEndPtr (((Parser *)parser)->eventEndPtr) -#define positionPtr (((Parser *)parser)->positionPtr) -#define position (((Parser *)parser)->position) -#define tagLevel (((Parser *)parser)->tagLevel) -#define buffer (((Parser *)parser)->buffer) -#define bufferPtr (((Parser *)parser)->bufferPtr) -#define bufferEnd (((Parser *)parser)->bufferEnd) -#define parseEndByteIndex (((Parser *)parser)->parseEndByteIndex) -#define parseEndPtr (((Parser *)parser)->parseEndPtr) -#define bufferLim (((Parser *)parser)->bufferLim) -#define dataBuf (((Parser *)parser)->dataBuf) -#define dataBufEnd (((Parser *)parser)->dataBufEnd) -#define dtd (((Parser *)parser)->dtd) -#define declEntity (((Parser *)parser)->declEntity) -#define declNotationName (((Parser *)parser)->declNotationName) -#define declNotationPublicId (((Parser *)parser)->declNotationPublicId) -#define declElementType (((Parser *)parser)->declElementType) -#define declAttributeId (((Parser *)parser)->declAttributeId) -#define declAttributeIsCdata (((Parser *)parser)->declAttributeIsCdata) -#define freeTagList (((Parser *)parser)->freeTagList) -#define tagStack (((Parser *)parser)->tagStack) -#define atts (((Parser *)parser)->atts) -#define attsSize (((Parser *)parser)->attsSize) -#define tempPool (((Parser *)parser)->tempPool) -#define temp2Pool (((Parser *)parser)->temp2Pool) -#define groupConnector (((Parser *)parser)->groupConnector) -#define groupSize (((Parser *)parser)->groupSize) -#define hadExternalDoctype (((Parser *)parser)->hadExternalDoctype) + (((Parser *)parser)->m_unknownEncodingHandlerData) +#define unknownEncodingRelease (((Parser *)parser)->m_unknownEncodingRelease) +#define protocolEncodingName (((Parser *)parser)->m_protocolEncodingName) +#define ns (((Parser *)parser)->m_ns) +#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 declEntity (((Parser *)parser)->m_declEntity) +#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 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 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) + +#ifdef _MSC_VER +#ifdef _DEBUG +Parser *asParser(XML_Parser parser) +{ + return parser; +} +#endif +#endif XML_Parser XML_ParserCreate(const XML_Char *encodingName) { @@ -320,10 +419,17 @@ XML_Parser XML_ParserCreate(const XML_Char *encodingName) endElementHandler = 0; characterDataHandler = 0; processingInstructionHandler = 0; + commentHandler = 0; + startCdataSectionHandler = 0; + endCdataSectionHandler = 0; defaultHandler = 0; unparsedEntityDeclHandler = 0; notationDeclHandler = 0; + startNamespaceDeclHandler = 0; + endNamespaceDeclHandler = 0; + notStandaloneHandler = 0; externalEntityRefHandler = 0; + externalEntityRefHandlerArg = parser; unknownEncodingHandler = 0; buffer = 0; bufferPtr = 0; @@ -341,11 +447,15 @@ XML_Parser XML_ParserCreate(const XML_Char *encodingName) eventPtr = 0; eventEndPtr = 0; positionPtr = 0; + openInternalEntities = 0; tagLevel = 0; tagStack = 0; freeTagList = 0; + freeBindingList = 0; + inheritedBindings = 0; attsSize = INIT_ATTS_SIZE; atts = malloc(attsSize * sizeof(ATTRIBUTE)); + nSpecifiedAtts = 0; dataBuf = malloc(INIT_DATA_BUF_SIZE * sizeof(XML_Char)); groupSize = 0; groupConnector = 0; @@ -354,6 +464,8 @@ XML_Parser XML_ParserCreate(const XML_Char *encodingName) unknownEncodingRelease = 0; unknownEncodingData = 0; unknownEncodingHandlerData = 0; + namespaceSeparator = '!'; + ns = 0; poolInit(&tempPool); poolInit(&temp2Pool); protocolEncodingName = encodingName ? poolCopyString(&tempPool, encodingName) : 0; @@ -367,8 +479,49 @@ XML_Parser XML_ParserCreate(const XML_Char *encodingName) return parser; } +XML_Parser XML_ParserCreateNS(const XML_Char *encodingName, XML_Char nsSep) +{ + 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') + }; + + XML_Parser parser = XML_ParserCreate(encodingName); + if (parser) { + XmlInitEncodingNS(&initEncoding, &encoding, 0); + ns = 1; + namespaceSeparator = nsSep; + } + if (!setContext(parser, implicitContext)) { + XML_ParserFree(parser); + return 0; + } + return parser; +} + +int XML_SetEncoding(XML_Parser parser, const XML_Char *encodingName) +{ + if (!encodingName) + protocolEncodingName = 0; + else { + protocolEncodingName = poolCopyString(&tempPool, encodingName); + if (!protocolEncodingName) + return 0; + } + return 1; +} + XML_Parser XML_ExternalEntityParserCreate(XML_Parser oldParser, - const XML_Char *openEntityNames, + const XML_Char *context, const XML_Char *encodingName) { XML_Parser parser = oldParser; @@ -377,20 +530,36 @@ XML_Parser XML_ExternalEntityParserCreate(XML_Parser oldParser, XML_EndElementHandler oldEndElementHandler = endElementHandler; XML_CharacterDataHandler oldCharacterDataHandler = characterDataHandler; XML_ProcessingInstructionHandler oldProcessingInstructionHandler = processingInstructionHandler; + XML_CommentHandler oldCommentHandler = commentHandler; + XML_StartCdataSectionHandler oldStartCdataSectionHandler = startCdataSectionHandler; + XML_EndCdataSectionHandler oldEndCdataSectionHandler = endCdataSectionHandler; XML_DefaultHandler oldDefaultHandler = defaultHandler; + XML_StartNamespaceDeclHandler oldStartNamespaceDeclHandler = startNamespaceDeclHandler; + XML_EndNamespaceDeclHandler oldEndNamespaceDeclHandler = endNamespaceDeclHandler; + XML_NotStandaloneHandler oldNotStandaloneHandler = notStandaloneHandler; XML_ExternalEntityRefHandler oldExternalEntityRefHandler = externalEntityRefHandler; XML_UnknownEncodingHandler oldUnknownEncodingHandler = unknownEncodingHandler; void *oldUserData = userData; void *oldHandlerArg = handlerArg; + int oldDefaultExpandInternalEntities = defaultExpandInternalEntities; + void *oldExternalEntityRefHandlerArg = externalEntityRefHandlerArg; - parser = XML_ParserCreate(encodingName); + parser = (ns + ? XML_ParserCreateNS(encodingName, namespaceSeparator) + : XML_ParserCreate(encodingName)); if (!parser) return 0; startElementHandler = oldStartElementHandler; endElementHandler = oldEndElementHandler; characterDataHandler = oldCharacterDataHandler; processingInstructionHandler = oldProcessingInstructionHandler; + commentHandler = oldCommentHandler; + startCdataSectionHandler = oldStartCdataSectionHandler; + endCdataSectionHandler = oldEndCdataSectionHandler; defaultHandler = oldDefaultHandler; + startNamespaceDeclHandler = oldStartNamespaceDeclHandler; + endNamespaceDeclHandler = oldEndNamespaceDeclHandler; + notStandaloneHandler = oldNotStandaloneHandler; externalEntityRefHandler = oldExternalEntityRefHandler; unknownEncodingHandler = oldUnknownEncodingHandler; userData = oldUserData; @@ -398,7 +567,10 @@ XML_Parser XML_ExternalEntityParserCreate(XML_Parser oldParser, handlerArg = userData; else handlerArg = parser; - if (!dtdCopy(&dtd, oldDtd) || !setOpenEntityNames(parser, openEntityNames)) { + if (oldExternalEntityRefHandlerArg != oldParser) + externalEntityRefHandlerArg = oldExternalEntityRefHandlerArg; + defaultExpandInternalEntities = oldDefaultExpandInternalEntities; + if (!dtdCopy(&dtd, oldDtd) || !setContext(parser, context)) { XML_ParserFree(parser); return 0; } @@ -406,6 +578,19 @@ XML_Parser XML_ExternalEntityParserCreate(XML_Parser oldParser, return parser; } +static +void destroyBindings(BINDING *bindings) +{ + for (;;) { + BINDING *b = bindings; + if (!b) + break; + bindings = b->nextTagBinding; + free(b->uri); + free(b); + } +} + void XML_ParserFree(XML_Parser parser) { for (;;) { @@ -419,8 +604,11 @@ void XML_ParserFree(XML_Parser parser) p = tagStack; tagStack = tagStack->parent; free(p->buf); + destroyBindings(p->bindings); free(p); } + destroyBindings(freeBindingList); + destroyBindings(inheritedBindings); poolDestroy(&tempPool); poolDestroy(&temp2Pool); dtdDestroy(&dtd); @@ -465,6 +653,11 @@ const XML_Char *XML_GetBase(XML_Parser parser) return dtd.base; } +int XML_GetSpecifiedAttributeCount(XML_Parser parser) +{ + return nSpecifiedAtts; +} + void XML_SetElementHandler(XML_Parser parser, XML_StartElementHandler start, XML_EndElementHandler end) @@ -485,10 +678,32 @@ void XML_SetProcessingInstructionHandler(XML_Parser parser, processingInstructionHandler = handler; } +void XML_SetCommentHandler(XML_Parser parser, + XML_CommentHandler handler) +{ + commentHandler = handler; +} + +void XML_SetCdataSectionHandler(XML_Parser parser, + XML_StartCdataSectionHandler start, + XML_EndCdataSectionHandler end) +{ + startCdataSectionHandler = start; + endCdataSectionHandler = end; +} + void XML_SetDefaultHandler(XML_Parser parser, XML_DefaultHandler handler) { defaultHandler = handler; + defaultExpandInternalEntities = 0; +} + +void XML_SetDefaultHandlerExpand(XML_Parser parser, + XML_DefaultHandler handler) +{ + defaultHandler = handler; + defaultExpandInternalEntities = 1; } void XML_SetUnparsedEntityDeclHandler(XML_Parser parser, @@ -503,12 +718,34 @@ void XML_SetNotationDeclHandler(XML_Parser parser, notationDeclHandler = handler; } +void XML_SetNamespaceDeclHandler(XML_Parser parser, + XML_StartNamespaceDeclHandler start, + XML_EndNamespaceDeclHandler end) +{ + startNamespaceDeclHandler = start; + endNamespaceDeclHandler = end; +} + +void XML_SetNotStandaloneHandler(XML_Parser parser, + XML_NotStandaloneHandler handler) +{ + notStandaloneHandler = handler; +} + void XML_SetExternalEntityRefHandler(XML_Parser parser, XML_ExternalEntityRefHandler handler) { externalEntityRefHandler = handler; } +void XML_SetExternalEntityRefHandlerArg(XML_Parser parser, void *arg) +{ + if (arg) + externalEntityRefHandlerArg = arg; + else + externalEntityRefHandlerArg = parser; +} + void XML_SetUnknownEncodingHandler(XML_Parser parser, XML_UnknownEncodingHandler handler, void *data) @@ -522,6 +759,7 @@ int XML_Parse(XML_Parser parser, const char *s, int len, int isFinal) if (len == 0) { if (!isFinal) return 1; + positionPtr = bufferPtr; errorCode = processor(parser, bufferPtr, parseEndPtr = bufferEnd, 0); if (errorCode == XML_ERROR_NONE) return 1; @@ -636,6 +874,13 @@ long XML_GetCurrentByteIndex(XML_Parser parser) return -1; } +int XML_GetCurrentByteCount(XML_Parser parser) +{ + if (eventEndPtr && eventPtr) + return eventEndPtr - eventPtr; + return 0; +} + int XML_GetCurrentLineNumber(XML_Parser parser) { if (eventPtr) { @@ -656,8 +901,15 @@ int XML_GetCurrentColumnNumber(XML_Parser parser) void XML_DefaultCurrent(XML_Parser parser) { - if (defaultHandler) - reportDefault(parser, encoding, eventPtr, eventEndPtr); + if (defaultHandler) { + if (openInternalEntities) + reportDefault(parser, + ns ? XmlGetInternalEncodingNS() : XmlGetInternalEncoding(), + openInternalEntities->internalEventPtr, + openInternalEntities->internalEventEndPtr); + else + reportDefault(parser, encoding, eventPtr, eventEndPtr); + } } const XML_LChar *XML_ErrorString(int code) @@ -684,7 +936,8 @@ const XML_LChar *XML_ErrorString(int code) 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("error in processing external entity reference"), + XML_T("document is not standalone") }; if (code > 0 && code < sizeof(message)/sizeof(message[0])) return message[code]; @@ -798,19 +1051,20 @@ doContent(XML_Parser parser, const char *end, const char **nextPtr) { - const ENCODING *internalEnc = XmlGetInternalEncoding(); - const char *dummy; + const ENCODING *internalEnc = ns ? XmlGetInternalEncodingNS() : XmlGetInternalEncoding(); const char **eventPP; const char **eventEndPP; if (enc == encoding) { eventPP = &eventPtr; - *eventPP = s; eventEndPP = &eventEndPtr; } - else - eventPP = eventEndPP = &dummy; + else { + eventPP = &(openInternalEntities->internalEventPtr); + eventEndPP = &(openInternalEntities->internalEventEndPtr); + } + *eventPP = s; for (;;) { - const char *next; + const char *next = s; /* XmlContentTok doesn't always set the last arg */ int tok = XmlContentTok(enc, s, end, &next); *eventEndPP = next; switch (tok) { @@ -821,7 +1075,7 @@ doContent(XML_Parser parser, } *eventEndPP = end; if (characterDataHandler) { - XML_Char c = XML_T('\n'); + XML_Char c = 0xA; characterDataHandler(handlerArg, &c, 1); } else if (defaultHandler) @@ -892,14 +1146,17 @@ doContent(XML_Parser parser, if (entity) { if (entity->textPtr) { enum XML_Error result; - if (defaultHandler) { + OPEN_INTERNAL_ENTITY openEntity; + if (defaultHandler && !defaultExpandInternalEntities) { reportDefault(parser, enc, s, next); break; } - /* Protect against the possibility that somebody sets - the defaultHandler from inside another handler. */ - *eventEndPP = *eventPP; entity->open = 1; + openEntity.next = openInternalEntities; + openInternalEntities = &openEntity; + openEntity.entity = entity; + openEntity.internalEventPtr = 0; + openEntity.internalEventEndPtr = 0; result = doContent(parser, tagLevel, internalEnc, @@ -907,17 +1164,22 @@ doContent(XML_Parser parser, (char *)(entity->textPtr + entity->textLen), 0); entity->open = 0; + openInternalEntities = openEntity.next; if (result) return result; } else if (externalEntityRefHandler) { - const XML_Char *openEntityNames; + const XML_Char *context; entity->open = 1; - openEntityNames = getOpenEntityNames(parser); + context = getContext(parser); entity->open = 0; - if (!openEntityNames) + if (!context) return XML_ERROR_NO_MEMORY; - if (!externalEntityRefHandler(parser, openEntityNames, dtd.base, entity->systemId, entity->publicId)) + if (!externalEntityRefHandler(externalEntityRefHandlerArg, + context, + dtd.base, + entity->systemId, + entity->publicId)) return XML_ERROR_EXTERNAL_ENTITY_HANDLING; poolDiscard(&tempPool); } @@ -928,7 +1190,7 @@ doContent(XML_Parser parser, } case XML_TOK_START_TAG_WITH_ATTS: if (!startElementHandler) { - enum XML_Error result = storeAtts(parser, enc, 0, s); + enum XML_Error result = storeAtts(parser, enc, s, 0, 0); if (result) return result; } @@ -949,12 +1211,16 @@ doContent(XML_Parser parser, 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) { - if (tag->rawNameLength > tag->bufEnd - tag->buf) { + /* 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); @@ -977,7 +1243,7 @@ doContent(XML_Parser parser, toPtr = (XML_Char *)(tag->buf + ROUND_UP(tag->rawNameLength, sizeof(XML_Char))); else toPtr = (XML_Char *)tag->buf; - tag->name = toPtr; + tag->name.str = toPtr; XmlConvert(enc, &fromPtr, rawNameEnd, (ICHAR **)&toPtr, (ICHAR *)tag->bufEnd - 1); @@ -992,14 +1258,14 @@ doContent(XML_Parser parser, tag->rawName = tag->buf; } *toPtr = XML_T('\0'); - result = storeAtts(parser, enc, tag->name, s); + result = storeAtts(parser, enc, s, &(tag->name), &(tag->bindings)); if (result) return result; - startElementHandler(handlerArg, tag->name, (const XML_Char **)atts); + startElementHandler(handlerArg, tag->name.str, (const XML_Char **)atts); poolClear(&tempPool); } else { - tag->name = 0; + tag->name.str = 0; if (defaultHandler) reportDefault(parser, enc, s, next); } @@ -1007,7 +1273,7 @@ doContent(XML_Parser parser, } case XML_TOK_EMPTY_ELEMENT_WITH_ATTS: if (!startElementHandler) { - enum XML_Error result = storeAtts(parser, enc, 0, s); + enum XML_Error result = storeAtts(parser, enc, s, 0, 0); if (result) return result; } @@ -1015,24 +1281,35 @@ doContent(XML_Parser parser, case XML_TOK_EMPTY_ELEMENT_NO_ATTS: if (startElementHandler || endElementHandler) { const char *rawName = s + enc->minBytesPerChar; - const XML_Char *name = poolStoreString(&tempPool, enc, rawName, - rawName - + XmlNameLength(enc, rawName)); - if (!name) + 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); - if (startElementHandler) { - enum XML_Error result = storeAtts(parser, enc, name, s); - if (result) - return result; - startElementHandler(handlerArg, name, (const XML_Char **)atts); - } + 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); + 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; + } } else if (defaultHandler) reportDefault(parser, enc, s, next); @@ -1057,20 +1334,26 @@ doContent(XML_Parser parser, return XML_ERROR_TAG_MISMATCH; } --tagLevel; - if (endElementHandler) { - if (tag->name) - endElementHandler(handlerArg, tag->name); - else { - const XML_Char *name = poolStoreString(&tempPool, enc, rawName, - rawName + len); - if (!name) - return XML_ERROR_NO_MEMORY; - endElementHandler(handlerArg, name); - poolClear(&tempPool); + 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); } @@ -1092,7 +1375,7 @@ doContent(XML_Parser parser, return XML_ERROR_MISPLACED_XML_PI; case XML_TOK_DATA_NEWLINE: if (characterDataHandler) { - XML_Char c = XML_T('\n'); + XML_Char c = 0xA; characterDataHandler(handlerArg, &c, 1); } else if (defaultHandler) @@ -1101,8 +1384,23 @@ doContent(XML_Parser parser, case XML_TOK_CDATA_SECT_OPEN: { enum XML_Error result; - if (characterDataHandler) + 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); +#endif else if (defaultHandler) reportDefault(parser, enc, s, next); result = doCdataSection(parser, enc, &next, end, nextPtr); @@ -1164,6 +1462,10 @@ doContent(XML_Parser parser, 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; default: if (defaultHandler) reportDefault(parser, enc, s, next); @@ -1174,24 +1476,37 @@ doContent(XML_Parser parser, /* not reached */ } -/* If tagName is non-null, build a real list of attributes, +/* 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 XML_Char *tagName, const char *s) + const char *s, TAG_NAME *tagNamePtr, + BINDING **bindingsPtr) { ELEMENT_TYPE *elementType = 0; int nDefaultAtts = 0; const XML_Char **appAtts; + int attIndex = 0; int i; int n; + int nPrefixes = 0; + BINDING *binding; + const XML_Char *localPart; - if (tagName) { - elementType = (ELEMENT_TYPE *)lookup(&dtd.elementTypes, tagName, 0); - if (elementType) - nDefaultAtts = elementType->nDefaultAtts; + if (tagNamePtr) { + 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)); + if (!elementType) + return XML_ERROR_NO_MEMORY; + if (ns && !setElementTypePrefix(parser, elementType)) + return XML_ERROR_NO_MEMORY; + } + nDefaultAtts = elementType->nDefaultAtts; } - n = XmlGetAttributes(enc, s, attsSize, atts); if (n + nDefaultAtts > attsSize) { int oldAttsSize = attsSize; @@ -1205,8 +1520,8 @@ static enum XML_Error storeAtts(XML_Parser parser, const ENCODING *enc, appAtts = (const XML_Char **)atts; for (i = 0; i < n; i++) { 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; if ((attId->name)[-1]) { @@ -1215,7 +1530,7 @@ static enum XML_Error storeAtts(XML_Parser parser, const ENCODING *enc, return XML_ERROR_DUPLICATE_ATTRIBUTE; } (attId->name)[-1] = 1; - appAtts[i << 1] = attId->name; + appAtts[attIndex++] = attId->name; if (!atts[i].normalized) { enum XML_Error result; int isCdata = 1; @@ -1235,38 +1550,176 @@ static enum XML_Error storeAtts(XML_Parser parser, const ENCODING *enc, &tempPool); if (result) return result; - if (tagName) { - appAtts[(i << 1) + 1] = poolStart(&tempPool); + if (tagNamePtr) { + appAtts[attIndex] = poolStart(&tempPool); poolFinish(&tempPool); } else poolDiscard(&tempPool); } - else if (tagName) { - appAtts[(i << 1) + 1] = poolStoreString(&tempPool, enc, atts[i].valuePtr, atts[i].valueEnd); - if (appAtts[(i << 1) + 1] == 0) + else if (tagNamePtr) { + appAtts[attIndex] = poolStoreString(&tempPool, enc, atts[i].valuePtr, atts[i].valueEnd); + if (appAtts[attIndex] == 0) return XML_ERROR_NO_MEMORY; poolFinish(&tempPool); } + if (attId->prefix && tagNamePtr) { + if (attId->xmlns) { + if (!addBinding(parser, attId->prefix, attId, appAtts[attIndex], bindingsPtr)) + return XML_ERROR_NO_MEMORY; + --attIndex; + } + else { + attIndex++; + nPrefixes++; + (attId->name)[-1] = 2; + } + } + else + attIndex++; } - if (tagName) { + nSpecifiedAtts = attIndex; + if (tagNamePtr) { int j; for (j = 0; j < nDefaultAtts; j++) { const DEFAULT_ATTRIBUTE *da = elementType->defaultAtts + j; if (!(da->id->name)[-1] && da->value) { - (da->id->name)[-1] = 1; - appAtts[i << 1] = da->id->name; - appAtts[(i << 1) + 1] = da->value; - i++; + if (da->id->prefix) { + if (da->id->xmlns) { + if (!addBinding(parser, da->id->prefix, da->id, da->value, bindingsPtr)) + return XML_ERROR_NO_MEMORY; + } + 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; + } } } - appAtts[i << 1] = 0; + appAtts[attIndex] = 0; } - while (i-- > 0) - ((XML_Char *)appAtts[i << 1])[-1] = 0; + i = 0; + if (nPrefixes) { + for (; i < attIndex; i += 2) { + 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++); + appAtts[i] = poolStart(&tempPool); + poolFinish(&tempPool); + } + if (!--nPrefixes) + break; + } + else + ((XML_Char *)(appAtts[i]))[-1] = 0; + } + } + for (; i < attIndex; i += 2) + ((XML_Char *)(appAtts[i]))[-1] = 0; + if (!tagNamePtr) + return XML_ERROR_NONE; + for (binding = *bindingsPtr; binding; binding = binding->nextTagBinding) + binding->attId->name[-1] = 0; + if (elementType->prefix) { + binding = elementType->prefix->binding; + if (!binding) + return XML_ERROR_NONE; + localPart = tagNamePtr->str; + while (*localPart++ != XML_T(':')) + ; + } + else if (dtd.defaultPrefix.binding) { + binding = dtd.defaultPrefix.binding; + localPart = tagNamePtr->str; + } + else + return XML_ERROR_NONE; + tagNamePtr->localPart = localPart; + tagNamePtr->uriLen = binding->uriLen; + i = binding->uriLen; + do { + if (i == binding->uriAlloc) { + binding->uri = realloc(binding->uri, binding->uriAlloc *= 2); + if (!binding->uri) + return XML_ERROR_NO_MEMORY; + } + binding->uri[i++] = *localPart; + } while (*localPart++); + 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) +{ + BINDING *b; + int len; + for (len = 0; uri[len]; len++) + ; + if (namespaceSeparator) + len++; + if (freeBindingList) { + b = freeBindingList; + if (len > b->uriAlloc) { + b->uri = realloc(b->uri, len + EXPAND_SPARE); + if (!b->uri) + return 0; + b->uriAlloc = len + EXPAND_SPARE; + } + freeBindingList = b->nextTagBinding; + } + else { + b = malloc(sizeof(BINDING)); + if (!b) + return 0; + b->uri = malloc(sizeof(XML_Char) * len + EXPAND_SPARE); + if (!b->uri) { + free(b); + return 0; + } + b->uriAlloc = len; + } + b->uriLen = len; + memcpy(b->uri, uri, len * sizeof(XML_Char)); + if (namespaceSeparator) + b->uri[len - 1] = namespaceSeparator; + b->prefix = prefix; + b->attId = attId; + b->prevPrefixBinding = prefix->binding; + if (*uri == XML_T('\0') && prefix == &dtd.defaultPrefix) + prefix->binding = 0; + else + prefix->binding = b; + b->nextTagBinding = *bindingsPtr; + *bindingsPtr = b; + if (startNamespaceDeclHandler) + startNamespaceDeclHandler(handlerArg, prefix->name, + prefix->binding ? uri : 0); + return 1; +} + /* The idea here is to avoid using stack for each CDATA section when the whole file is parsed with one call. */ @@ -1295,7 +1748,6 @@ enum XML_Error doCdataSection(XML_Parser parser, const char **nextPtr) { const char *s = *startPtr; - const char *dummy; const char **eventPP; const char **eventEndPP; if (enc == encoding) { @@ -1303,8 +1755,11 @@ enum XML_Error doCdataSection(XML_Parser parser, *eventPP = s; eventEndPP = &eventEndPtr; } - else - eventPP = eventEndPP = &dummy; + else { + eventPP = &(openInternalEntities->internalEventPtr); + eventEndPP = &(openInternalEntities->internalEventEndPtr); + } + *eventPP = s; *startPtr = 0; for (;;) { const char *next; @@ -1312,15 +1767,20 @@ enum XML_Error doCdataSection(XML_Parser parser, *eventEndPP = next; switch (tok) { case XML_TOK_CDATA_SECT_CLOSE: - if (characterDataHandler) + if (endCdataSectionHandler) + endCdataSectionHandler(handlerArg); +#if 0 + /* see comment under XML_TOK_CDATA_SECT_OPEN */ + else if (characterDataHandler) characterDataHandler(handlerArg, dataBuf, 0); +#endif else if (defaultHandler) reportDefault(parser, enc, s, next); *startPtr = next; return XML_ERROR_NONE; case XML_TOK_DATA_NEWLINE: if (characterDataHandler) { - XML_Char c = XML_T('\n'); + XML_Char c = 0xA; characterDataHandler(handlerArg, &c, 1); } else if (defaultHandler) @@ -1396,7 +1856,7 @@ initializeEncoding(XML_Parser parser) #else s = protocolEncodingName; #endif - if (XmlInitEncoding(&initEncoding, &encoding, s)) + if ((ns ? XmlInitEncodingNS : XmlInitEncoding)(&initEncoding, &encoding, s)) return XML_ERROR_NONE; return handleUnknownEncoding(parser, protocolEncodingName); } @@ -1409,15 +1869,17 @@ processXmlDecl(XML_Parser parser, int isGeneralTextEntity, const ENCODING *newEncoding = 0; const char *version; int standalone = -1; - if (!XmlParseXmlDecl(isGeneralTextEntity, - encoding, - s, - next, - &eventPtr, - &version, - &encodingName, - &newEncoding, - &standalone)) + if (!(ns + ? XmlParseXmlDeclNS + : XmlParseXmlDecl)(isGeneralTextEntity, + encoding, + s, + next, + &eventPtr, + &version, + &encodingName, + &newEncoding, + &standalone)) return XML_ERROR_SYNTAX; if (!isGeneralTextEntity && standalone == 1) dtd.standalone = 1; @@ -1469,10 +1931,12 @@ handleUnknownEncoding(XML_Parser parser, const XML_Char *encodingName) info.release(info.data); return XML_ERROR_NO_MEMORY; } - enc = XmlInitUnknownEncoding(unknownEncodingMem, - info.map, - info.convert, - info.data); + enc = (ns + ? XmlInitUnknownEncodingNS + : XmlInitUnknownEncoding)(unknownEncodingMem, + info.map, + info.convert, + info.data); if (enc) { unknownEncodingData = info.data; unknownEncodingRelease = info.release; @@ -1539,6 +2003,10 @@ prologProcessor(XML_Parser parser, } break; case XML_ROLE_DOCTYPE_SYSTEM_ID: + if (!dtd.standalone + && notStandaloneHandler + && !notStandaloneHandler(handlerArg)) + return XML_ERROR_NOT_STANDALONE; hadExternalDoctype = 1; break; case XML_ROLE_DOCTYPE_PUBLIC_ID: @@ -1572,8 +2040,11 @@ prologProcessor(XML_Parser parser, return XML_ERROR_NO_MEMORY; if (declElementType->name != name) poolDiscard(&dtd.pool); - else + else { poolFinish(&dtd.pool); + if (!setElementTypePrefix(parser, declElementType)) + return XML_ERROR_NO_MEMORY; + } break; } case XML_ROLE_ATTRIBUTE_NAME: @@ -1764,6 +2235,10 @@ prologProcessor(XML_Parser parser, groupConnector[prologState.level] = '|'; break; case XML_ROLE_PARAM_ENTITY_REF: + if (!dtd.standalone + && notStandaloneHandler + && !notStandaloneHandler(handlerArg)) + return XML_ERROR_NOT_STANDALONE; dtd.complete = 0; break; case XML_ROLE_NONE: @@ -1774,12 +2249,19 @@ prologProcessor(XML_Parser parser, if (!reportProcessingInstruction(parser, encoding, s, next)) return XML_ERROR_NO_MEMORY; break; + case XML_TOK_COMMENT: + eventPtr = s; + eventEndPtr = next; + if (!reportComment(parser, encoding, s, next)) + return XML_ERROR_NO_MEMORY; + break; } break; } if (defaultHandler) { switch (tok) { case XML_TOK_PI: + case XML_TOK_COMMENT: case XML_TOK_BOM: case XML_TOK_XML_DECL: break; @@ -1818,7 +2300,6 @@ enum XML_Error epilogProcessor(XML_Parser parser, *nextPtr = end; return XML_ERROR_NONE; case XML_TOK_PROLOG_S: - case XML_TOK_COMMENT: if (defaultHandler) reportDefault(parser, encoding, s, next); break; @@ -1826,6 +2307,10 @@ enum XML_Error epilogProcessor(XML_Parser parser, if (!reportProcessingInstruction(parser, encoding, s, next)) return XML_ERROR_NO_MEMORY; break; + case XML_TOK_COMMENT: + if (!reportComment(parser, encoding, s, next)) + return XML_ERROR_NO_MEMORY; + break; case XML_TOK_INVALID: eventPtr = next; return XML_ERROR_INVALID_TOKEN; @@ -1865,7 +2350,7 @@ storeAttributeValue(XML_Parser parser, const ENCODING *enc, int isCdata, enum XML_Error result = appendAttributeValue(parser, enc, isCdata, ptr, end, pool); if (result) return result; - if (!isCdata && poolLength(pool) && poolLastChar(pool) == XML_T(' ')) + if (!isCdata && poolLength(pool) && poolLastChar(pool) == 0x20) poolChop(pool); if (!poolAppendChar(pool, XML_T('\0'))) return XML_ERROR_NO_MEMORY; @@ -1877,7 +2362,7 @@ appendAttributeValue(XML_Parser parser, const ENCODING *enc, int isCdata, const char *ptr, const char *end, STRING_POOL *pool) { - const ENCODING *internalEnc = XmlGetInternalEncoding(); + const ENCODING *internalEnc = ns ? XmlGetInternalEncodingNS() : XmlGetInternalEncoding(); for (;;) { const char *next; int tok = XmlAttributeValueTok(enc, ptr, end, &next); @@ -1904,7 +2389,7 @@ appendAttributeValue(XML_Parser parser, const ENCODING *enc, int isCdata, } if (!isCdata && n == 0x20 /* space */ - && (poolLength(pool) == 0 || poolLastChar(pool) == XML_T(' '))) + && (poolLength(pool) == 0 || poolLastChar(pool) == 0x20)) break; n = XmlEncode(n, (ICHAR *)buf); if (!n) { @@ -1928,9 +2413,9 @@ appendAttributeValue(XML_Parser parser, const ENCODING *enc, int isCdata, /* fall through */ case XML_TOK_ATTRIBUTE_VALUE_S: case XML_TOK_DATA_NEWLINE: - if (!isCdata && (poolLength(pool) == 0 || poolLastChar(pool) == XML_T(' '))) + if (!isCdata && (poolLength(pool) == 0 || poolLastChar(pool) == 0x20)) break; - if (!poolAppendChar(pool, XML_T(' '))) + if (!poolAppendChar(pool, 0x20)) return XML_ERROR_NO_MEMORY; break; case XML_TOK_ENTITY_REF: @@ -1998,7 +2483,7 @@ enum XML_Error storeEntityValue(XML_Parser parser, const char *entityTextPtr, const char *entityTextEnd) { - const ENCODING *internalEnc = XmlGetInternalEncoding(); + const ENCODING *internalEnc = ns ? XmlGetInternalEncodingNS() : XmlGetInternalEncoding(); STRING_POOL *pool = &(dtd.pool); entityTextPtr += encoding->minBytesPerChar; entityTextEnd -= encoding->minBytesPerChar; @@ -2029,7 +2514,7 @@ enum XML_Error storeEntityValue(XML_Parser parser, case XML_TOK_DATA_NEWLINE: if (pool->end == pool->ptr && !poolGrow(pool)) return XML_ERROR_NO_MEMORY; - *(pool->ptr)++ = XML_T('\n'); + *(pool->ptr)++ = 0xA; break; case XML_TOK_CHAR_REF: { @@ -2073,14 +2558,14 @@ normalizeLines(XML_Char *s) for (;; s++) { if (*s == XML_T('\0')) return; - if (*s == XML_T('\r')) + if (*s == 0xD) break; } p = s; do { - if (*s == XML_T('\r')) { - *p++ = XML_T('\n'); - if (*++s == XML_T('\n')) + if (*s == 0xD) { + *p++ = 0xA; + if (*++s == 0xA) s++; } else @@ -2117,25 +2602,48 @@ reportProcessingInstruction(XML_Parser parser, const ENCODING *enc, const char * return 1; } +static int +reportComment(XML_Parser parser, const ENCODING *enc, const char *start, const char *end) +{ + XML_Char *data; + if (!commentHandler) { + if (defaultHandler) + reportDefault(parser, enc, start, end); + return 1; + } + data = poolStoreString(&tempPool, + enc, + start + enc->minBytesPerChar * 4, + end - enc->minBytesPerChar * 3); + if (!data) + return 0; + normalizeLines(data); + commentHandler(handlerArg, data); + poolClear(&tempPool); + return 1; +} + static void reportDefault(XML_Parser parser, const ENCODING *enc, const char *s, const char *end) { if (MUST_CONVERT(enc, s)) { - for (;;) { + const char **eventPP; + const char **eventEndPP; + if (enc == encoding) { + eventPP = &eventPtr; + eventEndPP = &eventEndPtr; + } + else { + eventPP = &(openInternalEntities->internalEventPtr); + eventEndPP = &(openInternalEntities->internalEventEndPtr); + } + do { ICHAR *dataPtr = (ICHAR *)dataBuf; XmlConvert(enc, &s, end, &dataPtr, (ICHAR *)dataBufEnd); - if (s == end) { - defaultHandler(handlerArg, dataBuf, dataPtr - (ICHAR *)dataBuf); - break; - } - if (enc == encoding) { - eventEndPtr = s; - defaultHandler(handlerArg, dataBuf, dataPtr - (ICHAR *)dataBuf); - eventPtr = s; - } - else - defaultHandler(handlerArg, dataBuf, dataPtr - (ICHAR *)dataBuf); - } + *eventEndPP = s; + defaultHandler(handlerArg, dataBuf, dataPtr - (ICHAR *)dataBuf); + *eventPP = s; + } while (s != end); } else defaultHandler(handlerArg, (XML_Char *)s, (XML_Char *)end - (XML_Char *)s); @@ -2169,6 +2677,33 @@ defineAttribute(ELEMENT_TYPE *type, ATTRIBUTE_ID *attId, int isCdata, const XML_ return 1; } +static int setElementTypePrefix(XML_Parser parser, ELEMENT_TYPE *elementType) +{ + 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, 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); + else + poolDiscard(&dtd.pool); + elementType->prefix = prefix; + + } + } + return 1; +} + static ATTRIBUTE_ID * getAttributeId(XML_Parser parser, const ENCODING *enc, const char *start, const char *end) { @@ -2185,15 +2720,94 @@ getAttributeId(XML_Parser parser, const ENCODING *enc, const char *start, const return 0; if (id->name != name) poolDiscard(&dtd.pool); - else + else { 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 + id->prefix = (PREFIX *)lookup(&dtd.prefixes, name + 6, sizeof(PREFIX)); + id->xmlns = 1; + } + 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; + } + } + } + } return id; } +#define CONTEXT_SEP XML_T('\f') + static -const XML_Char *getOpenEntityNames(XML_Parser parser) +const XML_Char *getContext(XML_Parser parser) { HASH_TABLE_ITER iter; + int needSep = 0; + + if (dtd.defaultPrefix.binding) { + int i; + int len; + if (!poolAppendChar(&tempPool, XML_T('='))) + return 0; + 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; + } + + hashTableIterInit(&iter, &(dtd.prefixes)); + for (;;) { + int i; + int len; + const XML_Char *s; + PREFIX *prefix = (PREFIX *)hashTableIterNext(&iter); + if (!prefix) + break; + if (!prefix->binding) + continue; + if (needSep && !poolAppendChar(&tempPool, CONTEXT_SEP)) + return 0; + for (s = prefix->name; *s; s++) + if (!poolAppendChar(&tempPool, *s)) + return 0; + if (!poolAppendChar(&tempPool, XML_T('='))) + return 0; + 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; + } + hashTableIterInit(&iter, &(dtd.generalEntities)); for (;;) { @@ -2203,11 +2817,12 @@ const XML_Char *getOpenEntityNames(XML_Parser parser) break; if (!e->open) continue; - if (poolLength(&tempPool) > 0 && !poolAppendChar(&tempPool, XML_T(' '))) + if (needSep && !poolAppendChar(&tempPool, CONTEXT_SEP)) return 0; for (s = e->name; *s; s++) if (!poolAppendChar(&tempPool, *s)) return 0; + needSep = 1; } if (!poolAppendChar(&tempPool, XML_T('\0'))) @@ -2216,22 +2831,50 @@ const XML_Char *getOpenEntityNames(XML_Parser parser) } static -int setOpenEntityNames(XML_Parser parser, const XML_Char *openEntityNames) +int setContext(XML_Parser parser, const XML_Char *context) { - const XML_Char *s = openEntityNames; - while (*openEntityNames != XML_T('\0')) { - if (*s == XML_T(' ') || *s == XML_T('\0')) { + 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); if (e) e->open = 1; - if (*s == XML_T(' ')) + if (*s != XML_T('\0')) s++; - openEntityNames = s; + context = s; poolDiscard(&tempPool); } + else if (*s == '=') { + PREFIX *prefix; + if (poolLength(&tempPool) == 0) + 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 (prefix->name == poolStart(&tempPool)) + poolFinish(&tempPool); + else + poolDiscard(&tempPool); + } + for (context = s + 1; *context != CONTEXT_SEP && *context != XML_T('\0'); context++) + if (!poolAppendChar(&tempPool, *context)) + return 0; + if (!poolAppendChar(&tempPool, XML_T('\0'))) + return 0; + if (!addBinding(parser, prefix, 0, poolStart(&tempPool), &inheritedBindings)) + return 0; + poolDiscard(&tempPool); + if (*context != XML_T('\0')) + ++context; + s = context; + } else { if (!poolAppendChar(&tempPool, *s)) return 0; @@ -2249,17 +2892,17 @@ void normalizePublicId(XML_Char *publicId) XML_Char *s; for (s = publicId; *s; s++) { switch (*s) { - case XML_T(' '): - case XML_T('\r'): - case XML_T('\n'): - if (p != publicId && p[-1] != XML_T(' ')) - *p++ = XML_T(' '); + case 0x20: + case 0xD: + case 0xA: + if (p != publicId && p[-1] != 0x20) + *p++ = 0x20; break; default: *p++ = *s; } } - if (p != publicId && p[-1] == XML_T(' ')) + if (p != publicId && p[-1] == 0x20) --p; *p = XML_T('\0'); } @@ -2270,9 +2913,12 @@ static int dtdInit(DTD *p) hashTableInit(&(p->generalEntities)); hashTableInit(&(p->elementTypes)); hashTableInit(&(p->attributeIds)); + hashTableInit(&(p->prefixes)); p->complete = 1; p->standalone = 0; p->base = 0; + p->defaultPrefix.name = 0; + p->defaultPrefix.binding = 0; return 1; } @@ -2290,6 +2936,7 @@ static void dtdDestroy(DTD *p) hashTableDestroy(&(p->generalEntities)); hashTableDestroy(&(p->elementTypes)); hashTableDestroy(&(p->attributeIds)); + hashTableDestroy(&(p->prefixes)); poolDestroy(&(p->pool)); } @@ -2307,6 +2954,21 @@ static int dtdCopy(DTD *newDtd, const DTD *oldDtd) newDtd->base = tem; } + /* Copy the prefix table. */ + + hashTableIterInit(&iter, &(oldDtd->prefixes)); + for (;;) { + const XML_Char *name; + const PREFIX *oldP = (PREFIX *)hashTableIterNext(&iter); + if (!oldP) + break; + name = poolCopyString(&(newDtd->pool), oldP->name); + if (!name) + return 0; + if (!lookup(&(newDtd->prefixes), name, sizeof(PREFIX))) + return 0; + } + hashTableIterInit(&iter, &(oldDtd->attributeIds)); /* Copy the attribute id table. */ @@ -2329,6 +2991,13 @@ static int dtdCopy(DTD *newDtd, const DTD *oldDtd) if (!newA) return 0; newA->maybeTokenized = oldA->maybeTokenized; + if (oldA->prefix) { + newA->xmlns = oldA->xmlns; + if (oldA->prefix == &oldDtd->defaultPrefix) + newA->prefix = &newDtd->defaultPrefix; + else + newA->prefix = (PREFIX *)lookup(&(newDtd->prefixes), oldA->prefix->name, 0); + } } /* Copy the element type table. */ @@ -2348,10 +3017,14 @@ static int dtdCopy(DTD *newDtd, const DTD *oldDtd) newE = (ELEMENT_TYPE *)lookup(&(newDtd->elementTypes), name, sizeof(ELEMENT_TYPE)); if (!newE) return 0; - newE->defaultAtts = (DEFAULT_ATTRIBUTE *)malloc(oldE->nDefaultAtts * sizeof(DEFAULT_ATTRIBUTE)); - if (!newE->defaultAtts) - return 0; + if (oldE->nDefaultAtts) { + newE->defaultAtts = (DEFAULT_ATTRIBUTE *)malloc(oldE->nDefaultAtts * sizeof(DEFAULT_ATTRIBUTE)); + if (!newE->defaultAtts) + return 0; + } newE->allocDefaultAtts = newE->nDefaultAtts = oldE->nDefaultAtts; + if (oldE->prefix) + 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].isCdata = oldE->defaultAtts[i].isCdata; diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmlparse/xmlparse.h b/mozilla/extensions/transformiix/source/xml/parser/xmlparse/xmlparse.h index 13d5885ca2a..f2f9c9be1c0 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmlparse/xmlparse.h +++ b/mozilla/extensions/transformiix/source/xml/parser/xmlparse/xmlparse.h @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,10 +12,20 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ #ifndef XmlParse_INCLUDED @@ -70,6 +80,19 @@ protocol or null if there is none specified. */ XML_Parser XMLPARSEAPI XML_ParserCreate(const XML_Char *encoding); +/* Constructs a new parser and namespace processor. Element type names +and attribute names that belong to a namespace will be expanded; +unprefixed attribute names are never expanded; unprefixed element type +names are expanded only if there is a default namespace. The expanded +name is the concatenation of the namespace URI, the namespace separator character, +and the local part of the name. If the namespace separator is '\0' then +the namespace URI and the local part will be concatenated without any +separator. When a namespace is not declared, the name and prefix will be +passed through without expansion. */ + +XML_Parser XMLPARSEAPI +XML_ParserCreateNS(const XML_Char *encoding, XML_Char namespaceSeparator); + /* atts is array of name/value pairs, terminated by 0; names and values are 0 terminated. */ @@ -91,6 +114,12 @@ typedef void (*XML_ProcessingInstructionHandler)(void *userData, const XML_Char *target, const XML_Char *data); +/* data is 0 terminated */ +typedef void (*XML_CommentHandler)(void *userData, const XML_Char *data); + +typedef void (*XML_StartCdataSectionHandler)(void *userData); +typedef void (*XML_EndCdataSectionHandler)(void *userData); + /* This is called for any characters in the XML document for which there is no applicable handler. This includes both characters that are part of markup which is of a kind that is @@ -100,10 +129,9 @@ for which no handler has been supplied. The characters are passed exactly as they were in the XML document except that they will be encoded in UTF-8. Line boundaries are not normalized. Note that a byte order mark character is not passed to the default handler. -If a default handler is set, internal entity references -are not expanded. There are no guarantees about -how characters are divided between calls to the default handler: -for example, a comment might be split between multiple calls. */ +There are no guarantees about how characters are divided between calls +to the default handler: for example, a comment might be split between +multiple calls. */ typedef void (*XML_DefaultHandler)(void *userData, const XML_Char *s, @@ -131,6 +159,27 @@ typedef void (*XML_NotationDeclHandler)(void *userData, const XML_Char *systemId, const XML_Char *publicId); +/* When namespace processing is enabled, these are called once for +each namespace declaration. The call to the start and end element +handlers occur between the calls to the start and end namespace +declaration handlers. For an xmlns attribute, prefix will be null. +For an xmlns="" attribute, uri will be null. */ + +typedef void (*XML_StartNamespaceDeclHandler)(void *userData, + const XML_Char *prefix, + const XML_Char *uri); + +typedef void (*XML_EndNamespaceDeclHandler)(void *userData, + const XML_Char *prefix); + +/* This is called if the document is not standalone (it has an +external subset or a reference to a parameter entity, but does not +have standalone="yes"). If this handler returns 0, then processing +will not continue, and the parser will return a +XML_ERROR_NOT_STANDALONE error. */ + +typedef int (*XML_NotStandaloneHandler)(void *userData); + /* This is called for a reference to an external parsed general entity. The referenced entity is not automatically parsed. The application can parse it immediately or later using @@ -145,10 +194,9 @@ it may be null. The publicId argument is the public identifier as specified in the entity declaration, or null if none was specified; the whitespace in the public identifier will have been normalized as required by the XML spec. -The openEntityNames argument is a space-separated list of the names of the entities -that are open for the parse of this entity (including the name of the referenced -entity); this can be passed as the openEntityNames argument to -XML_ExternalEntityParserCreate; openEntityNames is valid only until the handler +The context argument specifies the parsing context in the format +expected by the context argument to +XML_ExternalEntityParserCreate; context is valid only until the handler returns, so if the referenced entity is to be parsed later, it must be copied. The handler should return 0 if processing should not continue because of a fatal error in the handling of the external entity. @@ -157,7 +205,7 @@ error. Note that unlike other handlers the first argument is the parser, not userData. */ typedef int (*XML_ExternalEntityRefHandler)(XML_Parser parser, - const XML_Char *openEntityNames, + const XML_Char *context, const XML_Char *base, const XML_Char *systemId, const XML_Char *publicId); @@ -237,11 +285,29 @@ XML_SetCharacterDataHandler(XML_Parser parser, void XMLPARSEAPI XML_SetProcessingInstructionHandler(XML_Parser parser, XML_ProcessingInstructionHandler handler); +void XMLPARSEAPI +XML_SetCommentHandler(XML_Parser parser, + XML_CommentHandler handler); + +void XMLPARSEAPI +XML_SetCdataSectionHandler(XML_Parser parser, + XML_StartCdataSectionHandler start, + XML_EndCdataSectionHandler end); + +/* This sets the default handler and also inhibits expansion of internal entities. +The entity reference will be passed to the default handler. */ void XMLPARSEAPI XML_SetDefaultHandler(XML_Parser parser, XML_DefaultHandler handler); +/* This sets the default handler but does not inhibit expansion of internal entities. +The entity reference will not be passed to the default handler. */ + +void XMLPARSEAPI +XML_SetDefaultHandlerExpand(XML_Parser parser, + XML_DefaultHandler handler); + void XMLPARSEAPI XML_SetUnparsedEntityDeclHandler(XML_Parser parser, XML_UnparsedEntityDeclHandler handler); @@ -250,10 +316,25 @@ void XMLPARSEAPI XML_SetNotationDeclHandler(XML_Parser parser, XML_NotationDeclHandler handler); +void XMLPARSEAPI +XML_SetNamespaceDeclHandler(XML_Parser parser, + XML_StartNamespaceDeclHandler start, + XML_EndNamespaceDeclHandler end); + +void XMLPARSEAPI +XML_SetNotStandaloneHandler(XML_Parser parser, + XML_NotStandaloneHandler handler); + void XMLPARSEAPI XML_SetExternalEntityRefHandler(XML_Parser parser, XML_ExternalEntityRefHandler handler); +/* If a non-null value for arg is specified here, then it will be passed +as the first argument to the external entity ref handler instead +of the parser object. */ +void XMLPARSEAPI +XML_SetExternalEntityRefHandlerArg(XML_Parser, void *arg); + void XMLPARSEAPI XML_SetUnknownEncodingHandler(XML_Parser parser, XML_UnknownEncodingHandler handler, @@ -261,10 +342,7 @@ XML_SetUnknownEncodingHandler(XML_Parser parser, /* This can be called within a handler for a start element, end element, processing instruction or character data. It causes the corresponding -markup to be passed to the default handler. -Within the expansion of an internal entity, nothing will be passed -to the default handler, although this usually will not happen since -setting a default handler inhibits expansion of internal entities. */ +markup to be passed to the default handler. */ void XMLPARSEAPI XML_DefaultCurrent(XML_Parser parser); /* This value is passed as the userData argument to callbacks. */ @@ -274,6 +352,13 @@ XML_SetUserData(XML_Parser parser, void *userData); /* Returns the last value set by XML_SetUserData or null. */ #define XML_GetUserData(parser) (*(void **)(parser)) +/* This is equivalent to supplying an encoding argument +to XML_CreateParser. It must not be called after XML_Parse +or XML_ParseBuffer. */ + +int XMLPARSEAPI +XML_SetEncoding(XML_Parser parser, const XML_Char *encoding); + /* If this function is called, then the parser will be passed as the first argument to callbacks instead of userData. The userData will still be accessible using XML_GetUserData. */ @@ -294,6 +379,12 @@ XML_SetBase(XML_Parser parser, const XML_Char *base); const XML_Char XMLPARSEAPI * XML_GetBase(XML_Parser parser); +/* Returns the number of the attributes passed in last call to the +XML_StartElementHandler that were specified in the start-tag rather +than defaulted. */ + +int XMLPARSEAPI XML_GetSpecifiedAttributeCount(XML_Parser parser); + /* Parses some input. Returns 0 if a fatal error is detected. The last call to XML_Parse must have isFinal true; len may be zero for this call (or any other). */ @@ -307,10 +398,13 @@ int XMLPARSEAPI XML_ParseBuffer(XML_Parser parser, int len, int isFinal); /* Creates an XML_Parser object that can parse an external general entity; -openEntityNames is a space-separated list of the names of the entities that are open -for the parse of this entity (including the name of this one); -encoding is the externally specified encoding, +context is a '\0'-terminated string specifying the parse context; +encoding is a '\0'-terminated string giving the name of the externally specified encoding, or null if there is no externally specified encoding. +The context string consists of a sequence of tokens separated by formfeeds (\f); +a token consisting of a name specifies that the general entity of the name +is open; a token of the form prefix=uri specifies the namespace for a particular +prefix; a token of the form =uri specifies the default namespace. This can be called at any point after the first call to an ExternalEntityRefHandler so longer as the parser has not yet been freed. The new parser is completely independent and may safely be used in a separate thread. @@ -318,7 +412,7 @@ The handlers and userData are initialized from the parser argument. Returns 0 if out of memory. Otherwise returns a new XML_Parser object. */ XML_Parser XMLPARSEAPI XML_ExternalEntityParserCreate(XML_Parser parser, - const XML_Char *openEntityNames, + const XML_Char *context, const XML_Char *encoding); enum XML_Error { @@ -343,7 +437,8 @@ enum XML_Error { XML_ERROR_UNKNOWN_ENCODING, XML_ERROR_INCORRECT_ENCODING, XML_ERROR_UNCLOSED_CDATA_SECTION, - XML_ERROR_EXTERNAL_ENTITY_HANDLING + XML_ERROR_EXTERNAL_ENTITY_HANDLING, + XML_ERROR_NOT_STANDALONE }; /* If XML_Parse or XML_ParseBuffer have returned 0, then XML_GetErrorCode @@ -363,6 +458,11 @@ int XMLPARSEAPI XML_GetCurrentLineNumber(XML_Parser parser); int XMLPARSEAPI XML_GetCurrentColumnNumber(XML_Parser parser); long XMLPARSEAPI XML_GetCurrentByteIndex(XML_Parser parser); +/* Return the number of bytes in the current event. +Returns 0 if the event is in an internal entity. */ + +int XMLPARSEAPI XML_GetCurrentByteCount(XML_Parser parser); + /* For backwards compatibility with previous versions. */ #define XML_GetErrorLineNumber XML_GetCurrentLineNumber #define XML_GetErrorColumnNumber XML_GetCurrentColumnNumber diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmltok/asciitab.h b/mozilla/extensions/transformiix/source/xml/parser/xmltok/asciitab.h index f7d78da4f82..8a8a2dd388d 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmltok/asciitab.h +++ b/mozilla/extensions/transformiix/source/xml/parser/xmltok/asciitab.h @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,10 +12,20 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ /* 0x00 */ BT_NONXML, BT_NONXML, BT_NONXML, BT_NONXML, @@ -32,7 +42,7 @@ Contributor(s): /* 0x2C */ BT_COMMA, BT_MINUS, BT_NAME, BT_SOL, /* 0x30 */ BT_DIGIT, BT_DIGIT, BT_DIGIT, BT_DIGIT, /* 0x34 */ BT_DIGIT, BT_DIGIT, BT_DIGIT, BT_DIGIT, -/* 0x38 */ BT_DIGIT, BT_DIGIT, BT_NMSTRT, BT_SEMI, +/* 0x38 */ BT_DIGIT, BT_DIGIT, BT_COLON, BT_SEMI, /* 0x3C */ BT_LT, BT_EQUALS, BT_GT, BT_QUEST, /* 0x40 */ BT_OTHER, BT_HEX, BT_HEX, BT_HEX, /* 0x44 */ BT_HEX, BT_HEX, BT_HEX, BT_NMSTRT, diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmltok/dllmain.c b/mozilla/extensions/transformiix/source/xml/parser/xmltok/dllmain.c index 579d6567e08..deb7fafc81a 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmltok/dllmain.c +++ b/mozilla/extensions/transformiix/source/xml/parser/xmltok/dllmain.c @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,12 +12,25 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ +#define STRICT 1 +#define WIN32_LEAN_AND_MEAN 1 + #include BOOL WINAPI DllMain(HANDLE hInst, ULONG ul_reason_for_call, LPVOID lpReserved) diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmltok/iasciitab.h b/mozilla/extensions/transformiix/source/xml/parser/xmltok/iasciitab.h index d894074771a..333d6bb779d 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmltok/iasciitab.h +++ b/mozilla/extensions/transformiix/source/xml/parser/xmltok/iasciitab.h @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,10 +12,20 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ /* Like asciitab.h, except that 0xD has code BT_S rather than BT_CR */ @@ -33,7 +43,7 @@ Contributor(s): /* 0x2C */ BT_COMMA, BT_MINUS, BT_NAME, BT_SOL, /* 0x30 */ BT_DIGIT, BT_DIGIT, BT_DIGIT, BT_DIGIT, /* 0x34 */ BT_DIGIT, BT_DIGIT, BT_DIGIT, BT_DIGIT, -/* 0x38 */ BT_DIGIT, BT_DIGIT, BT_NMSTRT, BT_SEMI, +/* 0x38 */ BT_DIGIT, BT_DIGIT, BT_COLON, BT_SEMI, /* 0x3C */ BT_LT, BT_EQUALS, BT_GT, BT_QUEST, /* 0x40 */ BT_OTHER, BT_HEX, BT_HEX, BT_HEX, /* 0x44 */ BT_HEX, BT_HEX, BT_HEX, BT_NMSTRT, diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmltok/latin1tab.h b/mozilla/extensions/transformiix/source/xml/parser/xmltok/latin1tab.h index 378697512e6..48609aa8f9f 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmltok/latin1tab.h +++ b/mozilla/extensions/transformiix/source/xml/parser/xmltok/latin1tab.h @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,10 +12,20 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ /* 0x80 */ BT_OTHER, BT_OTHER, BT_OTHER, BT_OTHER, diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmltok/utf8tab.h b/mozilla/extensions/transformiix/source/xml/parser/xmltok/utf8tab.h index 57ff8074c16..a38fe624e88 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmltok/utf8tab.h +++ b/mozilla/extensions/transformiix/source/xml/parser/xmltok/utf8tab.h @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,10 +12,20 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmldef.h b/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmldef.h index 26ddf042547..49ce9ed636c 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmldef.h +++ b/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmldef.h @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,19 +12,50 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ +#include + +#ifdef XML_WINLIB + +#define WIN32_LEAN_AND_MEAN +#define STRICT +#include + +#define malloc(x) HeapAlloc(GetProcessHeap(), 0, (x)) +#define calloc(x, y) HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, (x)*(y)) +#define free(x) HeapFree(GetProcessHeap(), 0, (x)) +#define realloc(x, y) HeapReAlloc(GetProcessHeap(), 0, x, y) +#define abort() /* as nothing */ + +#else /* not XML_WINLIB */ + +#include + +#endif /* not XML_WINLIB */ + /* This file can be used for any definitions needed in particular environments. */ -#ifdef MOZ_XSL +#ifdef MOZILLA #include "nspr.h" -#define malloc(x) PR_Calloc(1,(x)) +#define malloc(x) PR_Malloc(x) +#define realloc(x, y) PR_Realloc((x), (y)) #define calloc(x, y) PR_Calloc((x),(y)) #define free(x) PR_Free(x) #define int int32 diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmlrole.c b/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmlrole.c index 72be89bff8f..b18e35eb3c4 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmlrole.c +++ b/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmlrole.c @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,10 +12,20 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ #include "xmldef.h" @@ -149,6 +159,7 @@ int doctype0(PROLOG_STATE *state, case XML_TOK_PROLOG_S: return XML_ROLE_NONE; case XML_TOK_NAME: + case XML_TOK_PREFIXED_NAME: state->handler = doctype1; return XML_ROLE_DOCTYPE_NAME; } @@ -610,6 +621,7 @@ int attlist0(PROLOG_STATE *state, case XML_TOK_PROLOG_S: return XML_ROLE_NONE; case XML_TOK_NAME: + case XML_TOK_PREFIXED_NAME: state->handler = attlist1; return XML_ROLE_ATTLIST_ELEMENT_NAME; } @@ -630,6 +642,7 @@ int attlist1(PROLOG_STATE *state, state->handler = internalSubset; return XML_ROLE_NONE; case XML_TOK_NAME: + case XML_TOK_PREFIXED_NAME: state->handler = attlist2; return XML_ROLE_ATTRIBUTE_NAME; } @@ -689,6 +702,7 @@ int attlist3(PROLOG_STATE *state, return XML_ROLE_NONE; case XML_TOK_NMTOKEN: case XML_TOK_NAME: + case XML_TOK_PREFIXED_NAME: state->handler = attlist4; return XML_ROLE_ATTRIBUTE_ENUM_VALUE; } @@ -836,6 +850,7 @@ int element0(PROLOG_STATE *state, case XML_TOK_PROLOG_S: return XML_ROLE_NONE; case XML_TOK_NAME: + case XML_TOK_PREFIXED_NAME: state->handler = element1; return XML_ROLE_ELEMENT_NAME; } @@ -893,6 +908,7 @@ int element2(PROLOG_STATE *state, state->handler = element6; return XML_ROLE_GROUP_OPEN; case XML_TOK_NAME: + case XML_TOK_PREFIXED_NAME: state->handler = element7; return XML_ROLE_CONTENT_ELEMENT; case XML_TOK_NAME_QUESTION: @@ -940,6 +956,7 @@ int element4(PROLOG_STATE *state, case XML_TOK_PROLOG_S: return XML_ROLE_NONE; case XML_TOK_NAME: + case XML_TOK_PREFIXED_NAME: state->handler = element5; return XML_ROLE_CONTENT_ELEMENT; } @@ -980,6 +997,7 @@ int element6(PROLOG_STATE *state, state->level += 1; return XML_ROLE_GROUP_OPEN; case XML_TOK_NAME: + case XML_TOK_PREFIXED_NAME: state->handler = element7; return XML_ROLE_CONTENT_ELEMENT; case XML_TOK_NAME_QUESTION: diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmlrole.h b/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmlrole.h index ecbcc26dff0..877c40ba1f8 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmlrole.h +++ b/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmlrole.h @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,10 +12,20 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ #ifndef XmlRole_INCLUDED diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok.c b/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok.c index 281b318efbb..8d058d41e58 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok.c +++ b/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok.c @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,10 +12,20 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ #include "xmldef.h" @@ -129,6 +139,13 @@ int utf8_isInvalid4(const ENCODING *enc, const char *p) struct normal_encoding { ENCODING enc; unsigned char type[256]; +#ifdef XML_MIN_SIZE + int (*byteType)(const ENCODING *, const char *); + int (*isNameMin)(const ENCODING *, const char *); + int (*isNmstrtMin)(const ENCODING *, const char *); + int (*byteToAscii)(const ENCODING *, const char *); + int (*charMatches)(const ENCODING *, const char *, int); +#endif /* XML_MIN_SIZE */ int (*isName2)(const ENCODING *, const char *); int (*isName3)(const ENCODING *, const char *); int (*isName4)(const ENCODING *, const char *); @@ -140,6 +157,21 @@ struct normal_encoding { int (*isInvalid4)(const ENCODING *, const char *); }; +#ifdef XML_MIN_SIZE + +#define STANDARD_VTABLE(E) \ + E ## byteType, \ + E ## isNameMin, \ + E ## isNmstrtMin, \ + E ## byteToAscii, \ + E ## charMatches, + +#else + +#define STANDARD_VTABLE(E) /* as nothing */ + +#endif + #define NORMAL_VTABLE(E) \ E ## isName2, \ E ## isName3, \ @@ -150,16 +182,49 @@ struct normal_encoding { E ## isInvalid2, \ E ## isInvalid3, \ E ## isInvalid4 - + static int checkCharRefNumber(int); #include "xmltok_impl.h" +#ifdef XML_MIN_SIZE +#define sb_isNameMin isNever +#define sb_isNmstrtMin isNever +#endif + +#ifdef XML_MIN_SIZE +#define MINBPC(enc) ((enc)->minBytesPerChar) +#else /* minimum bytes per character */ -#define MINBPC 1 -#define BYTE_TYPE(enc, p) \ +#define MINBPC(enc) 1 +#endif + +#define SB_BYTE_TYPE(enc, p) \ (((struct normal_encoding *)(enc))->type[(unsigned char)*(p)]) + +#ifdef XML_MIN_SIZE +static +int sb_byteType(const ENCODING *enc, const char *p) +{ + return SB_BYTE_TYPE(enc, p); +} +#define BYTE_TYPE(enc, p) \ + (((const struct normal_encoding *)(enc))->byteType(enc, p)) +#else +#define BYTE_TYPE(enc, p) SB_BYTE_TYPE(enc, p) +#endif + +#ifdef XML_MIN_SIZE +#define BYTE_TO_ASCII(enc, p) \ + (((const struct normal_encoding *)(enc))->byteToAscii(enc, p)) +static +int sb_byteToAscii(const ENCODING *enc, const char *p) +{ + return *p; +} +#else #define BYTE_TO_ASCII(enc, p) (*p) +#endif #define IS_NAME_CHAR(enc, p, n) \ (((const struct normal_encoding *)(enc))->isName ## n(enc, p)) @@ -168,11 +233,28 @@ static int checkCharRefNumber(int); #define IS_INVALID_CHAR(enc, p, n) \ (((const struct normal_encoding *)(enc))->isInvalid ## n(enc, p)) +#ifdef XML_MIN_SIZE +#define IS_NAME_CHAR_MINBPC(enc, p) \ + (((const struct normal_encoding *)(enc))->isNameMin(enc, p)) +#define IS_NMSTRT_CHAR_MINBPC(enc, p) \ + (((const struct normal_encoding *)(enc))->isNmstrtMin(enc, p)) +#else #define IS_NAME_CHAR_MINBPC(enc, p) (0) #define IS_NMSTRT_CHAR_MINBPC(enc, p) (0) +#endif +#ifdef XML_MIN_SIZE +#define CHAR_MATCHES(enc, p, c) \ + (((const struct normal_encoding *)(enc))->charMatches(enc, p, c)) +static +int sb_charMatches(const ENCODING *enc, const char *p, int c) +{ + return *p == c; +} +#else /* c is an ASCII character */ #define CHAR_MATCHES(enc, p, c) (*(p) == c) +#endif #define PREFIX(ident) normal_ ## ident #include "xmltok_impl.c" @@ -252,22 +334,50 @@ void utf8_toUtf16(const ENCODING *enc, *toP = to; } -static const struct normal_encoding utf8_encoding = { +#ifdef XML_NS +static const struct normal_encoding utf8_encoding_ns = { { VTABLE1, utf8_toUtf8, utf8_toUtf16, 1, 1, 0 }, { #include "asciitab.h" #include "utf8tab.h" }, - NORMAL_VTABLE(utf8_) + STANDARD_VTABLE(sb_) NORMAL_VTABLE(utf8_) +}; +#endif + +static const struct normal_encoding utf8_encoding = { + { VTABLE1, utf8_toUtf8, utf8_toUtf16, 1, 1, 0 }, + { +#define BT_COLON BT_NMSTRT +#include "asciitab.h" +#undef BT_COLON +#include "utf8tab.h" + }, + STANDARD_VTABLE(sb_) NORMAL_VTABLE(utf8_) }; -static const struct normal_encoding internal_utf8_encoding = { +#ifdef XML_NS + +static const struct normal_encoding internal_utf8_encoding_ns = { { VTABLE1, utf8_toUtf8, utf8_toUtf16, 1, 1, 0 }, { #include "iasciitab.h" #include "utf8tab.h" }, - NORMAL_VTABLE(utf8_) + STANDARD_VTABLE(sb_) NORMAL_VTABLE(utf8_) +}; + +#endif + +static const struct normal_encoding internal_utf8_encoding = { + { VTABLE1, utf8_toUtf8, utf8_toUtf16, 1, 1, 0 }, + { +#define BT_COLON BT_NMSTRT +#include "iasciitab.h" +#undef BT_COLON +#include "utf8tab.h" + }, + STANDARD_VTABLE(sb_) NORMAL_VTABLE(utf8_) }; static @@ -304,12 +414,28 @@ void latin1_toUtf16(const ENCODING *enc, *(*toP)++ = (unsigned char)*(*fromP)++; } -static const struct normal_encoding latin1_encoding = { +#ifdef XML_NS + +static const struct normal_encoding latin1_encoding_ns = { { VTABLE1, latin1_toUtf8, latin1_toUtf16, 1, 0, 0 }, { #include "asciitab.h" #include "latin1tab.h" - } + }, + STANDARD_VTABLE(sb_) +}; + +#endif + +static const struct normal_encoding latin1_encoding = { + { VTABLE1, latin1_toUtf8, latin1_toUtf16, 1, 0, 0 }, + { +#define BT_COLON BT_NMSTRT +#include "asciitab.h" +#undef BT_COLON +#include "latin1tab.h" + }, + STANDARD_VTABLE(sb_) }; static @@ -321,15 +447,29 @@ void ascii_toUtf8(const ENCODING *enc, *(*toP)++ = *(*fromP)++; } -static const struct normal_encoding ascii_encoding = { +#ifdef XML_NS + +static const struct normal_encoding ascii_encoding_ns = { { VTABLE1, ascii_toUtf8, latin1_toUtf16, 1, 1, 0 }, { #include "asciitab.h" /* BT_NONXML == 0 */ - } + }, + STANDARD_VTABLE(sb_) }; -#undef PREFIX +#endif + +static const struct normal_encoding ascii_encoding = { + { VTABLE1, ascii_toUtf8, latin1_toUtf16, 1, 1, 0 }, + { +#define BT_COLON BT_NMSTRT +#include "asciitab.h" +#undef BT_COLON +/* BT_NONXML == 0 */ + }, + STANDARD_VTABLE(sb_) +}; static int unicode_byte_type(char hi, char lo) { @@ -349,11 +489,11 @@ static int unicode_byte_type(char hi, char lo) return BT_NONASCII; } -#define DEFINE_UTF16_TO_UTF8 \ +#define DEFINE_UTF16_TO_UTF8(E) \ static \ -void PREFIX(toUtf8)(const ENCODING *enc, \ - const char **fromP, const char *fromLim, \ - char **toP, const char *toLim) \ +void E ## toUtf8(const ENCODING *enc, \ + const char **fromP, const char *fromLim, \ + char **toP, const char *toLim) \ { \ const char *from; \ for (from = *fromP; from != fromLim; from += 2) { \ @@ -412,11 +552,11 @@ void PREFIX(toUtf8)(const ENCODING *enc, \ *fromP = from; \ } -#define DEFINE_UTF16_TO_UTF16 \ +#define DEFINE_UTF16_TO_UTF16(E) \ static \ -void PREFIX(toUtf16)(const ENCODING *enc, \ - const char **fromP, const char *fromLim, \ - unsigned short **toP, const unsigned short *toLim) \ +void E ## toUtf16(const ENCODING *enc, \ + const char **fromP, const char *fromLim, \ + unsigned short **toP, const unsigned short *toLim) \ { \ /* Avoid copying first half only of surrogate */ \ if (fromLim - *fromP > ((toLim - *toP) << 1) \ @@ -426,97 +566,92 @@ void PREFIX(toUtf16)(const ENCODING *enc, \ *(*toP)++ = (GET_HI(*fromP) << 8) | GET_LO(*fromP); \ } -#define PREFIX(ident) little2_ ## ident -#define MINBPC 2 -#define BYTE_TYPE(enc, p) \ - ((p)[1] == 0 \ - ? ((struct normal_encoding *)(enc))->type[(unsigned char)*(p)] \ - : unicode_byte_type((p)[1], (p)[0])) -#define BYTE_TO_ASCII(enc, p) ((p)[1] == 0 ? (p)[0] : -1) -#define CHAR_MATCHES(enc, p, c) ((p)[1] == 0 && (p)[0] == c) -#define IS_NAME_CHAR(enc, p, n) (0) -#define IS_NAME_CHAR_MINBPC(enc, p) \ - UCS2_GET_NAMING(namePages, (unsigned char)p[1], (unsigned char)p[0]) -#define IS_NMSTRT_CHAR(enc, p, n) (0) -#define IS_NMSTRT_CHAR_MINBPC(enc, p) \ - UCS2_GET_NAMING(nmstrtPages, (unsigned char)p[1], (unsigned char)p[0]) - -#include "xmltok_impl.c" - #define SET2(ptr, ch) \ (((ptr)[0] = ((ch) & 0xff)), ((ptr)[1] = ((ch) >> 8))) #define GET_LO(ptr) ((unsigned char)(ptr)[0]) #define GET_HI(ptr) ((unsigned char)(ptr)[1]) -DEFINE_UTF16_TO_UTF8 -DEFINE_UTF16_TO_UTF16 +DEFINE_UTF16_TO_UTF8(little2_) +DEFINE_UTF16_TO_UTF16(little2_) #undef SET2 #undef GET_LO #undef GET_HI -#undef MINBPC -#undef BYTE_TYPE -#undef BYTE_TO_ASCII -#undef CHAR_MATCHES -#undef IS_NAME_CHAR -#undef IS_NAME_CHAR_MINBPC -#undef IS_NMSTRT_CHAR -#undef IS_NMSTRT_CHAR_MINBPC -#undef IS_INVALID_CHAR - -static const struct normal_encoding little2_encoding = { - { VTABLE, 2, 0, -#if BYTE_ORDER == 12 - 1 -#else - 0 -#endif - }, -#include "asciitab.h" -#include "latin1tab.h" -}; - -#if BYTE_ORDER != 21 - -static const struct normal_encoding internal_little2_encoding = { - { VTABLE, 2, 0, 1 }, -#include "iasciitab.h" -#include "latin1tab.h" -}; - -#endif - -#undef PREFIX - -#define PREFIX(ident) big2_ ## ident -#define MINBPC 2 -/* CHAR_MATCHES is guaranteed to have MINBPC bytes available. */ -#define BYTE_TYPE(enc, p) \ - ((p)[0] == 0 \ - ? ((struct normal_encoding *)(enc))->type[(unsigned char)(p)[1]] \ - : unicode_byte_type((p)[0], (p)[1])) -#define BYTE_TO_ASCII(enc, p) ((p)[0] == 0 ? (p)[1] : -1) -#define CHAR_MATCHES(enc, p, c) ((p)[0] == 0 && (p)[1] == c) -#define IS_NAME_CHAR(enc, p, n) 0 -#define IS_NAME_CHAR_MINBPC(enc, p) \ - UCS2_GET_NAMING(namePages, (unsigned char)p[0], (unsigned char)p[1]) -#define IS_NMSTRT_CHAR(enc, p, n) (0) -#define IS_NMSTRT_CHAR_MINBPC(enc, p) \ - UCS2_GET_NAMING(nmstrtPages, (unsigned char)p[0], (unsigned char)p[1]) - -#include "xmltok_impl.c" #define SET2(ptr, ch) \ (((ptr)[0] = ((ch) >> 8)), ((ptr)[1] = ((ch) & 0xFF))) #define GET_LO(ptr) ((unsigned char)(ptr)[1]) #define GET_HI(ptr) ((unsigned char)(ptr)[0]) -DEFINE_UTF16_TO_UTF8 -DEFINE_UTF16_TO_UTF16 +DEFINE_UTF16_TO_UTF8(big2_) +DEFINE_UTF16_TO_UTF16(big2_) #undef SET2 #undef GET_LO #undef GET_HI + +#define LITTLE2_BYTE_TYPE(enc, p) \ + ((p)[1] == 0 \ + ? ((struct normal_encoding *)(enc))->type[(unsigned char)*(p)] \ + : unicode_byte_type((p)[1], (p)[0])) +#define LITTLE2_BYTE_TO_ASCII(enc, p) ((p)[1] == 0 ? (p)[0] : -1) +#define LITTLE2_CHAR_MATCHES(enc, p, c) ((p)[1] == 0 && (p)[0] == c) +#define LITTLE2_IS_NAME_CHAR_MINBPC(enc, p) \ + UCS2_GET_NAMING(namePages, (unsigned char)p[1], (unsigned char)p[0]) +#define LITTLE2_IS_NMSTRT_CHAR_MINBPC(enc, p) \ + UCS2_GET_NAMING(nmstrtPages, (unsigned char)p[1], (unsigned char)p[0]) + +#ifdef XML_MIN_SIZE + +static +int little2_byteType(const ENCODING *enc, const char *p) +{ + return LITTLE2_BYTE_TYPE(enc, p); +} + +static +int little2_byteToAscii(const ENCODING *enc, const char *p) +{ + return LITTLE2_BYTE_TO_ASCII(enc, p); +} + +static +int little2_charMatches(const ENCODING *enc, const char *p, int c) +{ + return LITTLE2_CHAR_MATCHES(enc, p, c); +} + +static +int little2_isNameMin(const ENCODING *enc, const char *p) +{ + return LITTLE2_IS_NAME_CHAR_MINBPC(enc, p); +} + +static +int little2_isNmstrtMin(const ENCODING *enc, const char *p) +{ + return LITTLE2_IS_NMSTRT_CHAR_MINBPC(enc, p); +} + +#undef VTABLE +#define VTABLE VTABLE1, little2_toUtf8, little2_toUtf16 + +#else /* not XML_MIN_SIZE */ + +#undef PREFIX +#define PREFIX(ident) little2_ ## ident +#define MINBPC(enc) 2 +/* CHAR_MATCHES is guaranteed to have MINBPC bytes available. */ +#define BYTE_TYPE(enc, p) LITTLE2_BYTE_TYPE(enc, p) +#define BYTE_TO_ASCII(enc, p) LITTLE2_BYTE_TO_ASCII(enc, p) +#define CHAR_MATCHES(enc, p, c) LITTLE2_CHAR_MATCHES(enc, p, c) +#define IS_NAME_CHAR(enc, p, n) 0 +#define IS_NAME_CHAR_MINBPC(enc, p) LITTLE2_IS_NAME_CHAR_MINBPC(enc, p) +#define IS_NMSTRT_CHAR(enc, p, n) (0) +#define IS_NMSTRT_CHAR_MINBPC(enc, p) LITTLE2_IS_NMSTRT_CHAR_MINBPC(enc, p) + +#include "xmltok_impl.c" + #undef MINBPC #undef BYTE_TYPE #undef BYTE_TO_ASCII @@ -527,24 +662,207 @@ DEFINE_UTF16_TO_UTF16 #undef IS_NMSTRT_CHAR_MINBPC #undef IS_INVALID_CHAR -static const struct normal_encoding big2_encoding = { +#endif /* not XML_MIN_SIZE */ + +#ifdef XML_NS + +static const struct normal_encoding little2_encoding_ns = { { VTABLE, 2, 0, -#if BYTE_ORDER == 21 +#if XML_BYTE_ORDER == 12 + 1 +#else + 0 +#endif + }, + { +#include "asciitab.h" +#include "latin1tab.h" + }, + STANDARD_VTABLE(little2_) +}; + +#endif + +static const struct normal_encoding little2_encoding = { + { VTABLE, 2, 0, +#if XML_BYTE_ORDER == 12 + 1 +#else + 0 +#endif + }, + { +#define BT_COLON BT_NMSTRT +#include "asciitab.h" +#undef BT_COLON +#include "latin1tab.h" + }, + STANDARD_VTABLE(little2_) +}; + +#if XML_BYTE_ORDER != 21 + +#ifdef XML_NS + +static const struct normal_encoding internal_little2_encoding_ns = { + { VTABLE, 2, 0, 1 }, + { +#include "iasciitab.h" +#include "latin1tab.h" + }, + STANDARD_VTABLE(little2_) +}; + +#endif + +static const struct normal_encoding internal_little2_encoding = { + { VTABLE, 2, 0, 1 }, + { +#define BT_COLON BT_NMSTRT +#include "iasciitab.h" +#undef BT_COLON +#include "latin1tab.h" + }, + STANDARD_VTABLE(little2_) +}; + +#endif + + +#define BIG2_BYTE_TYPE(enc, p) \ + ((p)[0] == 0 \ + ? ((struct normal_encoding *)(enc))->type[(unsigned char)(p)[1]] \ + : unicode_byte_type((p)[0], (p)[1])) +#define BIG2_BYTE_TO_ASCII(enc, p) ((p)[0] == 0 ? (p)[1] : -1) +#define BIG2_CHAR_MATCHES(enc, p, c) ((p)[0] == 0 && (p)[1] == c) +#define BIG2_IS_NAME_CHAR_MINBPC(enc, p) \ + UCS2_GET_NAMING(namePages, (unsigned char)p[0], (unsigned char)p[1]) +#define BIG2_IS_NMSTRT_CHAR_MINBPC(enc, p) \ + UCS2_GET_NAMING(nmstrtPages, (unsigned char)p[0], (unsigned char)p[1]) + +#ifdef XML_MIN_SIZE + +static +int big2_byteType(const ENCODING *enc, const char *p) +{ + return BIG2_BYTE_TYPE(enc, p); +} + +static +int big2_byteToAscii(const ENCODING *enc, const char *p) +{ + return BIG2_BYTE_TO_ASCII(enc, p); +} + +static +int big2_charMatches(const ENCODING *enc, const char *p, int c) +{ + return BIG2_CHAR_MATCHES(enc, p, c); +} + +static +int big2_isNameMin(const ENCODING *enc, const char *p) +{ + return BIG2_IS_NAME_CHAR_MINBPC(enc, p); +} + +static +int big2_isNmstrtMin(const ENCODING *enc, const char *p) +{ + return BIG2_IS_NMSTRT_CHAR_MINBPC(enc, p); +} + +#undef VTABLE +#define VTABLE VTABLE1, big2_toUtf8, big2_toUtf16 + +#else /* not XML_MIN_SIZE */ + +#undef PREFIX +#define PREFIX(ident) big2_ ## ident +#define MINBPC(enc) 2 +/* CHAR_MATCHES is guaranteed to have MINBPC bytes available. */ +#define BYTE_TYPE(enc, p) BIG2_BYTE_TYPE(enc, p) +#define BYTE_TO_ASCII(enc, p) BIG2_BYTE_TO_ASCII(enc, p) +#define CHAR_MATCHES(enc, p, c) BIG2_CHAR_MATCHES(enc, p, c) +#define IS_NAME_CHAR(enc, p, n) 0 +#define IS_NAME_CHAR_MINBPC(enc, p) BIG2_IS_NAME_CHAR_MINBPC(enc, p) +#define IS_NMSTRT_CHAR(enc, p, n) (0) +#define IS_NMSTRT_CHAR_MINBPC(enc, p) BIG2_IS_NMSTRT_CHAR_MINBPC(enc, p) + +#include "xmltok_impl.c" + +#undef MINBPC +#undef BYTE_TYPE +#undef BYTE_TO_ASCII +#undef CHAR_MATCHES +#undef IS_NAME_CHAR +#undef IS_NAME_CHAR_MINBPC +#undef IS_NMSTRT_CHAR +#undef IS_NMSTRT_CHAR_MINBPC +#undef IS_INVALID_CHAR + +#endif /* not XML_MIN_SIZE */ + +#ifdef XML_NS + +static const struct normal_encoding big2_encoding_ns = { + { VTABLE, 2, 0, +#if XML_BYTE_ORDER == 21 1 #else 0 #endif }, + { #include "asciitab.h" #include "latin1tab.h" + }, + STANDARD_VTABLE(big2_) }; -#if BYTE_ORDER != 12 +#endif + +static const struct normal_encoding big2_encoding = { + { VTABLE, 2, 0, +#if XML_BYTE_ORDER == 21 + 1 +#else + 0 +#endif + }, + { +#define BT_COLON BT_NMSTRT +#include "asciitab.h" +#undef BT_COLON +#include "latin1tab.h" + }, + STANDARD_VTABLE(big2_) +}; + +#if XML_BYTE_ORDER != 12 + +#ifdef XML_NS + +static const struct normal_encoding internal_big2_encoding_ns = { + { VTABLE, 2, 0, 1 }, + { +#include "iasciitab.h" +#include "latin1tab.h" + }, + STANDARD_VTABLE(big2_) +}; + +#endif static const struct normal_encoding internal_big2_encoding = { { VTABLE, 2, 0, 1 }, + { +#define BT_COLON BT_NMSTRT #include "iasciitab.h" +#undef BT_COLON #include "latin1tab.h" + }, + STANDARD_VTABLE(big2_) }; #endif @@ -569,60 +887,6 @@ int streqci(const char *s1, const char *s2) return 1; } -static -int initScan(const ENCODING *enc, int state, const char *ptr, const char *end, - const char **nextTokPtr) -{ - const ENCODING **encPtr; - - if (ptr == end) - return XML_TOK_NONE; - encPtr = ((const INIT_ENCODING *)enc)->encPtr; - if (ptr + 1 == end) { - switch ((unsigned char)*ptr) { - case 0xFE: - case 0xFF: - case 0x00: - case 0x3C: - return XML_TOK_PARTIAL; - } - } - else { - switch (((unsigned char)ptr[0] << 8) | (unsigned char)ptr[1]) { - case 0x003C: - *encPtr = &big2_encoding.enc; - return XmlTok(*encPtr, state, ptr, end, nextTokPtr); - case 0xFEFF: - *nextTokPtr = ptr + 2; - *encPtr = &big2_encoding.enc; - return XML_TOK_BOM; - case 0x3C00: - *encPtr = &little2_encoding.enc; - return XmlTok(*encPtr, state, ptr, end, nextTokPtr); - case 0xFFFE: - *nextTokPtr = ptr + 2; - *encPtr = &little2_encoding.enc; - return XML_TOK_BOM; - } - } - *encPtr = &utf8_encoding.enc; - return XmlTok(*encPtr, state, ptr, end, nextTokPtr); -} - -static -int initScanProlog(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) -{ - return initScan(enc, XML_PROLOG_STATE, ptr, end, nextTokPtr); -} - -static -int initScanContent(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) -{ - return initScan(enc, XML_CONTENT_STATE, ptr, end, nextTokPtr); -} - static void initUpdatePosition(const ENCODING *enc, const char *ptr, const char *end, POSITION *pos) @@ -630,50 +894,6 @@ void initUpdatePosition(const ENCODING *enc, const char *ptr, normal_updatePosition(&utf8_encoding.enc, ptr, end, pos); } -const ENCODING *XmlGetUtf8InternalEncoding() -{ - return &internal_utf8_encoding.enc; -} - -const ENCODING *XmlGetUtf16InternalEncoding() -{ -#if BYTE_ORDER == 12 - return &internal_little2_encoding.enc; -#elif BYTE_ORDER == 21 - return &internal_big2_encoding.enc; -#else - const short n = 1; - return *(const char *)&n ? &internal_little2_encoding.enc : &internal_big2_encoding.enc; -#endif -} - -int XmlInitEncoding(INIT_ENCODING *p, const ENCODING **encPtr, const char *name) -{ - if (name) { - if (streqci(name, "ISO-8859-1")) { - *encPtr = &latin1_encoding.enc; - return 1; - } - if (streqci(name, "UTF-8")) { - *encPtr = &utf8_encoding.enc; - return 1; - } - if (streqci(name, "US-ASCII")) { - *encPtr = &ascii_encoding.enc; - return 1; - } - if (!streqci(name, "UTF-16")) - return 0; - } - p->initEnc.scanners[XML_PROLOG_STATE] = initScanProlog; - p->initEnc.scanners[XML_CONTENT_STATE] = initScanContent; - p->initEnc.updatePosition = initUpdatePosition; - p->initEnc.minBytesPerChar = 1; - p->encPtr = encPtr; - *encPtr = &(p->initEnc); - return 1; -} - static int toAscii(const ENCODING *enc, const char *ptr, const char *end) { @@ -690,10 +910,10 @@ static int isSpace(int c) { switch (c) { - case ' ': - case '\r': - case '\n': - case '\t': + case 0x20: + case 0xD: + case 0xA: + case 0x9: return 1; } return 0; @@ -783,44 +1003,18 @@ int parsePseudoAttribute(const ENCODING *enc, } static -const ENCODING *findEncoding(const ENCODING *enc, const char *ptr, const char *end) -{ -#define ENCODING_MAX 128 - char buf[ENCODING_MAX]; - char *p = buf; - int i; - XmlUtf8Convert(enc, &ptr, end, &p, p + ENCODING_MAX - 1); - if (ptr != end) - return 0; - *p = 0; - for (i = 0; buf[i]; i++) { - if ('a' <= buf[i] && buf[i] <= 'z') - buf[i] += 'A' - 'a'; - } - if (streqci(buf, "UTF-8")) - return &utf8_encoding.enc; - if (streqci(buf, "ISO-8859-1")) - return &latin1_encoding.enc; - if (streqci(buf, "US-ASCII")) - return &ascii_encoding.enc; - if (streqci(buf, "UTF-16")) { - static const unsigned short n = 1; - if (enc->minBytesPerChar == 2) - return enc; - return &big2_encoding.enc; - } - return 0; -} - -int XmlParseXmlDecl(int isGeneralTextEntity, - const ENCODING *enc, - const char *ptr, - const char *end, - const char **badPtr, - const char **versionPtr, - const char **encodingName, - const ENCODING **encoding, - int *standalone) +int doParseXmlDecl(const ENCODING *(*encodingFinder)(const ENCODING *, + const char *, + const char *), + int isGeneralTextEntity, + const ENCODING *enc, + const char *ptr, + const char *end, + const char **badPtr, + const char **versionPtr, + const char **encodingName, + const ENCODING **encoding, + int *standalone) { const char *val = 0; const char *name = 0; @@ -861,7 +1055,7 @@ int XmlParseXmlDecl(int isGeneralTextEntity, if (encodingName) *encodingName = val; if (encoding) - *encoding = findEncoding(enc, val, ptr - enc->minBytesPerChar); + *encoding = encodingFinder(enc, val, ptr - enc->minBytesPerChar); if (!parsePseudoAttribute(enc, ptr, end, &name, &val, &ptr)) { *badPtr = ptr; return 0; @@ -1139,3 +1333,195 @@ XmlInitUnknownEncoding(void *mem, e->normal.enc.utf16Convert = unknown_toUtf16; return &(e->normal.enc); } + +/* If this enumeration is changed, getEncodingIndex and encodings +must also be changed. */ +enum { + UNKNOWN_ENC = -1, + ISO_8859_1_ENC = 0, + US_ASCII_ENC, + UTF_8_ENC, + UTF_16_ENC, + UTF_16BE_ENC, + UTF_16LE_ENC, + /* must match encodingNames up to here */ + NO_ENC +}; + +static +int getEncodingIndex(const char *name) +{ + static const char *encodingNames[] = { + "ISO-8859-1", + "US-ASCII", + "UTF-8", + "UTF-16", + "UTF-16BE" + "UTF-16LE", + }; + int i; + if (name == 0) + return NO_ENC; + for (i = 0; i < sizeof(encodingNames)/sizeof(encodingNames[0]); i++) + if (streqci(name, encodingNames[i])) + return i; + return UNKNOWN_ENC; +} + +/* For binary compatibility, we store the index of the encoding specified +at initialization in the isUtf16 member. */ + +#define INIT_ENC_INDEX(enc) ((enc)->initEnc.isUtf16) + +/* This is what detects the encoding. +encodingTable maps from encoding indices to encodings; +INIT_ENC_INDEX(enc) is the index of the external (protocol) specified encoding; +state is XML_CONTENT_STATE if we're parsing an external text entity, +and XML_PROLOG_STATE otherwise. +*/ + + +static +int initScan(const ENCODING **encodingTable, + const INIT_ENCODING *enc, + int state, + const char *ptr, + const char *end, + const char **nextTokPtr) +{ + const ENCODING **encPtr; + + if (ptr == end) + return XML_TOK_NONE; + encPtr = enc->encPtr; + if (ptr + 1 == end) { + /* only a single byte available for auto-detection */ + /* a well-formed document entity must have more than one byte */ + if (state != XML_CONTENT_STATE) + return XML_TOK_PARTIAL; + /* so we're parsing an external text entity... */ + /* if UTF-16 was externally specified, then we need at least 2 bytes */ + switch (INIT_ENC_INDEX(enc)) { + case UTF_16_ENC: + case UTF_16LE_ENC: + case UTF_16BE_ENC: + return XML_TOK_PARTIAL; + } + switch ((unsigned char)*ptr) { + case 0xFE: + case 0xFF: + case 0xEF: /* possibly first byte of UTF-8 BOM */ + if (INIT_ENC_INDEX(enc) == ISO_8859_1_ENC + && state == XML_CONTENT_STATE) + break; + /* fall through */ + case 0x00: + case 0x3C: + return XML_TOK_PARTIAL; + } + } + else { + switch (((unsigned char)ptr[0] << 8) | (unsigned char)ptr[1]) { + case 0xFEFF: + if (INIT_ENC_INDEX(enc) == ISO_8859_1_ENC + && state == XML_CONTENT_STATE) + break; + *nextTokPtr = ptr + 2; + *encPtr = encodingTable[UTF_16BE_ENC]; + return XML_TOK_BOM; + /* 00 3C is handled in the default case */ + case 0x3C00: + if ((INIT_ENC_INDEX(enc) == UTF_16BE_ENC + || INIT_ENC_INDEX(enc) == UTF_16_ENC) + && state == XML_CONTENT_STATE) + break; + *encPtr = encodingTable[UTF_16LE_ENC]; + return XmlTok(*encPtr, state, ptr, end, nextTokPtr); + case 0xFFFE: + if (INIT_ENC_INDEX(enc) == ISO_8859_1_ENC + && state == XML_CONTENT_STATE) + break; + *nextTokPtr = ptr + 2; + *encPtr = encodingTable[UTF_16LE_ENC]; + return XML_TOK_BOM; + case 0xEFBB: + /* Maybe a UTF-8 BOM (EF BB BF) */ + /* If there's an explicitly specified (external) encoding + of ISO-8859-1 or some flavour of UTF-16 + and this is an external text entity, + don't look for the BOM, + because it might be a legal data. */ + if (state == XML_CONTENT_STATE) { + int e = INIT_ENC_INDEX(enc); + if (e == ISO_8859_1_ENC || e == UTF_16BE_ENC || e == UTF_16LE_ENC || e == UTF_16_ENC) + break; + } + if (ptr + 2 == end) + return XML_TOK_PARTIAL; + if ((unsigned char)ptr[2] == 0xBF) { + *encPtr = encodingTable[UTF_8_ENC]; + return XML_TOK_BOM; + } + break; + default: + if (ptr[0] == '\0') { + /* 0 isn't a legal data character. Furthermore a document entity can only + start with ASCII characters. So the only way this can fail to be big-endian + UTF-16 if it it's an external parsed general entity that's labelled as + UTF-16LE. */ + if (state == XML_CONTENT_STATE && INIT_ENC_INDEX(enc) == UTF_16LE_ENC) + break; + *encPtr = encodingTable[UTF_16BE_ENC]; + return XmlTok(*encPtr, state, ptr, end, nextTokPtr); + } + else if (ptr[1] == '\0') { + /* We could recover here in the case: + - parsing an external entity + - second byte is 0 + - no externally specified encoding + - no encoding declaration + by assuming UTF-16LE. But we don't, because this would mean when + presented just with a single byte, we couldn't reliably determine + whether we needed further bytes. */ + if (state == XML_CONTENT_STATE) + break; + *encPtr = encodingTable[UTF_16LE_ENC]; + return XmlTok(*encPtr, state, ptr, end, nextTokPtr); + } + break; + } + } + *encPtr = encodingTable[INIT_ENC_INDEX(enc)]; + return XmlTok(*encPtr, state, ptr, end, nextTokPtr); +} + + +#define NS(x) x +#define ns(x) x +#include "xmltok_ns.c" +#undef NS +#undef ns + +#ifdef XML_NS + +#define NS(x) x ## NS +#define ns(x) x ## _ns + +#include "xmltok_ns.c" + +#undef NS +#undef ns + +ENCODING * +XmlInitUnknownEncodingNS(void *mem, + int *table, + int (*convert)(void *userData, const char *p), + void *userData) +{ + ENCODING *enc = XmlInitUnknownEncoding(mem, table, convert, userData); + if (enc) + ((struct normal_encoding *)enc)->type[':'] = BT_COLON; + return enc; +} + +#endif /* XML_NS */ diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok.h b/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok.h index 9cddd36c442..06544d15cb2 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok.h +++ b/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok.h @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,10 +12,20 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ #ifndef XmlTok_INCLUDED @@ -94,6 +104,10 @@ extern "C" { /* The following token is returned only by XmlCdataSectionTok */ #define XML_TOK_CDATA_SECT_CLOSE 40 +/* With namespace processing this is returned by XmlPrologTok + for a name with a colon. */ +#define XML_TOK_PREFIXED_NAME 41 + #define XML_N_STATES 3 #define XML_PROLOG_STATE 0 #define XML_CONTENT_STATE 1 @@ -186,16 +200,16 @@ literals, comments and processing instructions. #define XmlTok(enc, state, ptr, end, nextTokPtr) \ - (((enc)->scanners[state]) (enc, ptr, end, nextTokPtr)) + (((enc)->scanners[state])(enc, ptr, end, nextTokPtr)) #define XmlPrologTok(enc, ptr, end, nextTokPtr) \ - (((enc)->scanners[XML_PROLOG_STATE]) (enc, ptr, end, nextTokPtr)) + XmlTok(enc, XML_PROLOG_STATE, ptr, end, nextTokPtr) #define XmlContentTok(enc, ptr, end, nextTokPtr) \ - (((enc)->scanners[XML_CONTENT_STATE]) (enc, ptr, end, nextTokPtr)) + XmlTok(enc, XML_CONTENT_STATE, ptr, end, nextTokPtr) #define XmlCdataSectionTok(enc, ptr, end, nextTokPtr) \ - (((enc)->scanners[XML_CDATA_SECTION_STATE]) (enc, ptr, end, nextTokPtr)) + XmlTok(enc, XML_CDATA_SECTION_STATE, ptr, end, nextTokPtr) /* This is used for performing a 2nd-level tokenization on the content of a literal that has already been returned by XmlTok. */ @@ -204,10 +218,10 @@ the content of a literal that has already been returned by XmlTok. */ (((enc)->literalScanners[literalType])(enc, ptr, end, nextTokPtr)) #define XmlAttributeValueTok(enc, ptr, end, nextTokPtr) \ - (((enc)->literalScanners[XML_ATTRIBUTE_VALUE_LITERAL])(enc, ptr, end, nextTokPtr)) + XmlLiteralTok(enc, XML_ATTRIBUTE_VALUE_LITERAL, ptr, end, nextTokPtr) #define XmlEntityValueTok(enc, ptr, end, nextTokPtr) \ - (((enc)->literalScanners[XML_ENTITY_VALUE_LITERAL])(enc, ptr, end, nextTokPtr)) + XmlLiteralTok(enc, XML_ENTITY_VALUE_LITERAL, ptr, end, nextTokPtr) #define XmlSameName(enc, ptr1, ptr2) (((enc)->sameName)(enc, ptr1, ptr2)) @@ -266,9 +280,26 @@ int XMLTOKAPI XmlSizeOfUnknownEncoding(); ENCODING XMLTOKAPI * XmlInitUnknownEncoding(void *mem, int *table, - int (*convert)(void *userData, const char *p), + int (*conv)(void *userData, const char *p), void *userData); +int XMLTOKAPI XmlParseXmlDeclNS(int isGeneralTextEntity, + const ENCODING *enc, + const char *ptr, + const char *end, + const char **badPtr, + const char **versionPtr, + const char **encodingNamePtr, + const ENCODING **namedEncodingPtr, + int *standalonePtr); +int XMLTOKAPI XmlInitEncodingNS(INIT_ENCODING *, const ENCODING **, const char *name); +const ENCODING XMLTOKAPI *XmlGetUtf8InternalEncodingNS(); +const ENCODING XMLTOKAPI *XmlGetUtf16InternalEncodingNS(); +ENCODING XMLTOKAPI * +XmlInitUnknownEncodingNS(void *mem, + int *table, + int (*conv)(void *userData, const char *p), + void *userData); #ifdef __cplusplus } #endif diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok_impl.c b/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok_impl.c index fa4916252ff..f343b3fa0f7 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok_impl.c +++ b/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok_impl.c @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,10 +12,20 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ #ifndef IS_INVALID_CHAR @@ -25,7 +35,7 @@ Contributor(s): #define INVALID_LEAD_CASE(n, ptr, nextTokPtr) \ case BT_LEAD ## n: \ if (end - ptr < n) \ - return XML_TOK_PARTIAL_CHAR; \ + return XML_TOK_PARTIAL_CHAR; \ if (IS_INVALID_CHAR(enc, ptr, n)) { \ *(nextTokPtr) = (ptr); \ return XML_TOK_INVALID; \ @@ -65,7 +75,7 @@ Contributor(s): case BT_DIGIT: \ case BT_NAME: \ case BT_MINUS: \ - ptr += MINBPC; \ + ptr += MINBPC(enc); \ break; \ CHECK_NAME_CASE(2, enc, ptr, end, nextTokPtr) \ CHECK_NAME_CASE(3, enc, ptr, end, nextTokPtr) \ @@ -90,7 +100,7 @@ Contributor(s): } \ case BT_NMSTRT: \ case BT_HEX: \ - ptr += MINBPC; \ + ptr += MINBPC(enc); \ break; \ CHECK_NMSTRT_CASE(2, enc, ptr, end, nextTokPtr) \ CHECK_NMSTRT_CASE(3, enc, ptr, end, nextTokPtr) \ @@ -104,34 +114,34 @@ Contributor(s): static int PREFIX(scanComment)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { if (ptr != end) { if (!CHAR_MATCHES(enc, ptr, '-')) { *nextTokPtr = ptr; return XML_TOK_INVALID; } - ptr += MINBPC; + ptr += MINBPC(enc); while (ptr != end) { switch (BYTE_TYPE(enc, ptr)) { INVALID_CASES(ptr, nextTokPtr) case BT_MINUS: - if ((ptr += MINBPC) == end) - return XML_TOK_PARTIAL; - if (CHAR_MATCHES(enc, ptr, '-')) { - if ((ptr += MINBPC) == end) - return XML_TOK_PARTIAL; - if (!CHAR_MATCHES(enc, ptr, '>')) { - *nextTokPtr = ptr; - return XML_TOK_INVALID; - } - *nextTokPtr = ptr + MINBPC; - return XML_TOK_COMMENT; - } - break; + if ((ptr += MINBPC(enc)) == end) + return XML_TOK_PARTIAL; + if (CHAR_MATCHES(enc, ptr, '-')) { + if ((ptr += MINBPC(enc)) == end) + return XML_TOK_PARTIAL; + if (!CHAR_MATCHES(enc, ptr, '>')) { + *nextTokPtr = ptr; + return XML_TOK_INVALID; + } + *nextTokPtr = ptr + MINBPC(enc); + return XML_TOK_COMMENT; + } + break; default: - ptr += MINBPC; - break; + ptr += MINBPC(enc); + break; } } } @@ -142,19 +152,19 @@ int PREFIX(scanComment)(const ENCODING *enc, const char *ptr, const char *end, static int PREFIX(scanDecl)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { if (ptr == end) return XML_TOK_PARTIAL; switch (BYTE_TYPE(enc, ptr)) { case BT_MINUS: - return PREFIX(scanComment)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanComment)(enc, ptr + MINBPC(enc), end, nextTokPtr); case BT_LSQB: - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_COND_SECT_OPEN; case BT_NMSTRT: case BT_HEX: - ptr += MINBPC; + ptr += MINBPC(enc); break; default: *nextTokPtr = ptr; @@ -163,13 +173,13 @@ int PREFIX(scanDecl)(const ENCODING *enc, const char *ptr, const char *end, while (ptr != end) { switch (BYTE_TYPE(enc, ptr)) { case BT_PERCNT: - if (ptr + MINBPC == end) - return XML_TOK_PARTIAL; + if (ptr + MINBPC(enc) == end) + return XML_TOK_PARTIAL; /* don't allow */ - switch (BYTE_TYPE(enc, ptr + MINBPC)) { + switch (BYTE_TYPE(enc, ptr + MINBPC(enc))) { case BT_S: case BT_CR: case BT_LF: case BT_PERCNT: - *nextTokPtr = ptr; - return XML_TOK_INVALID; + *nextTokPtr = ptr; + return XML_TOK_INVALID; } /* fall through */ case BT_S: case BT_CR: case BT_LF: @@ -177,7 +187,7 @@ int PREFIX(scanDecl)(const ENCODING *enc, const char *ptr, const char *end, return XML_TOK_DECL_OPEN; case BT_NMSTRT: case BT_HEX: - ptr += MINBPC; + ptr += MINBPC(enc); break; default: *nextTokPtr = ptr; @@ -192,7 +202,7 @@ int PREFIX(checkPiTarget)(const ENCODING *enc, const char *ptr, const char *end, { int upper = 0; *tokPtr = XML_TOK_PI; - if (end - ptr != MINBPC*3) + if (end - ptr != MINBPC(enc)*3) return 1; switch (BYTE_TO_ASCII(enc, ptr)) { case 'x': @@ -203,7 +213,7 @@ int PREFIX(checkPiTarget)(const ENCODING *enc, const char *ptr, const char *end, default: return 1; } - ptr += MINBPC; + ptr += MINBPC(enc); switch (BYTE_TO_ASCII(enc, ptr)) { case 'm': break; @@ -213,7 +223,7 @@ int PREFIX(checkPiTarget)(const ENCODING *enc, const char *ptr, const char *end, default: return 1; } - ptr += MINBPC; + ptr += MINBPC(enc); switch (BYTE_TO_ASCII(enc, ptr)) { case 'l': break; @@ -233,7 +243,7 @@ int PREFIX(checkPiTarget)(const ENCODING *enc, const char *ptr, const char *end, static int PREFIX(scanPi)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { int tok; const char *target = ptr; @@ -250,39 +260,39 @@ int PREFIX(scanPi)(const ENCODING *enc, const char *ptr, const char *end, CHECK_NAME_CASES(enc, ptr, end, nextTokPtr) case BT_S: case BT_CR: case BT_LF: if (!PREFIX(checkPiTarget)(enc, target, ptr, &tok)) { - *nextTokPtr = ptr; - return XML_TOK_INVALID; + *nextTokPtr = ptr; + return XML_TOK_INVALID; } - ptr += MINBPC; + ptr += MINBPC(enc); while (ptr != end) { switch (BYTE_TYPE(enc, ptr)) { INVALID_CASES(ptr, nextTokPtr) - case BT_QUEST: - ptr += MINBPC; - if (ptr == end) - return XML_TOK_PARTIAL; - if (CHAR_MATCHES(enc, ptr, '>')) { - *nextTokPtr = ptr + MINBPC; - return tok; - } - break; - default: - ptr += MINBPC; - break; - } + case BT_QUEST: + ptr += MINBPC(enc); + if (ptr == end) + return XML_TOK_PARTIAL; + if (CHAR_MATCHES(enc, ptr, '>')) { + *nextTokPtr = ptr + MINBPC(enc); + return tok; + } + break; + default: + ptr += MINBPC(enc); + break; + } } return XML_TOK_PARTIAL; case BT_QUEST: if (!PREFIX(checkPiTarget)(enc, target, ptr, &tok)) { - *nextTokPtr = ptr; - return XML_TOK_INVALID; + *nextTokPtr = ptr; + return XML_TOK_INVALID; } - ptr += MINBPC; + ptr += MINBPC(enc); if (ptr == end) - return XML_TOK_PARTIAL; + return XML_TOK_PARTIAL; if (CHAR_MATCHES(enc, ptr, '>')) { - *nextTokPtr = ptr + MINBPC; - return tok; + *nextTokPtr = ptr + MINBPC(enc); + return tok; } /* fall through */ default: @@ -296,13 +306,13 @@ int PREFIX(scanPi)(const ENCODING *enc, const char *ptr, const char *end, static int PREFIX(scanCdataSection)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { int i; /* CDATA[ */ - if (end - ptr < 6 * MINBPC) + if (end - ptr < 6 * MINBPC(enc)) return XML_TOK_PARTIAL; - for (i = 0; i < 6; i++, ptr += MINBPC) { + for (i = 0; i < 6; i++, ptr += MINBPC(enc)) { if (!CHAR_MATCHES(enc, ptr, "CDATA["[i])) { *nextTokPtr = ptr; return XML_TOK_INVALID; @@ -314,51 +324,49 @@ int PREFIX(scanCdataSection)(const ENCODING *enc, const char *ptr, const char *e static int PREFIX(cdataSectionTok)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { if (ptr == end) return XML_TOK_NONE; -#if MINBPC > 1 - { + if (MINBPC(enc) > 1) { size_t n = end - ptr; - if (n & (MINBPC - 1)) { - n &= ~(MINBPC - 1); + if (n & (MINBPC(enc) - 1)) { + n &= ~(MINBPC(enc) - 1); if (n == 0) - return XML_TOK_PARTIAL; + return XML_TOK_PARTIAL; end = ptr + n; } } -#endif switch (BYTE_TYPE(enc, ptr)) { case BT_RSQB: - ptr += MINBPC; + ptr += MINBPC(enc); if (ptr == end) return XML_TOK_PARTIAL; if (!CHAR_MATCHES(enc, ptr, ']')) break; - ptr += MINBPC; + ptr += MINBPC(enc); if (ptr == end) return XML_TOK_PARTIAL; if (!CHAR_MATCHES(enc, ptr, '>')) { - ptr -= MINBPC; + ptr -= MINBPC(enc); break; } - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_CDATA_SECT_CLOSE; case BT_CR: - ptr += MINBPC; + ptr += MINBPC(enc); if (ptr == end) return XML_TOK_PARTIAL; if (BYTE_TYPE(enc, ptr) == BT_LF) - ptr += MINBPC; + ptr += MINBPC(enc); *nextTokPtr = ptr; return XML_TOK_DATA_NEWLINE; case BT_LF: - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_DATA_NEWLINE; INVALID_CASES(ptr, nextTokPtr) default: - ptr += MINBPC; + ptr += MINBPC(enc); break; } while (ptr != end) { @@ -366,8 +374,8 @@ int PREFIX(cdataSectionTok)(const ENCODING *enc, const char *ptr, const char *en #define LEAD_CASE(n) \ case BT_LEAD ## n: \ if (end - ptr < n || IS_INVALID_CHAR(enc, ptr, n)) { \ - *nextTokPtr = ptr; \ - return XML_TOK_DATA_CHARS; \ + *nextTokPtr = ptr; \ + return XML_TOK_DATA_CHARS; \ } \ ptr += n; \ break; @@ -382,7 +390,7 @@ int PREFIX(cdataSectionTok)(const ENCODING *enc, const char *ptr, const char *en *nextTokPtr = ptr; return XML_TOK_DATA_CHARS; default: - ptr += MINBPC; + ptr += MINBPC(enc); break; } } @@ -394,7 +402,7 @@ int PREFIX(cdataSectionTok)(const ENCODING *enc, const char *ptr, const char *en static int PREFIX(scanEndTag)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { if (ptr == end) return XML_TOK_PARTIAL; @@ -408,21 +416,27 @@ int PREFIX(scanEndTag)(const ENCODING *enc, const char *ptr, const char *end, switch (BYTE_TYPE(enc, ptr)) { CHECK_NAME_CASES(enc, ptr, end, nextTokPtr) case BT_S: case BT_CR: case BT_LF: - for (ptr += MINBPC; ptr != end; ptr += MINBPC) { - switch (BYTE_TYPE(enc, ptr)) { - case BT_S: case BT_CR: case BT_LF: - break; - case BT_GT: - *nextTokPtr = ptr + MINBPC; + for (ptr += MINBPC(enc); ptr != end; ptr += MINBPC(enc)) { + switch (BYTE_TYPE(enc, ptr)) { + case BT_S: case BT_CR: case BT_LF: + break; + case BT_GT: + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_END_TAG; - default: - *nextTokPtr = ptr; - return XML_TOK_INVALID; - } + default: + *nextTokPtr = ptr; + return XML_TOK_INVALID; + } } return XML_TOK_PARTIAL; +#ifdef XML_NS + case BT_COLON: + /* no need to check qname syntax here, since end-tag must match exactly */ + ptr += MINBPC(enc); + break; +#endif case BT_GT: - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_END_TAG; default: *nextTokPtr = ptr; @@ -436,7 +450,7 @@ int PREFIX(scanEndTag)(const ENCODING *enc, const char *ptr, const char *end, static int PREFIX(scanHexCharRef)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { if (ptr != end) { switch (BYTE_TYPE(enc, ptr)) { @@ -447,17 +461,17 @@ int PREFIX(scanHexCharRef)(const ENCODING *enc, const char *ptr, const char *end *nextTokPtr = ptr; return XML_TOK_INVALID; } - for (ptr += MINBPC; ptr != end; ptr += MINBPC) { + for (ptr += MINBPC(enc); ptr != end; ptr += MINBPC(enc)) { switch (BYTE_TYPE(enc, ptr)) { case BT_DIGIT: case BT_HEX: - break; + break; case BT_SEMI: - *nextTokPtr = ptr + MINBPC; - return XML_TOK_CHAR_REF; + *nextTokPtr = ptr + MINBPC(enc); + return XML_TOK_CHAR_REF; default: - *nextTokPtr = ptr; - return XML_TOK_INVALID; + *nextTokPtr = ptr; + return XML_TOK_INVALID; } } } @@ -468,11 +482,11 @@ int PREFIX(scanHexCharRef)(const ENCODING *enc, const char *ptr, const char *end static int PREFIX(scanCharRef)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { if (ptr != end) { if (CHAR_MATCHES(enc, ptr, 'x')) - return PREFIX(scanHexCharRef)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanHexCharRef)(enc, ptr + MINBPC(enc), end, nextTokPtr); switch (BYTE_TYPE(enc, ptr)) { case BT_DIGIT: break; @@ -480,16 +494,16 @@ int PREFIX(scanCharRef)(const ENCODING *enc, const char *ptr, const char *end, *nextTokPtr = ptr; return XML_TOK_INVALID; } - for (ptr += MINBPC; ptr != end; ptr += MINBPC) { + for (ptr += MINBPC(enc); ptr != end; ptr += MINBPC(enc)) { switch (BYTE_TYPE(enc, ptr)) { case BT_DIGIT: - break; + break; case BT_SEMI: - *nextTokPtr = ptr + MINBPC; - return XML_TOK_CHAR_REF; + *nextTokPtr = ptr + MINBPC(enc); + return XML_TOK_CHAR_REF; default: - *nextTokPtr = ptr; - return XML_TOK_INVALID; + *nextTokPtr = ptr; + return XML_TOK_INVALID; } } } @@ -500,14 +514,14 @@ int PREFIX(scanCharRef)(const ENCODING *enc, const char *ptr, const char *end, static int PREFIX(scanRef)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { if (ptr == end) return XML_TOK_PARTIAL; switch (BYTE_TYPE(enc, ptr)) { CHECK_NMSTRT_CASES(enc, ptr, end, nextTokPtr) case BT_NUM: - return PREFIX(scanCharRef)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanCharRef)(enc, ptr + MINBPC(enc), end, nextTokPtr); default: *nextTokPtr = ptr; return XML_TOK_INVALID; @@ -516,7 +530,7 @@ int PREFIX(scanRef)(const ENCODING *enc, const char *ptr, const char *end, switch (BYTE_TYPE(enc, ptr)) { CHECK_NAME_CASES(enc, ptr, end, nextTokPtr) case BT_SEMI: - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_ENTITY_REF; default: *nextTokPtr = ptr; @@ -530,129 +544,153 @@ int PREFIX(scanRef)(const ENCODING *enc, const char *ptr, const char *end, static int PREFIX(scanAtts)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { +#ifdef XML_NS + int hadColon = 0; +#endif while (ptr != end) { switch (BYTE_TYPE(enc, ptr)) { CHECK_NAME_CASES(enc, ptr, end, nextTokPtr) +#ifdef XML_NS + case BT_COLON: + if (hadColon) { + *nextTokPtr = ptr; + return XML_TOK_INVALID; + } + hadColon = 1; + ptr += MINBPC(enc); + if (ptr == end) + return XML_TOK_PARTIAL; + switch (BYTE_TYPE(enc, ptr)) { + CHECK_NMSTRT_CASES(enc, ptr, end, nextTokPtr) + default: + *nextTokPtr = ptr; + return XML_TOK_INVALID; + } + break; +#endif case BT_S: case BT_CR: case BT_LF: for (;;) { - int t; + int t; - ptr += MINBPC; - if (ptr == end) - return XML_TOK_PARTIAL; - t = BYTE_TYPE(enc, ptr); - if (t == BT_EQUALS) - break; - switch (t) { - case BT_S: - case BT_LF: - case BT_CR: - break; - default: - *nextTokPtr = ptr; - return XML_TOK_INVALID; - } + ptr += MINBPC(enc); + if (ptr == end) + return XML_TOK_PARTIAL; + t = BYTE_TYPE(enc, ptr); + if (t == BT_EQUALS) + break; + switch (t) { + case BT_S: + case BT_LF: + case BT_CR: + break; + default: + *nextTokPtr = ptr; + return XML_TOK_INVALID; + } } /* fall through */ case BT_EQUALS: { - int open; - for (;;) { - - ptr += MINBPC; - if (ptr == end) - return XML_TOK_PARTIAL; - open = BYTE_TYPE(enc, ptr); - if (open == BT_QUOT || open == BT_APOS) - break; - switch (open) { - case BT_S: - case BT_LF: - case BT_CR: - break; - default: - *nextTokPtr = ptr; - return XML_TOK_INVALID; - } - } - ptr += MINBPC; - /* in attribute value */ - for (;;) { - int t; - if (ptr == end) - return XML_TOK_PARTIAL; - t = BYTE_TYPE(enc, ptr); - if (t == open) - break; - switch (t) { - INVALID_CASES(ptr, nextTokPtr) - case BT_AMP: - { - int tok = PREFIX(scanRef)(enc, ptr + MINBPC, end, &ptr); - if (tok <= 0) { - if (tok == XML_TOK_INVALID) - *nextTokPtr = ptr; - return tok; - } - break; - } - case BT_LT: - *nextTokPtr = ptr; - return XML_TOK_INVALID; - default: - ptr += MINBPC; - break; - } - } - ptr += MINBPC; - if (ptr == end) - return XML_TOK_PARTIAL; - switch (BYTE_TYPE(enc, ptr)) { - case BT_S: - case BT_CR: - case BT_LF: - break; - case BT_SOL: - goto sol; - case BT_GT: - goto gt; - default: - *nextTokPtr = ptr; - return XML_TOK_INVALID; - } - /* ptr points to closing quote */ - for (;;) { - ptr += MINBPC; - if (ptr == end) - return XML_TOK_PARTIAL; - switch (BYTE_TYPE(enc, ptr)) { - CHECK_NMSTRT_CASES(enc, ptr, end, nextTokPtr) - case BT_S: case BT_CR: case BT_LF: - continue; - case BT_GT: + int open; +#ifdef XML_NS + hadColon = 0; +#endif + for (;;) { + + ptr += MINBPC(enc); + if (ptr == end) + return XML_TOK_PARTIAL; + open = BYTE_TYPE(enc, ptr); + if (open == BT_QUOT || open == BT_APOS) + break; + switch (open) { + case BT_S: + case BT_LF: + case BT_CR: + break; + default: + *nextTokPtr = ptr; + return XML_TOK_INVALID; + } + } + ptr += MINBPC(enc); + /* in attribute value */ + for (;;) { + int t; + if (ptr == end) + return XML_TOK_PARTIAL; + t = BYTE_TYPE(enc, ptr); + if (t == open) + break; + switch (t) { + INVALID_CASES(ptr, nextTokPtr) + case BT_AMP: + { + int tok = PREFIX(scanRef)(enc, ptr + MINBPC(enc), end, &ptr); + if (tok <= 0) { + if (tok == XML_TOK_INVALID) + *nextTokPtr = ptr; + return tok; + } + break; + } + case BT_LT: + *nextTokPtr = ptr; + return XML_TOK_INVALID; + default: + ptr += MINBPC(enc); + break; + } + } + ptr += MINBPC(enc); + if (ptr == end) + return XML_TOK_PARTIAL; + switch (BYTE_TYPE(enc, ptr)) { + case BT_S: + case BT_CR: + case BT_LF: + break; + case BT_SOL: + goto sol; + case BT_GT: + goto gt; + default: + *nextTokPtr = ptr; + return XML_TOK_INVALID; + } + /* ptr points to closing quote */ + for (;;) { + ptr += MINBPC(enc); + if (ptr == end) + return XML_TOK_PARTIAL; + switch (BYTE_TYPE(enc, ptr)) { + CHECK_NMSTRT_CASES(enc, ptr, end, nextTokPtr) + case BT_S: case BT_CR: case BT_LF: + continue; + case BT_GT: gt: - *nextTokPtr = ptr + MINBPC; - return XML_TOK_START_TAG_WITH_ATTS; - case BT_SOL: + *nextTokPtr = ptr + MINBPC(enc); + return XML_TOK_START_TAG_WITH_ATTS; + case BT_SOL: sol: - ptr += MINBPC; - if (ptr == end) - return XML_TOK_PARTIAL; - if (!CHAR_MATCHES(enc, ptr, '>')) { - *nextTokPtr = ptr; - return XML_TOK_INVALID; - } - *nextTokPtr = ptr + MINBPC; - return XML_TOK_EMPTY_ELEMENT_WITH_ATTS; - default: - *nextTokPtr = ptr; - return XML_TOK_INVALID; - } - break; - } - break; + ptr += MINBPC(enc); + if (ptr == end) + return XML_TOK_PARTIAL; + if (!CHAR_MATCHES(enc, ptr, '>')) { + *nextTokPtr = ptr; + return XML_TOK_INVALID; + } + *nextTokPtr = ptr + MINBPC(enc); + return XML_TOK_EMPTY_ELEMENT_WITH_ATTS; + default: + *nextTokPtr = ptr; + return XML_TOK_INVALID; + } + break; + } + break; } default: *nextTokPtr = ptr; @@ -666,70 +704,94 @@ int PREFIX(scanAtts)(const ENCODING *enc, const char *ptr, const char *end, static int PREFIX(scanLt)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { +#ifdef XML_NS + int hadColon; +#endif if (ptr == end) return XML_TOK_PARTIAL; switch (BYTE_TYPE(enc, ptr)) { CHECK_NMSTRT_CASES(enc, ptr, end, nextTokPtr) case BT_EXCL: - if ((ptr += MINBPC) == end) + if ((ptr += MINBPC(enc)) == end) return XML_TOK_PARTIAL; switch (BYTE_TYPE(enc, ptr)) { case BT_MINUS: - return PREFIX(scanComment)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanComment)(enc, ptr + MINBPC(enc), end, nextTokPtr); case BT_LSQB: - return PREFIX(scanCdataSection)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanCdataSection)(enc, ptr + MINBPC(enc), end, nextTokPtr); } *nextTokPtr = ptr; return XML_TOK_INVALID; case BT_QUEST: - return PREFIX(scanPi)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanPi)(enc, ptr + MINBPC(enc), end, nextTokPtr); case BT_SOL: - return PREFIX(scanEndTag)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanEndTag)(enc, ptr + MINBPC(enc), end, nextTokPtr); default: *nextTokPtr = ptr; return XML_TOK_INVALID; } +#ifdef XML_NS + hadColon = 0; +#endif /* we have a start-tag */ while (ptr != end) { switch (BYTE_TYPE(enc, ptr)) { CHECK_NAME_CASES(enc, ptr, end, nextTokPtr) +#ifdef XML_NS + case BT_COLON: + if (hadColon) { + *nextTokPtr = ptr; + return XML_TOK_INVALID; + } + hadColon = 1; + ptr += MINBPC(enc); + if (ptr == end) + return XML_TOK_PARTIAL; + switch (BYTE_TYPE(enc, ptr)) { + CHECK_NMSTRT_CASES(enc, ptr, end, nextTokPtr) + default: + *nextTokPtr = ptr; + return XML_TOK_INVALID; + } + break; +#endif case BT_S: case BT_CR: case BT_LF: { - ptr += MINBPC; - while (ptr != end) { - switch (BYTE_TYPE(enc, ptr)) { - CHECK_NMSTRT_CASES(enc, ptr, end, nextTokPtr) - case BT_GT: - goto gt; - case BT_SOL: - goto sol; - case BT_S: case BT_CR: case BT_LF: - ptr += MINBPC; - continue; - default: - *nextTokPtr = ptr; - return XML_TOK_INVALID; - } - return PREFIX(scanAtts)(enc, ptr, end, nextTokPtr); - } - return XML_TOK_PARTIAL; + ptr += MINBPC(enc); + while (ptr != end) { + switch (BYTE_TYPE(enc, ptr)) { + CHECK_NMSTRT_CASES(enc, ptr, end, nextTokPtr) + case BT_GT: + goto gt; + case BT_SOL: + goto sol; + case BT_S: case BT_CR: case BT_LF: + ptr += MINBPC(enc); + continue; + default: + *nextTokPtr = ptr; + return XML_TOK_INVALID; + } + return PREFIX(scanAtts)(enc, ptr, end, nextTokPtr); + } + return XML_TOK_PARTIAL; } case BT_GT: gt: - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_START_TAG_NO_ATTS; case BT_SOL: sol: - ptr += MINBPC; + ptr += MINBPC(enc); if (ptr == end) - return XML_TOK_PARTIAL; + return XML_TOK_PARTIAL; if (!CHAR_MATCHES(enc, ptr, '>')) { - *nextTokPtr = ptr; - return XML_TOK_INVALID; + *nextTokPtr = ptr; + return XML_TOK_INVALID; } - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_EMPTY_ELEMENT_NO_ATTS; default: *nextTokPtr = ptr; @@ -741,55 +803,53 @@ int PREFIX(scanLt)(const ENCODING *enc, const char *ptr, const char *end, static int PREFIX(contentTok)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { if (ptr == end) return XML_TOK_NONE; -#if MINBPC > 1 - { + if (MINBPC(enc) > 1) { size_t n = end - ptr; - if (n & (MINBPC - 1)) { - n &= ~(MINBPC - 1); + if (n & (MINBPC(enc) - 1)) { + n &= ~(MINBPC(enc) - 1); if (n == 0) - return XML_TOK_PARTIAL; + return XML_TOK_PARTIAL; end = ptr + n; } } -#endif switch (BYTE_TYPE(enc, ptr)) { case BT_LT: - return PREFIX(scanLt)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanLt)(enc, ptr + MINBPC(enc), end, nextTokPtr); case BT_AMP: - return PREFIX(scanRef)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanRef)(enc, ptr + MINBPC(enc), end, nextTokPtr); case BT_CR: - ptr += MINBPC; + ptr += MINBPC(enc); if (ptr == end) return XML_TOK_TRAILING_CR; if (BYTE_TYPE(enc, ptr) == BT_LF) - ptr += MINBPC; + ptr += MINBPC(enc); *nextTokPtr = ptr; return XML_TOK_DATA_NEWLINE; case BT_LF: - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_DATA_NEWLINE; case BT_RSQB: - ptr += MINBPC; + ptr += MINBPC(enc); if (ptr == end) return XML_TOK_TRAILING_RSQB; if (!CHAR_MATCHES(enc, ptr, ']')) break; - ptr += MINBPC; + ptr += MINBPC(enc); if (ptr == end) return XML_TOK_TRAILING_RSQB; if (!CHAR_MATCHES(enc, ptr, '>')) { - ptr -= MINBPC; + ptr -= MINBPC(enc); break; } *nextTokPtr = ptr; return XML_TOK_INVALID; INVALID_CASES(ptr, nextTokPtr) default: - ptr += MINBPC; + ptr += MINBPC(enc); break; } while (ptr != end) { @@ -797,27 +857,27 @@ int PREFIX(contentTok)(const ENCODING *enc, const char *ptr, const char *end, #define LEAD_CASE(n) \ case BT_LEAD ## n: \ if (end - ptr < n || IS_INVALID_CHAR(enc, ptr, n)) { \ - *nextTokPtr = ptr; \ - return XML_TOK_DATA_CHARS; \ + *nextTokPtr = ptr; \ + return XML_TOK_DATA_CHARS; \ } \ ptr += n; \ break; LEAD_CASE(2) LEAD_CASE(3) LEAD_CASE(4) #undef LEAD_CASE case BT_RSQB: - if (ptr + MINBPC != end) { - if (!CHAR_MATCHES(enc, ptr + MINBPC, ']')) { - ptr += MINBPC; - break; - } - if (ptr + 2*MINBPC != end) { - if (!CHAR_MATCHES(enc, ptr + 2*MINBPC, '>')) { - ptr += MINBPC; - break; - } - *nextTokPtr = ptr + 2*MINBPC; - return XML_TOK_INVALID; - } + if (ptr + MINBPC(enc) != end) { + if (!CHAR_MATCHES(enc, ptr + MINBPC(enc), ']')) { + ptr += MINBPC(enc); + break; + } + if (ptr + 2*MINBPC(enc) != end) { + if (!CHAR_MATCHES(enc, ptr + 2*MINBPC(enc), '>')) { + ptr += MINBPC(enc); + break; + } + *nextTokPtr = ptr + 2*MINBPC(enc); + return XML_TOK_INVALID; + } } /* fall through */ case BT_AMP: @@ -830,7 +890,7 @@ int PREFIX(contentTok)(const ENCODING *enc, const char *ptr, const char *end, *nextTokPtr = ptr; return XML_TOK_DATA_CHARS; default: - ptr += MINBPC; + ptr += MINBPC(enc); break; } } @@ -842,7 +902,7 @@ int PREFIX(contentTok)(const ENCODING *enc, const char *ptr, const char *end, static int PREFIX(scanPercent)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { if (ptr == end) return XML_TOK_PARTIAL; @@ -859,7 +919,7 @@ int PREFIX(scanPercent)(const ENCODING *enc, const char *ptr, const char *end, switch (BYTE_TYPE(enc, ptr)) { CHECK_NAME_CASES(enc, ptr, end, nextTokPtr) case BT_SEMI: - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_PARAM_ENTITY_REF; default: *nextTokPtr = ptr; @@ -871,7 +931,7 @@ int PREFIX(scanPercent)(const ENCODING *enc, const char *ptr, const char *end, static int PREFIX(scanPoundName)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { if (ptr == end) return XML_TOK_PARTIAL; @@ -898,8 +958,8 @@ int PREFIX(scanPoundName)(const ENCODING *enc, const char *ptr, const char *end, static int PREFIX(scanLit)(int open, const ENCODING *enc, - const char *ptr, const char *end, - const char **nextTokPtr) + const char *ptr, const char *end, + const char **nextTokPtr) { while (ptr != end) { int t = BYTE_TYPE(enc, ptr); @@ -907,21 +967,21 @@ int PREFIX(scanLit)(int open, const ENCODING *enc, INVALID_CASES(ptr, nextTokPtr) case BT_QUOT: case BT_APOS: - ptr += MINBPC; + ptr += MINBPC(enc); if (t != open) - break; + break; if (ptr == end) - return XML_TOK_PARTIAL; + return XML_TOK_PARTIAL; *nextTokPtr = ptr; switch (BYTE_TYPE(enc, ptr)) { case BT_S: case BT_CR: case BT_LF: case BT_GT: case BT_PERCNT: case BT_LSQB: - return XML_TOK_LITERAL; + return XML_TOK_LITERAL; default: - return XML_TOK_INVALID; + return XML_TOK_INVALID; } default: - ptr += MINBPC; + ptr += MINBPC(enc); break; } } @@ -930,111 +990,109 @@ int PREFIX(scanLit)(int open, const ENCODING *enc, static int PREFIX(prologTok)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { int tok; if (ptr == end) return XML_TOK_NONE; -#if MINBPC > 1 - { + if (MINBPC(enc) > 1) { size_t n = end - ptr; - if (n & (MINBPC - 1)) { - n &= ~(MINBPC - 1); + if (n & (MINBPC(enc) - 1)) { + n &= ~(MINBPC(enc) - 1); if (n == 0) - return XML_TOK_PARTIAL; + return XML_TOK_PARTIAL; end = ptr + n; } } -#endif switch (BYTE_TYPE(enc, ptr)) { case BT_QUOT: - return PREFIX(scanLit)(BT_QUOT, enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanLit)(BT_QUOT, enc, ptr + MINBPC(enc), end, nextTokPtr); case BT_APOS: - return PREFIX(scanLit)(BT_APOS, enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanLit)(BT_APOS, enc, ptr + MINBPC(enc), end, nextTokPtr); case BT_LT: { - ptr += MINBPC; + ptr += MINBPC(enc); if (ptr == end) - return XML_TOK_PARTIAL; + return XML_TOK_PARTIAL; switch (BYTE_TYPE(enc, ptr)) { case BT_EXCL: - return PREFIX(scanDecl)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanDecl)(enc, ptr + MINBPC(enc), end, nextTokPtr); case BT_QUEST: - return PREFIX(scanPi)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanPi)(enc, ptr + MINBPC(enc), end, nextTokPtr); case BT_NMSTRT: case BT_HEX: case BT_NONASCII: case BT_LEAD2: case BT_LEAD3: case BT_LEAD4: - *nextTokPtr = ptr - MINBPC; - return XML_TOK_INSTANCE_START; + *nextTokPtr = ptr - MINBPC(enc); + return XML_TOK_INSTANCE_START; } *nextTokPtr = ptr; return XML_TOK_INVALID; } case BT_CR: - if (ptr + MINBPC == end) + if (ptr + MINBPC(enc) == end) return XML_TOK_TRAILING_CR; /* fall through */ case BT_S: case BT_LF: for (;;) { - ptr += MINBPC; + ptr += MINBPC(enc); if (ptr == end) - break; + break; switch (BYTE_TYPE(enc, ptr)) { case BT_S: case BT_LF: - break; + break; case BT_CR: - /* don't split CR/LF pair */ - if (ptr + MINBPC != end) - break; - /* fall through */ + /* don't split CR/LF pair */ + if (ptr + MINBPC(enc) != end) + break; + /* fall through */ default: - *nextTokPtr = ptr; - return XML_TOK_PROLOG_S; + *nextTokPtr = ptr; + return XML_TOK_PROLOG_S; } } *nextTokPtr = ptr; return XML_TOK_PROLOG_S; case BT_PERCNT: - return PREFIX(scanPercent)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanPercent)(enc, ptr + MINBPC(enc), end, nextTokPtr); case BT_COMMA: - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_COMMA; case BT_LSQB: - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_OPEN_BRACKET; case BT_RSQB: - ptr += MINBPC; + ptr += MINBPC(enc); if (ptr == end) return XML_TOK_PARTIAL; if (CHAR_MATCHES(enc, ptr, ']')) { - if (ptr + MINBPC == end) - return XML_TOK_PARTIAL; - if (CHAR_MATCHES(enc, ptr + MINBPC, '>')) { - *nextTokPtr = ptr + 2*MINBPC; - return XML_TOK_COND_SECT_CLOSE; + if (ptr + MINBPC(enc) == end) + return XML_TOK_PARTIAL; + if (CHAR_MATCHES(enc, ptr + MINBPC(enc), '>')) { + *nextTokPtr = ptr + 2*MINBPC(enc); + return XML_TOK_COND_SECT_CLOSE; } } *nextTokPtr = ptr; return XML_TOK_CLOSE_BRACKET; case BT_LPAR: - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_OPEN_PAREN; case BT_RPAR: - ptr += MINBPC; + ptr += MINBPC(enc); if (ptr == end) return XML_TOK_PARTIAL; switch (BYTE_TYPE(enc, ptr)) { case BT_AST: - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_CLOSE_PAREN_ASTERISK; case BT_QUEST: - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_CLOSE_PAREN_QUESTION; case BT_PLUS: - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_CLOSE_PAREN_PLUS; case BT_CR: case BT_LF: case BT_S: case BT_GT: case BT_COMMA: case BT_VERBAR: @@ -1045,13 +1103,13 @@ int PREFIX(prologTok)(const ENCODING *enc, const char *ptr, const char *end, *nextTokPtr = ptr; return XML_TOK_INVALID; case BT_VERBAR: - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_OR; case BT_GT: - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_DECL_CLOSE; case BT_NUM: - return PREFIX(scanPoundName)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanPoundName)(enc, ptr + MINBPC(enc), end, nextTokPtr); #define LEAD_CASE(n) \ case BT_LEAD ## n: \ if (end - ptr < n) \ @@ -1073,22 +1131,25 @@ int PREFIX(prologTok)(const ENCODING *enc, const char *ptr, const char *end, case BT_NMSTRT: case BT_HEX: tok = XML_TOK_NAME; - ptr += MINBPC; + ptr += MINBPC(enc); break; case BT_DIGIT: case BT_NAME: case BT_MINUS: +#ifdef XML_NS + case BT_COLON: +#endif tok = XML_TOK_NMTOKEN; - ptr += MINBPC; + ptr += MINBPC(enc); break; case BT_NONASCII: if (IS_NMSTRT_CHAR_MINBPC(enc, ptr)) { - ptr += MINBPC; + ptr += MINBPC(enc); tok = XML_TOK_NAME; break; } if (IS_NAME_CHAR_MINBPC(enc, ptr)) { - ptr += MINBPC; + ptr += MINBPC(enc); tok = XML_TOK_NMTOKEN; break; } @@ -1105,26 +1166,47 @@ int PREFIX(prologTok)(const ENCODING *enc, const char *ptr, const char *end, case BT_S: case BT_CR: case BT_LF: *nextTokPtr = ptr; return tok; - case BT_PLUS: - if (tok != XML_TOK_NAME) { - *nextTokPtr = ptr; - return XML_TOK_INVALID; +#ifdef XML_NS + case BT_COLON: + ptr += MINBPC(enc); + switch (tok) { + case XML_TOK_NAME: + if (ptr == end) + return XML_TOK_PARTIAL; + tok = XML_TOK_PREFIXED_NAME; + switch (BYTE_TYPE(enc, ptr)) { + CHECK_NAME_CASES(enc, ptr, end, nextTokPtr) + default: + tok = XML_TOK_NMTOKEN; + break; + } + break; + case XML_TOK_PREFIXED_NAME: + tok = XML_TOK_NMTOKEN; + break; } - *nextTokPtr = ptr + MINBPC; + break; +#endif + case BT_PLUS: + if (tok == XML_TOK_NMTOKEN) { + *nextTokPtr = ptr; + return XML_TOK_INVALID; + } + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_NAME_PLUS; case BT_AST: - if (tok != XML_TOK_NAME) { - *nextTokPtr = ptr; - return XML_TOK_INVALID; + if (tok == XML_TOK_NMTOKEN) { + *nextTokPtr = ptr; + return XML_TOK_INVALID; } - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_NAME_ASTERISK; case BT_QUEST: - if (tok != XML_TOK_NAME) { - *nextTokPtr = ptr; - return XML_TOK_INVALID; + if (tok == XML_TOK_NMTOKEN) { + *nextTokPtr = ptr; + return XML_TOK_INVALID; } - *nextTokPtr = ptr + MINBPC; + *nextTokPtr = ptr + MINBPC(enc); return XML_TOK_NAME_QUESTION; default: *nextTokPtr = ptr; @@ -1136,7 +1218,7 @@ int PREFIX(prologTok)(const ENCODING *enc, const char *ptr, const char *end, static int PREFIX(attributeValueTok)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { const char *start; if (ptr == end) @@ -1150,7 +1232,7 @@ int PREFIX(attributeValueTok)(const ENCODING *enc, const char *ptr, const char * #undef LEAD_CASE case BT_AMP: if (ptr == start) - return PREFIX(scanRef)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanRef)(enc, ptr + MINBPC(enc), end, nextTokPtr); *nextTokPtr = ptr; return XML_TOK_DATA_CHARS; case BT_LT: @@ -1159,32 +1241,32 @@ int PREFIX(attributeValueTok)(const ENCODING *enc, const char *ptr, const char * return XML_TOK_INVALID; case BT_LF: if (ptr == start) { - *nextTokPtr = ptr + MINBPC; - return XML_TOK_DATA_NEWLINE; + *nextTokPtr = ptr + MINBPC(enc); + return XML_TOK_DATA_NEWLINE; } *nextTokPtr = ptr; return XML_TOK_DATA_CHARS; case BT_CR: if (ptr == start) { - ptr += MINBPC; - if (ptr == end) - return XML_TOK_TRAILING_CR; - if (BYTE_TYPE(enc, ptr) == BT_LF) - ptr += MINBPC; - *nextTokPtr = ptr; - return XML_TOK_DATA_NEWLINE; + ptr += MINBPC(enc); + if (ptr == end) + return XML_TOK_TRAILING_CR; + if (BYTE_TYPE(enc, ptr) == BT_LF) + ptr += MINBPC(enc); + *nextTokPtr = ptr; + return XML_TOK_DATA_NEWLINE; } *nextTokPtr = ptr; return XML_TOK_DATA_CHARS; case BT_S: if (ptr == start) { - *nextTokPtr = ptr + MINBPC; - return XML_TOK_ATTRIBUTE_VALUE_S; + *nextTokPtr = ptr + MINBPC(enc); + return XML_TOK_ATTRIBUTE_VALUE_S; } *nextTokPtr = ptr; return XML_TOK_DATA_CHARS; default: - ptr += MINBPC; + ptr += MINBPC(enc); break; } } @@ -1194,7 +1276,7 @@ int PREFIX(attributeValueTok)(const ENCODING *enc, const char *ptr, const char * static int PREFIX(entityValueTok)(const ENCODING *enc, const char *ptr, const char *end, - const char **nextTokPtr) + const char **nextTokPtr) { const char *start; if (ptr == end) @@ -1208,35 +1290,35 @@ int PREFIX(entityValueTok)(const ENCODING *enc, const char *ptr, const char *end #undef LEAD_CASE case BT_AMP: if (ptr == start) - return PREFIX(scanRef)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanRef)(enc, ptr + MINBPC(enc), end, nextTokPtr); *nextTokPtr = ptr; return XML_TOK_DATA_CHARS; case BT_PERCNT: if (ptr == start) - return PREFIX(scanPercent)(enc, ptr + MINBPC, end, nextTokPtr); + return PREFIX(scanPercent)(enc, ptr + MINBPC(enc), end, nextTokPtr); *nextTokPtr = ptr; return XML_TOK_DATA_CHARS; case BT_LF: if (ptr == start) { - *nextTokPtr = ptr + MINBPC; - return XML_TOK_DATA_NEWLINE; + *nextTokPtr = ptr + MINBPC(enc); + return XML_TOK_DATA_NEWLINE; } *nextTokPtr = ptr; return XML_TOK_DATA_CHARS; case BT_CR: if (ptr == start) { - ptr += MINBPC; - if (ptr == end) - return XML_TOK_TRAILING_CR; - if (BYTE_TYPE(enc, ptr) == BT_LF) - ptr += MINBPC; - *nextTokPtr = ptr; - return XML_TOK_DATA_NEWLINE; + ptr += MINBPC(enc); + if (ptr == end) + return XML_TOK_TRAILING_CR; + if (BYTE_TYPE(enc, ptr) == BT_LF) + ptr += MINBPC(enc); + *nextTokPtr = ptr; + return XML_TOK_DATA_NEWLINE; } *nextTokPtr = ptr; return XML_TOK_DATA_CHARS; default: - ptr += MINBPC; + ptr += MINBPC(enc); break; } } @@ -1246,11 +1328,11 @@ int PREFIX(entityValueTok)(const ENCODING *enc, const char *ptr, const char *end static int PREFIX(isPublicId)(const ENCODING *enc, const char *ptr, const char *end, - const char **badPtr) + const char **badPtr) { - ptr += MINBPC; - end -= MINBPC; - for (; ptr != end; ptr += MINBPC) { + ptr += MINBPC(enc); + end -= MINBPC(enc); + for (; ptr != end; ptr += MINBPC(enc)) { switch (BYTE_TYPE(enc, ptr)) { case BT_DIGIT: case BT_HEX: @@ -1270,25 +1352,28 @@ int PREFIX(isPublicId)(const ENCODING *enc, const char *ptr, const char *end, case BT_AST: case BT_PERCNT: case BT_NUM: +#ifdef XML_NS + case BT_COLON: +#endif break; case BT_S: if (CHAR_MATCHES(enc, ptr, '\t')) { - *badPtr = ptr; - return 0; + *badPtr = ptr; + return 0; } break; case BT_NAME: case BT_NMSTRT: if (!(BYTE_TO_ASCII(enc, ptr) & ~0x7f)) - break; + break; default: switch (BYTE_TO_ASCII(enc, ptr)) { case 0x24: /* $ */ case 0x40: /* @ */ - break; + break; default: - *badPtr = ptr; - return 0; + *badPtr = ptr; + return 0; } break; } @@ -1297,29 +1382,29 @@ int PREFIX(isPublicId)(const ENCODING *enc, const char *ptr, const char *end, } /* This must only be called for a well-formed start-tag or empty element tag. -Returns the number of attributes. Pointers to the first attsMax attributes +Returns the number of attributes. Pointers to the first attsMax attributes are stored in atts. */ static int PREFIX(getAtts)(const ENCODING *enc, const char *ptr, - int attsMax, ATTRIBUTE *atts) + int attsMax, ATTRIBUTE *atts) { enum { other, inName, inValue } state = inName; int nAtts = 0; int open; - for (ptr += MINBPC;; ptr += MINBPC) { + for (ptr += MINBPC(enc);; ptr += MINBPC(enc)) { switch (BYTE_TYPE(enc, ptr)) { #define START_NAME \ if (state == other) { \ - if (nAtts < attsMax) { \ - atts[nAtts].name = ptr; \ - atts[nAtts].normalized = 1; \ - } \ - state = inName; \ + if (nAtts < attsMax) { \ + atts[nAtts].name = ptr; \ + atts[nAtts].normalized = 1; \ + } \ + state = inName; \ } #define LEAD_CASE(n) \ - case BT_LEAD ## n: START_NAME ptr += (n - MINBPC); break; + case BT_LEAD ## n: START_NAME ptr += (n - MINBPC(enc)); break; LEAD_CASE(2) LEAD_CASE(3) LEAD_CASE(4) #undef LEAD_CASE case BT_NONASCII: @@ -1330,47 +1415,47 @@ int PREFIX(getAtts)(const ENCODING *enc, const char *ptr, #undef START_NAME case BT_QUOT: if (state != inValue) { - if (nAtts < attsMax) - atts[nAtts].valuePtr = ptr + MINBPC; + if (nAtts < attsMax) + atts[nAtts].valuePtr = ptr + MINBPC(enc); state = inValue; open = BT_QUOT; } else if (open == BT_QUOT) { state = other; - if (nAtts < attsMax) - atts[nAtts].valueEnd = ptr; - nAtts++; + if (nAtts < attsMax) + atts[nAtts].valueEnd = ptr; + nAtts++; } break; case BT_APOS: if (state != inValue) { - if (nAtts < attsMax) - atts[nAtts].valuePtr = ptr + MINBPC; + if (nAtts < attsMax) + atts[nAtts].valuePtr = ptr + MINBPC(enc); state = inValue; open = BT_APOS; } else if (open == BT_APOS) { state = other; - if (nAtts < attsMax) - atts[nAtts].valueEnd = ptr; - nAtts++; + if (nAtts < attsMax) + atts[nAtts].valueEnd = ptr; + nAtts++; } break; case BT_AMP: if (nAtts < attsMax) - atts[nAtts].normalized = 0; + atts[nAtts].normalized = 0; break; case BT_S: if (state == inName) state = other; else if (state == inValue - && nAtts < attsMax - && atts[nAtts].normalized - && (ptr == atts[nAtts].valuePtr - || BYTE_TO_ASCII(enc, ptr) != ' ' - || BYTE_TO_ASCII(enc, ptr + MINBPC) == ' ' - || BYTE_TYPE(enc, ptr + MINBPC) == open)) - atts[nAtts].normalized = 0; + && nAtts < attsMax + && atts[nAtts].normalized + && (ptr == atts[nAtts].valuePtr + || BYTE_TO_ASCII(enc, ptr) != ' ' + || BYTE_TO_ASCII(enc, ptr + MINBPC(enc)) == ' ' + || BYTE_TYPE(enc, ptr + MINBPC(enc)) == open)) + atts[nAtts].normalized = 0; break; case BT_CR: case BT_LF: /* This case ensures that the first attribute name is counted @@ -1378,12 +1463,12 @@ int PREFIX(getAtts)(const ENCODING *enc, const char *ptr, if (state == inName) state = other; else if (state == inValue && nAtts < attsMax) - atts[nAtts].normalized = 0; + atts[nAtts].normalized = 0; break; case BT_GT: case BT_SOL: if (state != inValue) - return nAtts; + return nAtts; break; default: break; @@ -1397,36 +1482,36 @@ int PREFIX(charRefNumber)(const ENCODING *enc, const char *ptr) { int result = 0; /* skip &# */ - ptr += 2*MINBPC; + ptr += 2*MINBPC(enc); if (CHAR_MATCHES(enc, ptr, 'x')) { - for (ptr += MINBPC; !CHAR_MATCHES(enc, ptr, ';'); ptr += MINBPC) { + for (ptr += MINBPC(enc); !CHAR_MATCHES(enc, ptr, ';'); ptr += MINBPC(enc)) { int c = BYTE_TO_ASCII(enc, ptr); switch (c) { case '0': case '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9': - result <<= 4; - result |= (c - '0'); - break; + result <<= 4; + result |= (c - '0'); + break; case 'A': case 'B': case 'C': case 'D': case 'E': case 'F': - result <<= 4; - result += 10 + (c - 'A'); - break; + result <<= 4; + result += 10 + (c - 'A'); + break; case 'a': case 'b': case 'c': case 'd': case 'e': case 'f': - result <<= 4; - result += 10 + (c - 'a'); - break; + result <<= 4; + result += 10 + (c - 'a'); + break; } if (result >= 0x110000) - return -1; + return -1; } } else { - for (; !CHAR_MATCHES(enc, ptr, ';'); ptr += MINBPC) { + for (; !CHAR_MATCHES(enc, ptr, ';'); ptr += MINBPC(enc)) { int c = BYTE_TO_ASCII(enc, ptr); result *= 10; result += (c - '0'); if (result >= 0x110000) - return -1; + return -1; } } return checkCharRefNumber(result); @@ -1435,49 +1520,49 @@ int PREFIX(charRefNumber)(const ENCODING *enc, const char *ptr) static int PREFIX(predefinedEntityName)(const ENCODING *enc, const char *ptr, const char *end) { - switch (end - ptr) { - case 2 * MINBPC: - if (CHAR_MATCHES(enc, ptr + MINBPC, 't')) { + switch ((end - ptr)/MINBPC(enc)) { + case 2: + if (CHAR_MATCHES(enc, ptr + MINBPC(enc), 't')) { switch (BYTE_TO_ASCII(enc, ptr)) { case 'l': - return '<'; + return '<'; case 'g': - return '>'; + return '>'; } } break; - case 3 * MINBPC: + case 3: if (CHAR_MATCHES(enc, ptr, 'a')) { - ptr += MINBPC; + ptr += MINBPC(enc); if (CHAR_MATCHES(enc, ptr, 'm')) { - ptr += MINBPC; - if (CHAR_MATCHES(enc, ptr, 'p')) - return '&'; + ptr += MINBPC(enc); + if (CHAR_MATCHES(enc, ptr, 'p')) + return '&'; } } break; - case 4 * MINBPC: + case 4: switch (BYTE_TO_ASCII(enc, ptr)) { case 'q': - ptr += MINBPC; + ptr += MINBPC(enc); if (CHAR_MATCHES(enc, ptr, 'u')) { - ptr += MINBPC; - if (CHAR_MATCHES(enc, ptr, 'o')) { - ptr += MINBPC; - if (CHAR_MATCHES(enc, ptr, 't')) - return '"'; - } + ptr += MINBPC(enc); + if (CHAR_MATCHES(enc, ptr, 'o')) { + ptr += MINBPC(enc); + if (CHAR_MATCHES(enc, ptr, 't')) + return '"'; + } } break; case 'a': - ptr += MINBPC; + ptr += MINBPC(enc); if (CHAR_MATCHES(enc, ptr, 'p')) { - ptr += MINBPC; - if (CHAR_MATCHES(enc, ptr, 'o')) { - ptr += MINBPC; - if (CHAR_MATCHES(enc, ptr, 's')) - return '\''; - } + ptr += MINBPC(enc); + if (CHAR_MATCHES(enc, ptr, 'o')) { + ptr += MINBPC(enc); + if (CHAR_MATCHES(enc, ptr, 's')) + return '\''; + } } break; } @@ -1493,52 +1578,56 @@ int PREFIX(sameName)(const ENCODING *enc, const char *ptr1, const char *ptr2) #define LEAD_CASE(n) \ case BT_LEAD ## n: \ if (*ptr1++ != *ptr2++) \ - return 0; + return 0; LEAD_CASE(4) LEAD_CASE(3) LEAD_CASE(2) #undef LEAD_CASE /* fall through */ if (*ptr1++ != *ptr2++) - return 0; + return 0; break; case BT_NONASCII: case BT_NMSTRT: +#ifdef XML_NS + case BT_COLON: +#endif case BT_HEX: case BT_DIGIT: case BT_NAME: case BT_MINUS: if (*ptr2++ != *ptr1++) - return 0; -#if MINBPC > 1 - if (*ptr2++ != *ptr1++) - return 0; -#if MINBPC > 2 - if (*ptr2++ != *ptr1++) - return 0; -#if MINBPC > 3 - if (*ptr2++ != *ptr1++) - return 0; -#endif -#endif -#endif + return 0; + if (MINBPC(enc) > 1) { + if (*ptr2++ != *ptr1++) + return 0; + if (MINBPC(enc) > 2) { + if (*ptr2++ != *ptr1++) + return 0; + if (MINBPC(enc) > 3) { + if (*ptr2++ != *ptr1++) + return 0; + } + } + } break; default: -#if MINBPC == 1 - if (*ptr1 == *ptr2) - return 1; -#endif + if (MINBPC(enc) == 1 && *ptr1 == *ptr2) + return 1; switch (BYTE_TYPE(enc, ptr2)) { case BT_LEAD2: case BT_LEAD3: case BT_LEAD4: case BT_NONASCII: case BT_NMSTRT: +#ifdef XML_NS + case BT_COLON: +#endif case BT_HEX: case BT_DIGIT: case BT_NAME: case BT_MINUS: - return 0; + return 0; default: - return 1; + return 1; } } } @@ -1548,8 +1637,8 @@ int PREFIX(sameName)(const ENCODING *enc, const char *ptr1, const char *ptr2) static int PREFIX(nameMatchesAscii)(const ENCODING *enc, const char *ptr1, const char *ptr2) { - for (; *ptr2; ptr1 += MINBPC, ptr2++) { - if (!CHAR_MATCHES(end, ptr1, *ptr2)) + for (; *ptr2; ptr1 += MINBPC(enc), ptr2++) { + if (!CHAR_MATCHES(enc, ptr1, *ptr2)) return 0; } switch (BYTE_TYPE(enc, ptr1)) { @@ -1558,6 +1647,9 @@ int PREFIX(nameMatchesAscii)(const ENCODING *enc, const char *ptr1, const char * case BT_LEAD4: case BT_NONASCII: case BT_NMSTRT: +#ifdef XML_NS + case BT_COLON: +#endif case BT_HEX: case BT_DIGIT: case BT_NAME: @@ -1580,11 +1672,14 @@ int PREFIX(nameLength)(const ENCODING *enc, const char *ptr) #undef LEAD_CASE case BT_NONASCII: case BT_NMSTRT: +#ifdef XML_NS + case BT_COLON: +#endif case BT_HEX: case BT_DIGIT: case BT_NAME: case BT_MINUS: - ptr += MINBPC; + ptr += MINBPC(enc); break; default: return ptr - start; @@ -1600,7 +1695,7 @@ const char *PREFIX(skipS)(const ENCODING *enc, const char *ptr) case BT_LF: case BT_CR: case BT_S: - ptr += MINBPC; + ptr += MINBPC(enc); break; default: return ptr; @@ -1610,9 +1705,9 @@ const char *PREFIX(skipS)(const ENCODING *enc, const char *ptr) static void PREFIX(updatePosition)(const ENCODING *enc, - const char *ptr, - const char *end, - POSITION *pos) + const char *ptr, + const char *end, + POSITION *pos) { while (ptr != end) { switch (BYTE_TYPE(enc, ptr)) { @@ -1625,17 +1720,17 @@ void PREFIX(updatePosition)(const ENCODING *enc, case BT_LF: pos->columnNumber = (unsigned)-1; pos->lineNumber++; - ptr += MINBPC; + ptr += MINBPC(enc); break; case BT_CR: pos->lineNumber++; - ptr += MINBPC; + ptr += MINBPC(enc); if (ptr != end && BYTE_TYPE(enc, ptr) == BT_LF) - ptr += MINBPC; + ptr += MINBPC(enc); pos->columnNumber = (unsigned)-1; break; default: - ptr += MINBPC; + ptr += MINBPC(enc); break; } pos->columnNumber++; diff --git a/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok_impl.h b/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok_impl.h index 3b0444ad2a6..e72b225c838 100644 --- a/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok_impl.h +++ b/mozilla/extensions/transformiix/source/xml/parser/xmltok/xmltok_impl.h @@ -1,6 +1,6 @@ /* The contents of this file are subject to the Mozilla Public License -Version 1.0 (the "License"); you may not use this file except in +Version 1.1 (the "License"); you may not use this file except in compliance with the License. You may obtain a copy of the License at http://www.mozilla.org/MPL/ @@ -12,10 +12,20 @@ under the License. The Original Code is expat. The Initial Developer of the Original Code is James Clark. -Portions created by James Clark are Copyright (C) 1998 +Portions created by James Clark are Copyright (C) 1998, 1999 James Clark. All Rights Reserved. Contributor(s): + +Alternatively, the contents of this file may be used under the terms +of the GNU General Public License (the "GPL"), in which case the +provisions of the GPL are applicable instead of those above. If you +wish to allow use of your version of this file only under the terms of +the GPL and not to allow others to use your version of this file under +the MPL, indicate your decision by deleting the provisions above and +replace them with the notice and other provisions required by the +GPL. If you do not delete the provisions above, a recipient may use +your version of this file under either the MPL or the GPL. */ enum { @@ -42,6 +52,7 @@ enum { BT_LSQB, BT_S, BT_NMSTRT, + BT_COLON, BT_HEX, BT_DIGIT, BT_NAME,