xmlparse.c revision 1.6 1 1.1 tron /* Copyright (c) 1998, 1999, 2000 Thai Open Source Software Center Ltd
2 1.1 tron See the file COPYING for copying permission.
3 1.1 tron */
4 1.1 tron
5 1.1 tron #include <stddef.h>
6 1.1 tron #include <string.h> /* memset(), memcpy() */
7 1.1 tron #include <assert.h>
8 1.3 spz #include <limits.h> /* UINT_MAX */
9 1.6 spz
10 1.6 spz #ifdef WIN32
11 1.6 spz #define getpid GetCurrentProcessId
12 1.6 spz #else
13 1.6 spz #include <sys/time.h> /* gettimeofday() */
14 1.6 spz #include <sys/types.h> /* getpid() */
15 1.6 spz #include <unistd.h> /* getpid() */
16 1.6 spz #endif
17 1.1 tron
18 1.1 tron #define XML_BUILDING_EXPAT 1
19 1.1 tron
20 1.6 spz #ifdef WIN32
21 1.1 tron #include "winconfig.h"
22 1.1 tron #elif defined(MACOS_CLASSIC)
23 1.1 tron #include "macconfig.h"
24 1.3 spz #elif defined(__amigaos__)
25 1.1 tron #include "amigaconfig.h"
26 1.1 tron #elif defined(__WATCOMC__)
27 1.1 tron #include "watcomconfig.h"
28 1.1 tron #elif defined(HAVE_EXPAT_CONFIG_H)
29 1.1 tron #include <expat_config.h>
30 1.6 spz #endif /* ndef WIN32 */
31 1.1 tron
32 1.1 tron #include "ascii.h"
33 1.1 tron #include "expat.h"
34 1.1 tron
35 1.1 tron #ifdef XML_UNICODE
36 1.1 tron #define XML_ENCODE_MAX XML_UTF16_ENCODE_MAX
37 1.1 tron #define XmlConvert XmlUtf16Convert
38 1.1 tron #define XmlGetInternalEncoding XmlGetUtf16InternalEncoding
39 1.1 tron #define XmlGetInternalEncodingNS XmlGetUtf16InternalEncodingNS
40 1.1 tron #define XmlEncode XmlUtf16Encode
41 1.1 tron /* Using pointer subtraction to convert to integer type. */
42 1.1 tron #define MUST_CONVERT(enc, s) (!(enc)->isUtf16 || (((char *)(s) - (char *)NULL) & 1))
43 1.1 tron typedef unsigned short ICHAR;
44 1.1 tron #else
45 1.1 tron #define XML_ENCODE_MAX XML_UTF8_ENCODE_MAX
46 1.1 tron #define XmlConvert XmlUtf8Convert
47 1.1 tron #define XmlGetInternalEncoding XmlGetUtf8InternalEncoding
48 1.1 tron #define XmlGetInternalEncodingNS XmlGetUtf8InternalEncodingNS
49 1.1 tron #define XmlEncode XmlUtf8Encode
50 1.1 tron #define MUST_CONVERT(enc, s) (!(enc)->isUtf8)
51 1.1 tron typedef char ICHAR;
52 1.1 tron #endif
53 1.1 tron
54 1.1 tron
55 1.1 tron #ifndef XML_NS
56 1.1 tron
57 1.1 tron #define XmlInitEncodingNS XmlInitEncoding
58 1.1 tron #define XmlInitUnknownEncodingNS XmlInitUnknownEncoding
59 1.1 tron #undef XmlGetInternalEncodingNS
60 1.1 tron #define XmlGetInternalEncodingNS XmlGetInternalEncoding
61 1.1 tron #define XmlParseXmlDeclNS XmlParseXmlDecl
62 1.1 tron
63 1.1 tron #endif
64 1.1 tron
65 1.1 tron #ifdef XML_UNICODE
66 1.1 tron
67 1.1 tron #ifdef XML_UNICODE_WCHAR_T
68 1.1 tron #define XML_T(x) (const wchar_t)x
69 1.1 tron #define XML_L(x) L ## x
70 1.1 tron #else
71 1.1 tron #define XML_T(x) (const unsigned short)x
72 1.1 tron #define XML_L(x) x
73 1.1 tron #endif
74 1.1 tron
75 1.1 tron #else
76 1.1 tron
77 1.1 tron #define XML_T(x) x
78 1.1 tron #define XML_L(x) x
79 1.1 tron
80 1.1 tron #endif
81 1.1 tron
82 1.1 tron /* Round up n to be a multiple of sz, where sz is a power of 2. */
83 1.1 tron #define ROUND_UP(n, sz) (((n) + ((sz) - 1)) & ~((sz) - 1))
84 1.1 tron
85 1.1 tron /* Handle the case where memmove() doesn't exist. */
86 1.1 tron #ifndef HAVE_MEMMOVE
87 1.1 tron #ifdef HAVE_BCOPY
88 1.1 tron #define memmove(d,s,l) bcopy((s),(d),(l))
89 1.1 tron #else
90 1.1 tron #error memmove does not exist on this platform, nor is a substitute available
91 1.1 tron #endif /* HAVE_BCOPY */
92 1.1 tron #endif /* HAVE_MEMMOVE */
93 1.1 tron
94 1.1 tron #include "internal.h"
95 1.1 tron #include "xmltok.h"
96 1.1 tron #include "xmlrole.h"
97 1.1 tron
98 1.1 tron typedef const XML_Char *KEY;
99 1.1 tron
100 1.1 tron typedef struct {
101 1.1 tron KEY name;
102 1.1 tron } NAMED;
103 1.1 tron
104 1.1 tron typedef struct {
105 1.1 tron NAMED **v;
106 1.1 tron unsigned char power;
107 1.1 tron size_t size;
108 1.1 tron size_t used;
109 1.1 tron const XML_Memory_Handling_Suite *mem;
110 1.1 tron } HASH_TABLE;
111 1.1 tron
112 1.1 tron /* Basic character hash algorithm, taken from Python's string hash:
113 1.1 tron h = h * 1000003 ^ character, the constant being a prime number.
114 1.1 tron
115 1.1 tron */
116 1.1 tron #ifdef XML_UNICODE
117 1.1 tron #define CHAR_HASH(h, c) \
118 1.1 tron (((h) * 0xF4243) ^ (unsigned short)(c))
119 1.1 tron #else
120 1.1 tron #define CHAR_HASH(h, c) \
121 1.1 tron (((h) * 0xF4243) ^ (unsigned char)(c))
122 1.1 tron #endif
123 1.1 tron
124 1.1 tron /* For probing (after a collision) we need a step size relative prime
125 1.1 tron to the hash table size, which is a power of 2. We use double-hashing,
126 1.1 tron since we can calculate a second hash value cheaply by taking those bits
127 1.1 tron of the first hash value that were discarded (masked out) when the table
128 1.1 tron index was calculated: index = hash & mask, where mask = table->size - 1.
129 1.1 tron We limit the maximum step size to table->size / 4 (mask >> 2) and make
130 1.1 tron it odd, since odd numbers are always relative prime to a power of 2.
131 1.1 tron */
132 1.1 tron #define SECOND_HASH(hash, mask, power) \
133 1.1 tron ((((hash) & ~(mask)) >> ((power) - 1)) & ((mask) >> 2))
134 1.1 tron #define PROBE_STEP(hash, mask, power) \
135 1.1 tron ((unsigned char)((SECOND_HASH(hash, mask, power)) | 1))
136 1.1 tron
137 1.1 tron typedef struct {
138 1.1 tron NAMED **p;
139 1.1 tron NAMED **end;
140 1.1 tron } HASH_TABLE_ITER;
141 1.1 tron
142 1.1 tron #define INIT_TAG_BUF_SIZE 32 /* must be a multiple of sizeof(XML_Char) */
143 1.1 tron #define INIT_DATA_BUF_SIZE 1024
144 1.1 tron #define INIT_ATTS_SIZE 16
145 1.1 tron #define INIT_ATTS_VERSION 0xFFFFFFFF
146 1.1 tron #define INIT_BLOCK_SIZE 1024
147 1.1 tron #define INIT_BUFFER_SIZE 1024
148 1.1 tron
149 1.1 tron #define EXPAND_SPARE 24
150 1.1 tron
151 1.1 tron typedef struct binding {
152 1.1 tron struct prefix *prefix;
153 1.1 tron struct binding *nextTagBinding;
154 1.1 tron struct binding *prevPrefixBinding;
155 1.1 tron const struct attribute_id *attId;
156 1.1 tron XML_Char *uri;
157 1.1 tron int uriLen;
158 1.1 tron int uriAlloc;
159 1.1 tron } BINDING;
160 1.1 tron
161 1.1 tron typedef struct prefix {
162 1.1 tron const XML_Char *name;
163 1.1 tron BINDING *binding;
164 1.1 tron } PREFIX;
165 1.1 tron
166 1.1 tron typedef struct {
167 1.1 tron const XML_Char *str;
168 1.1 tron const XML_Char *localPart;
169 1.1 tron const XML_Char *prefix;
170 1.1 tron int strLen;
171 1.1 tron int uriLen;
172 1.1 tron int prefixLen;
173 1.1 tron } TAG_NAME;
174 1.1 tron
175 1.1 tron /* TAG represents an open element.
176 1.1 tron The name of the element is stored in both the document and API
177 1.1 tron encodings. The memory buffer 'buf' is a separately-allocated
178 1.1 tron memory area which stores the name. During the XML_Parse()/
179 1.1 tron XMLParseBuffer() when the element is open, the memory for the 'raw'
180 1.1 tron version of the name (in the document encoding) is shared with the
181 1.1 tron document buffer. If the element is open across calls to
182 1.1 tron XML_Parse()/XML_ParseBuffer(), the buffer is re-allocated to
183 1.1 tron contain the 'raw' name as well.
184 1.1 tron
185 1.1 tron A parser re-uses these structures, maintaining a list of allocated
186 1.1 tron TAG objects in a free list.
187 1.1 tron */
188 1.1 tron typedef struct tag {
189 1.1 tron struct tag *parent; /* parent of this element */
190 1.1 tron const char *rawName; /* tagName in the original encoding */
191 1.1 tron int rawNameLength;
192 1.1 tron TAG_NAME name; /* tagName in the API encoding */
193 1.1 tron char *buf; /* buffer for name components */
194 1.1 tron char *bufEnd; /* end of the buffer */
195 1.1 tron BINDING *bindings;
196 1.1 tron } TAG;
197 1.1 tron
198 1.1 tron typedef struct {
199 1.1 tron const XML_Char *name;
200 1.1 tron const XML_Char *textPtr;
201 1.1 tron int textLen; /* length in XML_Chars */
202 1.1 tron int processed; /* # of processed bytes - when suspended */
203 1.1 tron const XML_Char *systemId;
204 1.1 tron const XML_Char *base;
205 1.1 tron const XML_Char *publicId;
206 1.1 tron const XML_Char *notation;
207 1.1 tron XML_Bool open;
208 1.1 tron XML_Bool is_param;
209 1.1 tron XML_Bool is_internal; /* true if declared in internal subset outside PE */
210 1.1 tron } ENTITY;
211 1.1 tron
212 1.1 tron typedef struct {
213 1.1 tron enum XML_Content_Type type;
214 1.1 tron enum XML_Content_Quant quant;
215 1.1 tron const XML_Char * name;
216 1.1 tron int firstchild;
217 1.1 tron int lastchild;
218 1.1 tron int childcnt;
219 1.1 tron int nextsib;
220 1.1 tron } CONTENT_SCAFFOLD;
221 1.1 tron
222 1.1 tron #define INIT_SCAFFOLD_ELEMENTS 32
223 1.1 tron
224 1.1 tron typedef struct block {
225 1.1 tron struct block *next;
226 1.1 tron int size;
227 1.1 tron XML_Char s[1];
228 1.1 tron } BLOCK;
229 1.1 tron
230 1.1 tron typedef struct {
231 1.1 tron BLOCK *blocks;
232 1.1 tron BLOCK *freeBlocks;
233 1.1 tron const XML_Char *end;
234 1.1 tron XML_Char *ptr;
235 1.1 tron XML_Char *start;
236 1.1 tron const XML_Memory_Handling_Suite *mem;
237 1.1 tron } STRING_POOL;
238 1.1 tron
239 1.1 tron /* The XML_Char before the name is used to determine whether
240 1.1 tron an attribute has been specified. */
241 1.1 tron typedef struct attribute_id {
242 1.1 tron XML_Char *name;
243 1.1 tron PREFIX *prefix;
244 1.1 tron XML_Bool maybeTokenized;
245 1.1 tron XML_Bool xmlns;
246 1.1 tron } ATTRIBUTE_ID;
247 1.1 tron
248 1.1 tron typedef struct {
249 1.1 tron const ATTRIBUTE_ID *id;
250 1.1 tron XML_Bool isCdata;
251 1.1 tron const XML_Char *value;
252 1.1 tron } DEFAULT_ATTRIBUTE;
253 1.1 tron
254 1.1 tron typedef struct {
255 1.1 tron unsigned long version;
256 1.1 tron unsigned long hash;
257 1.1 tron const XML_Char *uriName;
258 1.1 tron } NS_ATT;
259 1.1 tron
260 1.1 tron typedef struct {
261 1.1 tron const XML_Char *name;
262 1.1 tron PREFIX *prefix;
263 1.1 tron const ATTRIBUTE_ID *idAtt;
264 1.1 tron int nDefaultAtts;
265 1.1 tron int allocDefaultAtts;
266 1.1 tron DEFAULT_ATTRIBUTE *defaultAtts;
267 1.1 tron } ELEMENT_TYPE;
268 1.1 tron
269 1.1 tron typedef struct {
270 1.1 tron HASH_TABLE generalEntities;
271 1.1 tron HASH_TABLE elementTypes;
272 1.1 tron HASH_TABLE attributeIds;
273 1.1 tron HASH_TABLE prefixes;
274 1.1 tron STRING_POOL pool;
275 1.1 tron STRING_POOL entityValuePool;
276 1.1 tron /* false once a parameter entity reference has been skipped */
277 1.1 tron XML_Bool keepProcessing;
278 1.1 tron /* true once an internal or external PE reference has been encountered;
279 1.1 tron this includes the reference to an external subset */
280 1.1 tron XML_Bool hasParamEntityRefs;
281 1.1 tron XML_Bool standalone;
282 1.1 tron #ifdef XML_DTD
283 1.1 tron /* indicates if external PE has been read */
284 1.1 tron XML_Bool paramEntityRead;
285 1.1 tron HASH_TABLE paramEntities;
286 1.1 tron #endif /* XML_DTD */
287 1.1 tron PREFIX defaultPrefix;
288 1.1 tron /* === scaffolding for building content model === */
289 1.1 tron XML_Bool in_eldecl;
290 1.1 tron CONTENT_SCAFFOLD *scaffold;
291 1.1 tron unsigned contentStringLen;
292 1.1 tron unsigned scaffSize;
293 1.1 tron unsigned scaffCount;
294 1.1 tron int scaffLevel;
295 1.1 tron int *scaffIndex;
296 1.1 tron } DTD;
297 1.1 tron
298 1.1 tron typedef struct open_internal_entity {
299 1.1 tron const char *internalEventPtr;
300 1.1 tron const char *internalEventEndPtr;
301 1.1 tron struct open_internal_entity *next;
302 1.1 tron ENTITY *entity;
303 1.1 tron int startTagLevel;
304 1.1 tron XML_Bool betweenDecl; /* WFC: PE Between Declarations */
305 1.1 tron } OPEN_INTERNAL_ENTITY;
306 1.1 tron
307 1.1 tron typedef enum XML_Error PTRCALL Processor(XML_Parser parser,
308 1.1 tron const char *start,
309 1.1 tron const char *end,
310 1.1 tron const char **endPtr);
311 1.1 tron
312 1.1 tron static Processor prologProcessor;
313 1.1 tron static Processor prologInitProcessor;
314 1.1 tron static Processor contentProcessor;
315 1.1 tron static Processor cdataSectionProcessor;
316 1.1 tron #ifdef XML_DTD
317 1.1 tron static Processor ignoreSectionProcessor;
318 1.1 tron static Processor externalParEntProcessor;
319 1.1 tron static Processor externalParEntInitProcessor;
320 1.1 tron static Processor entityValueProcessor;
321 1.1 tron static Processor entityValueInitProcessor;
322 1.1 tron #endif /* XML_DTD */
323 1.1 tron static Processor epilogProcessor;
324 1.1 tron static Processor errorProcessor;
325 1.1 tron static Processor externalEntityInitProcessor;
326 1.1 tron static Processor externalEntityInitProcessor2;
327 1.1 tron static Processor externalEntityInitProcessor3;
328 1.1 tron static Processor externalEntityContentProcessor;
329 1.1 tron static Processor internalEntityProcessor;
330 1.1 tron
331 1.1 tron static enum XML_Error
332 1.1 tron handleUnknownEncoding(XML_Parser parser, const XML_Char *encodingName);
333 1.1 tron static enum XML_Error
334 1.1 tron processXmlDecl(XML_Parser parser, int isGeneralTextEntity,
335 1.1 tron const char *s, const char *next);
336 1.1 tron static enum XML_Error
337 1.1 tron initializeEncoding(XML_Parser parser);
338 1.1 tron static enum XML_Error
339 1.3 spz doProlog(XML_Parser parser, const ENCODING *enc, const char *s,
340 1.3 spz const char *end, int tok, const char *next, const char **nextPtr,
341 1.1 tron XML_Bool haveMore);
342 1.1 tron static enum XML_Error
343 1.3 spz processInternalEntity(XML_Parser parser, ENTITY *entity,
344 1.1 tron XML_Bool betweenDecl);
345 1.1 tron static enum XML_Error
346 1.1 tron doContent(XML_Parser parser, int startTagLevel, const ENCODING *enc,
347 1.3 spz const char *start, const char *end, const char **endPtr,
348 1.1 tron XML_Bool haveMore);
349 1.1 tron static enum XML_Error
350 1.1 tron doCdataSection(XML_Parser parser, const ENCODING *, const char **startPtr,
351 1.1 tron const char *end, const char **nextPtr, XML_Bool haveMore);
352 1.1 tron #ifdef XML_DTD
353 1.1 tron static enum XML_Error
354 1.1 tron doIgnoreSection(XML_Parser parser, const ENCODING *, const char **startPtr,
355 1.1 tron const char *end, const char **nextPtr, XML_Bool haveMore);
356 1.1 tron #endif /* XML_DTD */
357 1.1 tron
358 1.1 tron static enum XML_Error
359 1.1 tron storeAtts(XML_Parser parser, const ENCODING *, const char *s,
360 1.1 tron TAG_NAME *tagNamePtr, BINDING **bindingsPtr);
361 1.1 tron static enum XML_Error
362 1.1 tron addBinding(XML_Parser parser, PREFIX *prefix, const ATTRIBUTE_ID *attId,
363 1.1 tron const XML_Char *uri, BINDING **bindingsPtr);
364 1.1 tron static int
365 1.3 spz defineAttribute(ELEMENT_TYPE *type, ATTRIBUTE_ID *, XML_Bool isCdata,
366 1.1 tron XML_Bool isId, const XML_Char *dfltValue, XML_Parser parser);
367 1.1 tron static enum XML_Error
368 1.1 tron storeAttributeValue(XML_Parser parser, const ENCODING *, XML_Bool isCdata,
369 1.1 tron const char *, const char *, STRING_POOL *);
370 1.1 tron static enum XML_Error
371 1.1 tron appendAttributeValue(XML_Parser parser, const ENCODING *, XML_Bool isCdata,
372 1.1 tron const char *, const char *, STRING_POOL *);
373 1.1 tron static ATTRIBUTE_ID *
374 1.1 tron getAttributeId(XML_Parser parser, const ENCODING *enc, const char *start,
375 1.1 tron const char *end);
376 1.1 tron static int
377 1.1 tron setElementTypePrefix(XML_Parser parser, ELEMENT_TYPE *);
378 1.1 tron static enum XML_Error
379 1.1 tron storeEntityValue(XML_Parser parser, const ENCODING *enc, const char *start,
380 1.1 tron const char *end);
381 1.1 tron static int
382 1.1 tron reportProcessingInstruction(XML_Parser parser, const ENCODING *enc,
383 1.1 tron const char *start, const char *end);
384 1.1 tron static int
385 1.1 tron reportComment(XML_Parser parser, const ENCODING *enc, const char *start,
386 1.1 tron const char *end);
387 1.1 tron static void
388 1.1 tron reportDefault(XML_Parser parser, const ENCODING *enc, const char *start,
389 1.1 tron const char *end);
390 1.1 tron
391 1.1 tron static const XML_Char * getContext(XML_Parser parser);
392 1.1 tron static XML_Bool
393 1.1 tron setContext(XML_Parser parser, const XML_Char *context);
394 1.1 tron
395 1.1 tron static void FASTCALL normalizePublicId(XML_Char *s);
396 1.1 tron
397 1.1 tron static DTD * dtdCreate(const XML_Memory_Handling_Suite *ms);
398 1.1 tron /* do not call if parentParser != NULL */
399 1.1 tron static void dtdReset(DTD *p, const XML_Memory_Handling_Suite *ms);
400 1.1 tron static void
401 1.1 tron dtdDestroy(DTD *p, XML_Bool isDocEntity, const XML_Memory_Handling_Suite *ms);
402 1.1 tron static int
403 1.3 spz dtdCopy(XML_Parser oldParser,
404 1.3 spz DTD *newDtd, const DTD *oldDtd, const XML_Memory_Handling_Suite *ms);
405 1.1 tron static int
406 1.3 spz copyEntityTable(XML_Parser oldParser,
407 1.3 spz HASH_TABLE *, STRING_POOL *, const HASH_TABLE *);
408 1.1 tron static NAMED *
409 1.3 spz lookup(XML_Parser parser, HASH_TABLE *table, KEY name, size_t createSize);
410 1.1 tron static void FASTCALL
411 1.1 tron hashTableInit(HASH_TABLE *, const XML_Memory_Handling_Suite *ms);
412 1.1 tron static void FASTCALL hashTableClear(HASH_TABLE *);
413 1.1 tron static void FASTCALL hashTableDestroy(HASH_TABLE *);
414 1.1 tron static void FASTCALL
415 1.1 tron hashTableIterInit(HASH_TABLE_ITER *, const HASH_TABLE *);
416 1.1 tron static NAMED * FASTCALL hashTableIterNext(HASH_TABLE_ITER *);
417 1.1 tron
418 1.1 tron static void FASTCALL
419 1.1 tron poolInit(STRING_POOL *, const XML_Memory_Handling_Suite *ms);
420 1.1 tron static void FASTCALL poolClear(STRING_POOL *);
421 1.1 tron static void FASTCALL poolDestroy(STRING_POOL *);
422 1.1 tron static XML_Char *
423 1.1 tron poolAppend(STRING_POOL *pool, const ENCODING *enc,
424 1.1 tron const char *ptr, const char *end);
425 1.1 tron static XML_Char *
426 1.1 tron poolStoreString(STRING_POOL *pool, const ENCODING *enc,
427 1.1 tron const char *ptr, const char *end);
428 1.1 tron static XML_Bool FASTCALL poolGrow(STRING_POOL *pool);
429 1.1 tron static const XML_Char * FASTCALL
430 1.1 tron poolCopyString(STRING_POOL *pool, const XML_Char *s);
431 1.1 tron static const XML_Char *
432 1.1 tron poolCopyStringN(STRING_POOL *pool, const XML_Char *s, int n);
433 1.1 tron static const XML_Char * FASTCALL
434 1.1 tron poolAppendString(STRING_POOL *pool, const XML_Char *s);
435 1.1 tron
436 1.1 tron static int FASTCALL nextScaffoldPart(XML_Parser parser);
437 1.1 tron static XML_Content * build_model(XML_Parser parser);
438 1.1 tron static ELEMENT_TYPE *
439 1.1 tron getElementType(XML_Parser parser, const ENCODING *enc,
440 1.1 tron const char *ptr, const char *end);
441 1.1 tron
442 1.6 spz static unsigned long generate_hash_secret_salt(XML_Parser parser);
443 1.3 spz static XML_Bool startParsing(XML_Parser parser);
444 1.3 spz
445 1.1 tron static XML_Parser
446 1.1 tron parserCreate(const XML_Char *encodingName,
447 1.1 tron const XML_Memory_Handling_Suite *memsuite,
448 1.1 tron const XML_Char *nameSep,
449 1.1 tron DTD *dtd);
450 1.3 spz
451 1.1 tron static void
452 1.1 tron parserInit(XML_Parser parser, const XML_Char *encodingName);
453 1.1 tron
454 1.1 tron #define poolStart(pool) ((pool)->start)
455 1.1 tron #define poolEnd(pool) ((pool)->ptr)
456 1.1 tron #define poolLength(pool) ((pool)->ptr - (pool)->start)
457 1.1 tron #define poolChop(pool) ((void)--(pool->ptr))
458 1.1 tron #define poolLastChar(pool) (((pool)->ptr)[-1])
459 1.1 tron #define poolDiscard(pool) ((pool)->ptr = (pool)->start)
460 1.1 tron #define poolFinish(pool) ((pool)->start = (pool)->ptr)
461 1.1 tron #define poolAppendChar(pool, c) \
462 1.1 tron (((pool)->ptr == (pool)->end && !poolGrow(pool)) \
463 1.1 tron ? 0 \
464 1.1 tron : ((*((pool)->ptr)++ = c), 1))
465 1.1 tron
466 1.1 tron struct XML_ParserStruct {
467 1.1 tron /* The first member must be userData so that the XML_GetUserData
468 1.1 tron macro works. */
469 1.1 tron void *m_userData;
470 1.1 tron void *m_handlerArg;
471 1.1 tron char *m_buffer;
472 1.1 tron const XML_Memory_Handling_Suite m_mem;
473 1.1 tron /* first character to be parsed */
474 1.1 tron const char *m_bufferPtr;
475 1.1 tron /* past last character to be parsed */
476 1.1 tron char *m_bufferEnd;
477 1.1 tron /* allocated end of buffer */
478 1.1 tron const char *m_bufferLim;
479 1.1 tron XML_Index m_parseEndByteIndex;
480 1.1 tron const char *m_parseEndPtr;
481 1.1 tron XML_Char *m_dataBuf;
482 1.1 tron XML_Char *m_dataBufEnd;
483 1.1 tron XML_StartElementHandler m_startElementHandler;
484 1.1 tron XML_EndElementHandler m_endElementHandler;
485 1.1 tron XML_CharacterDataHandler m_characterDataHandler;
486 1.1 tron XML_ProcessingInstructionHandler m_processingInstructionHandler;
487 1.1 tron XML_CommentHandler m_commentHandler;
488 1.1 tron XML_StartCdataSectionHandler m_startCdataSectionHandler;
489 1.1 tron XML_EndCdataSectionHandler m_endCdataSectionHandler;
490 1.1 tron XML_DefaultHandler m_defaultHandler;
491 1.1 tron XML_StartDoctypeDeclHandler m_startDoctypeDeclHandler;
492 1.1 tron XML_EndDoctypeDeclHandler m_endDoctypeDeclHandler;
493 1.1 tron XML_UnparsedEntityDeclHandler m_unparsedEntityDeclHandler;
494 1.1 tron XML_NotationDeclHandler m_notationDeclHandler;
495 1.1 tron XML_StartNamespaceDeclHandler m_startNamespaceDeclHandler;
496 1.1 tron XML_EndNamespaceDeclHandler m_endNamespaceDeclHandler;
497 1.1 tron XML_NotStandaloneHandler m_notStandaloneHandler;
498 1.1 tron XML_ExternalEntityRefHandler m_externalEntityRefHandler;
499 1.1 tron XML_Parser m_externalEntityRefHandlerArg;
500 1.1 tron XML_SkippedEntityHandler m_skippedEntityHandler;
501 1.1 tron XML_UnknownEncodingHandler m_unknownEncodingHandler;
502 1.1 tron XML_ElementDeclHandler m_elementDeclHandler;
503 1.1 tron XML_AttlistDeclHandler m_attlistDeclHandler;
504 1.1 tron XML_EntityDeclHandler m_entityDeclHandler;
505 1.1 tron XML_XmlDeclHandler m_xmlDeclHandler;
506 1.1 tron const ENCODING *m_encoding;
507 1.1 tron INIT_ENCODING m_initEncoding;
508 1.1 tron const ENCODING *m_internalEncoding;
509 1.1 tron const XML_Char *m_protocolEncodingName;
510 1.1 tron XML_Bool m_ns;
511 1.1 tron XML_Bool m_ns_triplets;
512 1.1 tron void *m_unknownEncodingMem;
513 1.1 tron void *m_unknownEncodingData;
514 1.1 tron void *m_unknownEncodingHandlerData;
515 1.1 tron void (XMLCALL *m_unknownEncodingRelease)(void *);
516 1.1 tron PROLOG_STATE m_prologState;
517 1.1 tron Processor *m_processor;
518 1.1 tron enum XML_Error m_errorCode;
519 1.1 tron const char *m_eventPtr;
520 1.1 tron const char *m_eventEndPtr;
521 1.1 tron const char *m_positionPtr;
522 1.1 tron OPEN_INTERNAL_ENTITY *m_openInternalEntities;
523 1.1 tron OPEN_INTERNAL_ENTITY *m_freeInternalEntities;
524 1.1 tron XML_Bool m_defaultExpandInternalEntities;
525 1.1 tron int m_tagLevel;
526 1.1 tron ENTITY *m_declEntity;
527 1.1 tron const XML_Char *m_doctypeName;
528 1.1 tron const XML_Char *m_doctypeSysid;
529 1.1 tron const XML_Char *m_doctypePubid;
530 1.1 tron const XML_Char *m_declAttributeType;
531 1.1 tron const XML_Char *m_declNotationName;
532 1.1 tron const XML_Char *m_declNotationPublicId;
533 1.1 tron ELEMENT_TYPE *m_declElementType;
534 1.1 tron ATTRIBUTE_ID *m_declAttributeId;
535 1.1 tron XML_Bool m_declAttributeIsCdata;
536 1.1 tron XML_Bool m_declAttributeIsId;
537 1.1 tron DTD *m_dtd;
538 1.1 tron const XML_Char *m_curBase;
539 1.1 tron TAG *m_tagStack;
540 1.1 tron TAG *m_freeTagList;
541 1.1 tron BINDING *m_inheritedBindings;
542 1.1 tron BINDING *m_freeBindingList;
543 1.1 tron int m_attsSize;
544 1.1 tron int m_nSpecifiedAtts;
545 1.1 tron int m_idAttIndex;
546 1.1 tron ATTRIBUTE *m_atts;
547 1.1 tron NS_ATT *m_nsAtts;
548 1.1 tron unsigned long m_nsAttsVersion;
549 1.1 tron unsigned char m_nsAttsPower;
550 1.3 spz #ifdef XML_ATTR_INFO
551 1.3 spz XML_AttrInfo *m_attInfo;
552 1.3 spz #endif
553 1.1 tron POSITION m_position;
554 1.1 tron STRING_POOL m_tempPool;
555 1.1 tron STRING_POOL m_temp2Pool;
556 1.1 tron char *m_groupConnector;
557 1.1 tron unsigned int m_groupSize;
558 1.1 tron XML_Char m_namespaceSeparator;
559 1.1 tron XML_Parser m_parentParser;
560 1.1 tron XML_ParsingStatus m_parsingStatus;
561 1.1 tron #ifdef XML_DTD
562 1.1 tron XML_Bool m_isParamEntity;
563 1.1 tron XML_Bool m_useForeignDTD;
564 1.1 tron enum XML_ParamEntityParsing m_paramEntityParsing;
565 1.1 tron #endif
566 1.3 spz unsigned long m_hash_secret_salt;
567 1.1 tron };
568 1.1 tron
569 1.1 tron #define MALLOC(s) (parser->m_mem.malloc_fcn((s)))
570 1.1 tron #define REALLOC(p,s) (parser->m_mem.realloc_fcn((p),(s)))
571 1.1 tron #define FREE(p) (parser->m_mem.free_fcn((p)))
572 1.1 tron
573 1.1 tron #define userData (parser->m_userData)
574 1.1 tron #define handlerArg (parser->m_handlerArg)
575 1.1 tron #define startElementHandler (parser->m_startElementHandler)
576 1.1 tron #define endElementHandler (parser->m_endElementHandler)
577 1.1 tron #define characterDataHandler (parser->m_characterDataHandler)
578 1.1 tron #define processingInstructionHandler \
579 1.1 tron (parser->m_processingInstructionHandler)
580 1.1 tron #define commentHandler (parser->m_commentHandler)
581 1.1 tron #define startCdataSectionHandler \
582 1.1 tron (parser->m_startCdataSectionHandler)
583 1.1 tron #define endCdataSectionHandler (parser->m_endCdataSectionHandler)
584 1.1 tron #define defaultHandler (parser->m_defaultHandler)
585 1.1 tron #define startDoctypeDeclHandler (parser->m_startDoctypeDeclHandler)
586 1.1 tron #define endDoctypeDeclHandler (parser->m_endDoctypeDeclHandler)
587 1.1 tron #define unparsedEntityDeclHandler \
588 1.1 tron (parser->m_unparsedEntityDeclHandler)
589 1.1 tron #define notationDeclHandler (parser->m_notationDeclHandler)
590 1.1 tron #define startNamespaceDeclHandler \
591 1.1 tron (parser->m_startNamespaceDeclHandler)
592 1.1 tron #define endNamespaceDeclHandler (parser->m_endNamespaceDeclHandler)
593 1.1 tron #define notStandaloneHandler (parser->m_notStandaloneHandler)
594 1.1 tron #define externalEntityRefHandler \
595 1.1 tron (parser->m_externalEntityRefHandler)
596 1.1 tron #define externalEntityRefHandlerArg \
597 1.1 tron (parser->m_externalEntityRefHandlerArg)
598 1.1 tron #define internalEntityRefHandler \
599 1.1 tron (parser->m_internalEntityRefHandler)
600 1.1 tron #define skippedEntityHandler (parser->m_skippedEntityHandler)
601 1.1 tron #define unknownEncodingHandler (parser->m_unknownEncodingHandler)
602 1.1 tron #define elementDeclHandler (parser->m_elementDeclHandler)
603 1.1 tron #define attlistDeclHandler (parser->m_attlistDeclHandler)
604 1.1 tron #define entityDeclHandler (parser->m_entityDeclHandler)
605 1.1 tron #define xmlDeclHandler (parser->m_xmlDeclHandler)
606 1.1 tron #define encoding (parser->m_encoding)
607 1.1 tron #define initEncoding (parser->m_initEncoding)
608 1.1 tron #define internalEncoding (parser->m_internalEncoding)
609 1.1 tron #define unknownEncodingMem (parser->m_unknownEncodingMem)
610 1.1 tron #define unknownEncodingData (parser->m_unknownEncodingData)
611 1.1 tron #define unknownEncodingHandlerData \
612 1.1 tron (parser->m_unknownEncodingHandlerData)
613 1.1 tron #define unknownEncodingRelease (parser->m_unknownEncodingRelease)
614 1.1 tron #define protocolEncodingName (parser->m_protocolEncodingName)
615 1.1 tron #define ns (parser->m_ns)
616 1.1 tron #define ns_triplets (parser->m_ns_triplets)
617 1.1 tron #define prologState (parser->m_prologState)
618 1.1 tron #define processor (parser->m_processor)
619 1.1 tron #define errorCode (parser->m_errorCode)
620 1.1 tron #define eventPtr (parser->m_eventPtr)
621 1.1 tron #define eventEndPtr (parser->m_eventEndPtr)
622 1.1 tron #define positionPtr (parser->m_positionPtr)
623 1.1 tron #define position (parser->m_position)
624 1.1 tron #define openInternalEntities (parser->m_openInternalEntities)
625 1.1 tron #define freeInternalEntities (parser->m_freeInternalEntities)
626 1.1 tron #define defaultExpandInternalEntities \
627 1.1 tron (parser->m_defaultExpandInternalEntities)
628 1.1 tron #define tagLevel (parser->m_tagLevel)
629 1.1 tron #define buffer (parser->m_buffer)
630 1.1 tron #define bufferPtr (parser->m_bufferPtr)
631 1.1 tron #define bufferEnd (parser->m_bufferEnd)
632 1.1 tron #define parseEndByteIndex (parser->m_parseEndByteIndex)
633 1.1 tron #define parseEndPtr (parser->m_parseEndPtr)
634 1.1 tron #define bufferLim (parser->m_bufferLim)
635 1.1 tron #define dataBuf (parser->m_dataBuf)
636 1.1 tron #define dataBufEnd (parser->m_dataBufEnd)
637 1.1 tron #define _dtd (parser->m_dtd)
638 1.1 tron #define curBase (parser->m_curBase)
639 1.1 tron #define declEntity (parser->m_declEntity)
640 1.1 tron #define doctypeName (parser->m_doctypeName)
641 1.1 tron #define doctypeSysid (parser->m_doctypeSysid)
642 1.1 tron #define doctypePubid (parser->m_doctypePubid)
643 1.1 tron #define declAttributeType (parser->m_declAttributeType)
644 1.1 tron #define declNotationName (parser->m_declNotationName)
645 1.1 tron #define declNotationPublicId (parser->m_declNotationPublicId)
646 1.1 tron #define declElementType (parser->m_declElementType)
647 1.1 tron #define declAttributeId (parser->m_declAttributeId)
648 1.1 tron #define declAttributeIsCdata (parser->m_declAttributeIsCdata)
649 1.1 tron #define declAttributeIsId (parser->m_declAttributeIsId)
650 1.1 tron #define freeTagList (parser->m_freeTagList)
651 1.1 tron #define freeBindingList (parser->m_freeBindingList)
652 1.1 tron #define inheritedBindings (parser->m_inheritedBindings)
653 1.1 tron #define tagStack (parser->m_tagStack)
654 1.1 tron #define atts (parser->m_atts)
655 1.1 tron #define attsSize (parser->m_attsSize)
656 1.1 tron #define nSpecifiedAtts (parser->m_nSpecifiedAtts)
657 1.1 tron #define idAttIndex (parser->m_idAttIndex)
658 1.1 tron #define nsAtts (parser->m_nsAtts)
659 1.1 tron #define nsAttsVersion (parser->m_nsAttsVersion)
660 1.1 tron #define nsAttsPower (parser->m_nsAttsPower)
661 1.3 spz #define attInfo (parser->m_attInfo)
662 1.1 tron #define tempPool (parser->m_tempPool)
663 1.1 tron #define temp2Pool (parser->m_temp2Pool)
664 1.1 tron #define groupConnector (parser->m_groupConnector)
665 1.1 tron #define groupSize (parser->m_groupSize)
666 1.1 tron #define namespaceSeparator (parser->m_namespaceSeparator)
667 1.1 tron #define parentParser (parser->m_parentParser)
668 1.1 tron #define ps_parsing (parser->m_parsingStatus.parsing)
669 1.1 tron #define ps_finalBuffer (parser->m_parsingStatus.finalBuffer)
670 1.1 tron #ifdef XML_DTD
671 1.1 tron #define isParamEntity (parser->m_isParamEntity)
672 1.1 tron #define useForeignDTD (parser->m_useForeignDTD)
673 1.1 tron #define paramEntityParsing (parser->m_paramEntityParsing)
674 1.1 tron #endif /* XML_DTD */
675 1.3 spz #define hash_secret_salt (parser->m_hash_secret_salt)
676 1.1 tron
677 1.1 tron XML_Parser XMLCALL
678 1.1 tron XML_ParserCreate(const XML_Char *encodingName)
679 1.1 tron {
680 1.1 tron return XML_ParserCreate_MM(encodingName, NULL, NULL);
681 1.1 tron }
682 1.1 tron
683 1.1 tron XML_Parser XMLCALL
684 1.1 tron XML_ParserCreateNS(const XML_Char *encodingName, XML_Char nsSep)
685 1.1 tron {
686 1.1 tron XML_Char tmp[2];
687 1.1 tron *tmp = nsSep;
688 1.1 tron return XML_ParserCreate_MM(encodingName, NULL, tmp);
689 1.1 tron }
690 1.1 tron
691 1.1 tron static const XML_Char implicitContext[] = {
692 1.1 tron ASCII_x, ASCII_m, ASCII_l, ASCII_EQUALS, ASCII_h, ASCII_t, ASCII_t, ASCII_p,
693 1.3 spz ASCII_COLON, ASCII_SLASH, ASCII_SLASH, ASCII_w, ASCII_w, ASCII_w,
694 1.1 tron ASCII_PERIOD, ASCII_w, ASCII_3, ASCII_PERIOD, ASCII_o, ASCII_r, ASCII_g,
695 1.1 tron ASCII_SLASH, ASCII_X, ASCII_M, ASCII_L, ASCII_SLASH, ASCII_1, ASCII_9,
696 1.1 tron ASCII_9, ASCII_8, ASCII_SLASH, ASCII_n, ASCII_a, ASCII_m, ASCII_e,
697 1.1 tron ASCII_s, ASCII_p, ASCII_a, ASCII_c, ASCII_e, '\0'
698 1.1 tron };
699 1.1 tron
700 1.3 spz static unsigned long
701 1.6 spz gather_time_entropy(void)
702 1.6 spz {
703 1.6 spz #ifdef WIN32
704 1.6 spz FILETIME ft;
705 1.6 spz GetSystemTimeAsFileTime(&ft); /* never fails */
706 1.6 spz return ft.dwHighDateTime ^ ft.dwLowDateTime;
707 1.6 spz #else
708 1.6 spz struct timeval tv;
709 1.6 spz int gettimeofday_res;
710 1.6 spz
711 1.6 spz gettimeofday_res = gettimeofday(&tv, NULL);
712 1.6 spz assert (gettimeofday_res == 0);
713 1.6 spz
714 1.6 spz /* Microseconds time is <20 bits entropy */
715 1.6 spz return tv.tv_usec;
716 1.6 spz #endif
717 1.6 spz }
718 1.6 spz
719 1.6 spz static unsigned long
720 1.6 spz generate_hash_secret_salt(XML_Parser parser)
721 1.3 spz {
722 1.6 spz /* Process ID is 0 bits entropy if attacker has local access
723 1.6 spz * XML_Parser address is few bits of entropy if attacker has local access */
724 1.6 spz const unsigned long entropy =
725 1.6 spz gather_time_entropy() ^ getpid() ^ (unsigned long)parser;
726 1.6 spz
727 1.6 spz /* Factors are 2^31-1 and 2^61-1 (Mersenne primes M31 and M61) */
728 1.6 spz if (sizeof(unsigned long) == 4) {
729 1.6 spz return entropy * 2147483647;
730 1.6 spz } else {
731 1.6 spz return entropy * (unsigned long)2305843009213693951;
732 1.6 spz }
733 1.3 spz }
734 1.3 spz
735 1.3 spz static XML_Bool /* only valid for root parser */
736 1.3 spz startParsing(XML_Parser parser)
737 1.3 spz {
738 1.3 spz /* hash functions must be initialized before setContext() is called */
739 1.3 spz if (hash_secret_salt == 0)
740 1.6 spz hash_secret_salt = generate_hash_secret_salt(parser);
741 1.3 spz if (ns) {
742 1.3 spz /* implicit context only set for root parser, since child
743 1.3 spz parsers (i.e. external entity parsers) will inherit it
744 1.3 spz */
745 1.3 spz return setContext(parser, implicitContext);
746 1.3 spz }
747 1.3 spz return XML_TRUE;
748 1.3 spz }
749 1.3 spz
750 1.1 tron XML_Parser XMLCALL
751 1.1 tron XML_ParserCreate_MM(const XML_Char *encodingName,
752 1.1 tron const XML_Memory_Handling_Suite *memsuite,
753 1.1 tron const XML_Char *nameSep)
754 1.1 tron {
755 1.3 spz return parserCreate(encodingName, memsuite, nameSep, NULL);
756 1.1 tron }
757 1.1 tron
758 1.1 tron static XML_Parser
759 1.1 tron parserCreate(const XML_Char *encodingName,
760 1.1 tron const XML_Memory_Handling_Suite *memsuite,
761 1.1 tron const XML_Char *nameSep,
762 1.1 tron DTD *dtd)
763 1.1 tron {
764 1.1 tron XML_Parser parser;
765 1.1 tron
766 1.1 tron if (memsuite) {
767 1.1 tron XML_Memory_Handling_Suite *mtemp;
768 1.1 tron parser = (XML_Parser)
769 1.1 tron memsuite->malloc_fcn(sizeof(struct XML_ParserStruct));
770 1.1 tron if (parser != NULL) {
771 1.1 tron mtemp = (XML_Memory_Handling_Suite *)&(parser->m_mem);
772 1.1 tron mtemp->malloc_fcn = memsuite->malloc_fcn;
773 1.1 tron mtemp->realloc_fcn = memsuite->realloc_fcn;
774 1.1 tron mtemp->free_fcn = memsuite->free_fcn;
775 1.1 tron }
776 1.1 tron }
777 1.1 tron else {
778 1.1 tron XML_Memory_Handling_Suite *mtemp;
779 1.1 tron parser = (XML_Parser)malloc(sizeof(struct XML_ParserStruct));
780 1.1 tron if (parser != NULL) {
781 1.1 tron mtemp = (XML_Memory_Handling_Suite *)&(parser->m_mem);
782 1.1 tron mtemp->malloc_fcn = malloc;
783 1.1 tron mtemp->realloc_fcn = realloc;
784 1.1 tron mtemp->free_fcn = free;
785 1.1 tron }
786 1.1 tron }
787 1.1 tron
788 1.1 tron if (!parser)
789 1.1 tron return parser;
790 1.1 tron
791 1.1 tron buffer = NULL;
792 1.1 tron bufferLim = NULL;
793 1.1 tron
794 1.1 tron attsSize = INIT_ATTS_SIZE;
795 1.1 tron atts = (ATTRIBUTE *)MALLOC(attsSize * sizeof(ATTRIBUTE));
796 1.1 tron if (atts == NULL) {
797 1.1 tron FREE(parser);
798 1.1 tron return NULL;
799 1.1 tron }
800 1.3 spz #ifdef XML_ATTR_INFO
801 1.3 spz attInfo = (XML_AttrInfo*)MALLOC(attsSize * sizeof(XML_AttrInfo));
802 1.3 spz if (attInfo == NULL) {
803 1.3 spz FREE(atts);
804 1.3 spz FREE(parser);
805 1.3 spz return NULL;
806 1.3 spz }
807 1.3 spz #endif
808 1.1 tron dataBuf = (XML_Char *)MALLOC(INIT_DATA_BUF_SIZE * sizeof(XML_Char));
809 1.1 tron if (dataBuf == NULL) {
810 1.1 tron FREE(atts);
811 1.3 spz #ifdef XML_ATTR_INFO
812 1.3 spz FREE(attInfo);
813 1.3 spz #endif
814 1.1 tron FREE(parser);
815 1.1 tron return NULL;
816 1.1 tron }
817 1.1 tron dataBufEnd = dataBuf + INIT_DATA_BUF_SIZE;
818 1.1 tron
819 1.1 tron if (dtd)
820 1.1 tron _dtd = dtd;
821 1.1 tron else {
822 1.1 tron _dtd = dtdCreate(&parser->m_mem);
823 1.1 tron if (_dtd == NULL) {
824 1.1 tron FREE(dataBuf);
825 1.1 tron FREE(atts);
826 1.3 spz #ifdef XML_ATTR_INFO
827 1.3 spz FREE(attInfo);
828 1.3 spz #endif
829 1.1 tron FREE(parser);
830 1.1 tron return NULL;
831 1.1 tron }
832 1.1 tron }
833 1.1 tron
834 1.1 tron freeBindingList = NULL;
835 1.1 tron freeTagList = NULL;
836 1.1 tron freeInternalEntities = NULL;
837 1.1 tron
838 1.1 tron groupSize = 0;
839 1.1 tron groupConnector = NULL;
840 1.1 tron
841 1.1 tron unknownEncodingHandler = NULL;
842 1.1 tron unknownEncodingHandlerData = NULL;
843 1.1 tron
844 1.1 tron namespaceSeparator = ASCII_EXCL;
845 1.1 tron ns = XML_FALSE;
846 1.1 tron ns_triplets = XML_FALSE;
847 1.1 tron
848 1.1 tron nsAtts = NULL;
849 1.1 tron nsAttsVersion = 0;
850 1.1 tron nsAttsPower = 0;
851 1.1 tron
852 1.1 tron poolInit(&tempPool, &(parser->m_mem));
853 1.1 tron poolInit(&temp2Pool, &(parser->m_mem));
854 1.1 tron parserInit(parser, encodingName);
855 1.1 tron
856 1.1 tron if (encodingName && !protocolEncodingName) {
857 1.1 tron XML_ParserFree(parser);
858 1.1 tron return NULL;
859 1.1 tron }
860 1.1 tron
861 1.1 tron if (nameSep) {
862 1.1 tron ns = XML_TRUE;
863 1.1 tron internalEncoding = XmlGetInternalEncodingNS();
864 1.1 tron namespaceSeparator = *nameSep;
865 1.1 tron }
866 1.1 tron else {
867 1.1 tron internalEncoding = XmlGetInternalEncoding();
868 1.1 tron }
869 1.1 tron
870 1.1 tron return parser;
871 1.1 tron }
872 1.1 tron
873 1.1 tron static void
874 1.1 tron parserInit(XML_Parser parser, const XML_Char *encodingName)
875 1.1 tron {
876 1.1 tron processor = prologInitProcessor;
877 1.1 tron XmlPrologStateInit(&prologState);
878 1.1 tron protocolEncodingName = (encodingName != NULL
879 1.1 tron ? poolCopyString(&tempPool, encodingName)
880 1.1 tron : NULL);
881 1.1 tron curBase = NULL;
882 1.1 tron XmlInitEncoding(&initEncoding, &encoding, 0);
883 1.1 tron userData = NULL;
884 1.1 tron handlerArg = NULL;
885 1.1 tron startElementHandler = NULL;
886 1.1 tron endElementHandler = NULL;
887 1.1 tron characterDataHandler = NULL;
888 1.1 tron processingInstructionHandler = NULL;
889 1.1 tron commentHandler = NULL;
890 1.1 tron startCdataSectionHandler = NULL;
891 1.1 tron endCdataSectionHandler = NULL;
892 1.1 tron defaultHandler = NULL;
893 1.1 tron startDoctypeDeclHandler = NULL;
894 1.1 tron endDoctypeDeclHandler = NULL;
895 1.1 tron unparsedEntityDeclHandler = NULL;
896 1.1 tron notationDeclHandler = NULL;
897 1.1 tron startNamespaceDeclHandler = NULL;
898 1.1 tron endNamespaceDeclHandler = NULL;
899 1.1 tron notStandaloneHandler = NULL;
900 1.1 tron externalEntityRefHandler = NULL;
901 1.1 tron externalEntityRefHandlerArg = parser;
902 1.1 tron skippedEntityHandler = NULL;
903 1.1 tron elementDeclHandler = NULL;
904 1.1 tron attlistDeclHandler = NULL;
905 1.1 tron entityDeclHandler = NULL;
906 1.1 tron xmlDeclHandler = NULL;
907 1.1 tron bufferPtr = buffer;
908 1.1 tron bufferEnd = buffer;
909 1.1 tron parseEndByteIndex = 0;
910 1.1 tron parseEndPtr = NULL;
911 1.1 tron declElementType = NULL;
912 1.1 tron declAttributeId = NULL;
913 1.1 tron declEntity = NULL;
914 1.1 tron doctypeName = NULL;
915 1.1 tron doctypeSysid = NULL;
916 1.1 tron doctypePubid = NULL;
917 1.1 tron declAttributeType = NULL;
918 1.1 tron declNotationName = NULL;
919 1.1 tron declNotationPublicId = NULL;
920 1.1 tron declAttributeIsCdata = XML_FALSE;
921 1.1 tron declAttributeIsId = XML_FALSE;
922 1.1 tron memset(&position, 0, sizeof(POSITION));
923 1.1 tron errorCode = XML_ERROR_NONE;
924 1.1 tron eventPtr = NULL;
925 1.1 tron eventEndPtr = NULL;
926 1.1 tron positionPtr = NULL;
927 1.1 tron openInternalEntities = NULL;
928 1.1 tron defaultExpandInternalEntities = XML_TRUE;
929 1.1 tron tagLevel = 0;
930 1.1 tron tagStack = NULL;
931 1.1 tron inheritedBindings = NULL;
932 1.1 tron nSpecifiedAtts = 0;
933 1.1 tron unknownEncodingMem = NULL;
934 1.1 tron unknownEncodingRelease = NULL;
935 1.1 tron unknownEncodingData = NULL;
936 1.1 tron parentParser = NULL;
937 1.1 tron ps_parsing = XML_INITIALIZED;
938 1.1 tron #ifdef XML_DTD
939 1.1 tron isParamEntity = XML_FALSE;
940 1.1 tron useForeignDTD = XML_FALSE;
941 1.1 tron paramEntityParsing = XML_PARAM_ENTITY_PARSING_NEVER;
942 1.1 tron #endif
943 1.3 spz hash_secret_salt = 0;
944 1.1 tron }
945 1.1 tron
946 1.1 tron /* moves list of bindings to freeBindingList */
947 1.1 tron static void FASTCALL
948 1.1 tron moveToFreeBindingList(XML_Parser parser, BINDING *bindings)
949 1.1 tron {
950 1.1 tron while (bindings) {
951 1.1 tron BINDING *b = bindings;
952 1.1 tron bindings = bindings->nextTagBinding;
953 1.1 tron b->nextTagBinding = freeBindingList;
954 1.1 tron freeBindingList = b;
955 1.1 tron }
956 1.1 tron }
957 1.1 tron
958 1.1 tron XML_Bool XMLCALL
959 1.1 tron XML_ParserReset(XML_Parser parser, const XML_Char *encodingName)
960 1.1 tron {
961 1.1 tron TAG *tStk;
962 1.1 tron OPEN_INTERNAL_ENTITY *openEntityList;
963 1.1 tron if (parentParser)
964 1.1 tron return XML_FALSE;
965 1.1 tron /* move tagStack to freeTagList */
966 1.1 tron tStk = tagStack;
967 1.1 tron while (tStk) {
968 1.1 tron TAG *tag = tStk;
969 1.1 tron tStk = tStk->parent;
970 1.1 tron tag->parent = freeTagList;
971 1.1 tron moveToFreeBindingList(parser, tag->bindings);
972 1.1 tron tag->bindings = NULL;
973 1.1 tron freeTagList = tag;
974 1.1 tron }
975 1.1 tron /* move openInternalEntities to freeInternalEntities */
976 1.1 tron openEntityList = openInternalEntities;
977 1.1 tron while (openEntityList) {
978 1.1 tron OPEN_INTERNAL_ENTITY *openEntity = openEntityList;
979 1.1 tron openEntityList = openEntity->next;
980 1.1 tron openEntity->next = freeInternalEntities;
981 1.1 tron freeInternalEntities = openEntity;
982 1.1 tron }
983 1.1 tron moveToFreeBindingList(parser, inheritedBindings);
984 1.1 tron FREE(unknownEncodingMem);
985 1.1 tron if (unknownEncodingRelease)
986 1.1 tron unknownEncodingRelease(unknownEncodingData);
987 1.1 tron poolClear(&tempPool);
988 1.1 tron poolClear(&temp2Pool);
989 1.1 tron parserInit(parser, encodingName);
990 1.1 tron dtdReset(_dtd, &parser->m_mem);
991 1.3 spz return XML_TRUE;
992 1.1 tron }
993 1.1 tron
994 1.1 tron enum XML_Status XMLCALL
995 1.1 tron XML_SetEncoding(XML_Parser parser, const XML_Char *encodingName)
996 1.1 tron {
997 1.1 tron /* Block after XML_Parse()/XML_ParseBuffer() has been called.
998 1.1 tron XXX There's no way for the caller to determine which of the
999 1.1 tron XXX possible error cases caused the XML_STATUS_ERROR return.
1000 1.1 tron */
1001 1.1 tron if (ps_parsing == XML_PARSING || ps_parsing == XML_SUSPENDED)
1002 1.1 tron return XML_STATUS_ERROR;
1003 1.1 tron if (encodingName == NULL)
1004 1.1 tron protocolEncodingName = NULL;
1005 1.1 tron else {
1006 1.1 tron protocolEncodingName = poolCopyString(&tempPool, encodingName);
1007 1.1 tron if (!protocolEncodingName)
1008 1.1 tron return XML_STATUS_ERROR;
1009 1.1 tron }
1010 1.1 tron return XML_STATUS_OK;
1011 1.1 tron }
1012 1.1 tron
1013 1.1 tron XML_Parser XMLCALL
1014 1.1 tron XML_ExternalEntityParserCreate(XML_Parser oldParser,
1015 1.1 tron const XML_Char *context,
1016 1.1 tron const XML_Char *encodingName)
1017 1.1 tron {
1018 1.1 tron XML_Parser parser = oldParser;
1019 1.1 tron DTD *newDtd = NULL;
1020 1.1 tron DTD *oldDtd = _dtd;
1021 1.1 tron XML_StartElementHandler oldStartElementHandler = startElementHandler;
1022 1.1 tron XML_EndElementHandler oldEndElementHandler = endElementHandler;
1023 1.1 tron XML_CharacterDataHandler oldCharacterDataHandler = characterDataHandler;
1024 1.1 tron XML_ProcessingInstructionHandler oldProcessingInstructionHandler
1025 1.1 tron = processingInstructionHandler;
1026 1.1 tron XML_CommentHandler oldCommentHandler = commentHandler;
1027 1.1 tron XML_StartCdataSectionHandler oldStartCdataSectionHandler
1028 1.1 tron = startCdataSectionHandler;
1029 1.1 tron XML_EndCdataSectionHandler oldEndCdataSectionHandler
1030 1.1 tron = endCdataSectionHandler;
1031 1.1 tron XML_DefaultHandler oldDefaultHandler = defaultHandler;
1032 1.1 tron XML_UnparsedEntityDeclHandler oldUnparsedEntityDeclHandler
1033 1.1 tron = unparsedEntityDeclHandler;
1034 1.1 tron XML_NotationDeclHandler oldNotationDeclHandler = notationDeclHandler;
1035 1.1 tron XML_StartNamespaceDeclHandler oldStartNamespaceDeclHandler
1036 1.1 tron = startNamespaceDeclHandler;
1037 1.1 tron XML_EndNamespaceDeclHandler oldEndNamespaceDeclHandler
1038 1.1 tron = endNamespaceDeclHandler;
1039 1.1 tron XML_NotStandaloneHandler oldNotStandaloneHandler = notStandaloneHandler;
1040 1.1 tron XML_ExternalEntityRefHandler oldExternalEntityRefHandler
1041 1.1 tron = externalEntityRefHandler;
1042 1.1 tron XML_SkippedEntityHandler oldSkippedEntityHandler = skippedEntityHandler;
1043 1.1 tron XML_UnknownEncodingHandler oldUnknownEncodingHandler
1044 1.1 tron = unknownEncodingHandler;
1045 1.1 tron XML_ElementDeclHandler oldElementDeclHandler = elementDeclHandler;
1046 1.1 tron XML_AttlistDeclHandler oldAttlistDeclHandler = attlistDeclHandler;
1047 1.1 tron XML_EntityDeclHandler oldEntityDeclHandler = entityDeclHandler;
1048 1.1 tron XML_XmlDeclHandler oldXmlDeclHandler = xmlDeclHandler;
1049 1.1 tron ELEMENT_TYPE * oldDeclElementType = declElementType;
1050 1.1 tron
1051 1.1 tron void *oldUserData = userData;
1052 1.1 tron void *oldHandlerArg = handlerArg;
1053 1.1 tron XML_Bool oldDefaultExpandInternalEntities = defaultExpandInternalEntities;
1054 1.1 tron XML_Parser oldExternalEntityRefHandlerArg = externalEntityRefHandlerArg;
1055 1.1 tron #ifdef XML_DTD
1056 1.1 tron enum XML_ParamEntityParsing oldParamEntityParsing = paramEntityParsing;
1057 1.1 tron int oldInEntityValue = prologState.inEntityValue;
1058 1.1 tron #endif
1059 1.1 tron XML_Bool oldns_triplets = ns_triplets;
1060 1.3 spz /* Note that the new parser shares the same hash secret as the old
1061 1.3 spz parser, so that dtdCopy and copyEntityTable can lookup values
1062 1.3 spz from hash tables associated with either parser without us having
1063 1.3 spz to worry which hash secrets each table has.
1064 1.3 spz */
1065 1.3 spz unsigned long oldhash_secret_salt = hash_secret_salt;
1066 1.1 tron
1067 1.1 tron #ifdef XML_DTD
1068 1.1 tron if (!context)
1069 1.1 tron newDtd = oldDtd;
1070 1.1 tron #endif /* XML_DTD */
1071 1.1 tron
1072 1.1 tron /* Note that the magical uses of the pre-processor to make field
1073 1.1 tron access look more like C++ require that `parser' be overwritten
1074 1.1 tron here. This makes this function more painful to follow than it
1075 1.1 tron would be otherwise.
1076 1.1 tron */
1077 1.1 tron if (ns) {
1078 1.1 tron XML_Char tmp[2];
1079 1.1 tron *tmp = namespaceSeparator;
1080 1.1 tron parser = parserCreate(encodingName, &parser->m_mem, tmp, newDtd);
1081 1.1 tron }
1082 1.1 tron else {
1083 1.1 tron parser = parserCreate(encodingName, &parser->m_mem, NULL, newDtd);
1084 1.1 tron }
1085 1.1 tron
1086 1.1 tron if (!parser)
1087 1.1 tron return NULL;
1088 1.1 tron
1089 1.1 tron startElementHandler = oldStartElementHandler;
1090 1.1 tron endElementHandler = oldEndElementHandler;
1091 1.1 tron characterDataHandler = oldCharacterDataHandler;
1092 1.1 tron processingInstructionHandler = oldProcessingInstructionHandler;
1093 1.1 tron commentHandler = oldCommentHandler;
1094 1.1 tron startCdataSectionHandler = oldStartCdataSectionHandler;
1095 1.1 tron endCdataSectionHandler = oldEndCdataSectionHandler;
1096 1.1 tron defaultHandler = oldDefaultHandler;
1097 1.1 tron unparsedEntityDeclHandler = oldUnparsedEntityDeclHandler;
1098 1.1 tron notationDeclHandler = oldNotationDeclHandler;
1099 1.1 tron startNamespaceDeclHandler = oldStartNamespaceDeclHandler;
1100 1.1 tron endNamespaceDeclHandler = oldEndNamespaceDeclHandler;
1101 1.1 tron notStandaloneHandler = oldNotStandaloneHandler;
1102 1.1 tron externalEntityRefHandler = oldExternalEntityRefHandler;
1103 1.1 tron skippedEntityHandler = oldSkippedEntityHandler;
1104 1.1 tron unknownEncodingHandler = oldUnknownEncodingHandler;
1105 1.1 tron elementDeclHandler = oldElementDeclHandler;
1106 1.1 tron attlistDeclHandler = oldAttlistDeclHandler;
1107 1.1 tron entityDeclHandler = oldEntityDeclHandler;
1108 1.1 tron xmlDeclHandler = oldXmlDeclHandler;
1109 1.1 tron declElementType = oldDeclElementType;
1110 1.1 tron userData = oldUserData;
1111 1.1 tron if (oldUserData == oldHandlerArg)
1112 1.1 tron handlerArg = userData;
1113 1.1 tron else
1114 1.1 tron handlerArg = parser;
1115 1.1 tron if (oldExternalEntityRefHandlerArg != oldParser)
1116 1.1 tron externalEntityRefHandlerArg = oldExternalEntityRefHandlerArg;
1117 1.1 tron defaultExpandInternalEntities = oldDefaultExpandInternalEntities;
1118 1.1 tron ns_triplets = oldns_triplets;
1119 1.3 spz hash_secret_salt = oldhash_secret_salt;
1120 1.1 tron parentParser = oldParser;
1121 1.1 tron #ifdef XML_DTD
1122 1.1 tron paramEntityParsing = oldParamEntityParsing;
1123 1.1 tron prologState.inEntityValue = oldInEntityValue;
1124 1.1 tron if (context) {
1125 1.1 tron #endif /* XML_DTD */
1126 1.3 spz if (!dtdCopy(oldParser, _dtd, oldDtd, &parser->m_mem)
1127 1.1 tron || !setContext(parser, context)) {
1128 1.1 tron XML_ParserFree(parser);
1129 1.1 tron return NULL;
1130 1.1 tron }
1131 1.1 tron processor = externalEntityInitProcessor;
1132 1.1 tron #ifdef XML_DTD
1133 1.1 tron }
1134 1.1 tron else {
1135 1.1 tron /* The DTD instance referenced by _dtd is shared between the document's
1136 1.1 tron root parser and external PE parsers, therefore one does not need to
1137 1.1 tron call setContext. In addition, one also *must* not call setContext,
1138 1.1 tron because this would overwrite existing prefix->binding pointers in
1139 1.1 tron _dtd with ones that get destroyed with the external PE parser.
1140 1.1 tron This would leave those prefixes with dangling pointers.
1141 1.1 tron */
1142 1.1 tron isParamEntity = XML_TRUE;
1143 1.1 tron XmlPrologStateInitExternalEntity(&prologState);
1144 1.1 tron processor = externalParEntInitProcessor;
1145 1.1 tron }
1146 1.1 tron #endif /* XML_DTD */
1147 1.1 tron return parser;
1148 1.1 tron }
1149 1.1 tron
1150 1.1 tron static void FASTCALL
1151 1.1 tron destroyBindings(BINDING *bindings, XML_Parser parser)
1152 1.1 tron {
1153 1.1 tron for (;;) {
1154 1.1 tron BINDING *b = bindings;
1155 1.1 tron if (!b)
1156 1.1 tron break;
1157 1.1 tron bindings = b->nextTagBinding;
1158 1.1 tron FREE(b->uri);
1159 1.1 tron FREE(b);
1160 1.1 tron }
1161 1.1 tron }
1162 1.1 tron
1163 1.1 tron void XMLCALL
1164 1.1 tron XML_ParserFree(XML_Parser parser)
1165 1.1 tron {
1166 1.1 tron TAG *tagList;
1167 1.1 tron OPEN_INTERNAL_ENTITY *entityList;
1168 1.1 tron if (parser == NULL)
1169 1.1 tron return;
1170 1.1 tron /* free tagStack and freeTagList */
1171 1.1 tron tagList = tagStack;
1172 1.1 tron for (;;) {
1173 1.1 tron TAG *p;
1174 1.1 tron if (tagList == NULL) {
1175 1.1 tron if (freeTagList == NULL)
1176 1.1 tron break;
1177 1.1 tron tagList = freeTagList;
1178 1.1 tron freeTagList = NULL;
1179 1.1 tron }
1180 1.1 tron p = tagList;
1181 1.1 tron tagList = tagList->parent;
1182 1.1 tron FREE(p->buf);
1183 1.1 tron destroyBindings(p->bindings, parser);
1184 1.1 tron FREE(p);
1185 1.1 tron }
1186 1.1 tron /* free openInternalEntities and freeInternalEntities */
1187 1.1 tron entityList = openInternalEntities;
1188 1.1 tron for (;;) {
1189 1.1 tron OPEN_INTERNAL_ENTITY *openEntity;
1190 1.1 tron if (entityList == NULL) {
1191 1.1 tron if (freeInternalEntities == NULL)
1192 1.1 tron break;
1193 1.1 tron entityList = freeInternalEntities;
1194 1.1 tron freeInternalEntities = NULL;
1195 1.1 tron }
1196 1.1 tron openEntity = entityList;
1197 1.1 tron entityList = entityList->next;
1198 1.1 tron FREE(openEntity);
1199 1.1 tron }
1200 1.1 tron
1201 1.1 tron destroyBindings(freeBindingList, parser);
1202 1.1 tron destroyBindings(inheritedBindings, parser);
1203 1.1 tron poolDestroy(&tempPool);
1204 1.1 tron poolDestroy(&temp2Pool);
1205 1.1 tron #ifdef XML_DTD
1206 1.1 tron /* external parameter entity parsers share the DTD structure
1207 1.1 tron parser->m_dtd with the root parser, so we must not destroy it
1208 1.1 tron */
1209 1.1 tron if (!isParamEntity && _dtd)
1210 1.1 tron #else
1211 1.1 tron if (_dtd)
1212 1.1 tron #endif /* XML_DTD */
1213 1.1 tron dtdDestroy(_dtd, (XML_Bool)!parentParser, &parser->m_mem);
1214 1.1 tron FREE((void *)atts);
1215 1.3 spz #ifdef XML_ATTR_INFO
1216 1.3 spz FREE((void *)attInfo);
1217 1.3 spz #endif
1218 1.1 tron FREE(groupConnector);
1219 1.1 tron FREE(buffer);
1220 1.1 tron FREE(dataBuf);
1221 1.1 tron FREE(nsAtts);
1222 1.1 tron FREE(unknownEncodingMem);
1223 1.1 tron if (unknownEncodingRelease)
1224 1.1 tron unknownEncodingRelease(unknownEncodingData);
1225 1.1 tron FREE(parser);
1226 1.1 tron }
1227 1.1 tron
1228 1.1 tron void XMLCALL
1229 1.1 tron XML_UseParserAsHandlerArg(XML_Parser parser)
1230 1.1 tron {
1231 1.1 tron handlerArg = parser;
1232 1.1 tron }
1233 1.1 tron
1234 1.1 tron enum XML_Error XMLCALL
1235 1.1 tron XML_UseForeignDTD(XML_Parser parser, XML_Bool useDTD)
1236 1.1 tron {
1237 1.1 tron #ifdef XML_DTD
1238 1.1 tron /* block after XML_Parse()/XML_ParseBuffer() has been called */
1239 1.1 tron if (ps_parsing == XML_PARSING || ps_parsing == XML_SUSPENDED)
1240 1.1 tron return XML_ERROR_CANT_CHANGE_FEATURE_ONCE_PARSING;
1241 1.1 tron useForeignDTD = useDTD;
1242 1.1 tron return XML_ERROR_NONE;
1243 1.1 tron #else
1244 1.1 tron return XML_ERROR_FEATURE_REQUIRES_XML_DTD;
1245 1.1 tron #endif
1246 1.1 tron }
1247 1.1 tron
1248 1.1 tron void XMLCALL
1249 1.1 tron XML_SetReturnNSTriplet(XML_Parser parser, int do_nst)
1250 1.1 tron {
1251 1.1 tron /* block after XML_Parse()/XML_ParseBuffer() has been called */
1252 1.1 tron if (ps_parsing == XML_PARSING || ps_parsing == XML_SUSPENDED)
1253 1.1 tron return;
1254 1.1 tron ns_triplets = do_nst ? XML_TRUE : XML_FALSE;
1255 1.1 tron }
1256 1.1 tron
1257 1.1 tron void XMLCALL
1258 1.1 tron XML_SetUserData(XML_Parser parser, void *p)
1259 1.1 tron {
1260 1.1 tron if (handlerArg == userData)
1261 1.1 tron handlerArg = userData = p;
1262 1.1 tron else
1263 1.1 tron userData = p;
1264 1.1 tron }
1265 1.1 tron
1266 1.1 tron enum XML_Status XMLCALL
1267 1.1 tron XML_SetBase(XML_Parser parser, const XML_Char *p)
1268 1.1 tron {
1269 1.1 tron if (p) {
1270 1.1 tron p = poolCopyString(&_dtd->pool, p);
1271 1.1 tron if (!p)
1272 1.1 tron return XML_STATUS_ERROR;
1273 1.1 tron curBase = p;
1274 1.1 tron }
1275 1.1 tron else
1276 1.1 tron curBase = NULL;
1277 1.1 tron return XML_STATUS_OK;
1278 1.1 tron }
1279 1.1 tron
1280 1.1 tron const XML_Char * XMLCALL
1281 1.1 tron XML_GetBase(XML_Parser parser)
1282 1.1 tron {
1283 1.1 tron return curBase;
1284 1.1 tron }
1285 1.1 tron
1286 1.1 tron int XMLCALL
1287 1.1 tron XML_GetSpecifiedAttributeCount(XML_Parser parser)
1288 1.1 tron {
1289 1.1 tron return nSpecifiedAtts;
1290 1.1 tron }
1291 1.1 tron
1292 1.1 tron int XMLCALL
1293 1.1 tron XML_GetIdAttributeIndex(XML_Parser parser)
1294 1.1 tron {
1295 1.1 tron return idAttIndex;
1296 1.1 tron }
1297 1.1 tron
1298 1.3 spz #ifdef XML_ATTR_INFO
1299 1.3 spz const XML_AttrInfo * XMLCALL
1300 1.3 spz XML_GetAttributeInfo(XML_Parser parser)
1301 1.3 spz {
1302 1.3 spz return attInfo;
1303 1.3 spz }
1304 1.3 spz #endif
1305 1.3 spz
1306 1.1 tron void XMLCALL
1307 1.1 tron XML_SetElementHandler(XML_Parser parser,
1308 1.1 tron XML_StartElementHandler start,
1309 1.1 tron XML_EndElementHandler end)
1310 1.1 tron {
1311 1.1 tron startElementHandler = start;
1312 1.1 tron endElementHandler = end;
1313 1.1 tron }
1314 1.1 tron
1315 1.1 tron void XMLCALL
1316 1.1 tron XML_SetStartElementHandler(XML_Parser parser,
1317 1.1 tron XML_StartElementHandler start) {
1318 1.1 tron startElementHandler = start;
1319 1.1 tron }
1320 1.1 tron
1321 1.1 tron void XMLCALL
1322 1.1 tron XML_SetEndElementHandler(XML_Parser parser,
1323 1.1 tron XML_EndElementHandler end) {
1324 1.1 tron endElementHandler = end;
1325 1.1 tron }
1326 1.1 tron
1327 1.1 tron void XMLCALL
1328 1.1 tron XML_SetCharacterDataHandler(XML_Parser parser,
1329 1.1 tron XML_CharacterDataHandler handler)
1330 1.1 tron {
1331 1.1 tron characterDataHandler = handler;
1332 1.1 tron }
1333 1.1 tron
1334 1.1 tron void XMLCALL
1335 1.1 tron XML_SetProcessingInstructionHandler(XML_Parser parser,
1336 1.1 tron XML_ProcessingInstructionHandler handler)
1337 1.1 tron {
1338 1.1 tron processingInstructionHandler = handler;
1339 1.1 tron }
1340 1.1 tron
1341 1.1 tron void XMLCALL
1342 1.1 tron XML_SetCommentHandler(XML_Parser parser,
1343 1.1 tron XML_CommentHandler handler)
1344 1.1 tron {
1345 1.1 tron commentHandler = handler;
1346 1.1 tron }
1347 1.1 tron
1348 1.1 tron void XMLCALL
1349 1.1 tron XML_SetCdataSectionHandler(XML_Parser parser,
1350 1.1 tron XML_StartCdataSectionHandler start,
1351 1.1 tron XML_EndCdataSectionHandler end)
1352 1.1 tron {
1353 1.1 tron startCdataSectionHandler = start;
1354 1.1 tron endCdataSectionHandler = end;
1355 1.1 tron }
1356 1.1 tron
1357 1.1 tron void XMLCALL
1358 1.1 tron XML_SetStartCdataSectionHandler(XML_Parser parser,
1359 1.1 tron XML_StartCdataSectionHandler start) {
1360 1.1 tron startCdataSectionHandler = start;
1361 1.1 tron }
1362 1.1 tron
1363 1.1 tron void XMLCALL
1364 1.1 tron XML_SetEndCdataSectionHandler(XML_Parser parser,
1365 1.1 tron XML_EndCdataSectionHandler end) {
1366 1.1 tron endCdataSectionHandler = end;
1367 1.1 tron }
1368 1.1 tron
1369 1.1 tron void XMLCALL
1370 1.1 tron XML_SetDefaultHandler(XML_Parser parser,
1371 1.1 tron XML_DefaultHandler handler)
1372 1.1 tron {
1373 1.1 tron defaultHandler = handler;
1374 1.1 tron defaultExpandInternalEntities = XML_FALSE;
1375 1.1 tron }
1376 1.1 tron
1377 1.1 tron void XMLCALL
1378 1.1 tron XML_SetDefaultHandlerExpand(XML_Parser parser,
1379 1.1 tron XML_DefaultHandler handler)
1380 1.1 tron {
1381 1.1 tron defaultHandler = handler;
1382 1.1 tron defaultExpandInternalEntities = XML_TRUE;
1383 1.1 tron }
1384 1.1 tron
1385 1.1 tron void XMLCALL
1386 1.1 tron XML_SetDoctypeDeclHandler(XML_Parser parser,
1387 1.1 tron XML_StartDoctypeDeclHandler start,
1388 1.1 tron XML_EndDoctypeDeclHandler end)
1389 1.1 tron {
1390 1.1 tron startDoctypeDeclHandler = start;
1391 1.1 tron endDoctypeDeclHandler = end;
1392 1.1 tron }
1393 1.1 tron
1394 1.1 tron void XMLCALL
1395 1.1 tron XML_SetStartDoctypeDeclHandler(XML_Parser parser,
1396 1.1 tron XML_StartDoctypeDeclHandler start) {
1397 1.1 tron startDoctypeDeclHandler = start;
1398 1.1 tron }
1399 1.1 tron
1400 1.1 tron void XMLCALL
1401 1.1 tron XML_SetEndDoctypeDeclHandler(XML_Parser parser,
1402 1.1 tron XML_EndDoctypeDeclHandler end) {
1403 1.1 tron endDoctypeDeclHandler = end;
1404 1.1 tron }
1405 1.1 tron
1406 1.1 tron void XMLCALL
1407 1.1 tron XML_SetUnparsedEntityDeclHandler(XML_Parser parser,
1408 1.1 tron XML_UnparsedEntityDeclHandler handler)
1409 1.1 tron {
1410 1.1 tron unparsedEntityDeclHandler = handler;
1411 1.1 tron }
1412 1.1 tron
1413 1.1 tron void XMLCALL
1414 1.1 tron XML_SetNotationDeclHandler(XML_Parser parser,
1415 1.1 tron XML_NotationDeclHandler handler)
1416 1.1 tron {
1417 1.1 tron notationDeclHandler = handler;
1418 1.1 tron }
1419 1.1 tron
1420 1.1 tron void XMLCALL
1421 1.1 tron XML_SetNamespaceDeclHandler(XML_Parser parser,
1422 1.1 tron XML_StartNamespaceDeclHandler start,
1423 1.1 tron XML_EndNamespaceDeclHandler end)
1424 1.1 tron {
1425 1.1 tron startNamespaceDeclHandler = start;
1426 1.1 tron endNamespaceDeclHandler = end;
1427 1.1 tron }
1428 1.1 tron
1429 1.1 tron void XMLCALL
1430 1.1 tron XML_SetStartNamespaceDeclHandler(XML_Parser parser,
1431 1.1 tron XML_StartNamespaceDeclHandler start) {
1432 1.1 tron startNamespaceDeclHandler = start;
1433 1.1 tron }
1434 1.1 tron
1435 1.1 tron void XMLCALL
1436 1.1 tron XML_SetEndNamespaceDeclHandler(XML_Parser parser,
1437 1.1 tron XML_EndNamespaceDeclHandler end) {
1438 1.1 tron endNamespaceDeclHandler = end;
1439 1.1 tron }
1440 1.1 tron
1441 1.1 tron void XMLCALL
1442 1.1 tron XML_SetNotStandaloneHandler(XML_Parser parser,
1443 1.1 tron XML_NotStandaloneHandler handler)
1444 1.1 tron {
1445 1.1 tron notStandaloneHandler = handler;
1446 1.1 tron }
1447 1.1 tron
1448 1.1 tron void XMLCALL
1449 1.1 tron XML_SetExternalEntityRefHandler(XML_Parser parser,
1450 1.1 tron XML_ExternalEntityRefHandler handler)
1451 1.1 tron {
1452 1.1 tron externalEntityRefHandler = handler;
1453 1.1 tron }
1454 1.1 tron
1455 1.1 tron void XMLCALL
1456 1.1 tron XML_SetExternalEntityRefHandlerArg(XML_Parser parser, void *arg)
1457 1.1 tron {
1458 1.1 tron if (arg)
1459 1.1 tron externalEntityRefHandlerArg = (XML_Parser)arg;
1460 1.1 tron else
1461 1.1 tron externalEntityRefHandlerArg = parser;
1462 1.1 tron }
1463 1.1 tron
1464 1.1 tron void XMLCALL
1465 1.1 tron XML_SetSkippedEntityHandler(XML_Parser parser,
1466 1.1 tron XML_SkippedEntityHandler handler)
1467 1.1 tron {
1468 1.1 tron skippedEntityHandler = handler;
1469 1.1 tron }
1470 1.1 tron
1471 1.1 tron void XMLCALL
1472 1.1 tron XML_SetUnknownEncodingHandler(XML_Parser parser,
1473 1.1 tron XML_UnknownEncodingHandler handler,
1474 1.1 tron void *data)
1475 1.1 tron {
1476 1.1 tron unknownEncodingHandler = handler;
1477 1.1 tron unknownEncodingHandlerData = data;
1478 1.1 tron }
1479 1.1 tron
1480 1.1 tron void XMLCALL
1481 1.1 tron XML_SetElementDeclHandler(XML_Parser parser,
1482 1.1 tron XML_ElementDeclHandler eldecl)
1483 1.1 tron {
1484 1.1 tron elementDeclHandler = eldecl;
1485 1.1 tron }
1486 1.1 tron
1487 1.1 tron void XMLCALL
1488 1.1 tron XML_SetAttlistDeclHandler(XML_Parser parser,
1489 1.1 tron XML_AttlistDeclHandler attdecl)
1490 1.1 tron {
1491 1.1 tron attlistDeclHandler = attdecl;
1492 1.1 tron }
1493 1.1 tron
1494 1.1 tron void XMLCALL
1495 1.1 tron XML_SetEntityDeclHandler(XML_Parser parser,
1496 1.1 tron XML_EntityDeclHandler handler)
1497 1.1 tron {
1498 1.1 tron entityDeclHandler = handler;
1499 1.1 tron }
1500 1.1 tron
1501 1.1 tron void XMLCALL
1502 1.1 tron XML_SetXmlDeclHandler(XML_Parser parser,
1503 1.1 tron XML_XmlDeclHandler handler) {
1504 1.1 tron xmlDeclHandler = handler;
1505 1.1 tron }
1506 1.1 tron
1507 1.1 tron int XMLCALL
1508 1.1 tron XML_SetParamEntityParsing(XML_Parser parser,
1509 1.1 tron enum XML_ParamEntityParsing peParsing)
1510 1.1 tron {
1511 1.1 tron /* block after XML_Parse()/XML_ParseBuffer() has been called */
1512 1.1 tron if (ps_parsing == XML_PARSING || ps_parsing == XML_SUSPENDED)
1513 1.1 tron return 0;
1514 1.1 tron #ifdef XML_DTD
1515 1.1 tron paramEntityParsing = peParsing;
1516 1.1 tron return 1;
1517 1.1 tron #else
1518 1.1 tron return peParsing == XML_PARAM_ENTITY_PARSING_NEVER;
1519 1.1 tron #endif
1520 1.1 tron }
1521 1.1 tron
1522 1.3 spz int XMLCALL
1523 1.3 spz XML_SetHashSalt(XML_Parser parser,
1524 1.3 spz unsigned long hash_salt)
1525 1.3 spz {
1526 1.3 spz /* block after XML_Parse()/XML_ParseBuffer() has been called */
1527 1.3 spz if (ps_parsing == XML_PARSING || ps_parsing == XML_SUSPENDED)
1528 1.3 spz return 0;
1529 1.3 spz hash_secret_salt = hash_salt;
1530 1.3 spz return 1;
1531 1.3 spz }
1532 1.3 spz
1533 1.1 tron enum XML_Status XMLCALL
1534 1.1 tron XML_Parse(XML_Parser parser, const char *s, int len, int isFinal)
1535 1.1 tron {
1536 1.1 tron switch (ps_parsing) {
1537 1.1 tron case XML_SUSPENDED:
1538 1.1 tron errorCode = XML_ERROR_SUSPENDED;
1539 1.1 tron return XML_STATUS_ERROR;
1540 1.1 tron case XML_FINISHED:
1541 1.1 tron errorCode = XML_ERROR_FINISHED;
1542 1.1 tron return XML_STATUS_ERROR;
1543 1.3 spz case XML_INITIALIZED:
1544 1.3 spz if (parentParser == NULL && !startParsing(parser)) {
1545 1.3 spz errorCode = XML_ERROR_NO_MEMORY;
1546 1.3 spz return XML_STATUS_ERROR;
1547 1.3 spz }
1548 1.1 tron default:
1549 1.1 tron ps_parsing = XML_PARSING;
1550 1.1 tron }
1551 1.1 tron
1552 1.1 tron if (len == 0) {
1553 1.1 tron ps_finalBuffer = (XML_Bool)isFinal;
1554 1.1 tron if (!isFinal)
1555 1.1 tron return XML_STATUS_OK;
1556 1.1 tron positionPtr = bufferPtr;
1557 1.1 tron parseEndPtr = bufferEnd;
1558 1.1 tron
1559 1.1 tron /* If data are left over from last buffer, and we now know that these
1560 1.1 tron data are the final chunk of input, then we have to check them again
1561 1.1 tron to detect errors based on that fact.
1562 1.1 tron */
1563 1.1 tron errorCode = processor(parser, bufferPtr, parseEndPtr, &bufferPtr);
1564 1.1 tron
1565 1.1 tron if (errorCode == XML_ERROR_NONE) {
1566 1.1 tron switch (ps_parsing) {
1567 1.1 tron case XML_SUSPENDED:
1568 1.1 tron XmlUpdatePosition(encoding, positionPtr, bufferPtr, &position);
1569 1.1 tron positionPtr = bufferPtr;
1570 1.1 tron return XML_STATUS_SUSPENDED;
1571 1.3 spz case XML_INITIALIZED:
1572 1.1 tron case XML_PARSING:
1573 1.1 tron ps_parsing = XML_FINISHED;
1574 1.1 tron /* fall through */
1575 1.1 tron default:
1576 1.1 tron return XML_STATUS_OK;
1577 1.1 tron }
1578 1.1 tron }
1579 1.1 tron eventEndPtr = eventPtr;
1580 1.1 tron processor = errorProcessor;
1581 1.1 tron return XML_STATUS_ERROR;
1582 1.1 tron }
1583 1.1 tron #ifndef XML_CONTEXT_BYTES
1584 1.1 tron else if (bufferPtr == bufferEnd) {
1585 1.1 tron const char *end;
1586 1.1 tron int nLeftOver;
1587 1.4 spz enum XML_Status result;
1588 1.1 tron parseEndByteIndex += len;
1589 1.1 tron positionPtr = s;
1590 1.1 tron ps_finalBuffer = (XML_Bool)isFinal;
1591 1.1 tron
1592 1.1 tron errorCode = processor(parser, s, parseEndPtr = s + len, &end);
1593 1.1 tron
1594 1.1 tron if (errorCode != XML_ERROR_NONE) {
1595 1.1 tron eventEndPtr = eventPtr;
1596 1.1 tron processor = errorProcessor;
1597 1.1 tron return XML_STATUS_ERROR;
1598 1.1 tron }
1599 1.1 tron else {
1600 1.1 tron switch (ps_parsing) {
1601 1.1 tron case XML_SUSPENDED:
1602 1.1 tron result = XML_STATUS_SUSPENDED;
1603 1.1 tron break;
1604 1.1 tron case XML_INITIALIZED:
1605 1.1 tron case XML_PARSING:
1606 1.1 tron if (isFinal) {
1607 1.1 tron ps_parsing = XML_FINISHED;
1608 1.3 spz return XML_STATUS_OK;
1609 1.1 tron }
1610 1.3 spz /* fall through */
1611 1.3 spz default:
1612 1.3 spz result = XML_STATUS_OK;
1613 1.1 tron }
1614 1.1 tron }
1615 1.1 tron
1616 1.1 tron XmlUpdatePosition(encoding, positionPtr, end, &position);
1617 1.1 tron nLeftOver = s + len - end;
1618 1.1 tron if (nLeftOver) {
1619 1.1 tron if (buffer == NULL || nLeftOver > bufferLim - buffer) {
1620 1.1 tron /* FIXME avoid integer overflow */
1621 1.1 tron char *temp;
1622 1.1 tron temp = (buffer == NULL
1623 1.1 tron ? (char *)MALLOC(len * 2)
1624 1.1 tron : (char *)REALLOC(buffer, len * 2));
1625 1.1 tron if (temp == NULL) {
1626 1.1 tron errorCode = XML_ERROR_NO_MEMORY;
1627 1.1 tron eventPtr = eventEndPtr = NULL;
1628 1.1 tron processor = errorProcessor;
1629 1.1 tron return XML_STATUS_ERROR;
1630 1.1 tron }
1631 1.3 spz buffer = temp;
1632 1.1 tron bufferLim = buffer + len * 2;
1633 1.1 tron }
1634 1.1 tron memcpy(buffer, end, nLeftOver);
1635 1.1 tron }
1636 1.1 tron bufferPtr = buffer;
1637 1.1 tron bufferEnd = buffer + nLeftOver;
1638 1.1 tron positionPtr = bufferPtr;
1639 1.1 tron parseEndPtr = bufferEnd;
1640 1.1 tron eventPtr = bufferPtr;
1641 1.1 tron eventEndPtr = bufferPtr;
1642 1.1 tron return result;
1643 1.1 tron }
1644 1.1 tron #endif /* not defined XML_CONTEXT_BYTES */
1645 1.1 tron else {
1646 1.1 tron void *buff = XML_GetBuffer(parser, len);
1647 1.1 tron if (buff == NULL)
1648 1.1 tron return XML_STATUS_ERROR;
1649 1.1 tron else {
1650 1.1 tron memcpy(buff, s, len);
1651 1.1 tron return XML_ParseBuffer(parser, len, isFinal);
1652 1.1 tron }
1653 1.1 tron }
1654 1.1 tron }
1655 1.1 tron
1656 1.1 tron enum XML_Status XMLCALL
1657 1.1 tron XML_ParseBuffer(XML_Parser parser, int len, int isFinal)
1658 1.1 tron {
1659 1.1 tron const char *start;
1660 1.1 tron enum XML_Status result = XML_STATUS_OK;
1661 1.1 tron
1662 1.1 tron switch (ps_parsing) {
1663 1.1 tron case XML_SUSPENDED:
1664 1.1 tron errorCode = XML_ERROR_SUSPENDED;
1665 1.1 tron return XML_STATUS_ERROR;
1666 1.1 tron case XML_FINISHED:
1667 1.1 tron errorCode = XML_ERROR_FINISHED;
1668 1.1 tron return XML_STATUS_ERROR;
1669 1.3 spz case XML_INITIALIZED:
1670 1.3 spz if (parentParser == NULL && !startParsing(parser)) {
1671 1.3 spz errorCode = XML_ERROR_NO_MEMORY;
1672 1.3 spz return XML_STATUS_ERROR;
1673 1.3 spz }
1674 1.1 tron default:
1675 1.1 tron ps_parsing = XML_PARSING;
1676 1.1 tron }
1677 1.1 tron
1678 1.1 tron start = bufferPtr;
1679 1.1 tron positionPtr = start;
1680 1.1 tron bufferEnd += len;
1681 1.1 tron parseEndPtr = bufferEnd;
1682 1.1 tron parseEndByteIndex += len;
1683 1.1 tron ps_finalBuffer = (XML_Bool)isFinal;
1684 1.1 tron
1685 1.1 tron errorCode = processor(parser, start, parseEndPtr, &bufferPtr);
1686 1.1 tron
1687 1.1 tron if (errorCode != XML_ERROR_NONE) {
1688 1.1 tron eventEndPtr = eventPtr;
1689 1.1 tron processor = errorProcessor;
1690 1.1 tron return XML_STATUS_ERROR;
1691 1.1 tron }
1692 1.1 tron else {
1693 1.1 tron switch (ps_parsing) {
1694 1.1 tron case XML_SUSPENDED:
1695 1.1 tron result = XML_STATUS_SUSPENDED;
1696 1.1 tron break;
1697 1.3 spz case XML_INITIALIZED:
1698 1.1 tron case XML_PARSING:
1699 1.1 tron if (isFinal) {
1700 1.1 tron ps_parsing = XML_FINISHED;
1701 1.1 tron return result;
1702 1.1 tron }
1703 1.1 tron default: ; /* should not happen */
1704 1.1 tron }
1705 1.1 tron }
1706 1.1 tron
1707 1.1 tron XmlUpdatePosition(encoding, positionPtr, bufferPtr, &position);
1708 1.1 tron positionPtr = bufferPtr;
1709 1.1 tron return result;
1710 1.1 tron }
1711 1.1 tron
1712 1.1 tron void * XMLCALL
1713 1.1 tron XML_GetBuffer(XML_Parser parser, int len)
1714 1.1 tron {
1715 1.4 spz if (len < 0) {
1716 1.4 spz errorCode = XML_ERROR_NO_MEMORY;
1717 1.4 spz return NULL;
1718 1.4 spz }
1719 1.1 tron switch (ps_parsing) {
1720 1.1 tron case XML_SUSPENDED:
1721 1.1 tron errorCode = XML_ERROR_SUSPENDED;
1722 1.1 tron return NULL;
1723 1.1 tron case XML_FINISHED:
1724 1.1 tron errorCode = XML_ERROR_FINISHED;
1725 1.1 tron return NULL;
1726 1.1 tron default: ;
1727 1.1 tron }
1728 1.1 tron
1729 1.1 tron if (len > bufferLim - bufferEnd) {
1730 1.6 spz #ifdef XML_CONTEXT_BYTES
1731 1.6 spz int keep;
1732 1.6 spz #endif /* defined XML_CONTEXT_BYTES */
1733 1.5 spz /* Do not invoke signed arithmetic overflow: */
1734 1.5 spz int neededSize = (int) ((unsigned)len + (unsigned)(bufferEnd - bufferPtr));
1735 1.4 spz if (neededSize < 0) {
1736 1.4 spz errorCode = XML_ERROR_NO_MEMORY;
1737 1.4 spz return NULL;
1738 1.4 spz }
1739 1.1 tron #ifdef XML_CONTEXT_BYTES
1740 1.6 spz keep = (int)(bufferPtr - buffer);
1741 1.1 tron if (keep > XML_CONTEXT_BYTES)
1742 1.1 tron keep = XML_CONTEXT_BYTES;
1743 1.1 tron neededSize += keep;
1744 1.1 tron #endif /* defined XML_CONTEXT_BYTES */
1745 1.1 tron if (neededSize <= bufferLim - buffer) {
1746 1.1 tron #ifdef XML_CONTEXT_BYTES
1747 1.1 tron if (keep < bufferPtr - buffer) {
1748 1.1 tron int offset = (int)(bufferPtr - buffer) - keep;
1749 1.1 tron memmove(buffer, &buffer[offset], bufferEnd - bufferPtr + keep);
1750 1.1 tron bufferEnd -= offset;
1751 1.1 tron bufferPtr -= offset;
1752 1.1 tron }
1753 1.1 tron #else
1754 1.1 tron memmove(buffer, bufferPtr, bufferEnd - bufferPtr);
1755 1.1 tron bufferEnd = buffer + (bufferEnd - bufferPtr);
1756 1.1 tron bufferPtr = buffer;
1757 1.1 tron #endif /* not defined XML_CONTEXT_BYTES */
1758 1.1 tron }
1759 1.1 tron else {
1760 1.1 tron char *newBuf;
1761 1.1 tron int bufferSize = (int)(bufferLim - bufferPtr);
1762 1.1 tron if (bufferSize == 0)
1763 1.1 tron bufferSize = INIT_BUFFER_SIZE;
1764 1.1 tron do {
1765 1.5 spz /* Do not invoke signed arithmetic overflow: */
1766 1.5 spz bufferSize = (int) (2U * (unsigned) bufferSize);
1767 1.4 spz } while (bufferSize < neededSize && bufferSize > 0);
1768 1.4 spz if (bufferSize <= 0) {
1769 1.4 spz errorCode = XML_ERROR_NO_MEMORY;
1770 1.4 spz return NULL;
1771 1.4 spz }
1772 1.1 tron newBuf = (char *)MALLOC(bufferSize);
1773 1.1 tron if (newBuf == 0) {
1774 1.1 tron errorCode = XML_ERROR_NO_MEMORY;
1775 1.1 tron return NULL;
1776 1.1 tron }
1777 1.1 tron bufferLim = newBuf + bufferSize;
1778 1.1 tron #ifdef XML_CONTEXT_BYTES
1779 1.1 tron if (bufferPtr) {
1780 1.1 tron int keep = (int)(bufferPtr - buffer);
1781 1.1 tron if (keep > XML_CONTEXT_BYTES)
1782 1.1 tron keep = XML_CONTEXT_BYTES;
1783 1.1 tron memcpy(newBuf, &bufferPtr[-keep], bufferEnd - bufferPtr + keep);
1784 1.1 tron FREE(buffer);
1785 1.1 tron buffer = newBuf;
1786 1.1 tron bufferEnd = buffer + (bufferEnd - bufferPtr) + keep;
1787 1.1 tron bufferPtr = buffer + keep;
1788 1.1 tron }
1789 1.1 tron else {
1790 1.1 tron bufferEnd = newBuf + (bufferEnd - bufferPtr);
1791 1.1 tron bufferPtr = buffer = newBuf;
1792 1.1 tron }
1793 1.1 tron #else
1794 1.1 tron if (bufferPtr) {
1795 1.1 tron memcpy(newBuf, bufferPtr, bufferEnd - bufferPtr);
1796 1.1 tron FREE(buffer);
1797 1.1 tron }
1798 1.1 tron bufferEnd = newBuf + (bufferEnd - bufferPtr);
1799 1.1 tron bufferPtr = buffer = newBuf;
1800 1.1 tron #endif /* not defined XML_CONTEXT_BYTES */
1801 1.1 tron }
1802 1.3 spz eventPtr = eventEndPtr = NULL;
1803 1.3 spz positionPtr = NULL;
1804 1.1 tron }
1805 1.1 tron return bufferEnd;
1806 1.1 tron }
1807 1.1 tron
1808 1.1 tron enum XML_Status XMLCALL
1809 1.1 tron XML_StopParser(XML_Parser parser, XML_Bool resumable)
1810 1.1 tron {
1811 1.1 tron switch (ps_parsing) {
1812 1.1 tron case XML_SUSPENDED:
1813 1.1 tron if (resumable) {
1814 1.1 tron errorCode = XML_ERROR_SUSPENDED;
1815 1.1 tron return XML_STATUS_ERROR;
1816 1.1 tron }
1817 1.1 tron ps_parsing = XML_FINISHED;
1818 1.1 tron break;
1819 1.1 tron case XML_FINISHED:
1820 1.1 tron errorCode = XML_ERROR_FINISHED;
1821 1.1 tron return XML_STATUS_ERROR;
1822 1.1 tron default:
1823 1.1 tron if (resumable) {
1824 1.1 tron #ifdef XML_DTD
1825 1.1 tron if (isParamEntity) {
1826 1.1 tron errorCode = XML_ERROR_SUSPEND_PE;
1827 1.1 tron return XML_STATUS_ERROR;
1828 1.1 tron }
1829 1.1 tron #endif
1830 1.1 tron ps_parsing = XML_SUSPENDED;
1831 1.1 tron }
1832 1.1 tron else
1833 1.1 tron ps_parsing = XML_FINISHED;
1834 1.1 tron }
1835 1.1 tron return XML_STATUS_OK;
1836 1.1 tron }
1837 1.1 tron
1838 1.1 tron enum XML_Status XMLCALL
1839 1.1 tron XML_ResumeParser(XML_Parser parser)
1840 1.1 tron {
1841 1.1 tron enum XML_Status result = XML_STATUS_OK;
1842 1.1 tron
1843 1.1 tron if (ps_parsing != XML_SUSPENDED) {
1844 1.1 tron errorCode = XML_ERROR_NOT_SUSPENDED;
1845 1.1 tron return XML_STATUS_ERROR;
1846 1.1 tron }
1847 1.1 tron ps_parsing = XML_PARSING;
1848 1.1 tron
1849 1.1 tron errorCode = processor(parser, bufferPtr, parseEndPtr, &bufferPtr);
1850 1.1 tron
1851 1.1 tron if (errorCode != XML_ERROR_NONE) {
1852 1.1 tron eventEndPtr = eventPtr;
1853 1.1 tron processor = errorProcessor;
1854 1.1 tron return XML_STATUS_ERROR;
1855 1.1 tron }
1856 1.1 tron else {
1857 1.1 tron switch (ps_parsing) {
1858 1.1 tron case XML_SUSPENDED:
1859 1.1 tron result = XML_STATUS_SUSPENDED;
1860 1.1 tron break;
1861 1.3 spz case XML_INITIALIZED:
1862 1.1 tron case XML_PARSING:
1863 1.1 tron if (ps_finalBuffer) {
1864 1.1 tron ps_parsing = XML_FINISHED;
1865 1.1 tron return result;
1866 1.1 tron }
1867 1.1 tron default: ;
1868 1.1 tron }
1869 1.1 tron }
1870 1.1 tron
1871 1.1 tron XmlUpdatePosition(encoding, positionPtr, bufferPtr, &position);
1872 1.1 tron positionPtr = bufferPtr;
1873 1.1 tron return result;
1874 1.1 tron }
1875 1.1 tron
1876 1.1 tron void XMLCALL
1877 1.1 tron XML_GetParsingStatus(XML_Parser parser, XML_ParsingStatus *status)
1878 1.1 tron {
1879 1.1 tron assert(status != NULL);
1880 1.1 tron *status = parser->m_parsingStatus;
1881 1.1 tron }
1882 1.1 tron
1883 1.1 tron enum XML_Error XMLCALL
1884 1.1 tron XML_GetErrorCode(XML_Parser parser)
1885 1.1 tron {
1886 1.1 tron return errorCode;
1887 1.1 tron }
1888 1.1 tron
1889 1.1 tron XML_Index XMLCALL
1890 1.1 tron XML_GetCurrentByteIndex(XML_Parser parser)
1891 1.1 tron {
1892 1.1 tron if (eventPtr)
1893 1.6 spz return (XML_Index)(parseEndByteIndex - (parseEndPtr - eventPtr));
1894 1.1 tron return -1;
1895 1.1 tron }
1896 1.1 tron
1897 1.1 tron int XMLCALL
1898 1.1 tron XML_GetCurrentByteCount(XML_Parser parser)
1899 1.1 tron {
1900 1.1 tron if (eventEndPtr && eventPtr)
1901 1.1 tron return (int)(eventEndPtr - eventPtr);
1902 1.1 tron return 0;
1903 1.1 tron }
1904 1.1 tron
1905 1.1 tron const char * XMLCALL
1906 1.1 tron XML_GetInputContext(XML_Parser parser, int *offset, int *size)
1907 1.1 tron {
1908 1.1 tron #ifdef XML_CONTEXT_BYTES
1909 1.1 tron if (eventPtr && buffer) {
1910 1.1 tron *offset = (int)(eventPtr - buffer);
1911 1.1 tron *size = (int)(bufferEnd - buffer);
1912 1.1 tron return buffer;
1913 1.1 tron }
1914 1.1 tron #endif /* defined XML_CONTEXT_BYTES */
1915 1.1 tron return (char *) 0;
1916 1.1 tron }
1917 1.1 tron
1918 1.1 tron XML_Size XMLCALL
1919 1.1 tron XML_GetCurrentLineNumber(XML_Parser parser)
1920 1.1 tron {
1921 1.1 tron if (eventPtr && eventPtr >= positionPtr) {
1922 1.1 tron XmlUpdatePosition(encoding, positionPtr, eventPtr, &position);
1923 1.1 tron positionPtr = eventPtr;
1924 1.1 tron }
1925 1.1 tron return position.lineNumber + 1;
1926 1.1 tron }
1927 1.1 tron
1928 1.1 tron XML_Size XMLCALL
1929 1.1 tron XML_GetCurrentColumnNumber(XML_Parser parser)
1930 1.1 tron {
1931 1.1 tron if (eventPtr && eventPtr >= positionPtr) {
1932 1.1 tron XmlUpdatePosition(encoding, positionPtr, eventPtr, &position);
1933 1.1 tron positionPtr = eventPtr;
1934 1.1 tron }
1935 1.1 tron return position.columnNumber;
1936 1.1 tron }
1937 1.1 tron
1938 1.1 tron void XMLCALL
1939 1.1 tron XML_FreeContentModel(XML_Parser parser, XML_Content *model)
1940 1.1 tron {
1941 1.1 tron FREE(model);
1942 1.1 tron }
1943 1.1 tron
1944 1.1 tron void * XMLCALL
1945 1.1 tron XML_MemMalloc(XML_Parser parser, size_t size)
1946 1.1 tron {
1947 1.1 tron return MALLOC(size);
1948 1.1 tron }
1949 1.1 tron
1950 1.1 tron void * XMLCALL
1951 1.1 tron XML_MemRealloc(XML_Parser parser, void *ptr, size_t size)
1952 1.1 tron {
1953 1.1 tron return REALLOC(ptr, size);
1954 1.1 tron }
1955 1.1 tron
1956 1.1 tron void XMLCALL
1957 1.1 tron XML_MemFree(XML_Parser parser, void *ptr)
1958 1.1 tron {
1959 1.1 tron FREE(ptr);
1960 1.1 tron }
1961 1.1 tron
1962 1.1 tron void XMLCALL
1963 1.1 tron XML_DefaultCurrent(XML_Parser parser)
1964 1.1 tron {
1965 1.1 tron if (defaultHandler) {
1966 1.1 tron if (openInternalEntities)
1967 1.1 tron reportDefault(parser,
1968 1.1 tron internalEncoding,
1969 1.1 tron openInternalEntities->internalEventPtr,
1970 1.1 tron openInternalEntities->internalEventEndPtr);
1971 1.1 tron else
1972 1.1 tron reportDefault(parser, encoding, eventPtr, eventEndPtr);
1973 1.1 tron }
1974 1.1 tron }
1975 1.1 tron
1976 1.1 tron const XML_LChar * XMLCALL
1977 1.1 tron XML_ErrorString(enum XML_Error code)
1978 1.1 tron {
1979 1.1 tron static const XML_LChar* const message[] = {
1980 1.1 tron 0,
1981 1.1 tron XML_L("out of memory"),
1982 1.1 tron XML_L("syntax error"),
1983 1.1 tron XML_L("no element found"),
1984 1.1 tron XML_L("not well-formed (invalid token)"),
1985 1.1 tron XML_L("unclosed token"),
1986 1.1 tron XML_L("partial character"),
1987 1.1 tron XML_L("mismatched tag"),
1988 1.1 tron XML_L("duplicate attribute"),
1989 1.1 tron XML_L("junk after document element"),
1990 1.1 tron XML_L("illegal parameter entity reference"),
1991 1.1 tron XML_L("undefined entity"),
1992 1.1 tron XML_L("recursive entity reference"),
1993 1.1 tron XML_L("asynchronous entity"),
1994 1.1 tron XML_L("reference to invalid character number"),
1995 1.1 tron XML_L("reference to binary entity"),
1996 1.1 tron XML_L("reference to external entity in attribute"),
1997 1.1 tron XML_L("XML or text declaration not at start of entity"),
1998 1.1 tron XML_L("unknown encoding"),
1999 1.1 tron XML_L("encoding specified in XML declaration is incorrect"),
2000 1.1 tron XML_L("unclosed CDATA section"),
2001 1.1 tron XML_L("error in processing external entity reference"),
2002 1.1 tron XML_L("document is not standalone"),
2003 1.1 tron XML_L("unexpected parser state - please send a bug report"),
2004 1.1 tron XML_L("entity declared in parameter entity"),
2005 1.1 tron XML_L("requested feature requires XML_DTD support in Expat"),
2006 1.1 tron XML_L("cannot change setting once parsing has begun"),
2007 1.1 tron XML_L("unbound prefix"),
2008 1.1 tron XML_L("must not undeclare prefix"),
2009 1.1 tron XML_L("incomplete markup in parameter entity"),
2010 1.1 tron XML_L("XML declaration not well-formed"),
2011 1.1 tron XML_L("text declaration not well-formed"),
2012 1.1 tron XML_L("illegal character(s) in public id"),
2013 1.1 tron XML_L("parser suspended"),
2014 1.1 tron XML_L("parser not suspended"),
2015 1.1 tron XML_L("parsing aborted"),
2016 1.1 tron XML_L("parsing finished"),
2017 1.1 tron XML_L("cannot suspend in external parameter entity"),
2018 1.1 tron XML_L("reserved prefix (xml) must not be undeclared or bound to another namespace name"),
2019 1.1 tron XML_L("reserved prefix (xmlns) must not be declared or undeclared"),
2020 1.1 tron XML_L("prefix must not be bound to one of the reserved namespace names")
2021 1.1 tron };
2022 1.1 tron if (code > 0 && code < sizeof(message)/sizeof(message[0]))
2023 1.1 tron return message[code];
2024 1.1 tron return NULL;
2025 1.1 tron }
2026 1.1 tron
2027 1.1 tron const XML_LChar * XMLCALL
2028 1.1 tron XML_ExpatVersion(void) {
2029 1.1 tron
2030 1.1 tron /* V1 is used to string-ize the version number. However, it would
2031 1.1 tron string-ize the actual version macro *names* unless we get them
2032 1.1 tron substituted before being passed to V1. CPP is defined to expand
2033 1.1 tron a macro, then rescan for more expansions. Thus, we use V2 to expand
2034 1.1 tron the version macros, then CPP will expand the resulting V1() macro
2035 1.1 tron with the correct numerals. */
2036 1.1 tron /* ### I'm assuming cpp is portable in this respect... */
2037 1.1 tron
2038 1.1 tron #define V1(a,b,c) XML_L(#a)XML_L(".")XML_L(#b)XML_L(".")XML_L(#c)
2039 1.1 tron #define V2(a,b,c) XML_L("expat_")V1(a,b,c)
2040 1.1 tron
2041 1.1 tron return V2(XML_MAJOR_VERSION, XML_MINOR_VERSION, XML_MICRO_VERSION);
2042 1.1 tron
2043 1.1 tron #undef V1
2044 1.1 tron #undef V2
2045 1.1 tron }
2046 1.1 tron
2047 1.1 tron XML_Expat_Version XMLCALL
2048 1.1 tron XML_ExpatVersionInfo(void)
2049 1.1 tron {
2050 1.1 tron XML_Expat_Version version;
2051 1.1 tron
2052 1.1 tron version.major = XML_MAJOR_VERSION;
2053 1.1 tron version.minor = XML_MINOR_VERSION;
2054 1.1 tron version.micro = XML_MICRO_VERSION;
2055 1.1 tron
2056 1.1 tron return version;
2057 1.1 tron }
2058 1.1 tron
2059 1.1 tron const XML_Feature * XMLCALL
2060 1.1 tron XML_GetFeatureList(void)
2061 1.1 tron {
2062 1.1 tron static const XML_Feature features[] = {
2063 1.1 tron {XML_FEATURE_SIZEOF_XML_CHAR, XML_L("sizeof(XML_Char)"),
2064 1.1 tron sizeof(XML_Char)},
2065 1.1 tron {XML_FEATURE_SIZEOF_XML_LCHAR, XML_L("sizeof(XML_LChar)"),
2066 1.1 tron sizeof(XML_LChar)},
2067 1.1 tron #ifdef XML_UNICODE
2068 1.1 tron {XML_FEATURE_UNICODE, XML_L("XML_UNICODE"), 0},
2069 1.1 tron #endif
2070 1.1 tron #ifdef XML_UNICODE_WCHAR_T
2071 1.1 tron {XML_FEATURE_UNICODE_WCHAR_T, XML_L("XML_UNICODE_WCHAR_T"), 0},
2072 1.1 tron #endif
2073 1.1 tron #ifdef XML_DTD
2074 1.1 tron {XML_FEATURE_DTD, XML_L("XML_DTD"), 0},
2075 1.1 tron #endif
2076 1.1 tron #ifdef XML_CONTEXT_BYTES
2077 1.1 tron {XML_FEATURE_CONTEXT_BYTES, XML_L("XML_CONTEXT_BYTES"),
2078 1.1 tron XML_CONTEXT_BYTES},
2079 1.1 tron #endif
2080 1.1 tron #ifdef XML_MIN_SIZE
2081 1.1 tron {XML_FEATURE_MIN_SIZE, XML_L("XML_MIN_SIZE"), 0},
2082 1.1 tron #endif
2083 1.1 tron #ifdef XML_NS
2084 1.1 tron {XML_FEATURE_NS, XML_L("XML_NS"), 0},
2085 1.1 tron #endif
2086 1.1 tron #ifdef XML_LARGE_SIZE
2087 1.1 tron {XML_FEATURE_LARGE_SIZE, XML_L("XML_LARGE_SIZE"), 0},
2088 1.3 spz #endif
2089 1.3 spz #ifdef XML_ATTR_INFO
2090 1.3 spz {XML_FEATURE_ATTR_INFO, XML_L("XML_ATTR_INFO"), 0},
2091 1.3 spz #endif
2092 1.1 tron {XML_FEATURE_END, NULL, 0}
2093 1.1 tron };
2094 1.1 tron
2095 1.1 tron return features;
2096 1.1 tron }
2097 1.1 tron
2098 1.1 tron /* Initially tag->rawName always points into the parse buffer;
2099 1.1 tron for those TAG instances opened while the current parse buffer was
2100 1.1 tron processed, and not yet closed, we need to store tag->rawName in a more
2101 1.1 tron permanent location, since the parse buffer is about to be discarded.
2102 1.1 tron */
2103 1.1 tron static XML_Bool
2104 1.1 tron storeRawNames(XML_Parser parser)
2105 1.1 tron {
2106 1.1 tron TAG *tag = tagStack;
2107 1.1 tron while (tag) {
2108 1.1 tron int bufSize;
2109 1.1 tron int nameLen = sizeof(XML_Char) * (tag->name.strLen + 1);
2110 1.1 tron char *rawNameBuf = tag->buf + nameLen;
2111 1.1 tron /* Stop if already stored. Since tagStack is a stack, we can stop
2112 1.1 tron at the first entry that has already been copied; everything
2113 1.1 tron below it in the stack is already been accounted for in a
2114 1.1 tron previous call to this function.
2115 1.1 tron */
2116 1.1 tron if (tag->rawName == rawNameBuf)
2117 1.1 tron break;
2118 1.1 tron /* For re-use purposes we need to ensure that the
2119 1.1 tron size of tag->buf is a multiple of sizeof(XML_Char).
2120 1.1 tron */
2121 1.1 tron bufSize = nameLen + ROUND_UP(tag->rawNameLength, sizeof(XML_Char));
2122 1.1 tron if (bufSize > tag->bufEnd - tag->buf) {
2123 1.1 tron char *temp = (char *)REALLOC(tag->buf, bufSize);
2124 1.1 tron if (temp == NULL)
2125 1.1 tron return XML_FALSE;
2126 1.1 tron /* if tag->name.str points to tag->buf (only when namespace
2127 1.1 tron processing is off) then we have to update it
2128 1.1 tron */
2129 1.1 tron if (tag->name.str == (XML_Char *)tag->buf)
2130 1.1 tron tag->name.str = (XML_Char *)temp;
2131 1.1 tron /* if tag->name.localPart is set (when namespace processing is on)
2132 1.1 tron then update it as well, since it will always point into tag->buf
2133 1.1 tron */
2134 1.1 tron if (tag->name.localPart)
2135 1.1 tron tag->name.localPart = (XML_Char *)temp + (tag->name.localPart -
2136 1.1 tron (XML_Char *)tag->buf);
2137 1.1 tron tag->buf = temp;
2138 1.1 tron tag->bufEnd = temp + bufSize;
2139 1.1 tron rawNameBuf = temp + nameLen;
2140 1.1 tron }
2141 1.1 tron memcpy(rawNameBuf, tag->rawName, tag->rawNameLength);
2142 1.1 tron tag->rawName = rawNameBuf;
2143 1.1 tron tag = tag->parent;
2144 1.1 tron }
2145 1.1 tron return XML_TRUE;
2146 1.1 tron }
2147 1.1 tron
2148 1.1 tron static enum XML_Error PTRCALL
2149 1.1 tron contentProcessor(XML_Parser parser,
2150 1.1 tron const char *start,
2151 1.1 tron const char *end,
2152 1.1 tron const char **endPtr)
2153 1.1 tron {
2154 1.3 spz enum XML_Error result = doContent(parser, 0, encoding, start, end,
2155 1.1 tron endPtr, (XML_Bool)!ps_finalBuffer);
2156 1.1 tron if (result == XML_ERROR_NONE) {
2157 1.1 tron if (!storeRawNames(parser))
2158 1.1 tron return XML_ERROR_NO_MEMORY;
2159 1.1 tron }
2160 1.1 tron return result;
2161 1.1 tron }
2162 1.1 tron
2163 1.1 tron static enum XML_Error PTRCALL
2164 1.1 tron externalEntityInitProcessor(XML_Parser parser,
2165 1.1 tron const char *start,
2166 1.1 tron const char *end,
2167 1.1 tron const char **endPtr)
2168 1.1 tron {
2169 1.1 tron enum XML_Error result = initializeEncoding(parser);
2170 1.1 tron if (result != XML_ERROR_NONE)
2171 1.1 tron return result;
2172 1.1 tron processor = externalEntityInitProcessor2;
2173 1.1 tron return externalEntityInitProcessor2(parser, start, end, endPtr);
2174 1.1 tron }
2175 1.1 tron
2176 1.1 tron static enum XML_Error PTRCALL
2177 1.1 tron externalEntityInitProcessor2(XML_Parser parser,
2178 1.1 tron const char *start,
2179 1.1 tron const char *end,
2180 1.1 tron const char **endPtr)
2181 1.1 tron {
2182 1.1 tron const char *next = start; /* XmlContentTok doesn't always set the last arg */
2183 1.1 tron int tok = XmlContentTok(encoding, start, end, &next);
2184 1.1 tron switch (tok) {
2185 1.1 tron case XML_TOK_BOM:
2186 1.1 tron /* If we are at the end of the buffer, this would cause the next stage,
2187 1.1 tron i.e. externalEntityInitProcessor3, to pass control directly to
2188 1.1 tron doContent (by detecting XML_TOK_NONE) without processing any xml text
2189 1.1 tron declaration - causing the error XML_ERROR_MISPLACED_XML_PI in doContent.
2190 1.1 tron */
2191 1.1 tron if (next == end && !ps_finalBuffer) {
2192 1.1 tron *endPtr = next;
2193 1.1 tron return XML_ERROR_NONE;
2194 1.1 tron }
2195 1.1 tron start = next;
2196 1.1 tron break;
2197 1.1 tron case XML_TOK_PARTIAL:
2198 1.1 tron if (!ps_finalBuffer) {
2199 1.1 tron *endPtr = start;
2200 1.1 tron return XML_ERROR_NONE;
2201 1.1 tron }
2202 1.1 tron eventPtr = start;
2203 1.1 tron return XML_ERROR_UNCLOSED_TOKEN;
2204 1.1 tron case XML_TOK_PARTIAL_CHAR:
2205 1.1 tron if (!ps_finalBuffer) {
2206 1.1 tron *endPtr = start;
2207 1.1 tron return XML_ERROR_NONE;
2208 1.1 tron }
2209 1.1 tron eventPtr = start;
2210 1.1 tron return XML_ERROR_PARTIAL_CHAR;
2211 1.1 tron }
2212 1.1 tron processor = externalEntityInitProcessor3;
2213 1.1 tron return externalEntityInitProcessor3(parser, start, end, endPtr);
2214 1.1 tron }
2215 1.1 tron
2216 1.1 tron static enum XML_Error PTRCALL
2217 1.1 tron externalEntityInitProcessor3(XML_Parser parser,
2218 1.1 tron const char *start,
2219 1.1 tron const char *end,
2220 1.1 tron const char **endPtr)
2221 1.1 tron {
2222 1.1 tron int tok;
2223 1.1 tron const char *next = start; /* XmlContentTok doesn't always set the last arg */
2224 1.1 tron eventPtr = start;
2225 1.1 tron tok = XmlContentTok(encoding, start, end, &next);
2226 1.1 tron eventEndPtr = next;
2227 1.1 tron
2228 1.1 tron switch (tok) {
2229 1.1 tron case XML_TOK_XML_DECL:
2230 1.1 tron {
2231 1.1 tron enum XML_Error result;
2232 1.1 tron result = processXmlDecl(parser, 1, start, next);
2233 1.1 tron if (result != XML_ERROR_NONE)
2234 1.1 tron return result;
2235 1.1 tron switch (ps_parsing) {
2236 1.3 spz case XML_SUSPENDED:
2237 1.1 tron *endPtr = next;
2238 1.1 tron return XML_ERROR_NONE;
2239 1.1 tron case XML_FINISHED:
2240 1.1 tron return XML_ERROR_ABORTED;
2241 1.1 tron default:
2242 1.1 tron start = next;
2243 1.1 tron }
2244 1.1 tron }
2245 1.1 tron break;
2246 1.1 tron case XML_TOK_PARTIAL:
2247 1.1 tron if (!ps_finalBuffer) {
2248 1.1 tron *endPtr = start;
2249 1.1 tron return XML_ERROR_NONE;
2250 1.1 tron }
2251 1.1 tron return XML_ERROR_UNCLOSED_TOKEN;
2252 1.1 tron case XML_TOK_PARTIAL_CHAR:
2253 1.1 tron if (!ps_finalBuffer) {
2254 1.1 tron *endPtr = start;
2255 1.1 tron return XML_ERROR_NONE;
2256 1.1 tron }
2257 1.1 tron return XML_ERROR_PARTIAL_CHAR;
2258 1.1 tron }
2259 1.1 tron processor = externalEntityContentProcessor;
2260 1.1 tron tagLevel = 1;
2261 1.1 tron return externalEntityContentProcessor(parser, start, end, endPtr);
2262 1.1 tron }
2263 1.1 tron
2264 1.1 tron static enum XML_Error PTRCALL
2265 1.1 tron externalEntityContentProcessor(XML_Parser parser,
2266 1.1 tron const char *start,
2267 1.1 tron const char *end,
2268 1.1 tron const char **endPtr)
2269 1.1 tron {
2270 1.3 spz enum XML_Error result = doContent(parser, 1, encoding, start, end,
2271 1.1 tron endPtr, (XML_Bool)!ps_finalBuffer);
2272 1.1 tron if (result == XML_ERROR_NONE) {
2273 1.1 tron if (!storeRawNames(parser))
2274 1.1 tron return XML_ERROR_NO_MEMORY;
2275 1.1 tron }
2276 1.1 tron return result;
2277 1.1 tron }
2278 1.1 tron
2279 1.1 tron static enum XML_Error
2280 1.1 tron doContent(XML_Parser parser,
2281 1.1 tron int startTagLevel,
2282 1.1 tron const ENCODING *enc,
2283 1.1 tron const char *s,
2284 1.1 tron const char *end,
2285 1.1 tron const char **nextPtr,
2286 1.1 tron XML_Bool haveMore)
2287 1.1 tron {
2288 1.1 tron /* save one level of indirection */
2289 1.3 spz DTD * const dtd = _dtd;
2290 1.1 tron
2291 1.1 tron const char **eventPP;
2292 1.1 tron const char **eventEndPP;
2293 1.1 tron if (enc == encoding) {
2294 1.1 tron eventPP = &eventPtr;
2295 1.1 tron eventEndPP = &eventEndPtr;
2296 1.1 tron }
2297 1.1 tron else {
2298 1.1 tron eventPP = &(openInternalEntities->internalEventPtr);
2299 1.1 tron eventEndPP = &(openInternalEntities->internalEventEndPtr);
2300 1.1 tron }
2301 1.1 tron *eventPP = s;
2302 1.1 tron
2303 1.1 tron for (;;) {
2304 1.1 tron const char *next = s; /* XmlContentTok doesn't always set the last arg */
2305 1.1 tron int tok = XmlContentTok(enc, s, end, &next);
2306 1.1 tron *eventEndPP = next;
2307 1.1 tron switch (tok) {
2308 1.1 tron case XML_TOK_TRAILING_CR:
2309 1.1 tron if (haveMore) {
2310 1.1 tron *nextPtr = s;
2311 1.1 tron return XML_ERROR_NONE;
2312 1.1 tron }
2313 1.1 tron *eventEndPP = end;
2314 1.1 tron if (characterDataHandler) {
2315 1.1 tron XML_Char c = 0xA;
2316 1.1 tron characterDataHandler(handlerArg, &c, 1);
2317 1.1 tron }
2318 1.1 tron else if (defaultHandler)
2319 1.1 tron reportDefault(parser, enc, s, end);
2320 1.3 spz /* We are at the end of the final buffer, should we check for
2321 1.3 spz XML_SUSPENDED, XML_FINISHED?
2322 1.1 tron */
2323 1.1 tron if (startTagLevel == 0)
2324 1.1 tron return XML_ERROR_NO_ELEMENTS;
2325 1.1 tron if (tagLevel != startTagLevel)
2326 1.1 tron return XML_ERROR_ASYNC_ENTITY;
2327 1.1 tron *nextPtr = end;
2328 1.1 tron return XML_ERROR_NONE;
2329 1.1 tron case XML_TOK_NONE:
2330 1.1 tron if (haveMore) {
2331 1.1 tron *nextPtr = s;
2332 1.1 tron return XML_ERROR_NONE;
2333 1.1 tron }
2334 1.1 tron if (startTagLevel > 0) {
2335 1.1 tron if (tagLevel != startTagLevel)
2336 1.1 tron return XML_ERROR_ASYNC_ENTITY;
2337 1.1 tron *nextPtr = s;
2338 1.1 tron return XML_ERROR_NONE;
2339 1.1 tron }
2340 1.1 tron return XML_ERROR_NO_ELEMENTS;
2341 1.1 tron case XML_TOK_INVALID:
2342 1.1 tron *eventPP = next;
2343 1.1 tron return XML_ERROR_INVALID_TOKEN;
2344 1.1 tron case XML_TOK_PARTIAL:
2345 1.1 tron if (haveMore) {
2346 1.1 tron *nextPtr = s;
2347 1.1 tron return XML_ERROR_NONE;
2348 1.1 tron }
2349 1.1 tron return XML_ERROR_UNCLOSED_TOKEN;
2350 1.1 tron case XML_TOK_PARTIAL_CHAR:
2351 1.1 tron if (haveMore) {
2352 1.1 tron *nextPtr = s;
2353 1.1 tron return XML_ERROR_NONE;
2354 1.1 tron }
2355 1.1 tron return XML_ERROR_PARTIAL_CHAR;
2356 1.1 tron case XML_TOK_ENTITY_REF:
2357 1.1 tron {
2358 1.1 tron const XML_Char *name;
2359 1.1 tron ENTITY *entity;
2360 1.1 tron XML_Char ch = (XML_Char) XmlPredefinedEntityName(enc,
2361 1.1 tron s + enc->minBytesPerChar,
2362 1.1 tron next - enc->minBytesPerChar);
2363 1.1 tron if (ch) {
2364 1.1 tron if (characterDataHandler)
2365 1.1 tron characterDataHandler(handlerArg, &ch, 1);
2366 1.1 tron else if (defaultHandler)
2367 1.1 tron reportDefault(parser, enc, s, next);
2368 1.1 tron break;
2369 1.1 tron }
2370 1.1 tron name = poolStoreString(&dtd->pool, enc,
2371 1.1 tron s + enc->minBytesPerChar,
2372 1.1 tron next - enc->minBytesPerChar);
2373 1.1 tron if (!name)
2374 1.1 tron return XML_ERROR_NO_MEMORY;
2375 1.3 spz entity = (ENTITY *)lookup(parser, &dtd->generalEntities, name, 0);
2376 1.1 tron poolDiscard(&dtd->pool);
2377 1.1 tron /* First, determine if a check for an existing declaration is needed;
2378 1.1 tron if yes, check that the entity exists, and that it is internal,
2379 1.1 tron otherwise call the skipped entity or default handler.
2380 1.1 tron */
2381 1.1 tron if (!dtd->hasParamEntityRefs || dtd->standalone) {
2382 1.1 tron if (!entity)
2383 1.1 tron return XML_ERROR_UNDEFINED_ENTITY;
2384 1.1 tron else if (!entity->is_internal)
2385 1.1 tron return XML_ERROR_ENTITY_DECLARED_IN_PE;
2386 1.1 tron }
2387 1.1 tron else if (!entity) {
2388 1.1 tron if (skippedEntityHandler)
2389 1.1 tron skippedEntityHandler(handlerArg, name, 0);
2390 1.1 tron else if (defaultHandler)
2391 1.1 tron reportDefault(parser, enc, s, next);
2392 1.1 tron break;
2393 1.1 tron }
2394 1.1 tron if (entity->open)
2395 1.1 tron return XML_ERROR_RECURSIVE_ENTITY_REF;
2396 1.1 tron if (entity->notation)
2397 1.1 tron return XML_ERROR_BINARY_ENTITY_REF;
2398 1.1 tron if (entity->textPtr) {
2399 1.1 tron enum XML_Error result;
2400 1.1 tron if (!defaultExpandInternalEntities) {
2401 1.1 tron if (skippedEntityHandler)
2402 1.1 tron skippedEntityHandler(handlerArg, entity->name, 0);
2403 1.1 tron else if (defaultHandler)
2404 1.1 tron reportDefault(parser, enc, s, next);
2405 1.1 tron break;
2406 1.1 tron }
2407 1.1 tron result = processInternalEntity(parser, entity, XML_FALSE);
2408 1.1 tron if (result != XML_ERROR_NONE)
2409 1.1 tron return result;
2410 1.1 tron }
2411 1.1 tron else if (externalEntityRefHandler) {
2412 1.1 tron const XML_Char *context;
2413 1.1 tron entity->open = XML_TRUE;
2414 1.1 tron context = getContext(parser);
2415 1.1 tron entity->open = XML_FALSE;
2416 1.1 tron if (!context)
2417 1.1 tron return XML_ERROR_NO_MEMORY;
2418 1.1 tron if (!externalEntityRefHandler(externalEntityRefHandlerArg,
2419 1.1 tron context,
2420 1.1 tron entity->base,
2421 1.1 tron entity->systemId,
2422 1.1 tron entity->publicId))
2423 1.1 tron return XML_ERROR_EXTERNAL_ENTITY_HANDLING;
2424 1.1 tron poolDiscard(&tempPool);
2425 1.1 tron }
2426 1.1 tron else if (defaultHandler)
2427 1.1 tron reportDefault(parser, enc, s, next);
2428 1.1 tron break;
2429 1.1 tron }
2430 1.1 tron case XML_TOK_START_TAG_NO_ATTS:
2431 1.1 tron /* fall through */
2432 1.1 tron case XML_TOK_START_TAG_WITH_ATTS:
2433 1.1 tron {
2434 1.1 tron TAG *tag;
2435 1.1 tron enum XML_Error result;
2436 1.1 tron XML_Char *toPtr;
2437 1.1 tron if (freeTagList) {
2438 1.1 tron tag = freeTagList;
2439 1.1 tron freeTagList = freeTagList->parent;
2440 1.1 tron }
2441 1.1 tron else {
2442 1.1 tron tag = (TAG *)MALLOC(sizeof(TAG));
2443 1.1 tron if (!tag)
2444 1.1 tron return XML_ERROR_NO_MEMORY;
2445 1.1 tron tag->buf = (char *)MALLOC(INIT_TAG_BUF_SIZE);
2446 1.1 tron if (!tag->buf) {
2447 1.1 tron FREE(tag);
2448 1.1 tron return XML_ERROR_NO_MEMORY;
2449 1.1 tron }
2450 1.1 tron tag->bufEnd = tag->buf + INIT_TAG_BUF_SIZE;
2451 1.1 tron }
2452 1.1 tron tag->bindings = NULL;
2453 1.1 tron tag->parent = tagStack;
2454 1.1 tron tagStack = tag;
2455 1.1 tron tag->name.localPart = NULL;
2456 1.1 tron tag->name.prefix = NULL;
2457 1.1 tron tag->rawName = s + enc->minBytesPerChar;
2458 1.1 tron tag->rawNameLength = XmlNameLength(enc, tag->rawName);
2459 1.1 tron ++tagLevel;
2460 1.1 tron {
2461 1.1 tron const char *rawNameEnd = tag->rawName + tag->rawNameLength;
2462 1.1 tron const char *fromPtr = tag->rawName;
2463 1.1 tron toPtr = (XML_Char *)tag->buf;
2464 1.1 tron for (;;) {
2465 1.1 tron int bufSize;
2466 1.1 tron int convLen;
2467 1.5 spz const enum XML_Convert_Result convert_res = XmlConvert(enc,
2468 1.1 tron &fromPtr, rawNameEnd,
2469 1.1 tron (ICHAR **)&toPtr, (ICHAR *)tag->bufEnd - 1);
2470 1.1 tron convLen = (int)(toPtr - (XML_Char *)tag->buf);
2471 1.5 spz if ((convert_res == XML_CONVERT_COMPLETED) || (convert_res == XML_CONVERT_INPUT_INCOMPLETE)) {
2472 1.1 tron tag->name.strLen = convLen;
2473 1.1 tron break;
2474 1.1 tron }
2475 1.1 tron bufSize = (int)(tag->bufEnd - tag->buf) << 1;
2476 1.1 tron {
2477 1.1 tron char *temp = (char *)REALLOC(tag->buf, bufSize);
2478 1.1 tron if (temp == NULL)
2479 1.1 tron return XML_ERROR_NO_MEMORY;
2480 1.1 tron tag->buf = temp;
2481 1.1 tron tag->bufEnd = temp + bufSize;
2482 1.1 tron toPtr = (XML_Char *)temp + convLen;
2483 1.1 tron }
2484 1.1 tron }
2485 1.1 tron }
2486 1.1 tron tag->name.str = (XML_Char *)tag->buf;
2487 1.1 tron *toPtr = XML_T('\0');
2488 1.1 tron result = storeAtts(parser, enc, s, &(tag->name), &(tag->bindings));
2489 1.1 tron if (result)
2490 1.1 tron return result;
2491 1.1 tron if (startElementHandler)
2492 1.1 tron startElementHandler(handlerArg, tag->name.str,
2493 1.1 tron (const XML_Char **)atts);
2494 1.1 tron else if (defaultHandler)
2495 1.1 tron reportDefault(parser, enc, s, next);
2496 1.1 tron poolClear(&tempPool);
2497 1.1 tron break;
2498 1.1 tron }
2499 1.1 tron case XML_TOK_EMPTY_ELEMENT_NO_ATTS:
2500 1.1 tron /* fall through */
2501 1.1 tron case XML_TOK_EMPTY_ELEMENT_WITH_ATTS:
2502 1.1 tron {
2503 1.1 tron const char *rawName = s + enc->minBytesPerChar;
2504 1.1 tron enum XML_Error result;
2505 1.1 tron BINDING *bindings = NULL;
2506 1.1 tron XML_Bool noElmHandlers = XML_TRUE;
2507 1.1 tron TAG_NAME name;
2508 1.1 tron name.str = poolStoreString(&tempPool, enc, rawName,
2509 1.1 tron rawName + XmlNameLength(enc, rawName));
2510 1.1 tron if (!name.str)
2511 1.1 tron return XML_ERROR_NO_MEMORY;
2512 1.1 tron poolFinish(&tempPool);
2513 1.1 tron result = storeAtts(parser, enc, s, &name, &bindings);
2514 1.1 tron if (result)
2515 1.1 tron return result;
2516 1.1 tron poolFinish(&tempPool);
2517 1.1 tron if (startElementHandler) {
2518 1.1 tron startElementHandler(handlerArg, name.str, (const XML_Char **)atts);
2519 1.1 tron noElmHandlers = XML_FALSE;
2520 1.1 tron }
2521 1.1 tron if (endElementHandler) {
2522 1.1 tron if (startElementHandler)
2523 1.1 tron *eventPP = *eventEndPP;
2524 1.1 tron endElementHandler(handlerArg, name.str);
2525 1.1 tron noElmHandlers = XML_FALSE;
2526 1.1 tron }
2527 1.1 tron if (noElmHandlers && defaultHandler)
2528 1.1 tron reportDefault(parser, enc, s, next);
2529 1.1 tron poolClear(&tempPool);
2530 1.1 tron while (bindings) {
2531 1.1 tron BINDING *b = bindings;
2532 1.1 tron if (endNamespaceDeclHandler)
2533 1.1 tron endNamespaceDeclHandler(handlerArg, b->prefix->name);
2534 1.1 tron bindings = bindings->nextTagBinding;
2535 1.1 tron b->nextTagBinding = freeBindingList;
2536 1.1 tron freeBindingList = b;
2537 1.1 tron b->prefix->binding = b->prevPrefixBinding;
2538 1.1 tron }
2539 1.1 tron }
2540 1.1 tron if (tagLevel == 0)
2541 1.1 tron return epilogProcessor(parser, next, end, nextPtr);
2542 1.1 tron break;
2543 1.1 tron case XML_TOK_END_TAG:
2544 1.1 tron if (tagLevel == startTagLevel)
2545 1.1 tron return XML_ERROR_ASYNC_ENTITY;
2546 1.1 tron else {
2547 1.1 tron int len;
2548 1.1 tron const char *rawName;
2549 1.1 tron TAG *tag = tagStack;
2550 1.1 tron tagStack = tag->parent;
2551 1.1 tron tag->parent = freeTagList;
2552 1.1 tron freeTagList = tag;
2553 1.1 tron rawName = s + enc->minBytesPerChar*2;
2554 1.1 tron len = XmlNameLength(enc, rawName);
2555 1.1 tron if (len != tag->rawNameLength
2556 1.1 tron || memcmp(tag->rawName, rawName, len) != 0) {
2557 1.1 tron *eventPP = rawName;
2558 1.1 tron return XML_ERROR_TAG_MISMATCH;
2559 1.1 tron }
2560 1.1 tron --tagLevel;
2561 1.1 tron if (endElementHandler) {
2562 1.1 tron const XML_Char *localPart;
2563 1.1 tron const XML_Char *prefix;
2564 1.1 tron XML_Char *uri;
2565 1.1 tron localPart = tag->name.localPart;
2566 1.1 tron if (ns && localPart) {
2567 1.1 tron /* localPart and prefix may have been overwritten in
2568 1.1 tron tag->name.str, since this points to the binding->uri
2569 1.1 tron buffer which gets re-used; so we have to add them again
2570 1.1 tron */
2571 1.1 tron uri = (XML_Char *)tag->name.str + tag->name.uriLen;
2572 1.1 tron /* don't need to check for space - already done in storeAtts() */
2573 1.1 tron while (*localPart) *uri++ = *localPart++;
2574 1.1 tron prefix = (XML_Char *)tag->name.prefix;
2575 1.1 tron if (ns_triplets && prefix) {
2576 1.1 tron *uri++ = namespaceSeparator;
2577 1.1 tron while (*prefix) *uri++ = *prefix++;
2578 1.1 tron }
2579 1.1 tron *uri = XML_T('\0');
2580 1.1 tron }
2581 1.1 tron endElementHandler(handlerArg, tag->name.str);
2582 1.1 tron }
2583 1.1 tron else if (defaultHandler)
2584 1.1 tron reportDefault(parser, enc, s, next);
2585 1.1 tron while (tag->bindings) {
2586 1.1 tron BINDING *b = tag->bindings;
2587 1.1 tron if (endNamespaceDeclHandler)
2588 1.1 tron endNamespaceDeclHandler(handlerArg, b->prefix->name);
2589 1.1 tron tag->bindings = tag->bindings->nextTagBinding;
2590 1.1 tron b->nextTagBinding = freeBindingList;
2591 1.1 tron freeBindingList = b;
2592 1.1 tron b->prefix->binding = b->prevPrefixBinding;
2593 1.1 tron }
2594 1.1 tron if (tagLevel == 0)
2595 1.1 tron return epilogProcessor(parser, next, end, nextPtr);
2596 1.1 tron }
2597 1.1 tron break;
2598 1.1 tron case XML_TOK_CHAR_REF:
2599 1.1 tron {
2600 1.1 tron int n = XmlCharRefNumber(enc, s);
2601 1.1 tron if (n < 0)
2602 1.1 tron return XML_ERROR_BAD_CHAR_REF;
2603 1.1 tron if (characterDataHandler) {
2604 1.1 tron XML_Char buf[XML_ENCODE_MAX];
2605 1.1 tron characterDataHandler(handlerArg, buf, XmlEncode(n, (ICHAR *)buf));
2606 1.1 tron }
2607 1.1 tron else if (defaultHandler)
2608 1.1 tron reportDefault(parser, enc, s, next);
2609 1.1 tron }
2610 1.1 tron break;
2611 1.1 tron case XML_TOK_XML_DECL:
2612 1.1 tron return XML_ERROR_MISPLACED_XML_PI;
2613 1.1 tron case XML_TOK_DATA_NEWLINE:
2614 1.1 tron if (characterDataHandler) {
2615 1.1 tron XML_Char c = 0xA;
2616 1.1 tron characterDataHandler(handlerArg, &c, 1);
2617 1.1 tron }
2618 1.1 tron else if (defaultHandler)
2619 1.1 tron reportDefault(parser, enc, s, next);
2620 1.1 tron break;
2621 1.1 tron case XML_TOK_CDATA_SECT_OPEN:
2622 1.1 tron {
2623 1.1 tron enum XML_Error result;
2624 1.1 tron if (startCdataSectionHandler)
2625 1.1 tron startCdataSectionHandler(handlerArg);
2626 1.1 tron #if 0
2627 1.1 tron /* Suppose you doing a transformation on a document that involves
2628 1.1 tron changing only the character data. You set up a defaultHandler
2629 1.1 tron and a characterDataHandler. The defaultHandler simply copies
2630 1.1 tron characters through. The characterDataHandler does the
2631 1.1 tron transformation and writes the characters out escaping them as
2632 1.1 tron necessary. This case will fail to work if we leave out the
2633 1.1 tron following two lines (because & and < inside CDATA sections will
2634 1.1 tron be incorrectly escaped).
2635 1.1 tron
2636 1.1 tron However, now we have a start/endCdataSectionHandler, so it seems
2637 1.1 tron easier to let the user deal with this.
2638 1.1 tron */
2639 1.1 tron else if (characterDataHandler)
2640 1.1 tron characterDataHandler(handlerArg, dataBuf, 0);
2641 1.1 tron #endif
2642 1.1 tron else if (defaultHandler)
2643 1.1 tron reportDefault(parser, enc, s, next);
2644 1.1 tron result = doCdataSection(parser, enc, &next, end, nextPtr, haveMore);
2645 1.1 tron if (result != XML_ERROR_NONE)
2646 1.1 tron return result;
2647 1.1 tron else if (!next) {
2648 1.1 tron processor = cdataSectionProcessor;
2649 1.1 tron return result;
2650 1.1 tron }
2651 1.1 tron }
2652 1.1 tron break;
2653 1.1 tron case XML_TOK_TRAILING_RSQB:
2654 1.1 tron if (haveMore) {
2655 1.1 tron *nextPtr = s;
2656 1.1 tron return XML_ERROR_NONE;
2657 1.1 tron }
2658 1.1 tron if (characterDataHandler) {
2659 1.1 tron if (MUST_CONVERT(enc, s)) {
2660 1.1 tron ICHAR *dataPtr = (ICHAR *)dataBuf;
2661 1.1 tron XmlConvert(enc, &s, end, &dataPtr, (ICHAR *)dataBufEnd);
2662 1.1 tron characterDataHandler(handlerArg, dataBuf,
2663 1.1 tron (int)(dataPtr - (ICHAR *)dataBuf));
2664 1.1 tron }
2665 1.1 tron else
2666 1.1 tron characterDataHandler(handlerArg,
2667 1.1 tron (XML_Char *)s,
2668 1.1 tron (int)((XML_Char *)end - (XML_Char *)s));
2669 1.1 tron }
2670 1.1 tron else if (defaultHandler)
2671 1.1 tron reportDefault(parser, enc, s, end);
2672 1.3 spz /* We are at the end of the final buffer, should we check for
2673 1.3 spz XML_SUSPENDED, XML_FINISHED?
2674 1.1 tron */
2675 1.1 tron if (startTagLevel == 0) {
2676 1.1 tron *eventPP = end;
2677 1.1 tron return XML_ERROR_NO_ELEMENTS;
2678 1.1 tron }
2679 1.1 tron if (tagLevel != startTagLevel) {
2680 1.1 tron *eventPP = end;
2681 1.1 tron return XML_ERROR_ASYNC_ENTITY;
2682 1.1 tron }
2683 1.1 tron *nextPtr = end;
2684 1.1 tron return XML_ERROR_NONE;
2685 1.3 spz case XML_TOK_DATA_CHARS:
2686 1.1 tron {
2687 1.1 tron XML_CharacterDataHandler charDataHandler = characterDataHandler;
2688 1.1 tron if (charDataHandler) {
2689 1.1 tron if (MUST_CONVERT(enc, s)) {
2690 1.1 tron for (;;) {
2691 1.1 tron ICHAR *dataPtr = (ICHAR *)dataBuf;
2692 1.5 spz const enum XML_Convert_Result convert_res = XmlConvert(enc, &s, next, &dataPtr, (ICHAR *)dataBufEnd);
2693 1.1 tron *eventEndPP = s;
2694 1.1 tron charDataHandler(handlerArg, dataBuf,
2695 1.1 tron (int)(dataPtr - (ICHAR *)dataBuf));
2696 1.5 spz if ((convert_res == XML_CONVERT_COMPLETED) || (convert_res == XML_CONVERT_INPUT_INCOMPLETE))
2697 1.1 tron break;
2698 1.1 tron *eventPP = s;
2699 1.1 tron }
2700 1.1 tron }
2701 1.1 tron else
2702 1.1 tron charDataHandler(handlerArg,
2703 1.1 tron (XML_Char *)s,
2704 1.1 tron (int)((XML_Char *)next - (XML_Char *)s));
2705 1.1 tron }
2706 1.1 tron else if (defaultHandler)
2707 1.1 tron reportDefault(parser, enc, s, next);
2708 1.1 tron }
2709 1.1 tron break;
2710 1.1 tron case XML_TOK_PI:
2711 1.1 tron if (!reportProcessingInstruction(parser, enc, s, next))
2712 1.1 tron return XML_ERROR_NO_MEMORY;
2713 1.1 tron break;
2714 1.1 tron case XML_TOK_COMMENT:
2715 1.1 tron if (!reportComment(parser, enc, s, next))
2716 1.1 tron return XML_ERROR_NO_MEMORY;
2717 1.1 tron break;
2718 1.1 tron default:
2719 1.1 tron if (defaultHandler)
2720 1.1 tron reportDefault(parser, enc, s, next);
2721 1.1 tron break;
2722 1.1 tron }
2723 1.1 tron *eventPP = s = next;
2724 1.1 tron switch (ps_parsing) {
2725 1.3 spz case XML_SUSPENDED:
2726 1.1 tron *nextPtr = next;
2727 1.1 tron return XML_ERROR_NONE;
2728 1.1 tron case XML_FINISHED:
2729 1.1 tron return XML_ERROR_ABORTED;
2730 1.1 tron default: ;
2731 1.1 tron }
2732 1.1 tron }
2733 1.1 tron /* not reached */
2734 1.1 tron }
2735 1.1 tron
2736 1.1 tron /* Precondition: all arguments must be non-NULL;
2737 1.1 tron Purpose:
2738 1.1 tron - normalize attributes
2739 1.1 tron - check attributes for well-formedness
2740 1.1 tron - generate namespace aware attribute names (URI, prefix)
2741 1.1 tron - build list of attributes for startElementHandler
2742 1.1 tron - default attributes
2743 1.1 tron - process namespace declarations (check and report them)
2744 1.1 tron - generate namespace aware element name (URI, prefix)
2745 1.1 tron */
2746 1.1 tron static enum XML_Error
2747 1.1 tron storeAtts(XML_Parser parser, const ENCODING *enc,
2748 1.1 tron const char *attStr, TAG_NAME *tagNamePtr,
2749 1.1 tron BINDING **bindingsPtr)
2750 1.1 tron {
2751 1.1 tron DTD * const dtd = _dtd; /* save one level of indirection */
2752 1.1 tron ELEMENT_TYPE *elementType;
2753 1.1 tron int nDefaultAtts;
2754 1.1 tron const XML_Char **appAtts; /* the attribute list for the application */
2755 1.1 tron int attIndex = 0;
2756 1.1 tron int prefixLen;
2757 1.1 tron int i;
2758 1.1 tron int n;
2759 1.1 tron XML_Char *uri;
2760 1.1 tron int nPrefixes = 0;
2761 1.1 tron BINDING *binding;
2762 1.1 tron const XML_Char *localPart;
2763 1.1 tron
2764 1.1 tron /* lookup the element type name */
2765 1.3 spz elementType = (ELEMENT_TYPE *)lookup(parser, &dtd->elementTypes, tagNamePtr->str,0);
2766 1.1 tron if (!elementType) {
2767 1.1 tron const XML_Char *name = poolCopyString(&dtd->pool, tagNamePtr->str);
2768 1.1 tron if (!name)
2769 1.1 tron return XML_ERROR_NO_MEMORY;
2770 1.3 spz elementType = (ELEMENT_TYPE *)lookup(parser, &dtd->elementTypes, name,
2771 1.1 tron sizeof(ELEMENT_TYPE));
2772 1.1 tron if (!elementType)
2773 1.1 tron return XML_ERROR_NO_MEMORY;
2774 1.1 tron if (ns && !setElementTypePrefix(parser, elementType))
2775 1.1 tron return XML_ERROR_NO_MEMORY;
2776 1.1 tron }
2777 1.1 tron nDefaultAtts = elementType->nDefaultAtts;
2778 1.1 tron
2779 1.1 tron /* get the attributes from the tokenizer */
2780 1.1 tron n = XmlGetAttributes(enc, attStr, attsSize, atts);
2781 1.1 tron if (n + nDefaultAtts > attsSize) {
2782 1.1 tron int oldAttsSize = attsSize;
2783 1.1 tron ATTRIBUTE *temp;
2784 1.3 spz #ifdef XML_ATTR_INFO
2785 1.3 spz XML_AttrInfo *temp2;
2786 1.3 spz #endif
2787 1.1 tron attsSize = n + nDefaultAtts + INIT_ATTS_SIZE;
2788 1.1 tron temp = (ATTRIBUTE *)REALLOC((void *)atts, attsSize * sizeof(ATTRIBUTE));
2789 1.1 tron if (temp == NULL)
2790 1.1 tron return XML_ERROR_NO_MEMORY;
2791 1.1 tron atts = temp;
2792 1.3 spz #ifdef XML_ATTR_INFO
2793 1.3 spz temp2 = (XML_AttrInfo *)REALLOC((void *)attInfo, attsSize * sizeof(XML_AttrInfo));
2794 1.3 spz if (temp2 == NULL)
2795 1.3 spz return XML_ERROR_NO_MEMORY;
2796 1.3 spz attInfo = temp2;
2797 1.3 spz #endif
2798 1.1 tron if (n > oldAttsSize)
2799 1.1 tron XmlGetAttributes(enc, attStr, n, atts);
2800 1.1 tron }
2801 1.1 tron
2802 1.1 tron appAtts = (const XML_Char **)atts;
2803 1.1 tron for (i = 0; i < n; i++) {
2804 1.3 spz ATTRIBUTE *currAtt = &atts[i];
2805 1.3 spz #ifdef XML_ATTR_INFO
2806 1.3 spz XML_AttrInfo *currAttInfo = &attInfo[i];
2807 1.3 spz #endif
2808 1.1 tron /* add the name and value to the attribute list */
2809 1.3 spz ATTRIBUTE_ID *attId = getAttributeId(parser, enc, currAtt->name,
2810 1.3 spz currAtt->name
2811 1.3 spz + XmlNameLength(enc, currAtt->name));
2812 1.1 tron if (!attId)
2813 1.1 tron return XML_ERROR_NO_MEMORY;
2814 1.3 spz #ifdef XML_ATTR_INFO
2815 1.3 spz currAttInfo->nameStart = parseEndByteIndex - (parseEndPtr - currAtt->name);
2816 1.3 spz currAttInfo->nameEnd = currAttInfo->nameStart +
2817 1.3 spz XmlNameLength(enc, currAtt->name);
2818 1.3 spz currAttInfo->valueStart = parseEndByteIndex -
2819 1.3 spz (parseEndPtr - currAtt->valuePtr);
2820 1.3 spz currAttInfo->valueEnd = parseEndByteIndex - (parseEndPtr - currAtt->valueEnd);
2821 1.3 spz #endif
2822 1.1 tron /* Detect duplicate attributes by their QNames. This does not work when
2823 1.1 tron namespace processing is turned on and different prefixes for the same
2824 1.1 tron namespace are used. For this case we have a check further down.
2825 1.1 tron */
2826 1.1 tron if ((attId->name)[-1]) {
2827 1.1 tron if (enc == encoding)
2828 1.1 tron eventPtr = atts[i].name;
2829 1.1 tron return XML_ERROR_DUPLICATE_ATTRIBUTE;
2830 1.1 tron }
2831 1.1 tron (attId->name)[-1] = 1;
2832 1.1 tron appAtts[attIndex++] = attId->name;
2833 1.1 tron if (!atts[i].normalized) {
2834 1.1 tron enum XML_Error result;
2835 1.1 tron XML_Bool isCdata = XML_TRUE;
2836 1.1 tron
2837 1.1 tron /* figure out whether declared as other than CDATA */
2838 1.1 tron if (attId->maybeTokenized) {
2839 1.1 tron int j;
2840 1.1 tron for (j = 0; j < nDefaultAtts; j++) {
2841 1.1 tron if (attId == elementType->defaultAtts[j].id) {
2842 1.1 tron isCdata = elementType->defaultAtts[j].isCdata;
2843 1.1 tron break;
2844 1.1 tron }
2845 1.1 tron }
2846 1.1 tron }
2847 1.1 tron
2848 1.1 tron /* normalize the attribute value */
2849 1.1 tron result = storeAttributeValue(parser, enc, isCdata,
2850 1.1 tron atts[i].valuePtr, atts[i].valueEnd,
2851 1.1 tron &tempPool);
2852 1.1 tron if (result)
2853 1.1 tron return result;
2854 1.1 tron appAtts[attIndex] = poolStart(&tempPool);
2855 1.1 tron poolFinish(&tempPool);
2856 1.1 tron }
2857 1.1 tron else {
2858 1.1 tron /* the value did not need normalizing */
2859 1.1 tron appAtts[attIndex] = poolStoreString(&tempPool, enc, atts[i].valuePtr,
2860 1.1 tron atts[i].valueEnd);
2861 1.1 tron if (appAtts[attIndex] == 0)
2862 1.1 tron return XML_ERROR_NO_MEMORY;
2863 1.1 tron poolFinish(&tempPool);
2864 1.1 tron }
2865 1.1 tron /* handle prefixed attribute names */
2866 1.1 tron if (attId->prefix) {
2867 1.1 tron if (attId->xmlns) {
2868 1.1 tron /* deal with namespace declarations here */
2869 1.1 tron enum XML_Error result = addBinding(parser, attId->prefix, attId,
2870 1.1 tron appAtts[attIndex], bindingsPtr);
2871 1.1 tron if (result)
2872 1.1 tron return result;
2873 1.1 tron --attIndex;
2874 1.1 tron }
2875 1.1 tron else {
2876 1.1 tron /* deal with other prefixed names later */
2877 1.1 tron attIndex++;
2878 1.1 tron nPrefixes++;
2879 1.1 tron (attId->name)[-1] = 2;
2880 1.1 tron }
2881 1.1 tron }
2882 1.1 tron else
2883 1.1 tron attIndex++;
2884 1.1 tron }
2885 1.1 tron
2886 1.1 tron /* set-up for XML_GetSpecifiedAttributeCount and XML_GetIdAttributeIndex */
2887 1.1 tron nSpecifiedAtts = attIndex;
2888 1.1 tron if (elementType->idAtt && (elementType->idAtt->name)[-1]) {
2889 1.1 tron for (i = 0; i < attIndex; i += 2)
2890 1.1 tron if (appAtts[i] == elementType->idAtt->name) {
2891 1.1 tron idAttIndex = i;
2892 1.1 tron break;
2893 1.1 tron }
2894 1.1 tron }
2895 1.1 tron else
2896 1.1 tron idAttIndex = -1;
2897 1.1 tron
2898 1.1 tron /* do attribute defaulting */
2899 1.1 tron for (i = 0; i < nDefaultAtts; i++) {
2900 1.1 tron const DEFAULT_ATTRIBUTE *da = elementType->defaultAtts + i;
2901 1.1 tron if (!(da->id->name)[-1] && da->value) {
2902 1.1 tron if (da->id->prefix) {
2903 1.1 tron if (da->id->xmlns) {
2904 1.1 tron enum XML_Error result = addBinding(parser, da->id->prefix, da->id,
2905 1.1 tron da->value, bindingsPtr);
2906 1.1 tron if (result)
2907 1.1 tron return result;
2908 1.1 tron }
2909 1.1 tron else {
2910 1.1 tron (da->id->name)[-1] = 2;
2911 1.1 tron nPrefixes++;
2912 1.1 tron appAtts[attIndex++] = da->id->name;
2913 1.1 tron appAtts[attIndex++] = da->value;
2914 1.1 tron }
2915 1.1 tron }
2916 1.1 tron else {
2917 1.1 tron (da->id->name)[-1] = 1;
2918 1.1 tron appAtts[attIndex++] = da->id->name;
2919 1.1 tron appAtts[attIndex++] = da->value;
2920 1.1 tron }
2921 1.1 tron }
2922 1.1 tron }
2923 1.1 tron appAtts[attIndex] = 0;
2924 1.1 tron
2925 1.1 tron /* expand prefixed attribute names, check for duplicates,
2926 1.1 tron and clear flags that say whether attributes were specified */
2927 1.1 tron i = 0;
2928 1.1 tron if (nPrefixes) {
2929 1.1 tron int j; /* hash table index */
2930 1.1 tron unsigned long version = nsAttsVersion;
2931 1.1 tron int nsAttsSize = (int)1 << nsAttsPower;
2932 1.1 tron /* size of hash table must be at least 2 * (# of prefixed attributes) */
2933 1.1 tron if ((nPrefixes << 1) >> nsAttsPower) { /* true for nsAttsPower = 0 */
2934 1.1 tron NS_ATT *temp;
2935 1.1 tron /* hash table size must also be a power of 2 and >= 8 */
2936 1.1 tron while (nPrefixes >> nsAttsPower++);
2937 1.1 tron if (nsAttsPower < 3)
2938 1.1 tron nsAttsPower = 3;
2939 1.1 tron nsAttsSize = (int)1 << nsAttsPower;
2940 1.1 tron temp = (NS_ATT *)REALLOC(nsAtts, nsAttsSize * sizeof(NS_ATT));
2941 1.1 tron if (!temp)
2942 1.1 tron return XML_ERROR_NO_MEMORY;
2943 1.1 tron nsAtts = temp;
2944 1.1 tron version = 0; /* force re-initialization of nsAtts hash table */
2945 1.1 tron }
2946 1.1 tron /* using a version flag saves us from initializing nsAtts every time */
2947 1.1 tron if (!version) { /* initialize version flags when version wraps around */
2948 1.1 tron version = INIT_ATTS_VERSION;
2949 1.1 tron for (j = nsAttsSize; j != 0; )
2950 1.1 tron nsAtts[--j].version = version;
2951 1.1 tron }
2952 1.1 tron nsAttsVersion = --version;
2953 1.1 tron
2954 1.1 tron /* expand prefixed names and check for duplicates */
2955 1.1 tron for (; i < attIndex; i += 2) {
2956 1.1 tron const XML_Char *s = appAtts[i];
2957 1.1 tron if (s[-1] == 2) { /* prefixed */
2958 1.1 tron ATTRIBUTE_ID *id;
2959 1.1 tron const BINDING *b;
2960 1.3 spz unsigned long uriHash = hash_secret_salt;
2961 1.1 tron ((XML_Char *)s)[-1] = 0; /* clear flag */
2962 1.3 spz id = (ATTRIBUTE_ID *)lookup(parser, &dtd->attributeIds, s, 0);
2963 1.4 spz if (!id || !id->prefix)
2964 1.4 spz return XML_ERROR_NO_MEMORY;
2965 1.1 tron b = id->prefix->binding;
2966 1.1 tron if (!b)
2967 1.1 tron return XML_ERROR_UNBOUND_PREFIX;
2968 1.1 tron
2969 1.1 tron /* as we expand the name we also calculate its hash value */
2970 1.1 tron for (j = 0; j < b->uriLen; j++) {
2971 1.1 tron const XML_Char c = b->uri[j];
2972 1.1 tron if (!poolAppendChar(&tempPool, c))
2973 1.1 tron return XML_ERROR_NO_MEMORY;
2974 1.1 tron uriHash = CHAR_HASH(uriHash, c);
2975 1.1 tron }
2976 1.1 tron while (*s++ != XML_T(ASCII_COLON))
2977 1.1 tron ;
2978 1.1 tron do { /* copies null terminator */
2979 1.1 tron const XML_Char c = *s;
2980 1.1 tron if (!poolAppendChar(&tempPool, *s))
2981 1.1 tron return XML_ERROR_NO_MEMORY;
2982 1.1 tron uriHash = CHAR_HASH(uriHash, c);
2983 1.1 tron } while (*s++);
2984 1.1 tron
2985 1.1 tron { /* Check hash table for duplicate of expanded name (uriName).
2986 1.3 spz Derived from code in lookup(parser, HASH_TABLE *table, ...).
2987 1.1 tron */
2988 1.1 tron unsigned char step = 0;
2989 1.1 tron unsigned long mask = nsAttsSize - 1;
2990 1.1 tron j = uriHash & mask; /* index into hash table */
2991 1.1 tron while (nsAtts[j].version == version) {
2992 1.1 tron /* for speed we compare stored hash values first */
2993 1.1 tron if (uriHash == nsAtts[j].hash) {
2994 1.1 tron const XML_Char *s1 = poolStart(&tempPool);
2995 1.1 tron const XML_Char *s2 = nsAtts[j].uriName;
2996 1.1 tron /* s1 is null terminated, but not s2 */
2997 1.1 tron for (; *s1 == *s2 && *s1 != 0; s1++, s2++);
2998 1.1 tron if (*s1 == 0)
2999 1.1 tron return XML_ERROR_DUPLICATE_ATTRIBUTE;
3000 1.1 tron }
3001 1.1 tron if (!step)
3002 1.1 tron step = PROBE_STEP(uriHash, mask, nsAttsPower);
3003 1.1 tron j < step ? (j += nsAttsSize - step) : (j -= step);
3004 1.1 tron }
3005 1.1 tron }
3006 1.1 tron
3007 1.1 tron if (ns_triplets) { /* append namespace separator and prefix */
3008 1.1 tron tempPool.ptr[-1] = namespaceSeparator;
3009 1.1 tron s = b->prefix->name;
3010 1.1 tron do {
3011 1.1 tron if (!poolAppendChar(&tempPool, *s))
3012 1.1 tron return XML_ERROR_NO_MEMORY;
3013 1.1 tron } while (*s++);
3014 1.1 tron }
3015 1.1 tron
3016 1.1 tron /* store expanded name in attribute list */
3017 1.1 tron s = poolStart(&tempPool);
3018 1.1 tron poolFinish(&tempPool);
3019 1.1 tron appAtts[i] = s;
3020 1.1 tron
3021 1.1 tron /* fill empty slot with new version, uriName and hash value */
3022 1.1 tron nsAtts[j].version = version;
3023 1.1 tron nsAtts[j].hash = uriHash;
3024 1.1 tron nsAtts[j].uriName = s;
3025 1.1 tron
3026 1.1 tron if (!--nPrefixes) {
3027 1.1 tron i += 2;
3028 1.1 tron break;
3029 1.1 tron }
3030 1.1 tron }
3031 1.1 tron else /* not prefixed */
3032 1.1 tron ((XML_Char *)s)[-1] = 0; /* clear flag */
3033 1.1 tron }
3034 1.1 tron }
3035 1.1 tron /* clear flags for the remaining attributes */
3036 1.1 tron for (; i < attIndex; i += 2)
3037 1.1 tron ((XML_Char *)(appAtts[i]))[-1] = 0;
3038 1.1 tron for (binding = *bindingsPtr; binding; binding = binding->nextTagBinding)
3039 1.1 tron binding->attId->name[-1] = 0;
3040 1.1 tron
3041 1.1 tron if (!ns)
3042 1.1 tron return XML_ERROR_NONE;
3043 1.1 tron
3044 1.1 tron /* expand the element type name */
3045 1.1 tron if (elementType->prefix) {
3046 1.1 tron binding = elementType->prefix->binding;
3047 1.1 tron if (!binding)
3048 1.1 tron return XML_ERROR_UNBOUND_PREFIX;
3049 1.1 tron localPart = tagNamePtr->str;
3050 1.1 tron while (*localPart++ != XML_T(ASCII_COLON))
3051 1.1 tron ;
3052 1.1 tron }
3053 1.1 tron else if (dtd->defaultPrefix.binding) {
3054 1.1 tron binding = dtd->defaultPrefix.binding;
3055 1.1 tron localPart = tagNamePtr->str;
3056 1.1 tron }
3057 1.1 tron else
3058 1.1 tron return XML_ERROR_NONE;
3059 1.1 tron prefixLen = 0;
3060 1.1 tron if (ns_triplets && binding->prefix->name) {
3061 1.1 tron for (; binding->prefix->name[prefixLen++];)
3062 1.1 tron ; /* prefixLen includes null terminator */
3063 1.1 tron }
3064 1.1 tron tagNamePtr->localPart = localPart;
3065 1.1 tron tagNamePtr->uriLen = binding->uriLen;
3066 1.1 tron tagNamePtr->prefix = binding->prefix->name;
3067 1.1 tron tagNamePtr->prefixLen = prefixLen;
3068 1.1 tron for (i = 0; localPart[i++];)
3069 1.1 tron ; /* i includes null terminator */
3070 1.1 tron n = i + binding->uriLen + prefixLen;
3071 1.1 tron if (n > binding->uriAlloc) {
3072 1.1 tron TAG *p;
3073 1.1 tron uri = (XML_Char *)MALLOC((n + EXPAND_SPARE) * sizeof(XML_Char));
3074 1.1 tron if (!uri)
3075 1.1 tron return XML_ERROR_NO_MEMORY;
3076 1.1 tron binding->uriAlloc = n + EXPAND_SPARE;
3077 1.1 tron memcpy(uri, binding->uri, binding->uriLen * sizeof(XML_Char));
3078 1.1 tron for (p = tagStack; p; p = p->parent)
3079 1.1 tron if (p->name.str == binding->uri)
3080 1.1 tron p->name.str = uri;
3081 1.1 tron FREE(binding->uri);
3082 1.1 tron binding->uri = uri;
3083 1.1 tron }
3084 1.1 tron /* if namespaceSeparator != '\0' then uri includes it already */
3085 1.1 tron uri = binding->uri + binding->uriLen;
3086 1.1 tron memcpy(uri, localPart, i * sizeof(XML_Char));
3087 1.1 tron /* we always have a namespace separator between localPart and prefix */
3088 1.1 tron if (prefixLen) {
3089 1.1 tron uri += i - 1;
3090 1.1 tron *uri = namespaceSeparator; /* replace null terminator */
3091 1.1 tron memcpy(uri + 1, binding->prefix->name, prefixLen * sizeof(XML_Char));
3092 1.1 tron }
3093 1.1 tron tagNamePtr->str = binding->uri;
3094 1.1 tron return XML_ERROR_NONE;
3095 1.1 tron }
3096 1.1 tron
3097 1.1 tron /* addBinding() overwrites the value of prefix->binding without checking.
3098 1.1 tron Therefore one must keep track of the old value outside of addBinding().
3099 1.1 tron */
3100 1.1 tron static enum XML_Error
3101 1.1 tron addBinding(XML_Parser parser, PREFIX *prefix, const ATTRIBUTE_ID *attId,
3102 1.1 tron const XML_Char *uri, BINDING **bindingsPtr)
3103 1.1 tron {
3104 1.1 tron static const XML_Char xmlNamespace[] = {
3105 1.1 tron ASCII_h, ASCII_t, ASCII_t, ASCII_p, ASCII_COLON, ASCII_SLASH, ASCII_SLASH,
3106 1.1 tron ASCII_w, ASCII_w, ASCII_w, ASCII_PERIOD, ASCII_w, ASCII_3, ASCII_PERIOD,
3107 1.3 spz ASCII_o, ASCII_r, ASCII_g, ASCII_SLASH, ASCII_X, ASCII_M, ASCII_L,
3108 1.1 tron ASCII_SLASH, ASCII_1, ASCII_9, ASCII_9, ASCII_8, ASCII_SLASH,
3109 1.1 tron ASCII_n, ASCII_a, ASCII_m, ASCII_e, ASCII_s, ASCII_p, ASCII_a, ASCII_c,
3110 1.1 tron ASCII_e, '\0'
3111 1.1 tron };
3112 1.3 spz static const int xmlLen =
3113 1.1 tron (int)sizeof(xmlNamespace)/sizeof(XML_Char) - 1;
3114 1.1 tron static const XML_Char xmlnsNamespace[] = {
3115 1.1 tron ASCII_h, ASCII_t, ASCII_t, ASCII_p, ASCII_COLON, ASCII_SLASH, ASCII_SLASH,
3116 1.1 tron ASCII_w, ASCII_w, ASCII_w, ASCII_PERIOD, ASCII_w, ASCII_3, ASCII_PERIOD,
3117 1.3 spz ASCII_o, ASCII_r, ASCII_g, ASCII_SLASH, ASCII_2, ASCII_0, ASCII_0,
3118 1.3 spz ASCII_0, ASCII_SLASH, ASCII_x, ASCII_m, ASCII_l, ASCII_n, ASCII_s,
3119 1.1 tron ASCII_SLASH, '\0'
3120 1.1 tron };
3121 1.3 spz static const int xmlnsLen =
3122 1.1 tron (int)sizeof(xmlnsNamespace)/sizeof(XML_Char) - 1;
3123 1.1 tron
3124 1.1 tron XML_Bool mustBeXML = XML_FALSE;
3125 1.1 tron XML_Bool isXML = XML_TRUE;
3126 1.1 tron XML_Bool isXMLNS = XML_TRUE;
3127 1.3 spz
3128 1.1 tron BINDING *b;
3129 1.1 tron int len;
3130 1.1 tron
3131 1.1 tron /* empty URI is only valid for default namespace per XML NS 1.0 (not 1.1) */
3132 1.1 tron if (*uri == XML_T('\0') && prefix->name)
3133 1.1 tron return XML_ERROR_UNDECLARING_PREFIX;
3134 1.1 tron
3135 1.1 tron if (prefix->name
3136 1.1 tron && prefix->name[0] == XML_T(ASCII_x)
3137 1.1 tron && prefix->name[1] == XML_T(ASCII_m)
3138 1.1 tron && prefix->name[2] == XML_T(ASCII_l)) {
3139 1.1 tron
3140 1.1 tron /* Not allowed to bind xmlns */
3141 1.1 tron if (prefix->name[3] == XML_T(ASCII_n)
3142 1.1 tron && prefix->name[4] == XML_T(ASCII_s)
3143 1.1 tron && prefix->name[5] == XML_T('\0'))
3144 1.1 tron return XML_ERROR_RESERVED_PREFIX_XMLNS;
3145 1.1 tron
3146 1.1 tron if (prefix->name[3] == XML_T('\0'))
3147 1.1 tron mustBeXML = XML_TRUE;
3148 1.1 tron }
3149 1.1 tron
3150 1.1 tron for (len = 0; uri[len]; len++) {
3151 1.1 tron if (isXML && (len > xmlLen || uri[len] != xmlNamespace[len]))
3152 1.1 tron isXML = XML_FALSE;
3153 1.1 tron
3154 1.3 spz if (!mustBeXML && isXMLNS
3155 1.1 tron && (len > xmlnsLen || uri[len] != xmlnsNamespace[len]))
3156 1.1 tron isXMLNS = XML_FALSE;
3157 1.1 tron }
3158 1.1 tron isXML = isXML && len == xmlLen;
3159 1.1 tron isXMLNS = isXMLNS && len == xmlnsLen;
3160 1.1 tron
3161 1.1 tron if (mustBeXML != isXML)
3162 1.1 tron return mustBeXML ? XML_ERROR_RESERVED_PREFIX_XML
3163 1.1 tron : XML_ERROR_RESERVED_NAMESPACE_URI;
3164 1.1 tron
3165 1.1 tron if (isXMLNS)
3166 1.1 tron return XML_ERROR_RESERVED_NAMESPACE_URI;
3167 1.1 tron
3168 1.1 tron if (namespaceSeparator)
3169 1.1 tron len++;
3170 1.1 tron if (freeBindingList) {
3171 1.1 tron b = freeBindingList;
3172 1.1 tron if (len > b->uriAlloc) {
3173 1.1 tron XML_Char *temp = (XML_Char *)REALLOC(b->uri,
3174 1.1 tron sizeof(XML_Char) * (len + EXPAND_SPARE));
3175 1.1 tron if (temp == NULL)
3176 1.1 tron return XML_ERROR_NO_MEMORY;
3177 1.1 tron b->uri = temp;
3178 1.1 tron b->uriAlloc = len + EXPAND_SPARE;
3179 1.1 tron }
3180 1.1 tron freeBindingList = b->nextTagBinding;
3181 1.1 tron }
3182 1.1 tron else {
3183 1.1 tron b = (BINDING *)MALLOC(sizeof(BINDING));
3184 1.1 tron if (!b)
3185 1.1 tron return XML_ERROR_NO_MEMORY;
3186 1.1 tron b->uri = (XML_Char *)MALLOC(sizeof(XML_Char) * (len + EXPAND_SPARE));
3187 1.1 tron if (!b->uri) {
3188 1.1 tron FREE(b);
3189 1.1 tron return XML_ERROR_NO_MEMORY;
3190 1.1 tron }
3191 1.1 tron b->uriAlloc = len + EXPAND_SPARE;
3192 1.1 tron }
3193 1.1 tron b->uriLen = len;
3194 1.1 tron memcpy(b->uri, uri, len * sizeof(XML_Char));
3195 1.1 tron if (namespaceSeparator)
3196 1.1 tron b->uri[len - 1] = namespaceSeparator;
3197 1.1 tron b->prefix = prefix;
3198 1.1 tron b->attId = attId;
3199 1.1 tron b->prevPrefixBinding = prefix->binding;
3200 1.1 tron /* NULL binding when default namespace undeclared */
3201 1.1 tron if (*uri == XML_T('\0') && prefix == &_dtd->defaultPrefix)
3202 1.1 tron prefix->binding = NULL;
3203 1.1 tron else
3204 1.1 tron prefix->binding = b;
3205 1.1 tron b->nextTagBinding = *bindingsPtr;
3206 1.1 tron *bindingsPtr = b;
3207 1.1 tron /* if attId == NULL then we are not starting a namespace scope */
3208 1.1 tron if (attId && startNamespaceDeclHandler)
3209 1.1 tron startNamespaceDeclHandler(handlerArg, prefix->name,
3210 1.1 tron prefix->binding ? uri : 0);
3211 1.1 tron return XML_ERROR_NONE;
3212 1.1 tron }
3213 1.1 tron
3214 1.1 tron /* The idea here is to avoid using stack for each CDATA section when
3215 1.1 tron the whole file is parsed with one call.
3216 1.1 tron */
3217 1.1 tron static enum XML_Error PTRCALL
3218 1.1 tron cdataSectionProcessor(XML_Parser parser,
3219 1.1 tron const char *start,
3220 1.1 tron const char *end,
3221 1.1 tron const char **endPtr)
3222 1.1 tron {
3223 1.1 tron enum XML_Error result = doCdataSection(parser, encoding, &start, end,
3224 1.1 tron endPtr, (XML_Bool)!ps_finalBuffer);
3225 1.1 tron if (result != XML_ERROR_NONE)
3226 1.1 tron return result;
3227 1.1 tron if (start) {
3228 1.1 tron if (parentParser) { /* we are parsing an external entity */
3229 1.1 tron processor = externalEntityContentProcessor;
3230 1.1 tron return externalEntityContentProcessor(parser, start, end, endPtr);
3231 1.1 tron }
3232 1.1 tron else {
3233 1.1 tron processor = contentProcessor;
3234 1.1 tron return contentProcessor(parser, start, end, endPtr);
3235 1.1 tron }
3236 1.1 tron }
3237 1.1 tron return result;
3238 1.1 tron }
3239 1.1 tron
3240 1.1 tron /* startPtr gets set to non-null if the section is closed, and to null if
3241 1.1 tron the section is not yet closed.
3242 1.1 tron */
3243 1.1 tron static enum XML_Error
3244 1.1 tron doCdataSection(XML_Parser parser,
3245 1.1 tron const ENCODING *enc,
3246 1.1 tron const char **startPtr,
3247 1.1 tron const char *end,
3248 1.1 tron const char **nextPtr,
3249 1.1 tron XML_Bool haveMore)
3250 1.1 tron {
3251 1.1 tron const char *s = *startPtr;
3252 1.1 tron const char **eventPP;
3253 1.1 tron const char **eventEndPP;
3254 1.1 tron if (enc == encoding) {
3255 1.1 tron eventPP = &eventPtr;
3256 1.1 tron *eventPP = s;
3257 1.1 tron eventEndPP = &eventEndPtr;
3258 1.1 tron }
3259 1.1 tron else {
3260 1.1 tron eventPP = &(openInternalEntities->internalEventPtr);
3261 1.1 tron eventEndPP = &(openInternalEntities->internalEventEndPtr);
3262 1.1 tron }
3263 1.1 tron *eventPP = s;
3264 1.1 tron *startPtr = NULL;
3265 1.1 tron
3266 1.1 tron for (;;) {
3267 1.1 tron const char *next;
3268 1.1 tron int tok = XmlCdataSectionTok(enc, s, end, &next);
3269 1.1 tron *eventEndPP = next;
3270 1.1 tron switch (tok) {
3271 1.1 tron case XML_TOK_CDATA_SECT_CLOSE:
3272 1.1 tron if (endCdataSectionHandler)
3273 1.1 tron endCdataSectionHandler(handlerArg);
3274 1.1 tron #if 0
3275 1.1 tron /* see comment under XML_TOK_CDATA_SECT_OPEN */
3276 1.1 tron else if (characterDataHandler)
3277 1.1 tron characterDataHandler(handlerArg, dataBuf, 0);
3278 1.1 tron #endif
3279 1.1 tron else if (defaultHandler)
3280 1.1 tron reportDefault(parser, enc, s, next);
3281 1.1 tron *startPtr = next;
3282 1.1 tron *nextPtr = next;
3283 1.1 tron if (ps_parsing == XML_FINISHED)
3284 1.1 tron return XML_ERROR_ABORTED;
3285 1.1 tron else
3286 1.1 tron return XML_ERROR_NONE;
3287 1.1 tron case XML_TOK_DATA_NEWLINE:
3288 1.1 tron if (characterDataHandler) {
3289 1.1 tron XML_Char c = 0xA;
3290 1.1 tron characterDataHandler(handlerArg, &c, 1);
3291 1.1 tron }
3292 1.1 tron else if (defaultHandler)
3293 1.1 tron reportDefault(parser, enc, s, next);
3294 1.1 tron break;
3295 1.1 tron case XML_TOK_DATA_CHARS:
3296 1.1 tron {
3297 1.1 tron XML_CharacterDataHandler charDataHandler = characterDataHandler;
3298 1.1 tron if (charDataHandler) {
3299 1.1 tron if (MUST_CONVERT(enc, s)) {
3300 1.1 tron for (;;) {
3301 1.1 tron ICHAR *dataPtr = (ICHAR *)dataBuf;
3302 1.5 spz const enum XML_Convert_Result convert_res = XmlConvert(enc, &s, next, &dataPtr, (ICHAR *)dataBufEnd);
3303 1.1 tron *eventEndPP = next;
3304 1.1 tron charDataHandler(handlerArg, dataBuf,
3305 1.1 tron (int)(dataPtr - (ICHAR *)dataBuf));
3306 1.5 spz if ((convert_res == XML_CONVERT_COMPLETED) || (convert_res == XML_CONVERT_INPUT_INCOMPLETE))
3307 1.1 tron break;
3308 1.1 tron *eventPP = s;
3309 1.1 tron }
3310 1.1 tron }
3311 1.1 tron else
3312 1.1 tron charDataHandler(handlerArg,
3313 1.1 tron (XML_Char *)s,
3314 1.1 tron (int)((XML_Char *)next - (XML_Char *)s));
3315 1.1 tron }
3316 1.1 tron else if (defaultHandler)
3317 1.1 tron reportDefault(parser, enc, s, next);
3318 1.1 tron }
3319 1.1 tron break;
3320 1.1 tron case XML_TOK_INVALID:
3321 1.1 tron *eventPP = next;
3322 1.1 tron return XML_ERROR_INVALID_TOKEN;
3323 1.1 tron case XML_TOK_PARTIAL_CHAR:
3324 1.1 tron if (haveMore) {
3325 1.1 tron *nextPtr = s;
3326 1.1 tron return XML_ERROR_NONE;
3327 1.1 tron }
3328 1.1 tron return XML_ERROR_PARTIAL_CHAR;
3329 1.1 tron case XML_TOK_PARTIAL:
3330 1.1 tron case XML_TOK_NONE:
3331 1.1 tron if (haveMore) {
3332 1.1 tron *nextPtr = s;
3333 1.1 tron return XML_ERROR_NONE;
3334 1.1 tron }
3335 1.1 tron return XML_ERROR_UNCLOSED_CDATA_SECTION;
3336 1.1 tron default:
3337 1.1 tron *eventPP = next;
3338 1.1 tron return XML_ERROR_UNEXPECTED_STATE;
3339 1.1 tron }
3340 1.1 tron
3341 1.1 tron *eventPP = s = next;
3342 1.1 tron switch (ps_parsing) {
3343 1.1 tron case XML_SUSPENDED:
3344 1.1 tron *nextPtr = next;
3345 1.1 tron return XML_ERROR_NONE;
3346 1.1 tron case XML_FINISHED:
3347 1.1 tron return XML_ERROR_ABORTED;
3348 1.1 tron default: ;
3349 1.1 tron }
3350 1.1 tron }
3351 1.1 tron /* not reached */
3352 1.1 tron }
3353 1.1 tron
3354 1.1 tron #ifdef XML_DTD
3355 1.1 tron
3356 1.1 tron /* The idea here is to avoid using stack for each IGNORE section when
3357 1.1 tron the whole file is parsed with one call.
3358 1.1 tron */
3359 1.1 tron static enum XML_Error PTRCALL
3360 1.1 tron ignoreSectionProcessor(XML_Parser parser,
3361 1.1 tron const char *start,
3362 1.1 tron const char *end,
3363 1.1 tron const char **endPtr)
3364 1.1 tron {
3365 1.3 spz enum XML_Error result = doIgnoreSection(parser, encoding, &start, end,
3366 1.1 tron endPtr, (XML_Bool)!ps_finalBuffer);
3367 1.1 tron if (result != XML_ERROR_NONE)
3368 1.1 tron return result;
3369 1.1 tron if (start) {
3370 1.1 tron processor = prologProcessor;
3371 1.1 tron return prologProcessor(parser, start, end, endPtr);
3372 1.1 tron }
3373 1.1 tron return result;
3374 1.1 tron }
3375 1.1 tron
3376 1.1 tron /* startPtr gets set to non-null is the section is closed, and to null
3377 1.1 tron if the section is not yet closed.
3378 1.1 tron */
3379 1.1 tron static enum XML_Error
3380 1.1 tron doIgnoreSection(XML_Parser parser,
3381 1.1 tron const ENCODING *enc,
3382 1.1 tron const char **startPtr,
3383 1.1 tron const char *end,
3384 1.1 tron const char **nextPtr,
3385 1.1 tron XML_Bool haveMore)
3386 1.1 tron {
3387 1.1 tron const char *next;
3388 1.1 tron int tok;
3389 1.1 tron const char *s = *startPtr;
3390 1.1 tron const char **eventPP;
3391 1.1 tron const char **eventEndPP;
3392 1.1 tron if (enc == encoding) {
3393 1.1 tron eventPP = &eventPtr;
3394 1.1 tron *eventPP = s;
3395 1.1 tron eventEndPP = &eventEndPtr;
3396 1.1 tron }
3397 1.1 tron else {
3398 1.1 tron eventPP = &(openInternalEntities->internalEventPtr);
3399 1.1 tron eventEndPP = &(openInternalEntities->internalEventEndPtr);
3400 1.1 tron }
3401 1.1 tron *eventPP = s;
3402 1.1 tron *startPtr = NULL;
3403 1.1 tron tok = XmlIgnoreSectionTok(enc, s, end, &next);
3404 1.1 tron *eventEndPP = next;
3405 1.1 tron switch (tok) {
3406 1.1 tron case XML_TOK_IGNORE_SECT:
3407 1.1 tron if (defaultHandler)
3408 1.1 tron reportDefault(parser, enc, s, next);
3409 1.1 tron *startPtr = next;
3410 1.1 tron *nextPtr = next;
3411 1.1 tron if (ps_parsing == XML_FINISHED)
3412 1.1 tron return XML_ERROR_ABORTED;
3413 1.1 tron else
3414 1.1 tron return XML_ERROR_NONE;
3415 1.1 tron case XML_TOK_INVALID:
3416 1.1 tron *eventPP = next;
3417 1.1 tron return XML_ERROR_INVALID_TOKEN;
3418 1.1 tron case XML_TOK_PARTIAL_CHAR:
3419 1.1 tron if (haveMore) {
3420 1.1 tron *nextPtr = s;
3421 1.1 tron return XML_ERROR_NONE;
3422 1.1 tron }
3423 1.1 tron return XML_ERROR_PARTIAL_CHAR;
3424 1.1 tron case XML_TOK_PARTIAL:
3425 1.1 tron case XML_TOK_NONE:
3426 1.1 tron if (haveMore) {
3427 1.1 tron *nextPtr = s;
3428 1.1 tron return XML_ERROR_NONE;
3429 1.1 tron }
3430 1.1 tron return XML_ERROR_SYNTAX; /* XML_ERROR_UNCLOSED_IGNORE_SECTION */
3431 1.1 tron default:
3432 1.1 tron *eventPP = next;
3433 1.1 tron return XML_ERROR_UNEXPECTED_STATE;
3434 1.1 tron }
3435 1.1 tron /* not reached */
3436 1.1 tron }
3437 1.1 tron
3438 1.1 tron #endif /* XML_DTD */
3439 1.1 tron
3440 1.1 tron static enum XML_Error
3441 1.1 tron initializeEncoding(XML_Parser parser)
3442 1.1 tron {
3443 1.1 tron const char *s;
3444 1.1 tron #ifdef XML_UNICODE
3445 1.1 tron char encodingBuf[128];
3446 1.1 tron if (!protocolEncodingName)
3447 1.1 tron s = NULL;
3448 1.1 tron else {
3449 1.1 tron int i;
3450 1.1 tron for (i = 0; protocolEncodingName[i]; i++) {
3451 1.1 tron if (i == sizeof(encodingBuf) - 1
3452 1.1 tron || (protocolEncodingName[i] & ~0x7f) != 0) {
3453 1.1 tron encodingBuf[0] = '\0';
3454 1.1 tron break;
3455 1.1 tron }
3456 1.1 tron encodingBuf[i] = (char)protocolEncodingName[i];
3457 1.1 tron }
3458 1.1 tron encodingBuf[i] = '\0';
3459 1.1 tron s = encodingBuf;
3460 1.1 tron }
3461 1.1 tron #else
3462 1.1 tron s = protocolEncodingName;
3463 1.1 tron #endif
3464 1.1 tron if ((ns ? XmlInitEncodingNS : XmlInitEncoding)(&initEncoding, &encoding, s))
3465 1.1 tron return XML_ERROR_NONE;
3466 1.1 tron return handleUnknownEncoding(parser, protocolEncodingName);
3467 1.1 tron }
3468 1.1 tron
3469 1.1 tron static enum XML_Error
3470 1.1 tron processXmlDecl(XML_Parser parser, int isGeneralTextEntity,
3471 1.1 tron const char *s, const char *next)
3472 1.1 tron {
3473 1.1 tron const char *encodingName = NULL;
3474 1.1 tron const XML_Char *storedEncName = NULL;
3475 1.1 tron const ENCODING *newEncoding = NULL;
3476 1.1 tron const char *version = NULL;
3477 1.1 tron const char *versionend;
3478 1.1 tron const XML_Char *storedversion = NULL;
3479 1.1 tron int standalone = -1;
3480 1.1 tron if (!(ns
3481 1.1 tron ? XmlParseXmlDeclNS
3482 1.1 tron : XmlParseXmlDecl)(isGeneralTextEntity,
3483 1.1 tron encoding,
3484 1.1 tron s,
3485 1.1 tron next,
3486 1.1 tron &eventPtr,
3487 1.1 tron &version,
3488 1.1 tron &versionend,
3489 1.1 tron &encodingName,
3490 1.1 tron &newEncoding,
3491 1.1 tron &standalone)) {
3492 1.1 tron if (isGeneralTextEntity)
3493 1.1 tron return XML_ERROR_TEXT_DECL;
3494 1.1 tron else
3495 1.1 tron return XML_ERROR_XML_DECL;
3496 1.1 tron }
3497 1.1 tron if (!isGeneralTextEntity && standalone == 1) {
3498 1.1 tron _dtd->standalone = XML_TRUE;
3499 1.1 tron #ifdef XML_DTD
3500 1.1 tron if (paramEntityParsing == XML_PARAM_ENTITY_PARSING_UNLESS_STANDALONE)
3501 1.1 tron paramEntityParsing = XML_PARAM_ENTITY_PARSING_NEVER;
3502 1.1 tron #endif /* XML_DTD */
3503 1.1 tron }
3504 1.1 tron if (xmlDeclHandler) {
3505 1.1 tron if (encodingName != NULL) {
3506 1.1 tron storedEncName = poolStoreString(&temp2Pool,
3507 1.1 tron encoding,
3508 1.1 tron encodingName,
3509 1.1 tron encodingName
3510 1.1 tron + XmlNameLength(encoding, encodingName));
3511 1.1 tron if (!storedEncName)
3512 1.1 tron return XML_ERROR_NO_MEMORY;
3513 1.1 tron poolFinish(&temp2Pool);
3514 1.1 tron }
3515 1.1 tron if (version) {
3516 1.1 tron storedversion = poolStoreString(&temp2Pool,
3517 1.1 tron encoding,
3518 1.1 tron version,
3519 1.1 tron versionend - encoding->minBytesPerChar);
3520 1.1 tron if (!storedversion)
3521 1.1 tron return XML_ERROR_NO_MEMORY;
3522 1.1 tron }
3523 1.1 tron xmlDeclHandler(handlerArg, storedversion, storedEncName, standalone);
3524 1.1 tron }
3525 1.1 tron else if (defaultHandler)
3526 1.1 tron reportDefault(parser, encoding, s, next);
3527 1.1 tron if (protocolEncodingName == NULL) {
3528 1.1 tron if (newEncoding) {
3529 1.1 tron if (newEncoding->minBytesPerChar != encoding->minBytesPerChar) {
3530 1.1 tron eventPtr = encodingName;
3531 1.1 tron return XML_ERROR_INCORRECT_ENCODING;
3532 1.1 tron }
3533 1.1 tron encoding = newEncoding;
3534 1.1 tron }
3535 1.1 tron else if (encodingName) {
3536 1.1 tron enum XML_Error result;
3537 1.1 tron if (!storedEncName) {
3538 1.1 tron storedEncName = poolStoreString(
3539 1.1 tron &temp2Pool, encoding, encodingName,
3540 1.1 tron encodingName + XmlNameLength(encoding, encodingName));
3541 1.1 tron if (!storedEncName)
3542 1.1 tron return XML_ERROR_NO_MEMORY;
3543 1.1 tron }
3544 1.1 tron result = handleUnknownEncoding(parser, storedEncName);
3545 1.1 tron poolClear(&temp2Pool);
3546 1.1 tron if (result == XML_ERROR_UNKNOWN_ENCODING)
3547 1.1 tron eventPtr = encodingName;
3548 1.1 tron return result;
3549 1.1 tron }
3550 1.1 tron }
3551 1.1 tron
3552 1.1 tron if (storedEncName || storedversion)
3553 1.1 tron poolClear(&temp2Pool);
3554 1.1 tron
3555 1.1 tron return XML_ERROR_NONE;
3556 1.1 tron }
3557 1.1 tron
3558 1.1 tron static enum XML_Error
3559 1.1 tron handleUnknownEncoding(XML_Parser parser, const XML_Char *encodingName)
3560 1.1 tron {
3561 1.1 tron if (unknownEncodingHandler) {
3562 1.1 tron XML_Encoding info;
3563 1.1 tron int i;
3564 1.1 tron for (i = 0; i < 256; i++)
3565 1.1 tron info.map[i] = -1;
3566 1.1 tron info.convert = NULL;
3567 1.1 tron info.data = NULL;
3568 1.1 tron info.release = NULL;
3569 1.1 tron if (unknownEncodingHandler(unknownEncodingHandlerData, encodingName,
3570 1.1 tron &info)) {
3571 1.1 tron ENCODING *enc;
3572 1.1 tron unknownEncodingMem = MALLOC(XmlSizeOfUnknownEncoding());
3573 1.1 tron if (!unknownEncodingMem) {
3574 1.1 tron if (info.release)
3575 1.1 tron info.release(info.data);
3576 1.1 tron return XML_ERROR_NO_MEMORY;
3577 1.1 tron }
3578 1.1 tron enc = (ns
3579 1.1 tron ? XmlInitUnknownEncodingNS
3580 1.1 tron : XmlInitUnknownEncoding)(unknownEncodingMem,
3581 1.1 tron info.map,
3582 1.1 tron info.convert,
3583 1.1 tron info.data);
3584 1.1 tron if (enc) {
3585 1.1 tron unknownEncodingData = info.data;
3586 1.1 tron unknownEncodingRelease = info.release;
3587 1.1 tron encoding = enc;
3588 1.1 tron return XML_ERROR_NONE;
3589 1.1 tron }
3590 1.1 tron }
3591 1.1 tron if (info.release != NULL)
3592 1.1 tron info.release(info.data);
3593 1.1 tron }
3594 1.1 tron return XML_ERROR_UNKNOWN_ENCODING;
3595 1.1 tron }
3596 1.1 tron
3597 1.1 tron static enum XML_Error PTRCALL
3598 1.1 tron prologInitProcessor(XML_Parser parser,
3599 1.1 tron const char *s,
3600 1.1 tron const char *end,
3601 1.1 tron const char **nextPtr)
3602 1.1 tron {
3603 1.1 tron enum XML_Error result = initializeEncoding(parser);
3604 1.1 tron if (result != XML_ERROR_NONE)
3605 1.1 tron return result;
3606 1.1 tron processor = prologProcessor;
3607 1.1 tron return prologProcessor(parser, s, end, nextPtr);
3608 1.1 tron }
3609 1.1 tron
3610 1.1 tron #ifdef XML_DTD
3611 1.1 tron
3612 1.1 tron static enum XML_Error PTRCALL
3613 1.1 tron externalParEntInitProcessor(XML_Parser parser,
3614 1.1 tron const char *s,
3615 1.1 tron const char *end,
3616 1.1 tron const char **nextPtr)
3617 1.1 tron {
3618 1.1 tron enum XML_Error result = initializeEncoding(parser);
3619 1.1 tron if (result != XML_ERROR_NONE)
3620 1.1 tron return result;
3621 1.1 tron
3622 1.1 tron /* we know now that XML_Parse(Buffer) has been called,
3623 1.1 tron so we consider the external parameter entity read */
3624 1.1 tron _dtd->paramEntityRead = XML_TRUE;
3625 1.1 tron
3626 1.1 tron if (prologState.inEntityValue) {
3627 1.1 tron processor = entityValueInitProcessor;
3628 1.1 tron return entityValueInitProcessor(parser, s, end, nextPtr);
3629 1.1 tron }
3630 1.1 tron else {
3631 1.1 tron processor = externalParEntProcessor;
3632 1.1 tron return externalParEntProcessor(parser, s, end, nextPtr);
3633 1.1 tron }
3634 1.1 tron }
3635 1.1 tron
3636 1.1 tron static enum XML_Error PTRCALL
3637 1.1 tron entityValueInitProcessor(XML_Parser parser,
3638 1.1 tron const char *s,
3639 1.1 tron const char *end,
3640 1.1 tron const char **nextPtr)
3641 1.1 tron {
3642 1.1 tron int tok;
3643 1.1 tron const char *start = s;
3644 1.1 tron const char *next = start;
3645 1.1 tron eventPtr = start;
3646 1.1 tron
3647 1.3 spz for (;;) {
3648 1.1 tron tok = XmlPrologTok(encoding, start, end, &next);
3649 1.1 tron eventEndPtr = next;
3650 1.1 tron if (tok <= 0) {
3651 1.1 tron if (!ps_finalBuffer && tok != XML_TOK_INVALID) {
3652 1.1 tron *nextPtr = s;
3653 1.1 tron return XML_ERROR_NONE;
3654 1.1 tron }
3655 1.1 tron switch (tok) {
3656 1.1 tron case XML_TOK_INVALID:
3657 1.1 tron return XML_ERROR_INVALID_TOKEN;
3658 1.1 tron case XML_TOK_PARTIAL:
3659 1.1 tron return XML_ERROR_UNCLOSED_TOKEN;
3660 1.1 tron case XML_TOK_PARTIAL_CHAR:
3661 1.1 tron return XML_ERROR_PARTIAL_CHAR;
3662 1.1 tron case XML_TOK_NONE: /* start == end */
3663 1.1 tron default:
3664 1.1 tron break;
3665 1.1 tron }
3666 1.1 tron /* found end of entity value - can store it now */
3667 1.1 tron return storeEntityValue(parser, encoding, s, end);
3668 1.1 tron }
3669 1.1 tron else if (tok == XML_TOK_XML_DECL) {
3670 1.1 tron enum XML_Error result;
3671 1.1 tron result = processXmlDecl(parser, 0, start, next);
3672 1.1 tron if (result != XML_ERROR_NONE)
3673 1.1 tron return result;
3674 1.1 tron switch (ps_parsing) {
3675 1.3 spz case XML_SUSPENDED:
3676 1.1 tron *nextPtr = next;
3677 1.1 tron return XML_ERROR_NONE;
3678 1.1 tron case XML_FINISHED:
3679 1.1 tron return XML_ERROR_ABORTED;
3680 1.1 tron default:
3681 1.1 tron *nextPtr = next;
3682 1.1 tron }
3683 1.1 tron /* stop scanning for text declaration - we found one */
3684 1.1 tron processor = entityValueProcessor;
3685 1.1 tron return entityValueProcessor(parser, next, end, nextPtr);
3686 1.1 tron }
3687 1.1 tron /* If we are at the end of the buffer, this would cause XmlPrologTok to
3688 1.1 tron return XML_TOK_NONE on the next call, which would then cause the
3689 1.1 tron function to exit with *nextPtr set to s - that is what we want for other
3690 1.1 tron tokens, but not for the BOM - we would rather like to skip it;
3691 1.1 tron then, when this routine is entered the next time, XmlPrologTok will
3692 1.1 tron return XML_TOK_INVALID, since the BOM is still in the buffer
3693 1.1 tron */
3694 1.1 tron else if (tok == XML_TOK_BOM && next == end && !ps_finalBuffer) {
3695 1.1 tron *nextPtr = next;
3696 1.1 tron return XML_ERROR_NONE;
3697 1.1 tron }
3698 1.1 tron start = next;
3699 1.1 tron eventPtr = start;
3700 1.1 tron }
3701 1.1 tron }
3702 1.1 tron
3703 1.1 tron static enum XML_Error PTRCALL
3704 1.1 tron externalParEntProcessor(XML_Parser parser,
3705 1.1 tron const char *s,
3706 1.1 tron const char *end,
3707 1.1 tron const char **nextPtr)
3708 1.1 tron {
3709 1.1 tron const char *next = s;
3710 1.1 tron int tok;
3711 1.1 tron
3712 1.1 tron tok = XmlPrologTok(encoding, s, end, &next);
3713 1.1 tron if (tok <= 0) {
3714 1.1 tron if (!ps_finalBuffer && tok != XML_TOK_INVALID) {
3715 1.1 tron *nextPtr = s;
3716 1.1 tron return XML_ERROR_NONE;
3717 1.1 tron }
3718 1.1 tron switch (tok) {
3719 1.1 tron case XML_TOK_INVALID:
3720 1.1 tron return XML_ERROR_INVALID_TOKEN;
3721 1.1 tron case XML_TOK_PARTIAL:
3722 1.1 tron return XML_ERROR_UNCLOSED_TOKEN;
3723 1.1 tron case XML_TOK_PARTIAL_CHAR:
3724 1.1 tron return XML_ERROR_PARTIAL_CHAR;
3725 1.1 tron case XML_TOK_NONE: /* start == end */
3726 1.1 tron default:
3727 1.1 tron break;
3728 1.1 tron }
3729 1.1 tron }
3730 1.1 tron /* This would cause the next stage, i.e. doProlog to be passed XML_TOK_BOM.
3731 1.1 tron However, when parsing an external subset, doProlog will not accept a BOM
3732 1.1 tron as valid, and report a syntax error, so we have to skip the BOM
3733 1.1 tron */
3734 1.1 tron else if (tok == XML_TOK_BOM) {
3735 1.1 tron s = next;
3736 1.1 tron tok = XmlPrologTok(encoding, s, end, &next);
3737 1.1 tron }
3738 1.1 tron
3739 1.1 tron processor = prologProcessor;
3740 1.3 spz return doProlog(parser, encoding, s, end, tok, next,
3741 1.1 tron nextPtr, (XML_Bool)!ps_finalBuffer);
3742 1.1 tron }
3743 1.1 tron
3744 1.1 tron static enum XML_Error PTRCALL
3745 1.1 tron entityValueProcessor(XML_Parser parser,
3746 1.1 tron const char *s,
3747 1.1 tron const char *end,
3748 1.1 tron const char **nextPtr)
3749 1.1 tron {
3750 1.1 tron const char *start = s;
3751 1.1 tron const char *next = s;
3752 1.1 tron const ENCODING *enc = encoding;
3753 1.1 tron int tok;
3754 1.1 tron
3755 1.1 tron for (;;) {
3756 1.1 tron tok = XmlPrologTok(enc, start, end, &next);
3757 1.1 tron if (tok <= 0) {
3758 1.1 tron if (!ps_finalBuffer && tok != XML_TOK_INVALID) {
3759 1.1 tron *nextPtr = s;
3760 1.1 tron return XML_ERROR_NONE;
3761 1.1 tron }
3762 1.1 tron switch (tok) {
3763 1.1 tron case XML_TOK_INVALID:
3764 1.1 tron return XML_ERROR_INVALID_TOKEN;
3765 1.1 tron case XML_TOK_PARTIAL:
3766 1.1 tron return XML_ERROR_UNCLOSED_TOKEN;
3767 1.1 tron case XML_TOK_PARTIAL_CHAR:
3768 1.1 tron return XML_ERROR_PARTIAL_CHAR;
3769 1.1 tron case XML_TOK_NONE: /* start == end */
3770 1.1 tron default:
3771 1.1 tron break;
3772 1.1 tron }
3773 1.1 tron /* found end of entity value - can store it now */
3774 1.1 tron return storeEntityValue(parser, enc, s, end);
3775 1.1 tron }
3776 1.1 tron start = next;
3777 1.1 tron }
3778 1.1 tron }
3779 1.1 tron
3780 1.1 tron #endif /* XML_DTD */
3781 1.1 tron
3782 1.1 tron static enum XML_Error PTRCALL
3783 1.1 tron prologProcessor(XML_Parser parser,
3784 1.1 tron const char *s,
3785 1.1 tron const char *end,
3786 1.1 tron const char **nextPtr)
3787 1.1 tron {
3788 1.1 tron const char *next = s;
3789 1.1 tron int tok = XmlPrologTok(encoding, s, end, &next);
3790 1.3 spz return doProlog(parser, encoding, s, end, tok, next,
3791 1.1 tron nextPtr, (XML_Bool)!ps_finalBuffer);
3792 1.1 tron }
3793 1.1 tron
3794 1.1 tron static enum XML_Error
3795 1.1 tron doProlog(XML_Parser parser,
3796 1.1 tron const ENCODING *enc,
3797 1.1 tron const char *s,
3798 1.1 tron const char *end,
3799 1.1 tron int tok,
3800 1.1 tron const char *next,
3801 1.1 tron const char **nextPtr,
3802 1.1 tron XML_Bool haveMore)
3803 1.1 tron {
3804 1.1 tron #ifdef XML_DTD
3805 1.1 tron static const XML_Char externalSubsetName[] = { ASCII_HASH , '\0' };
3806 1.1 tron #endif /* XML_DTD */
3807 1.3 spz static const XML_Char atypeCDATA[] =
3808 1.1 tron { ASCII_C, ASCII_D, ASCII_A, ASCII_T, ASCII_A, '\0' };
3809 1.1 tron static const XML_Char atypeID[] = { ASCII_I, ASCII_D, '\0' };
3810 1.1 tron static const XML_Char atypeIDREF[] =
3811 1.1 tron { ASCII_I, ASCII_D, ASCII_R, ASCII_E, ASCII_F, '\0' };
3812 1.1 tron static const XML_Char atypeIDREFS[] =
3813 1.1 tron { ASCII_I, ASCII_D, ASCII_R, ASCII_E, ASCII_F, ASCII_S, '\0' };
3814 1.1 tron static const XML_Char atypeENTITY[] =
3815 1.1 tron { ASCII_E, ASCII_N, ASCII_T, ASCII_I, ASCII_T, ASCII_Y, '\0' };
3816 1.1 tron static const XML_Char atypeENTITIES[] = { ASCII_E, ASCII_N,
3817 1.1 tron ASCII_T, ASCII_I, ASCII_T, ASCII_I, ASCII_E, ASCII_S, '\0' };
3818 1.1 tron static const XML_Char atypeNMTOKEN[] = {
3819 1.1 tron ASCII_N, ASCII_M, ASCII_T, ASCII_O, ASCII_K, ASCII_E, ASCII_N, '\0' };
3820 1.1 tron static const XML_Char atypeNMTOKENS[] = { ASCII_N, ASCII_M, ASCII_T,
3821 1.1 tron ASCII_O, ASCII_K, ASCII_E, ASCII_N, ASCII_S, '\0' };
3822 1.1 tron static const XML_Char notationPrefix[] = { ASCII_N, ASCII_O, ASCII_T,
3823 1.1 tron ASCII_A, ASCII_T, ASCII_I, ASCII_O, ASCII_N, ASCII_LPAREN, '\0' };
3824 1.1 tron static const XML_Char enumValueSep[] = { ASCII_PIPE, '\0' };
3825 1.1 tron static const XML_Char enumValueStart[] = { ASCII_LPAREN, '\0' };
3826 1.1 tron
3827 1.1 tron /* save one level of indirection */
3828 1.3 spz DTD * const dtd = _dtd;
3829 1.1 tron
3830 1.1 tron const char **eventPP;
3831 1.1 tron const char **eventEndPP;
3832 1.1 tron enum XML_Content_Quant quant;
3833 1.1 tron
3834 1.1 tron if (enc == encoding) {
3835 1.1 tron eventPP = &eventPtr;
3836 1.1 tron eventEndPP = &eventEndPtr;
3837 1.1 tron }
3838 1.1 tron else {
3839 1.1 tron eventPP = &(openInternalEntities->internalEventPtr);
3840 1.1 tron eventEndPP = &(openInternalEntities->internalEventEndPtr);
3841 1.1 tron }
3842 1.1 tron
3843 1.1 tron for (;;) {
3844 1.1 tron int role;
3845 1.1 tron XML_Bool handleDefault = XML_TRUE;
3846 1.1 tron *eventPP = s;
3847 1.1 tron *eventEndPP = next;
3848 1.1 tron if (tok <= 0) {
3849 1.1 tron if (haveMore && tok != XML_TOK_INVALID) {
3850 1.1 tron *nextPtr = s;
3851 1.1 tron return XML_ERROR_NONE;
3852 1.1 tron }
3853 1.1 tron switch (tok) {
3854 1.1 tron case XML_TOK_INVALID:
3855 1.1 tron *eventPP = next;
3856 1.1 tron return XML_ERROR_INVALID_TOKEN;
3857 1.1 tron case XML_TOK_PARTIAL:
3858 1.1 tron return XML_ERROR_UNCLOSED_TOKEN;
3859 1.1 tron case XML_TOK_PARTIAL_CHAR:
3860 1.1 tron return XML_ERROR_PARTIAL_CHAR;
3861 1.2 tron case -XML_TOK_PROLOG_S:
3862 1.3 spz tok = -tok;
3863 1.3 spz break;
3864 1.1 tron case XML_TOK_NONE:
3865 1.1 tron #ifdef XML_DTD
3866 1.1 tron /* for internal PE NOT referenced between declarations */
3867 1.1 tron if (enc != encoding && !openInternalEntities->betweenDecl) {
3868 1.1 tron *nextPtr = s;
3869 1.1 tron return XML_ERROR_NONE;
3870 1.1 tron }
3871 1.1 tron /* WFC: PE Between Declarations - must check that PE contains
3872 1.1 tron complete markup, not only for external PEs, but also for
3873 1.1 tron internal PEs if the reference occurs between declarations.
3874 1.1 tron */
3875 1.1 tron if (isParamEntity || enc != encoding) {
3876 1.1 tron if (XmlTokenRole(&prologState, XML_TOK_NONE, end, end, enc)
3877 1.1 tron == XML_ROLE_ERROR)
3878 1.1 tron return XML_ERROR_INCOMPLETE_PE;
3879 1.1 tron *nextPtr = s;
3880 1.1 tron return XML_ERROR_NONE;
3881 1.1 tron }
3882 1.1 tron #endif /* XML_DTD */
3883 1.1 tron return XML_ERROR_NO_ELEMENTS;
3884 1.1 tron default:
3885 1.1 tron tok = -tok;
3886 1.1 tron next = end;
3887 1.1 tron break;
3888 1.1 tron }
3889 1.1 tron }
3890 1.1 tron role = XmlTokenRole(&prologState, tok, s, next, enc);
3891 1.1 tron switch (role) {
3892 1.1 tron case XML_ROLE_XML_DECL:
3893 1.1 tron {
3894 1.1 tron enum XML_Error result = processXmlDecl(parser, 0, s, next);
3895 1.1 tron if (result != XML_ERROR_NONE)
3896 1.1 tron return result;
3897 1.1 tron enc = encoding;
3898 1.1 tron handleDefault = XML_FALSE;
3899 1.1 tron }
3900 1.1 tron break;
3901 1.1 tron case XML_ROLE_DOCTYPE_NAME:
3902 1.1 tron if (startDoctypeDeclHandler) {
3903 1.1 tron doctypeName = poolStoreString(&tempPool, enc, s, next);
3904 1.1 tron if (!doctypeName)
3905 1.1 tron return XML_ERROR_NO_MEMORY;
3906 1.1 tron poolFinish(&tempPool);
3907 1.1 tron doctypePubid = NULL;
3908 1.1 tron handleDefault = XML_FALSE;
3909 1.1 tron }
3910 1.1 tron doctypeSysid = NULL; /* always initialize to NULL */
3911 1.1 tron break;
3912 1.1 tron case XML_ROLE_DOCTYPE_INTERNAL_SUBSET:
3913 1.1 tron if (startDoctypeDeclHandler) {
3914 1.1 tron startDoctypeDeclHandler(handlerArg, doctypeName, doctypeSysid,
3915 1.1 tron doctypePubid, 1);
3916 1.1 tron doctypeName = NULL;
3917 1.1 tron poolClear(&tempPool);
3918 1.1 tron handleDefault = XML_FALSE;
3919 1.1 tron }
3920 1.1 tron break;
3921 1.1 tron #ifdef XML_DTD
3922 1.1 tron case XML_ROLE_TEXT_DECL:
3923 1.1 tron {
3924 1.1 tron enum XML_Error result = processXmlDecl(parser, 1, s, next);
3925 1.1 tron if (result != XML_ERROR_NONE)
3926 1.1 tron return result;
3927 1.1 tron enc = encoding;
3928 1.1 tron handleDefault = XML_FALSE;
3929 1.1 tron }
3930 1.1 tron break;
3931 1.1 tron #endif /* XML_DTD */
3932 1.1 tron case XML_ROLE_DOCTYPE_PUBLIC_ID:
3933 1.1 tron #ifdef XML_DTD
3934 1.1 tron useForeignDTD = XML_FALSE;
3935 1.3 spz declEntity = (ENTITY *)lookup(parser,
3936 1.3 spz &dtd->paramEntities,
3937 1.1 tron externalSubsetName,
3938 1.1 tron sizeof(ENTITY));
3939 1.1 tron if (!declEntity)
3940 1.1 tron return XML_ERROR_NO_MEMORY;
3941 1.1 tron #endif /* XML_DTD */
3942 1.1 tron dtd->hasParamEntityRefs = XML_TRUE;
3943 1.1 tron if (startDoctypeDeclHandler) {
3944 1.3 spz XML_Char *pubId;
3945 1.1 tron if (!XmlIsPublicId(enc, s, next, eventPP))
3946 1.1 tron return XML_ERROR_PUBLICID;
3947 1.3 spz pubId = poolStoreString(&tempPool, enc,
3948 1.3 spz s + enc->minBytesPerChar,
3949 1.3 spz next - enc->minBytesPerChar);
3950 1.3 spz if (!pubId)
3951 1.1 tron return XML_ERROR_NO_MEMORY;
3952 1.3 spz normalizePublicId(pubId);
3953 1.1 tron poolFinish(&tempPool);
3954 1.3 spz doctypePubid = pubId;
3955 1.1 tron handleDefault = XML_FALSE;
3956 1.1 tron goto alreadyChecked;
3957 1.1 tron }
3958 1.1 tron /* fall through */
3959 1.1 tron case XML_ROLE_ENTITY_PUBLIC_ID:
3960 1.1 tron if (!XmlIsPublicId(enc, s, next, eventPP))
3961 1.1 tron return XML_ERROR_PUBLICID;
3962 1.1 tron alreadyChecked:
3963 1.1 tron if (dtd->keepProcessing && declEntity) {
3964 1.1 tron XML_Char *tem = poolStoreString(&dtd->pool,
3965 1.1 tron enc,
3966 1.1 tron s + enc->minBytesPerChar,
3967 1.1 tron next - enc->minBytesPerChar);
3968 1.1 tron if (!tem)
3969 1.1 tron return XML_ERROR_NO_MEMORY;
3970 1.1 tron normalizePublicId(tem);
3971 1.1 tron declEntity->publicId = tem;
3972 1.1 tron poolFinish(&dtd->pool);
3973 1.1 tron if (entityDeclHandler)
3974 1.1 tron handleDefault = XML_FALSE;
3975 1.1 tron }
3976 1.1 tron break;
3977 1.1 tron case XML_ROLE_DOCTYPE_CLOSE:
3978 1.1 tron if (doctypeName) {
3979 1.1 tron startDoctypeDeclHandler(handlerArg, doctypeName,
3980 1.1 tron doctypeSysid, doctypePubid, 0);
3981 1.1 tron poolClear(&tempPool);
3982 1.1 tron handleDefault = XML_FALSE;
3983 1.1 tron }
3984 1.1 tron /* doctypeSysid will be non-NULL in the case of a previous
3985 1.1 tron XML_ROLE_DOCTYPE_SYSTEM_ID, even if startDoctypeDeclHandler
3986 1.1 tron was not set, indicating an external subset
3987 1.1 tron */
3988 1.1 tron #ifdef XML_DTD
3989 1.1 tron if (doctypeSysid || useForeignDTD) {
3990 1.1 tron XML_Bool hadParamEntityRefs = dtd->hasParamEntityRefs;
3991 1.1 tron dtd->hasParamEntityRefs = XML_TRUE;
3992 1.1 tron if (paramEntityParsing && externalEntityRefHandler) {
3993 1.3 spz ENTITY *entity = (ENTITY *)lookup(parser,
3994 1.3 spz &dtd->paramEntities,
3995 1.1 tron externalSubsetName,
3996 1.1 tron sizeof(ENTITY));
3997 1.1 tron if (!entity)
3998 1.1 tron return XML_ERROR_NO_MEMORY;
3999 1.1 tron if (useForeignDTD)
4000 1.1 tron entity->base = curBase;
4001 1.1 tron dtd->paramEntityRead = XML_FALSE;
4002 1.1 tron if (!externalEntityRefHandler(externalEntityRefHandlerArg,
4003 1.1 tron 0,
4004 1.1 tron entity->base,
4005 1.1 tron entity->systemId,
4006 1.1 tron entity->publicId))
4007 1.1 tron return XML_ERROR_EXTERNAL_ENTITY_HANDLING;
4008 1.1 tron if (dtd->paramEntityRead) {
4009 1.3 spz if (!dtd->standalone &&
4010 1.3 spz notStandaloneHandler &&
4011 1.1 tron !notStandaloneHandler(handlerArg))
4012 1.1 tron return XML_ERROR_NOT_STANDALONE;
4013 1.1 tron }
4014 1.1 tron /* if we didn't read the foreign DTD then this means that there
4015 1.1 tron is no external subset and we must reset dtd->hasParamEntityRefs
4016 1.1 tron */
4017 1.1 tron else if (!doctypeSysid)
4018 1.1 tron dtd->hasParamEntityRefs = hadParamEntityRefs;
4019 1.1 tron /* end of DTD - no need to update dtd->keepProcessing */
4020 1.1 tron }
4021 1.1 tron useForeignDTD = XML_FALSE;
4022 1.1 tron }
4023 1.1 tron #endif /* XML_DTD */
4024 1.1 tron if (endDoctypeDeclHandler) {
4025 1.1 tron endDoctypeDeclHandler(handlerArg);
4026 1.1 tron handleDefault = XML_FALSE;
4027 1.1 tron }
4028 1.1 tron break;
4029 1.1 tron case XML_ROLE_INSTANCE_START:
4030 1.1 tron #ifdef XML_DTD
4031 1.1 tron /* if there is no DOCTYPE declaration then now is the
4032 1.1 tron last chance to read the foreign DTD
4033 1.1 tron */
4034 1.1 tron if (useForeignDTD) {
4035 1.1 tron XML_Bool hadParamEntityRefs = dtd->hasParamEntityRefs;
4036 1.1 tron dtd->hasParamEntityRefs = XML_TRUE;
4037 1.1 tron if (paramEntityParsing && externalEntityRefHandler) {
4038 1.3 spz ENTITY *entity = (ENTITY *)lookup(parser, &dtd->paramEntities,
4039 1.1 tron externalSubsetName,
4040 1.1 tron sizeof(ENTITY));
4041 1.1 tron if (!entity)
4042 1.1 tron return XML_ERROR_NO_MEMORY;
4043 1.1 tron entity->base = curBase;
4044 1.1 tron dtd->paramEntityRead = XML_FALSE;
4045 1.1 tron if (!externalEntityRefHandler(externalEntityRefHandlerArg,
4046 1.1 tron 0,
4047 1.1 tron entity->base,
4048 1.1 tron entity->systemId,
4049 1.1 tron entity->publicId))
4050 1.1 tron return XML_ERROR_EXTERNAL_ENTITY_HANDLING;
4051 1.1 tron if (dtd->paramEntityRead) {
4052 1.1 tron if (!dtd->standalone &&
4053 1.1 tron notStandaloneHandler &&
4054 1.1 tron !notStandaloneHandler(handlerArg))
4055 1.1 tron return XML_ERROR_NOT_STANDALONE;
4056 1.1 tron }
4057 1.1 tron /* if we didn't read the foreign DTD then this means that there
4058 1.1 tron is no external subset and we must reset dtd->hasParamEntityRefs
4059 1.1 tron */
4060 1.1 tron else
4061 1.1 tron dtd->hasParamEntityRefs = hadParamEntityRefs;
4062 1.1 tron /* end of DTD - no need to update dtd->keepProcessing */
4063 1.1 tron }
4064 1.1 tron }
4065 1.1 tron #endif /* XML_DTD */
4066 1.1 tron processor = contentProcessor;
4067 1.1 tron return contentProcessor(parser, s, end, nextPtr);
4068 1.1 tron case XML_ROLE_ATTLIST_ELEMENT_NAME:
4069 1.1 tron declElementType = getElementType(parser, enc, s, next);
4070 1.1 tron if (!declElementType)
4071 1.1 tron return XML_ERROR_NO_MEMORY;
4072 1.1 tron goto checkAttListDeclHandler;
4073 1.1 tron case XML_ROLE_ATTRIBUTE_NAME:
4074 1.1 tron declAttributeId = getAttributeId(parser, enc, s, next);
4075 1.1 tron if (!declAttributeId)
4076 1.1 tron return XML_ERROR_NO_MEMORY;
4077 1.1 tron declAttributeIsCdata = XML_FALSE;
4078 1.1 tron declAttributeType = NULL;
4079 1.1 tron declAttributeIsId = XML_FALSE;
4080 1.1 tron goto checkAttListDeclHandler;
4081 1.1 tron case XML_ROLE_ATTRIBUTE_TYPE_CDATA:
4082 1.1 tron declAttributeIsCdata = XML_TRUE;
4083 1.1 tron declAttributeType = atypeCDATA;
4084 1.1 tron goto checkAttListDeclHandler;
4085 1.1 tron case XML_ROLE_ATTRIBUTE_TYPE_ID:
4086 1.1 tron declAttributeIsId = XML_TRUE;
4087 1.1 tron declAttributeType = atypeID;
4088 1.1 tron goto checkAttListDeclHandler;
4089 1.1 tron case XML_ROLE_ATTRIBUTE_TYPE_IDREF:
4090 1.1 tron declAttributeType = atypeIDREF;
4091 1.1 tron goto checkAttListDeclHandler;
4092 1.1 tron case XML_ROLE_ATTRIBUTE_TYPE_IDREFS:
4093 1.1 tron declAttributeType = atypeIDREFS;
4094 1.1 tron goto checkAttListDeclHandler;
4095 1.1 tron case XML_ROLE_ATTRIBUTE_TYPE_ENTITY:
4096 1.1 tron declAttributeType = atypeENTITY;
4097 1.1 tron goto checkAttListDeclHandler;
4098 1.1 tron case XML_ROLE_ATTRIBUTE_TYPE_ENTITIES:
4099 1.1 tron declAttributeType = atypeENTITIES;
4100 1.1 tron goto checkAttListDeclHandler;
4101 1.1 tron case XML_ROLE_ATTRIBUTE_TYPE_NMTOKEN:
4102 1.1 tron declAttributeType = atypeNMTOKEN;
4103 1.1 tron goto checkAttListDeclHandler;
4104 1.1 tron case XML_ROLE_ATTRIBUTE_TYPE_NMTOKENS:
4105 1.1 tron declAttributeType = atypeNMTOKENS;
4106 1.1 tron checkAttListDeclHandler:
4107 1.1 tron if (dtd->keepProcessing && attlistDeclHandler)
4108 1.1 tron handleDefault = XML_FALSE;
4109 1.1 tron break;
4110 1.1 tron case XML_ROLE_ATTRIBUTE_ENUM_VALUE:
4111 1.1 tron case XML_ROLE_ATTRIBUTE_NOTATION_VALUE:
4112 1.1 tron if (dtd->keepProcessing && attlistDeclHandler) {
4113 1.1 tron const XML_Char *prefix;
4114 1.1 tron if (declAttributeType) {
4115 1.1 tron prefix = enumValueSep;
4116 1.1 tron }
4117 1.1 tron else {
4118 1.1 tron prefix = (role == XML_ROLE_ATTRIBUTE_NOTATION_VALUE
4119 1.1 tron ? notationPrefix
4120 1.1 tron : enumValueStart);
4121 1.1 tron }
4122 1.1 tron if (!poolAppendString(&tempPool, prefix))
4123 1.1 tron return XML_ERROR_NO_MEMORY;
4124 1.1 tron if (!poolAppend(&tempPool, enc, s, next))
4125 1.1 tron return XML_ERROR_NO_MEMORY;
4126 1.1 tron declAttributeType = tempPool.start;
4127 1.1 tron handleDefault = XML_FALSE;
4128 1.1 tron }
4129 1.1 tron break;
4130 1.1 tron case XML_ROLE_IMPLIED_ATTRIBUTE_VALUE:
4131 1.1 tron case XML_ROLE_REQUIRED_ATTRIBUTE_VALUE:
4132 1.1 tron if (dtd->keepProcessing) {
4133 1.1 tron if (!defineAttribute(declElementType, declAttributeId,
4134 1.1 tron declAttributeIsCdata, declAttributeIsId,
4135 1.1 tron 0, parser))
4136 1.1 tron return XML_ERROR_NO_MEMORY;
4137 1.1 tron if (attlistDeclHandler && declAttributeType) {
4138 1.1 tron if (*declAttributeType == XML_T(ASCII_LPAREN)
4139 1.1 tron || (*declAttributeType == XML_T(ASCII_N)
4140 1.1 tron && declAttributeType[1] == XML_T(ASCII_O))) {
4141 1.1 tron /* Enumerated or Notation type */
4142 1.1 tron if (!poolAppendChar(&tempPool, XML_T(ASCII_RPAREN))
4143 1.1 tron || !poolAppendChar(&tempPool, XML_T('\0')))
4144 1.1 tron return XML_ERROR_NO_MEMORY;
4145 1.1 tron declAttributeType = tempPool.start;
4146 1.1 tron poolFinish(&tempPool);
4147 1.1 tron }
4148 1.1 tron *eventEndPP = s;
4149 1.1 tron attlistDeclHandler(handlerArg, declElementType->name,
4150 1.1 tron declAttributeId->name, declAttributeType,
4151 1.1 tron 0, role == XML_ROLE_REQUIRED_ATTRIBUTE_VALUE);
4152 1.1 tron poolClear(&tempPool);
4153 1.1 tron handleDefault = XML_FALSE;
4154 1.1 tron }
4155 1.1 tron }
4156 1.1 tron break;
4157 1.1 tron case XML_ROLE_DEFAULT_ATTRIBUTE_VALUE:
4158 1.1 tron case XML_ROLE_FIXED_ATTRIBUTE_VALUE:
4159 1.1 tron if (dtd->keepProcessing) {
4160 1.1 tron const XML_Char *attVal;
4161 1.1 tron enum XML_Error result =
4162 1.1 tron storeAttributeValue(parser, enc, declAttributeIsCdata,
4163 1.1 tron s + enc->minBytesPerChar,
4164 1.1 tron next - enc->minBytesPerChar,
4165 1.1 tron &dtd->pool);
4166 1.1 tron if (result)
4167 1.1 tron return result;
4168 1.1 tron attVal = poolStart(&dtd->pool);
4169 1.1 tron poolFinish(&dtd->pool);
4170 1.1 tron /* ID attributes aren't allowed to have a default */
4171 1.1 tron if (!defineAttribute(declElementType, declAttributeId,
4172 1.1 tron declAttributeIsCdata, XML_FALSE, attVal, parser))
4173 1.1 tron return XML_ERROR_NO_MEMORY;
4174 1.1 tron if (attlistDeclHandler && declAttributeType) {
4175 1.1 tron if (*declAttributeType == XML_T(ASCII_LPAREN)
4176 1.1 tron || (*declAttributeType == XML_T(ASCII_N)
4177 1.1 tron && declAttributeType[1] == XML_T(ASCII_O))) {
4178 1.1 tron /* Enumerated or Notation type */
4179 1.1 tron if (!poolAppendChar(&tempPool, XML_T(ASCII_RPAREN))
4180 1.1 tron || !poolAppendChar(&tempPool, XML_T('\0')))
4181 1.1 tron return XML_ERROR_NO_MEMORY;
4182 1.1 tron declAttributeType = tempPool.start;
4183 1.1 tron poolFinish(&tempPool);
4184 1.1 tron }
4185 1.1 tron *eventEndPP = s;
4186 1.1 tron attlistDeclHandler(handlerArg, declElementType->name,
4187 1.1 tron declAttributeId->name, declAttributeType,
4188 1.1 tron attVal,
4189 1.1 tron role == XML_ROLE_FIXED_ATTRIBUTE_VALUE);
4190 1.1 tron poolClear(&tempPool);
4191 1.1 tron handleDefault = XML_FALSE;
4192 1.1 tron }
4193 1.1 tron }
4194 1.1 tron break;
4195 1.1 tron case XML_ROLE_ENTITY_VALUE:
4196 1.1 tron if (dtd->keepProcessing) {
4197 1.1 tron enum XML_Error result = storeEntityValue(parser, enc,
4198 1.1 tron s + enc->minBytesPerChar,
4199 1.1 tron next - enc->minBytesPerChar);
4200 1.1 tron if (declEntity) {
4201 1.1 tron declEntity->textPtr = poolStart(&dtd->entityValuePool);
4202 1.1 tron declEntity->textLen = (int)(poolLength(&dtd->entityValuePool));
4203 1.1 tron poolFinish(&dtd->entityValuePool);
4204 1.1 tron if (entityDeclHandler) {
4205 1.1 tron *eventEndPP = s;
4206 1.1 tron entityDeclHandler(handlerArg,
4207 1.1 tron declEntity->name,
4208 1.1 tron declEntity->is_param,
4209 1.1 tron declEntity->textPtr,
4210 1.1 tron declEntity->textLen,
4211 1.1 tron curBase, 0, 0, 0);
4212 1.1 tron handleDefault = XML_FALSE;
4213 1.1 tron }
4214 1.1 tron }
4215 1.1 tron else
4216 1.1 tron poolDiscard(&dtd->entityValuePool);
4217 1.1 tron if (result != XML_ERROR_NONE)
4218 1.1 tron return result;
4219 1.1 tron }
4220 1.1 tron break;
4221 1.1 tron case XML_ROLE_DOCTYPE_SYSTEM_ID:
4222 1.1 tron #ifdef XML_DTD
4223 1.1 tron useForeignDTD = XML_FALSE;
4224 1.1 tron #endif /* XML_DTD */
4225 1.1 tron dtd->hasParamEntityRefs = XML_TRUE;
4226 1.1 tron if (startDoctypeDeclHandler) {
4227 1.1 tron doctypeSysid = poolStoreString(&tempPool, enc,
4228 1.1 tron s + enc->minBytesPerChar,
4229 1.1 tron next - enc->minBytesPerChar);
4230 1.1 tron if (doctypeSysid == NULL)
4231 1.1 tron return XML_ERROR_NO_MEMORY;
4232 1.1 tron poolFinish(&tempPool);
4233 1.1 tron handleDefault = XML_FALSE;
4234 1.1 tron }
4235 1.1 tron #ifdef XML_DTD
4236 1.1 tron else
4237 1.1 tron /* use externalSubsetName to make doctypeSysid non-NULL
4238 1.1 tron for the case where no startDoctypeDeclHandler is set */
4239 1.1 tron doctypeSysid = externalSubsetName;
4240 1.1 tron #endif /* XML_DTD */
4241 1.1 tron if (!dtd->standalone
4242 1.1 tron #ifdef XML_DTD
4243 1.1 tron && !paramEntityParsing
4244 1.1 tron #endif /* XML_DTD */
4245 1.1 tron && notStandaloneHandler
4246 1.1 tron && !notStandaloneHandler(handlerArg))
4247 1.1 tron return XML_ERROR_NOT_STANDALONE;
4248 1.1 tron #ifndef XML_DTD
4249 1.1 tron break;
4250 1.1 tron #else /* XML_DTD */
4251 1.1 tron if (!declEntity) {
4252 1.3 spz declEntity = (ENTITY *)lookup(parser,
4253 1.3 spz &dtd->paramEntities,
4254 1.1 tron externalSubsetName,
4255 1.1 tron sizeof(ENTITY));
4256 1.1 tron if (!declEntity)
4257 1.1 tron return XML_ERROR_NO_MEMORY;
4258 1.1 tron declEntity->publicId = NULL;
4259 1.1 tron }
4260 1.1 tron /* fall through */
4261 1.1 tron #endif /* XML_DTD */
4262 1.1 tron case XML_ROLE_ENTITY_SYSTEM_ID:
4263 1.1 tron if (dtd->keepProcessing && declEntity) {
4264 1.1 tron declEntity->systemId = poolStoreString(&dtd->pool, enc,
4265 1.1 tron s + enc->minBytesPerChar,
4266 1.1 tron next - enc->minBytesPerChar);
4267 1.1 tron if (!declEntity->systemId)
4268 1.1 tron return XML_ERROR_NO_MEMORY;
4269 1.1 tron declEntity->base = curBase;
4270 1.1 tron poolFinish(&dtd->pool);
4271 1.1 tron if (entityDeclHandler)
4272 1.1 tron handleDefault = XML_FALSE;
4273 1.1 tron }
4274 1.1 tron break;
4275 1.1 tron case XML_ROLE_ENTITY_COMPLETE:
4276 1.1 tron if (dtd->keepProcessing && declEntity && entityDeclHandler) {
4277 1.1 tron *eventEndPP = s;
4278 1.1 tron entityDeclHandler(handlerArg,
4279 1.1 tron declEntity->name,
4280 1.1 tron declEntity->is_param,
4281 1.1 tron 0,0,
4282 1.1 tron declEntity->base,
4283 1.1 tron declEntity->systemId,
4284 1.1 tron declEntity->publicId,
4285 1.1 tron 0);
4286 1.1 tron handleDefault = XML_FALSE;
4287 1.1 tron }
4288 1.1 tron break;
4289 1.1 tron case XML_ROLE_ENTITY_NOTATION_NAME:
4290 1.1 tron if (dtd->keepProcessing && declEntity) {
4291 1.1 tron declEntity->notation = poolStoreString(&dtd->pool, enc, s, next);
4292 1.1 tron if (!declEntity->notation)
4293 1.1 tron return XML_ERROR_NO_MEMORY;
4294 1.1 tron poolFinish(&dtd->pool);
4295 1.1 tron if (unparsedEntityDeclHandler) {
4296 1.1 tron *eventEndPP = s;
4297 1.1 tron unparsedEntityDeclHandler(handlerArg,
4298 1.1 tron declEntity->name,
4299 1.1 tron declEntity->base,
4300 1.1 tron declEntity->systemId,
4301 1.1 tron declEntity->publicId,
4302 1.1 tron declEntity->notation);
4303 1.1 tron handleDefault = XML_FALSE;
4304 1.1 tron }
4305 1.1 tron else if (entityDeclHandler) {
4306 1.1 tron *eventEndPP = s;
4307 1.1 tron entityDeclHandler(handlerArg,
4308 1.1 tron declEntity->name,
4309 1.1 tron 0,0,0,
4310 1.1 tron declEntity->base,
4311 1.1 tron declEntity->systemId,
4312 1.1 tron declEntity->publicId,
4313 1.1 tron declEntity->notation);
4314 1.1 tron handleDefault = XML_FALSE;
4315 1.1 tron }
4316 1.1 tron }
4317 1.1 tron break;
4318 1.1 tron case XML_ROLE_GENERAL_ENTITY_NAME:
4319 1.1 tron {
4320 1.1 tron if (XmlPredefinedEntityName(enc, s, next)) {
4321 1.1 tron declEntity = NULL;
4322 1.1 tron break;
4323 1.1 tron }
4324 1.1 tron if (dtd->keepProcessing) {
4325 1.1 tron const XML_Char *name = poolStoreString(&dtd->pool, enc, s, next);
4326 1.1 tron if (!name)
4327 1.1 tron return XML_ERROR_NO_MEMORY;
4328 1.3 spz declEntity = (ENTITY *)lookup(parser, &dtd->generalEntities, name,
4329 1.1 tron sizeof(ENTITY));
4330 1.1 tron if (!declEntity)
4331 1.1 tron return XML_ERROR_NO_MEMORY;
4332 1.1 tron if (declEntity->name != name) {
4333 1.1 tron poolDiscard(&dtd->pool);
4334 1.1 tron declEntity = NULL;
4335 1.1 tron }
4336 1.1 tron else {
4337 1.1 tron poolFinish(&dtd->pool);
4338 1.1 tron declEntity->publicId = NULL;
4339 1.1 tron declEntity->is_param = XML_FALSE;
4340 1.1 tron /* if we have a parent parser or are reading an internal parameter
4341 1.1 tron entity, then the entity declaration is not considered "internal"
4342 1.1 tron */
4343 1.1 tron declEntity->is_internal = !(parentParser || openInternalEntities);
4344 1.1 tron if (entityDeclHandler)
4345 1.1 tron handleDefault = XML_FALSE;
4346 1.1 tron }
4347 1.1 tron }
4348 1.1 tron else {
4349 1.1 tron poolDiscard(&dtd->pool);
4350 1.1 tron declEntity = NULL;
4351 1.1 tron }
4352 1.1 tron }
4353 1.1 tron break;
4354 1.1 tron case XML_ROLE_PARAM_ENTITY_NAME:
4355 1.1 tron #ifdef XML_DTD
4356 1.1 tron if (dtd->keepProcessing) {
4357 1.1 tron const XML_Char *name = poolStoreString(&dtd->pool, enc, s, next);
4358 1.1 tron if (!name)
4359 1.1 tron return XML_ERROR_NO_MEMORY;
4360 1.3 spz declEntity = (ENTITY *)lookup(parser, &dtd->paramEntities,
4361 1.1 tron name, sizeof(ENTITY));
4362 1.1 tron if (!declEntity)
4363 1.1 tron return XML_ERROR_NO_MEMORY;
4364 1.1 tron if (declEntity->name != name) {
4365 1.1 tron poolDiscard(&dtd->pool);
4366 1.1 tron declEntity = NULL;
4367 1.1 tron }
4368 1.1 tron else {
4369 1.1 tron poolFinish(&dtd->pool);
4370 1.1 tron declEntity->publicId = NULL;
4371 1.1 tron declEntity->is_param = XML_TRUE;
4372 1.1 tron /* if we have a parent parser or are reading an internal parameter
4373 1.1 tron entity, then the entity declaration is not considered "internal"
4374 1.1 tron */
4375 1.1 tron declEntity->is_internal = !(parentParser || openInternalEntities);
4376 1.1 tron if (entityDeclHandler)
4377 1.1 tron handleDefault = XML_FALSE;
4378 1.1 tron }
4379 1.1 tron }
4380 1.1 tron else {
4381 1.1 tron poolDiscard(&dtd->pool);
4382 1.1 tron declEntity = NULL;
4383 1.1 tron }
4384 1.1 tron #else /* not XML_DTD */
4385 1.1 tron declEntity = NULL;
4386 1.1 tron #endif /* XML_DTD */
4387 1.1 tron break;
4388 1.1 tron case XML_ROLE_NOTATION_NAME:
4389 1.1 tron declNotationPublicId = NULL;
4390 1.1 tron declNotationName = NULL;
4391 1.1 tron if (notationDeclHandler) {
4392 1.1 tron declNotationName = poolStoreString(&tempPool, enc, s, next);
4393 1.1 tron if (!declNotationName)
4394 1.1 tron return XML_ERROR_NO_MEMORY;
4395 1.1 tron poolFinish(&tempPool);
4396 1.1 tron handleDefault = XML_FALSE;
4397 1.1 tron }
4398 1.1 tron break;
4399 1.1 tron case XML_ROLE_NOTATION_PUBLIC_ID:
4400 1.1 tron if (!XmlIsPublicId(enc, s, next, eventPP))
4401 1.1 tron return XML_ERROR_PUBLICID;
4402 1.1 tron if (declNotationName) { /* means notationDeclHandler != NULL */
4403 1.1 tron XML_Char *tem = poolStoreString(&tempPool,
4404 1.1 tron enc,
4405 1.1 tron s + enc->minBytesPerChar,
4406 1.1 tron next - enc->minBytesPerChar);
4407 1.1 tron if (!tem)
4408 1.1 tron return XML_ERROR_NO_MEMORY;
4409 1.1 tron normalizePublicId(tem);
4410 1.1 tron declNotationPublicId = tem;
4411 1.1 tron poolFinish(&tempPool);
4412 1.1 tron handleDefault = XML_FALSE;
4413 1.1 tron }
4414 1.1 tron break;
4415 1.1 tron case XML_ROLE_NOTATION_SYSTEM_ID:
4416 1.1 tron if (declNotationName && notationDeclHandler) {
4417 1.1 tron const XML_Char *systemId
4418 1.1 tron = poolStoreString(&tempPool, enc,
4419 1.1 tron s + enc->minBytesPerChar,
4420 1.1 tron next - enc->minBytesPerChar);
4421 1.1 tron if (!systemId)
4422 1.1 tron return XML_ERROR_NO_MEMORY;
4423 1.1 tron *eventEndPP = s;
4424 1.1 tron notationDeclHandler(handlerArg,
4425 1.1 tron declNotationName,
4426 1.1 tron curBase,
4427 1.1 tron systemId,
4428 1.1 tron declNotationPublicId);
4429 1.1 tron handleDefault = XML_FALSE;
4430 1.1 tron }
4431 1.1 tron poolClear(&tempPool);
4432 1.1 tron break;
4433 1.1 tron case XML_ROLE_NOTATION_NO_SYSTEM_ID:
4434 1.1 tron if (declNotationPublicId && notationDeclHandler) {
4435 1.1 tron *eventEndPP = s;
4436 1.1 tron notationDeclHandler(handlerArg,
4437 1.1 tron declNotationName,
4438 1.1 tron curBase,
4439 1.1 tron 0,
4440 1.1 tron declNotationPublicId);
4441 1.1 tron handleDefault = XML_FALSE;
4442 1.1 tron }
4443 1.1 tron poolClear(&tempPool);
4444 1.1 tron break;
4445 1.1 tron case XML_ROLE_ERROR:
4446 1.1 tron switch (tok) {
4447 1.1 tron case XML_TOK_PARAM_ENTITY_REF:
4448 1.1 tron /* PE references in internal subset are
4449 1.3 spz not allowed within declarations. */
4450 1.1 tron return XML_ERROR_PARAM_ENTITY_REF;
4451 1.1 tron case XML_TOK_XML_DECL:
4452 1.1 tron return XML_ERROR_MISPLACED_XML_PI;
4453 1.1 tron default:
4454 1.1 tron return XML_ERROR_SYNTAX;
4455 1.1 tron }
4456 1.1 tron #ifdef XML_DTD
4457 1.1 tron case XML_ROLE_IGNORE_SECT:
4458 1.1 tron {
4459 1.1 tron enum XML_Error result;
4460 1.1 tron if (defaultHandler)
4461 1.1 tron reportDefault(parser, enc, s, next);
4462 1.1 tron handleDefault = XML_FALSE;
4463 1.1 tron result = doIgnoreSection(parser, enc, &next, end, nextPtr, haveMore);
4464 1.1 tron if (result != XML_ERROR_NONE)
4465 1.1 tron return result;
4466 1.1 tron else if (!next) {
4467 1.1 tron processor = ignoreSectionProcessor;
4468 1.1 tron return result;
4469 1.1 tron }
4470 1.1 tron }
4471 1.1 tron break;
4472 1.1 tron #endif /* XML_DTD */
4473 1.1 tron case XML_ROLE_GROUP_OPEN:
4474 1.1 tron if (prologState.level >= groupSize) {
4475 1.1 tron if (groupSize) {
4476 1.1 tron char *temp = (char *)REALLOC(groupConnector, groupSize *= 2);
4477 1.1 tron if (temp == NULL)
4478 1.1 tron return XML_ERROR_NO_MEMORY;
4479 1.1 tron groupConnector = temp;
4480 1.1 tron if (dtd->scaffIndex) {
4481 1.1 tron int *temp = (int *)REALLOC(dtd->scaffIndex,
4482 1.1 tron groupSize * sizeof(int));
4483 1.1 tron if (temp == NULL)
4484 1.1 tron return XML_ERROR_NO_MEMORY;
4485 1.1 tron dtd->scaffIndex = temp;
4486 1.1 tron }
4487 1.1 tron }
4488 1.1 tron else {
4489 1.1 tron groupConnector = (char *)MALLOC(groupSize = 32);
4490 1.1 tron if (!groupConnector)
4491 1.1 tron return XML_ERROR_NO_MEMORY;
4492 1.1 tron }
4493 1.1 tron }
4494 1.1 tron groupConnector[prologState.level] = 0;
4495 1.1 tron if (dtd->in_eldecl) {
4496 1.1 tron int myindex = nextScaffoldPart(parser);
4497 1.1 tron if (myindex < 0)
4498 1.1 tron return XML_ERROR_NO_MEMORY;
4499 1.1 tron dtd->scaffIndex[dtd->scaffLevel] = myindex;
4500 1.1 tron dtd->scaffLevel++;
4501 1.1 tron dtd->scaffold[myindex].type = XML_CTYPE_SEQ;
4502 1.1 tron if (elementDeclHandler)
4503 1.1 tron handleDefault = XML_FALSE;
4504 1.1 tron }
4505 1.1 tron break;
4506 1.1 tron case XML_ROLE_GROUP_SEQUENCE:
4507 1.1 tron if (groupConnector[prologState.level] == ASCII_PIPE)
4508 1.1 tron return XML_ERROR_SYNTAX;
4509 1.1 tron groupConnector[prologState.level] = ASCII_COMMA;
4510 1.1 tron if (dtd->in_eldecl && elementDeclHandler)
4511 1.1 tron handleDefault = XML_FALSE;
4512 1.1 tron break;
4513 1.1 tron case XML_ROLE_GROUP_CHOICE:
4514 1.1 tron if (groupConnector[prologState.level] == ASCII_COMMA)
4515 1.1 tron return XML_ERROR_SYNTAX;
4516 1.1 tron if (dtd->in_eldecl
4517 1.1 tron && !groupConnector[prologState.level]
4518 1.1 tron && (dtd->scaffold[dtd->scaffIndex[dtd->scaffLevel - 1]].type
4519 1.1 tron != XML_CTYPE_MIXED)
4520 1.1 tron ) {
4521 1.1 tron dtd->scaffold[dtd->scaffIndex[dtd->scaffLevel - 1]].type
4522 1.1 tron = XML_CTYPE_CHOICE;
4523 1.1 tron if (elementDeclHandler)
4524 1.1 tron handleDefault = XML_FALSE;
4525 1.1 tron }
4526 1.1 tron groupConnector[prologState.level] = ASCII_PIPE;
4527 1.1 tron break;
4528 1.1 tron case XML_ROLE_PARAM_ENTITY_REF:
4529 1.1 tron #ifdef XML_DTD
4530 1.1 tron case XML_ROLE_INNER_PARAM_ENTITY_REF:
4531 1.1 tron dtd->hasParamEntityRefs = XML_TRUE;
4532 1.1 tron if (!paramEntityParsing)
4533 1.1 tron dtd->keepProcessing = dtd->standalone;
4534 1.1 tron else {
4535 1.1 tron const XML_Char *name;
4536 1.1 tron ENTITY *entity;
4537 1.1 tron name = poolStoreString(&dtd->pool, enc,
4538 1.1 tron s + enc->minBytesPerChar,
4539 1.1 tron next - enc->minBytesPerChar);
4540 1.1 tron if (!name)
4541 1.1 tron return XML_ERROR_NO_MEMORY;
4542 1.3 spz entity = (ENTITY *)lookup(parser, &dtd->paramEntities, name, 0);
4543 1.1 tron poolDiscard(&dtd->pool);
4544 1.1 tron /* first, determine if a check for an existing declaration is needed;
4545 1.1 tron if yes, check that the entity exists, and that it is internal,
4546 1.1 tron otherwise call the skipped entity handler
4547 1.1 tron */
4548 1.1 tron if (prologState.documentEntity &&
4549 1.1 tron (dtd->standalone
4550 1.1 tron ? !openInternalEntities
4551 1.1 tron : !dtd->hasParamEntityRefs)) {
4552 1.1 tron if (!entity)
4553 1.1 tron return XML_ERROR_UNDEFINED_ENTITY;
4554 1.1 tron else if (!entity->is_internal)
4555 1.1 tron return XML_ERROR_ENTITY_DECLARED_IN_PE;
4556 1.1 tron }
4557 1.1 tron else if (!entity) {
4558 1.1 tron dtd->keepProcessing = dtd->standalone;
4559 1.1 tron /* cannot report skipped entities in declarations */
4560 1.1 tron if ((role == XML_ROLE_PARAM_ENTITY_REF) && skippedEntityHandler) {
4561 1.1 tron skippedEntityHandler(handlerArg, name, 1);
4562 1.1 tron handleDefault = XML_FALSE;
4563 1.1 tron }
4564 1.1 tron break;
4565 1.1 tron }
4566 1.1 tron if (entity->open)
4567 1.1 tron return XML_ERROR_RECURSIVE_ENTITY_REF;
4568 1.1 tron if (entity->textPtr) {
4569 1.1 tron enum XML_Error result;
4570 1.3 spz XML_Bool betweenDecl =
4571 1.1 tron (role == XML_ROLE_PARAM_ENTITY_REF ? XML_TRUE : XML_FALSE);
4572 1.1 tron result = processInternalEntity(parser, entity, betweenDecl);
4573 1.1 tron if (result != XML_ERROR_NONE)
4574 1.1 tron return result;
4575 1.1 tron handleDefault = XML_FALSE;
4576 1.1 tron break;
4577 1.1 tron }
4578 1.1 tron if (externalEntityRefHandler) {
4579 1.1 tron dtd->paramEntityRead = XML_FALSE;
4580 1.1 tron entity->open = XML_TRUE;
4581 1.1 tron if (!externalEntityRefHandler(externalEntityRefHandlerArg,
4582 1.1 tron 0,
4583 1.1 tron entity->base,
4584 1.1 tron entity->systemId,
4585 1.1 tron entity->publicId)) {
4586 1.1 tron entity->open = XML_FALSE;
4587 1.1 tron return XML_ERROR_EXTERNAL_ENTITY_HANDLING;
4588 1.1 tron }
4589 1.1 tron entity->open = XML_FALSE;
4590 1.1 tron handleDefault = XML_FALSE;
4591 1.1 tron if (!dtd->paramEntityRead) {
4592 1.1 tron dtd->keepProcessing = dtd->standalone;
4593 1.1 tron break;
4594 1.1 tron }
4595 1.1 tron }
4596 1.1 tron else {
4597 1.1 tron dtd->keepProcessing = dtd->standalone;
4598 1.1 tron break;
4599 1.1 tron }
4600 1.1 tron }
4601 1.1 tron #endif /* XML_DTD */
4602 1.1 tron if (!dtd->standalone &&
4603 1.1 tron notStandaloneHandler &&
4604 1.1 tron !notStandaloneHandler(handlerArg))
4605 1.1 tron return XML_ERROR_NOT_STANDALONE;
4606 1.1 tron break;
4607 1.1 tron
4608 1.1 tron /* Element declaration stuff */
4609 1.1 tron
4610 1.1 tron case XML_ROLE_ELEMENT_NAME:
4611 1.1 tron if (elementDeclHandler) {
4612 1.1 tron declElementType = getElementType(parser, enc, s, next);
4613 1.1 tron if (!declElementType)
4614 1.1 tron return XML_ERROR_NO_MEMORY;
4615 1.1 tron dtd->scaffLevel = 0;
4616 1.1 tron dtd->scaffCount = 0;
4617 1.1 tron dtd->in_eldecl = XML_TRUE;
4618 1.1 tron handleDefault = XML_FALSE;
4619 1.1 tron }
4620 1.1 tron break;
4621 1.1 tron
4622 1.1 tron case XML_ROLE_CONTENT_ANY:
4623 1.1 tron case XML_ROLE_CONTENT_EMPTY:
4624 1.1 tron if (dtd->in_eldecl) {
4625 1.1 tron if (elementDeclHandler) {
4626 1.1 tron XML_Content * content = (XML_Content *) MALLOC(sizeof(XML_Content));
4627 1.1 tron if (!content)
4628 1.1 tron return XML_ERROR_NO_MEMORY;
4629 1.1 tron content->quant = XML_CQUANT_NONE;
4630 1.1 tron content->name = NULL;
4631 1.1 tron content->numchildren = 0;
4632 1.1 tron content->children = NULL;
4633 1.1 tron content->type = ((role == XML_ROLE_CONTENT_ANY) ?
4634 1.1 tron XML_CTYPE_ANY :
4635 1.1 tron XML_CTYPE_EMPTY);
4636 1.1 tron *eventEndPP = s;
4637 1.1 tron elementDeclHandler(handlerArg, declElementType->name, content);
4638 1.1 tron handleDefault = XML_FALSE;
4639 1.1 tron }
4640 1.1 tron dtd->in_eldecl = XML_FALSE;
4641 1.1 tron }
4642 1.1 tron break;
4643 1.1 tron
4644 1.1 tron case XML_ROLE_CONTENT_PCDATA:
4645 1.1 tron if (dtd->in_eldecl) {
4646 1.1 tron dtd->scaffold[dtd->scaffIndex[dtd->scaffLevel - 1]].type
4647 1.1 tron = XML_CTYPE_MIXED;
4648 1.1 tron if (elementDeclHandler)
4649 1.1 tron handleDefault = XML_FALSE;
4650 1.1 tron }
4651 1.1 tron break;
4652 1.1 tron
4653 1.1 tron case XML_ROLE_CONTENT_ELEMENT:
4654 1.1 tron quant = XML_CQUANT_NONE;
4655 1.1 tron goto elementContent;
4656 1.1 tron case XML_ROLE_CONTENT_ELEMENT_OPT:
4657 1.1 tron quant = XML_CQUANT_OPT;
4658 1.1 tron goto elementContent;
4659 1.1 tron case XML_ROLE_CONTENT_ELEMENT_REP:
4660 1.1 tron quant = XML_CQUANT_REP;
4661 1.1 tron goto elementContent;
4662 1.1 tron case XML_ROLE_CONTENT_ELEMENT_PLUS:
4663 1.1 tron quant = XML_CQUANT_PLUS;
4664 1.1 tron elementContent:
4665 1.1 tron if (dtd->in_eldecl) {
4666 1.1 tron ELEMENT_TYPE *el;
4667 1.1 tron const XML_Char *name;
4668 1.1 tron int nameLen;
4669 1.1 tron const char *nxt = (quant == XML_CQUANT_NONE
4670 1.1 tron ? next
4671 1.1 tron : next - enc->minBytesPerChar);
4672 1.1 tron int myindex = nextScaffoldPart(parser);
4673 1.1 tron if (myindex < 0)
4674 1.1 tron return XML_ERROR_NO_MEMORY;
4675 1.1 tron dtd->scaffold[myindex].type = XML_CTYPE_NAME;
4676 1.1 tron dtd->scaffold[myindex].quant = quant;
4677 1.1 tron el = getElementType(parser, enc, s, nxt);
4678 1.1 tron if (!el)
4679 1.1 tron return XML_ERROR_NO_MEMORY;
4680 1.1 tron name = el->name;
4681 1.1 tron dtd->scaffold[myindex].name = name;
4682 1.1 tron nameLen = 0;
4683 1.1 tron for (; name[nameLen++]; );
4684 1.1 tron dtd->contentStringLen += nameLen;
4685 1.1 tron if (elementDeclHandler)
4686 1.1 tron handleDefault = XML_FALSE;
4687 1.1 tron }
4688 1.1 tron break;
4689 1.1 tron
4690 1.1 tron case XML_ROLE_GROUP_CLOSE:
4691 1.1 tron quant = XML_CQUANT_NONE;
4692 1.1 tron goto closeGroup;
4693 1.1 tron case XML_ROLE_GROUP_CLOSE_OPT:
4694 1.1 tron quant = XML_CQUANT_OPT;
4695 1.1 tron goto closeGroup;
4696 1.1 tron case XML_ROLE_GROUP_CLOSE_REP:
4697 1.1 tron quant = XML_CQUANT_REP;
4698 1.1 tron goto closeGroup;
4699 1.1 tron case XML_ROLE_GROUP_CLOSE_PLUS:
4700 1.1 tron quant = XML_CQUANT_PLUS;
4701 1.1 tron closeGroup:
4702 1.1 tron if (dtd->in_eldecl) {
4703 1.1 tron if (elementDeclHandler)
4704 1.1 tron handleDefault = XML_FALSE;
4705 1.1 tron dtd->scaffLevel--;
4706 1.1 tron dtd->scaffold[dtd->scaffIndex[dtd->scaffLevel]].quant = quant;
4707 1.1 tron if (dtd->scaffLevel == 0) {
4708 1.1 tron if (!handleDefault) {
4709 1.1 tron XML_Content *model = build_model(parser);
4710 1.1 tron if (!model)
4711 1.1 tron return XML_ERROR_NO_MEMORY;
4712 1.1 tron *eventEndPP = s;
4713 1.1 tron elementDeclHandler(handlerArg, declElementType->name, model);
4714 1.1 tron }
4715 1.1 tron dtd->in_eldecl = XML_FALSE;
4716 1.1 tron dtd->contentStringLen = 0;
4717 1.1 tron }
4718 1.1 tron }
4719 1.1 tron break;
4720 1.1 tron /* End element declaration stuff */
4721 1.1 tron
4722 1.1 tron case XML_ROLE_PI:
4723 1.1 tron if (!reportProcessingInstruction(parser, enc, s, next))
4724 1.1 tron return XML_ERROR_NO_MEMORY;
4725 1.1 tron handleDefault = XML_FALSE;
4726 1.1 tron break;
4727 1.1 tron case XML_ROLE_COMMENT:
4728 1.1 tron if (!reportComment(parser, enc, s, next))
4729 1.1 tron return XML_ERROR_NO_MEMORY;
4730 1.1 tron handleDefault = XML_FALSE;
4731 1.1 tron break;
4732 1.1 tron case XML_ROLE_NONE:
4733 1.1 tron switch (tok) {
4734 1.1 tron case XML_TOK_BOM:
4735 1.1 tron handleDefault = XML_FALSE;
4736 1.1 tron break;
4737 1.1 tron }
4738 1.1 tron break;
4739 1.1 tron case XML_ROLE_DOCTYPE_NONE:
4740 1.1 tron if (startDoctypeDeclHandler)
4741 1.1 tron handleDefault = XML_FALSE;
4742 1.1 tron break;
4743 1.1 tron case XML_ROLE_ENTITY_NONE:
4744 1.1 tron if (dtd->keepProcessing && entityDeclHandler)
4745 1.1 tron handleDefault = XML_FALSE;
4746 1.1 tron break;
4747 1.1 tron case XML_ROLE_NOTATION_NONE:
4748 1.1 tron if (notationDeclHandler)
4749 1.1 tron handleDefault = XML_FALSE;
4750 1.1 tron break;
4751 1.1 tron case XML_ROLE_ATTLIST_NONE:
4752 1.1 tron if (dtd->keepProcessing && attlistDeclHandler)
4753 1.1 tron handleDefault = XML_FALSE;
4754 1.1 tron break;
4755 1.1 tron case XML_ROLE_ELEMENT_NONE:
4756 1.1 tron if (elementDeclHandler)
4757 1.1 tron handleDefault = XML_FALSE;
4758 1.1 tron break;
4759 1.1 tron } /* end of big switch */
4760 1.1 tron
4761 1.1 tron if (handleDefault && defaultHandler)
4762 1.1 tron reportDefault(parser, enc, s, next);
4763 1.1 tron
4764 1.1 tron switch (ps_parsing) {
4765 1.3 spz case XML_SUSPENDED:
4766 1.1 tron *nextPtr = next;
4767 1.1 tron return XML_ERROR_NONE;
4768 1.1 tron case XML_FINISHED:
4769 1.1 tron return XML_ERROR_ABORTED;
4770 1.1 tron default:
4771 1.1 tron s = next;
4772 1.1 tron tok = XmlPrologTok(enc, s, end, &next);
4773 1.1 tron }
4774 1.1 tron }
4775 1.1 tron /* not reached */
4776 1.1 tron }
4777 1.1 tron
4778 1.1 tron static enum XML_Error PTRCALL
4779 1.1 tron epilogProcessor(XML_Parser parser,
4780 1.1 tron const char *s,
4781 1.1 tron const char *end,
4782 1.1 tron const char **nextPtr)
4783 1.1 tron {
4784 1.1 tron processor = epilogProcessor;
4785 1.1 tron eventPtr = s;
4786 1.1 tron for (;;) {
4787 1.1 tron const char *next = NULL;
4788 1.1 tron int tok = XmlPrologTok(encoding, s, end, &next);
4789 1.1 tron eventEndPtr = next;
4790 1.1 tron switch (tok) {
4791 1.1 tron /* report partial linebreak - it might be the last token */
4792 1.1 tron case -XML_TOK_PROLOG_S:
4793 1.1 tron if (defaultHandler) {
4794 1.1 tron reportDefault(parser, encoding, s, next);
4795 1.1 tron if (ps_parsing == XML_FINISHED)
4796 1.1 tron return XML_ERROR_ABORTED;
4797 1.1 tron }
4798 1.1 tron *nextPtr = next;
4799 1.1 tron return XML_ERROR_NONE;
4800 1.1 tron case XML_TOK_NONE:
4801 1.1 tron *nextPtr = s;
4802 1.1 tron return XML_ERROR_NONE;
4803 1.1 tron case XML_TOK_PROLOG_S:
4804 1.1 tron if (defaultHandler)
4805 1.1 tron reportDefault(parser, encoding, s, next);
4806 1.1 tron break;
4807 1.1 tron case XML_TOK_PI:
4808 1.1 tron if (!reportProcessingInstruction(parser, encoding, s, next))
4809 1.1 tron return XML_ERROR_NO_MEMORY;
4810 1.1 tron break;
4811 1.1 tron case XML_TOK_COMMENT:
4812 1.1 tron if (!reportComment(parser, encoding, s, next))
4813 1.1 tron return XML_ERROR_NO_MEMORY;
4814 1.1 tron break;
4815 1.1 tron case XML_TOK_INVALID:
4816 1.1 tron eventPtr = next;
4817 1.1 tron return XML_ERROR_INVALID_TOKEN;
4818 1.1 tron case XML_TOK_PARTIAL:
4819 1.1 tron if (!ps_finalBuffer) {
4820 1.1 tron *nextPtr = s;
4821 1.1 tron return XML_ERROR_NONE;
4822 1.1 tron }
4823 1.1 tron return XML_ERROR_UNCLOSED_TOKEN;
4824 1.1 tron case XML_TOK_PARTIAL_CHAR:
4825 1.1 tron if (!ps_finalBuffer) {
4826 1.1 tron *nextPtr = s;
4827 1.1 tron return XML_ERROR_NONE;
4828 1.1 tron }
4829 1.1 tron return XML_ERROR_PARTIAL_CHAR;
4830 1.1 tron default:
4831 1.1 tron return XML_ERROR_JUNK_AFTER_DOC_ELEMENT;
4832 1.1 tron }
4833 1.1 tron eventPtr = s = next;
4834 1.1 tron switch (ps_parsing) {
4835 1.3 spz case XML_SUSPENDED:
4836 1.1 tron *nextPtr = next;
4837 1.1 tron return XML_ERROR_NONE;
4838 1.1 tron case XML_FINISHED:
4839 1.1 tron return XML_ERROR_ABORTED;
4840 1.1 tron default: ;
4841 1.1 tron }
4842 1.1 tron }
4843 1.1 tron }
4844 1.1 tron
4845 1.1 tron static enum XML_Error
4846 1.1 tron processInternalEntity(XML_Parser parser, ENTITY *entity,
4847 1.1 tron XML_Bool betweenDecl)
4848 1.1 tron {
4849 1.1 tron const char *textStart, *textEnd;
4850 1.1 tron const char *next;
4851 1.1 tron enum XML_Error result;
4852 1.1 tron OPEN_INTERNAL_ENTITY *openEntity;
4853 1.1 tron
4854 1.1 tron if (freeInternalEntities) {
4855 1.1 tron openEntity = freeInternalEntities;
4856 1.1 tron freeInternalEntities = openEntity->next;
4857 1.1 tron }
4858 1.1 tron else {
4859 1.1 tron openEntity = (OPEN_INTERNAL_ENTITY *)MALLOC(sizeof(OPEN_INTERNAL_ENTITY));
4860 1.1 tron if (!openEntity)
4861 1.1 tron return XML_ERROR_NO_MEMORY;
4862 1.1 tron }
4863 1.1 tron entity->open = XML_TRUE;
4864 1.1 tron entity->processed = 0;
4865 1.1 tron openEntity->next = openInternalEntities;
4866 1.1 tron openInternalEntities = openEntity;
4867 1.1 tron openEntity->entity = entity;
4868 1.1 tron openEntity->startTagLevel = tagLevel;
4869 1.1 tron openEntity->betweenDecl = betweenDecl;
4870 1.1 tron openEntity->internalEventPtr = NULL;
4871 1.1 tron openEntity->internalEventEndPtr = NULL;
4872 1.1 tron textStart = (char *)entity->textPtr;
4873 1.1 tron textEnd = (char *)(entity->textPtr + entity->textLen);
4874 1.1 tron
4875 1.1 tron #ifdef XML_DTD
4876 1.1 tron if (entity->is_param) {
4877 1.1 tron int tok = XmlPrologTok(internalEncoding, textStart, textEnd, &next);
4878 1.3 spz result = doProlog(parser, internalEncoding, textStart, textEnd, tok,
4879 1.1 tron next, &next, XML_FALSE);
4880 1.1 tron }
4881 1.3 spz else
4882 1.1 tron #endif /* XML_DTD */
4883 1.3 spz result = doContent(parser, tagLevel, internalEncoding, textStart,
4884 1.1 tron textEnd, &next, XML_FALSE);
4885 1.1 tron
4886 1.1 tron if (result == XML_ERROR_NONE) {
4887 1.1 tron if (textEnd != next && ps_parsing == XML_SUSPENDED) {
4888 1.1 tron entity->processed = (int)(next - textStart);
4889 1.1 tron processor = internalEntityProcessor;
4890 1.1 tron }
4891 1.1 tron else {
4892 1.1 tron entity->open = XML_FALSE;
4893 1.1 tron openInternalEntities = openEntity->next;
4894 1.1 tron /* put openEntity back in list of free instances */
4895 1.1 tron openEntity->next = freeInternalEntities;
4896 1.1 tron freeInternalEntities = openEntity;
4897 1.1 tron }
4898 1.1 tron }
4899 1.1 tron return result;
4900 1.1 tron }
4901 1.1 tron
4902 1.1 tron static enum XML_Error PTRCALL
4903 1.1 tron internalEntityProcessor(XML_Parser parser,
4904 1.1 tron const char *s,
4905 1.1 tron const char *end,
4906 1.1 tron const char **nextPtr)
4907 1.1 tron {
4908 1.1 tron ENTITY *entity;
4909 1.1 tron const char *textStart, *textEnd;
4910 1.1 tron const char *next;
4911 1.1 tron enum XML_Error result;
4912 1.1 tron OPEN_INTERNAL_ENTITY *openEntity = openInternalEntities;
4913 1.1 tron if (!openEntity)
4914 1.1 tron return XML_ERROR_UNEXPECTED_STATE;
4915 1.1 tron
4916 1.1 tron entity = openEntity->entity;
4917 1.1 tron textStart = ((char *)entity->textPtr) + entity->processed;
4918 1.1 tron textEnd = (char *)(entity->textPtr + entity->textLen);
4919 1.1 tron
4920 1.1 tron #ifdef XML_DTD
4921 1.1 tron if (entity->is_param) {
4922 1.1 tron int tok = XmlPrologTok(internalEncoding, textStart, textEnd, &next);
4923 1.3 spz result = doProlog(parser, internalEncoding, textStart, textEnd, tok,
4924 1.1 tron next, &next, XML_FALSE);
4925 1.1 tron }
4926 1.1 tron else
4927 1.1 tron #endif /* XML_DTD */
4928 1.3 spz result = doContent(parser, openEntity->startTagLevel, internalEncoding,
4929 1.3 spz textStart, textEnd, &next, XML_FALSE);
4930 1.1 tron
4931 1.1 tron if (result != XML_ERROR_NONE)
4932 1.1 tron return result;
4933 1.1 tron else if (textEnd != next && ps_parsing == XML_SUSPENDED) {
4934 1.1 tron entity->processed = (int)(next - (char *)entity->textPtr);
4935 1.1 tron return result;
4936 1.1 tron }
4937 1.1 tron else {
4938 1.1 tron entity->open = XML_FALSE;
4939 1.1 tron openInternalEntities = openEntity->next;
4940 1.1 tron /* put openEntity back in list of free instances */
4941 1.1 tron openEntity->next = freeInternalEntities;
4942 1.1 tron freeInternalEntities = openEntity;
4943 1.1 tron }
4944 1.1 tron
4945 1.1 tron #ifdef XML_DTD
4946 1.1 tron if (entity->is_param) {
4947 1.1 tron int tok;
4948 1.1 tron processor = prologProcessor;
4949 1.1 tron tok = XmlPrologTok(encoding, s, end, &next);
4950 1.3 spz return doProlog(parser, encoding, s, end, tok, next, nextPtr,
4951 1.1 tron (XML_Bool)!ps_finalBuffer);
4952 1.1 tron }
4953 1.1 tron else
4954 1.1 tron #endif /* XML_DTD */
4955 1.1 tron {
4956 1.1 tron processor = contentProcessor;
4957 1.1 tron /* see externalEntityContentProcessor vs contentProcessor */
4958 1.1 tron return doContent(parser, parentParser ? 1 : 0, encoding, s, end,
4959 1.3 spz nextPtr, (XML_Bool)!ps_finalBuffer);
4960 1.3 spz }
4961 1.1 tron }
4962 1.1 tron
4963 1.1 tron static enum XML_Error PTRCALL
4964 1.1 tron errorProcessor(XML_Parser parser,
4965 1.6 spz const char *UNUSED_P(s),
4966 1.6 spz const char *UNUSED_P(end),
4967 1.6 spz const char **UNUSED_P(nextPtr))
4968 1.1 tron {
4969 1.1 tron return errorCode;
4970 1.1 tron }
4971 1.1 tron
4972 1.1 tron static enum XML_Error
4973 1.1 tron storeAttributeValue(XML_Parser parser, const ENCODING *enc, XML_Bool isCdata,
4974 1.1 tron const char *ptr, const char *end,
4975 1.1 tron STRING_POOL *pool)
4976 1.1 tron {
4977 1.1 tron enum XML_Error result = appendAttributeValue(parser, enc, isCdata, ptr,
4978 1.1 tron end, pool);
4979 1.1 tron if (result)
4980 1.1 tron return result;
4981 1.1 tron if (!isCdata && poolLength(pool) && poolLastChar(pool) == 0x20)
4982 1.1 tron poolChop(pool);
4983 1.1 tron if (!poolAppendChar(pool, XML_T('\0')))
4984 1.1 tron return XML_ERROR_NO_MEMORY;
4985 1.1 tron return XML_ERROR_NONE;
4986 1.1 tron }
4987 1.1 tron
4988 1.1 tron static enum XML_Error
4989 1.1 tron appendAttributeValue(XML_Parser parser, const ENCODING *enc, XML_Bool isCdata,
4990 1.1 tron const char *ptr, const char *end,
4991 1.1 tron STRING_POOL *pool)
4992 1.1 tron {
4993 1.1 tron DTD * const dtd = _dtd; /* save one level of indirection */
4994 1.1 tron for (;;) {
4995 1.1 tron const char *next;
4996 1.1 tron int tok = XmlAttributeValueTok(enc, ptr, end, &next);
4997 1.1 tron switch (tok) {
4998 1.1 tron case XML_TOK_NONE:
4999 1.1 tron return XML_ERROR_NONE;
5000 1.1 tron case XML_TOK_INVALID:
5001 1.1 tron if (enc == encoding)
5002 1.1 tron eventPtr = next;
5003 1.1 tron return XML_ERROR_INVALID_TOKEN;
5004 1.1 tron case XML_TOK_PARTIAL:
5005 1.1 tron if (enc == encoding)
5006 1.1 tron eventPtr = ptr;
5007 1.1 tron return XML_ERROR_INVALID_TOKEN;
5008 1.1 tron case XML_TOK_CHAR_REF:
5009 1.1 tron {
5010 1.1 tron XML_Char buf[XML_ENCODE_MAX];
5011 1.1 tron int i;
5012 1.1 tron int n = XmlCharRefNumber(enc, ptr);
5013 1.1 tron if (n < 0) {
5014 1.1 tron if (enc == encoding)
5015 1.1 tron eventPtr = ptr;
5016 1.1 tron return XML_ERROR_BAD_CHAR_REF;
5017 1.1 tron }
5018 1.1 tron if (!isCdata
5019 1.1 tron && n == 0x20 /* space */
5020 1.1 tron && (poolLength(pool) == 0 || poolLastChar(pool) == 0x20))
5021 1.1 tron break;
5022 1.1 tron n = XmlEncode(n, (ICHAR *)buf);
5023 1.1 tron if (!n) {
5024 1.1 tron if (enc == encoding)
5025 1.1 tron eventPtr = ptr;
5026 1.1 tron return XML_ERROR_BAD_CHAR_REF;
5027 1.1 tron }
5028 1.1 tron for (i = 0; i < n; i++) {
5029 1.1 tron if (!poolAppendChar(pool, buf[i]))
5030 1.1 tron return XML_ERROR_NO_MEMORY;
5031 1.1 tron }
5032 1.1 tron }
5033 1.1 tron break;
5034 1.1 tron case XML_TOK_DATA_CHARS:
5035 1.1 tron if (!poolAppend(pool, enc, ptr, next))
5036 1.1 tron return XML_ERROR_NO_MEMORY;
5037 1.1 tron break;
5038 1.1 tron case XML_TOK_TRAILING_CR:
5039 1.1 tron next = ptr + enc->minBytesPerChar;
5040 1.1 tron /* fall through */
5041 1.1 tron case XML_TOK_ATTRIBUTE_VALUE_S:
5042 1.1 tron case XML_TOK_DATA_NEWLINE:
5043 1.1 tron if (!isCdata && (poolLength(pool) == 0 || poolLastChar(pool) == 0x20))
5044 1.1 tron break;
5045 1.1 tron if (!poolAppendChar(pool, 0x20))
5046 1.1 tron return XML_ERROR_NO_MEMORY;
5047 1.1 tron break;
5048 1.1 tron case XML_TOK_ENTITY_REF:
5049 1.1 tron {
5050 1.1 tron const XML_Char *name;
5051 1.1 tron ENTITY *entity;
5052 1.1 tron char checkEntityDecl;
5053 1.1 tron XML_Char ch = (XML_Char) XmlPredefinedEntityName(enc,
5054 1.1 tron ptr + enc->minBytesPerChar,
5055 1.1 tron next - enc->minBytesPerChar);
5056 1.1 tron if (ch) {
5057 1.1 tron if (!poolAppendChar(pool, ch))
5058 1.1 tron return XML_ERROR_NO_MEMORY;
5059 1.1 tron break;
5060 1.1 tron }
5061 1.1 tron name = poolStoreString(&temp2Pool, enc,
5062 1.1 tron ptr + enc->minBytesPerChar,
5063 1.1 tron next - enc->minBytesPerChar);
5064 1.1 tron if (!name)
5065 1.1 tron return XML_ERROR_NO_MEMORY;
5066 1.3 spz entity = (ENTITY *)lookup(parser, &dtd->generalEntities, name, 0);
5067 1.1 tron poolDiscard(&temp2Pool);
5068 1.1 tron /* First, determine if a check for an existing declaration is needed;
5069 1.1 tron if yes, check that the entity exists, and that it is internal.
5070 1.1 tron */
5071 1.1 tron if (pool == &dtd->pool) /* are we called from prolog? */
5072 1.1 tron checkEntityDecl =
5073 1.1 tron #ifdef XML_DTD
5074 1.1 tron prologState.documentEntity &&
5075 1.1 tron #endif /* XML_DTD */
5076 1.1 tron (dtd->standalone
5077 1.1 tron ? !openInternalEntities
5078 1.1 tron : !dtd->hasParamEntityRefs);
5079 1.1 tron else /* if (pool == &tempPool): we are called from content */
5080 1.1 tron checkEntityDecl = !dtd->hasParamEntityRefs || dtd->standalone;
5081 1.1 tron if (checkEntityDecl) {
5082 1.1 tron if (!entity)
5083 1.1 tron return XML_ERROR_UNDEFINED_ENTITY;
5084 1.1 tron else if (!entity->is_internal)
5085 1.1 tron return XML_ERROR_ENTITY_DECLARED_IN_PE;
5086 1.1 tron }
5087 1.1 tron else if (!entity) {
5088 1.1 tron /* Cannot report skipped entity here - see comments on
5089 1.1 tron skippedEntityHandler.
5090 1.1 tron if (skippedEntityHandler)
5091 1.1 tron skippedEntityHandler(handlerArg, name, 0);
5092 1.1 tron */
5093 1.1 tron /* Cannot call the default handler because this would be
5094 1.1 tron out of sync with the call to the startElementHandler.
5095 1.1 tron if ((pool == &tempPool) && defaultHandler)
5096 1.1 tron reportDefault(parser, enc, ptr, next);
5097 1.1 tron */
5098 1.1 tron break;
5099 1.1 tron }
5100 1.1 tron if (entity->open) {
5101 1.1 tron if (enc == encoding)
5102 1.1 tron eventPtr = ptr;
5103 1.1 tron return XML_ERROR_RECURSIVE_ENTITY_REF;
5104 1.1 tron }
5105 1.1 tron if (entity->notation) {
5106 1.1 tron if (enc == encoding)
5107 1.1 tron eventPtr = ptr;
5108 1.1 tron return XML_ERROR_BINARY_ENTITY_REF;
5109 1.1 tron }
5110 1.1 tron if (!entity->textPtr) {
5111 1.1 tron if (enc == encoding)
5112 1.1 tron eventPtr = ptr;
5113 1.3 spz return XML_ERROR_ATTRIBUTE_EXTERNAL_ENTITY_REF;
5114 1.1 tron }
5115 1.1 tron else {
5116 1.1 tron enum XML_Error result;
5117 1.1 tron const XML_Char *textEnd = entity->textPtr + entity->textLen;
5118 1.1 tron entity->open = XML_TRUE;
5119 1.1 tron result = appendAttributeValue(parser, internalEncoding, isCdata,
5120 1.1 tron (char *)entity->textPtr,
5121 1.1 tron (char *)textEnd, pool);
5122 1.1 tron entity->open = XML_FALSE;
5123 1.1 tron if (result)
5124 1.1 tron return result;
5125 1.1 tron }
5126 1.1 tron }
5127 1.1 tron break;
5128 1.1 tron default:
5129 1.1 tron if (enc == encoding)
5130 1.1 tron eventPtr = ptr;
5131 1.1 tron return XML_ERROR_UNEXPECTED_STATE;
5132 1.1 tron }
5133 1.1 tron ptr = next;
5134 1.1 tron }
5135 1.1 tron /* not reached */
5136 1.1 tron }
5137 1.1 tron
5138 1.1 tron static enum XML_Error
5139 1.1 tron storeEntityValue(XML_Parser parser,
5140 1.1 tron const ENCODING *enc,
5141 1.1 tron const char *entityTextPtr,
5142 1.1 tron const char *entityTextEnd)
5143 1.1 tron {
5144 1.1 tron DTD * const dtd = _dtd; /* save one level of indirection */
5145 1.1 tron STRING_POOL *pool = &(dtd->entityValuePool);
5146 1.1 tron enum XML_Error result = XML_ERROR_NONE;
5147 1.1 tron #ifdef XML_DTD
5148 1.1 tron int oldInEntityValue = prologState.inEntityValue;
5149 1.1 tron prologState.inEntityValue = 1;
5150 1.1 tron #endif /* XML_DTD */
5151 1.1 tron /* never return Null for the value argument in EntityDeclHandler,
5152 1.1 tron since this would indicate an external entity; therefore we
5153 1.1 tron have to make sure that entityValuePool.start is not null */
5154 1.1 tron if (!pool->blocks) {
5155 1.1 tron if (!poolGrow(pool))
5156 1.1 tron return XML_ERROR_NO_MEMORY;
5157 1.1 tron }
5158 1.1 tron
5159 1.1 tron for (;;) {
5160 1.1 tron const char *next;
5161 1.1 tron int tok = XmlEntityValueTok(enc, entityTextPtr, entityTextEnd, &next);
5162 1.1 tron switch (tok) {
5163 1.1 tron case XML_TOK_PARAM_ENTITY_REF:
5164 1.1 tron #ifdef XML_DTD
5165 1.1 tron if (isParamEntity || enc != encoding) {
5166 1.1 tron const XML_Char *name;
5167 1.1 tron ENTITY *entity;
5168 1.1 tron name = poolStoreString(&tempPool, enc,
5169 1.1 tron entityTextPtr + enc->minBytesPerChar,
5170 1.1 tron next - enc->minBytesPerChar);
5171 1.1 tron if (!name) {
5172 1.1 tron result = XML_ERROR_NO_MEMORY;
5173 1.1 tron goto endEntityValue;
5174 1.1 tron }
5175 1.3 spz entity = (ENTITY *)lookup(parser, &dtd->paramEntities, name, 0);
5176 1.1 tron poolDiscard(&tempPool);
5177 1.1 tron if (!entity) {
5178 1.1 tron /* not a well-formedness error - see XML 1.0: WFC Entity Declared */
5179 1.1 tron /* cannot report skipped entity here - see comments on
5180 1.1 tron skippedEntityHandler
5181 1.1 tron if (skippedEntityHandler)
5182 1.1 tron skippedEntityHandler(handlerArg, name, 0);
5183 1.1 tron */
5184 1.1 tron dtd->keepProcessing = dtd->standalone;
5185 1.1 tron goto endEntityValue;
5186 1.1 tron }
5187 1.1 tron if (entity->open) {
5188 1.1 tron if (enc == encoding)
5189 1.1 tron eventPtr = entityTextPtr;
5190 1.1 tron result = XML_ERROR_RECURSIVE_ENTITY_REF;
5191 1.1 tron goto endEntityValue;
5192 1.1 tron }
5193 1.1 tron if (entity->systemId) {
5194 1.1 tron if (externalEntityRefHandler) {
5195 1.1 tron dtd->paramEntityRead = XML_FALSE;
5196 1.1 tron entity->open = XML_TRUE;
5197 1.1 tron if (!externalEntityRefHandler(externalEntityRefHandlerArg,
5198 1.1 tron 0,
5199 1.1 tron entity->base,
5200 1.1 tron entity->systemId,
5201 1.1 tron entity->publicId)) {
5202 1.1 tron entity->open = XML_FALSE;
5203 1.1 tron result = XML_ERROR_EXTERNAL_ENTITY_HANDLING;
5204 1.1 tron goto endEntityValue;
5205 1.1 tron }
5206 1.1 tron entity->open = XML_FALSE;
5207 1.1 tron if (!dtd->paramEntityRead)
5208 1.1 tron dtd->keepProcessing = dtd->standalone;
5209 1.1 tron }
5210 1.1 tron else
5211 1.1 tron dtd->keepProcessing = dtd->standalone;
5212 1.1 tron }
5213 1.1 tron else {
5214 1.1 tron entity->open = XML_TRUE;
5215 1.1 tron result = storeEntityValue(parser,
5216 1.1 tron internalEncoding,
5217 1.1 tron (char *)entity->textPtr,
5218 1.1 tron (char *)(entity->textPtr
5219 1.1 tron + entity->textLen));
5220 1.1 tron entity->open = XML_FALSE;
5221 1.1 tron if (result)
5222 1.1 tron goto endEntityValue;
5223 1.1 tron }
5224 1.1 tron break;
5225 1.1 tron }
5226 1.1 tron #endif /* XML_DTD */
5227 1.1 tron /* In the internal subset, PE references are not legal
5228 1.1 tron within markup declarations, e.g entity values in this case. */
5229 1.1 tron eventPtr = entityTextPtr;
5230 1.1 tron result = XML_ERROR_PARAM_ENTITY_REF;
5231 1.1 tron goto endEntityValue;
5232 1.1 tron case XML_TOK_NONE:
5233 1.1 tron result = XML_ERROR_NONE;
5234 1.1 tron goto endEntityValue;
5235 1.1 tron case XML_TOK_ENTITY_REF:
5236 1.1 tron case XML_TOK_DATA_CHARS:
5237 1.1 tron if (!poolAppend(pool, enc, entityTextPtr, next)) {
5238 1.1 tron result = XML_ERROR_NO_MEMORY;
5239 1.1 tron goto endEntityValue;
5240 1.1 tron }
5241 1.1 tron break;
5242 1.1 tron case XML_TOK_TRAILING_CR:
5243 1.1 tron next = entityTextPtr + enc->minBytesPerChar;
5244 1.1 tron /* fall through */
5245 1.1 tron case XML_TOK_DATA_NEWLINE:
5246 1.1 tron if (pool->end == pool->ptr && !poolGrow(pool)) {
5247 1.1 tron result = XML_ERROR_NO_MEMORY;
5248 1.1 tron goto endEntityValue;
5249 1.1 tron }
5250 1.1 tron *(pool->ptr)++ = 0xA;
5251 1.1 tron break;
5252 1.1 tron case XML_TOK_CHAR_REF:
5253 1.1 tron {
5254 1.1 tron XML_Char buf[XML_ENCODE_MAX];
5255 1.1 tron int i;
5256 1.1 tron int n = XmlCharRefNumber(enc, entityTextPtr);
5257 1.1 tron if (n < 0) {
5258 1.1 tron if (enc == encoding)
5259 1.1 tron eventPtr = entityTextPtr;
5260 1.1 tron result = XML_ERROR_BAD_CHAR_REF;
5261 1.1 tron goto endEntityValue;
5262 1.1 tron }
5263 1.1 tron n = XmlEncode(n, (ICHAR *)buf);
5264 1.1 tron if (!n) {
5265 1.1 tron if (enc == encoding)
5266 1.1 tron eventPtr = entityTextPtr;
5267 1.1 tron result = XML_ERROR_BAD_CHAR_REF;
5268 1.1 tron goto endEntityValue;
5269 1.1 tron }
5270 1.1 tron for (i = 0; i < n; i++) {
5271 1.1 tron if (pool->end == pool->ptr && !poolGrow(pool)) {
5272 1.1 tron result = XML_ERROR_NO_MEMORY;
5273 1.1 tron goto endEntityValue;
5274 1.1 tron }
5275 1.1 tron *(pool->ptr)++ = buf[i];
5276 1.1 tron }
5277 1.1 tron }
5278 1.1 tron break;
5279 1.1 tron case XML_TOK_PARTIAL:
5280 1.1 tron if (enc == encoding)
5281 1.1 tron eventPtr = entityTextPtr;
5282 1.1 tron result = XML_ERROR_INVALID_TOKEN;
5283 1.1 tron goto endEntityValue;
5284 1.1 tron case XML_TOK_INVALID:
5285 1.1 tron if (enc == encoding)
5286 1.1 tron eventPtr = next;
5287 1.1 tron result = XML_ERROR_INVALID_TOKEN;
5288 1.1 tron goto endEntityValue;
5289 1.1 tron default:
5290 1.1 tron if (enc == encoding)
5291 1.1 tron eventPtr = entityTextPtr;
5292 1.1 tron result = XML_ERROR_UNEXPECTED_STATE;
5293 1.1 tron goto endEntityValue;
5294 1.1 tron }
5295 1.1 tron entityTextPtr = next;
5296 1.1 tron }
5297 1.1 tron endEntityValue:
5298 1.1 tron #ifdef XML_DTD
5299 1.1 tron prologState.inEntityValue = oldInEntityValue;
5300 1.1 tron #endif /* XML_DTD */
5301 1.1 tron return result;
5302 1.1 tron }
5303 1.1 tron
5304 1.1 tron static void FASTCALL
5305 1.1 tron normalizeLines(XML_Char *s)
5306 1.1 tron {
5307 1.1 tron XML_Char *p;
5308 1.1 tron for (;; s++) {
5309 1.1 tron if (*s == XML_T('\0'))
5310 1.1 tron return;
5311 1.1 tron if (*s == 0xD)
5312 1.1 tron break;
5313 1.1 tron }
5314 1.1 tron p = s;
5315 1.1 tron do {
5316 1.1 tron if (*s == 0xD) {
5317 1.1 tron *p++ = 0xA;
5318 1.1 tron if (*++s == 0xA)
5319 1.1 tron s++;
5320 1.1 tron }
5321 1.1 tron else
5322 1.1 tron *p++ = *s++;
5323 1.1 tron } while (*s);
5324 1.1 tron *p = XML_T('\0');
5325 1.1 tron }
5326 1.1 tron
5327 1.1 tron static int
5328 1.1 tron reportProcessingInstruction(XML_Parser parser, const ENCODING *enc,
5329 1.1 tron const char *start, const char *end)
5330 1.1 tron {
5331 1.1 tron const XML_Char *target;
5332 1.1 tron XML_Char *data;
5333 1.1 tron const char *tem;
5334 1.1 tron if (!processingInstructionHandler) {
5335 1.1 tron if (defaultHandler)
5336 1.1 tron reportDefault(parser, enc, start, end);
5337 1.1 tron return 1;
5338 1.1 tron }
5339 1.1 tron start += enc->minBytesPerChar * 2;
5340 1.1 tron tem = start + XmlNameLength(enc, start);
5341 1.1 tron target = poolStoreString(&tempPool, enc, start, tem);
5342 1.1 tron if (!target)
5343 1.1 tron return 0;
5344 1.1 tron poolFinish(&tempPool);
5345 1.1 tron data = poolStoreString(&tempPool, enc,
5346 1.1 tron XmlSkipS(enc, tem),
5347 1.1 tron end - enc->minBytesPerChar*2);
5348 1.1 tron if (!data)
5349 1.1 tron return 0;
5350 1.1 tron normalizeLines(data);
5351 1.1 tron processingInstructionHandler(handlerArg, target, data);
5352 1.1 tron poolClear(&tempPool);
5353 1.1 tron return 1;
5354 1.1 tron }
5355 1.1 tron
5356 1.1 tron static int
5357 1.1 tron reportComment(XML_Parser parser, const ENCODING *enc,
5358 1.1 tron const char *start, const char *end)
5359 1.1 tron {
5360 1.1 tron XML_Char *data;
5361 1.1 tron if (!commentHandler) {
5362 1.1 tron if (defaultHandler)
5363 1.1 tron reportDefault(parser, enc, start, end);
5364 1.1 tron return 1;
5365 1.1 tron }
5366 1.1 tron data = poolStoreString(&tempPool,
5367 1.1 tron enc,
5368 1.1 tron start + enc->minBytesPerChar * 4,
5369 1.1 tron end - enc->minBytesPerChar * 3);
5370 1.1 tron if (!data)
5371 1.1 tron return 0;
5372 1.1 tron normalizeLines(data);
5373 1.1 tron commentHandler(handlerArg, data);
5374 1.1 tron poolClear(&tempPool);
5375 1.1 tron return 1;
5376 1.1 tron }
5377 1.1 tron
5378 1.1 tron static void
5379 1.1 tron reportDefault(XML_Parser parser, const ENCODING *enc,
5380 1.1 tron const char *s, const char *end)
5381 1.1 tron {
5382 1.1 tron if (MUST_CONVERT(enc, s)) {
5383 1.5 spz enum XML_Convert_Result convert_res;
5384 1.1 tron const char **eventPP;
5385 1.1 tron const char **eventEndPP;
5386 1.1 tron if (enc == encoding) {
5387 1.1 tron eventPP = &eventPtr;
5388 1.1 tron eventEndPP = &eventEndPtr;
5389 1.1 tron }
5390 1.1 tron else {
5391 1.1 tron eventPP = &(openInternalEntities->internalEventPtr);
5392 1.1 tron eventEndPP = &(openInternalEntities->internalEventEndPtr);
5393 1.1 tron }
5394 1.1 tron do {
5395 1.1 tron ICHAR *dataPtr = (ICHAR *)dataBuf;
5396 1.5 spz convert_res = XmlConvert(enc, &s, end, &dataPtr, (ICHAR *)dataBufEnd);
5397 1.1 tron *eventEndPP = s;
5398 1.1 tron defaultHandler(handlerArg, dataBuf, (int)(dataPtr - (ICHAR *)dataBuf));
5399 1.1 tron *eventPP = s;
5400 1.5 spz } while ((convert_res != XML_CONVERT_COMPLETED) && (convert_res != XML_CONVERT_INPUT_INCOMPLETE));
5401 1.1 tron }
5402 1.1 tron else
5403 1.1 tron defaultHandler(handlerArg, (XML_Char *)s, (int)((XML_Char *)end - (XML_Char *)s));
5404 1.1 tron }
5405 1.1 tron
5406 1.1 tron
5407 1.1 tron static int
5408 1.1 tron defineAttribute(ELEMENT_TYPE *type, ATTRIBUTE_ID *attId, XML_Bool isCdata,
5409 1.1 tron XML_Bool isId, const XML_Char *value, XML_Parser parser)
5410 1.1 tron {
5411 1.1 tron DEFAULT_ATTRIBUTE *att;
5412 1.1 tron if (value || isId) {
5413 1.1 tron /* The handling of default attributes gets messed up if we have
5414 1.1 tron a default which duplicates a non-default. */
5415 1.1 tron int i;
5416 1.1 tron for (i = 0; i < type->nDefaultAtts; i++)
5417 1.1 tron if (attId == type->defaultAtts[i].id)
5418 1.1 tron return 1;
5419 1.1 tron if (isId && !type->idAtt && !attId->xmlns)
5420 1.1 tron type->idAtt = attId;
5421 1.1 tron }
5422 1.1 tron if (type->nDefaultAtts == type->allocDefaultAtts) {
5423 1.1 tron if (type->allocDefaultAtts == 0) {
5424 1.1 tron type->allocDefaultAtts = 8;
5425 1.1 tron type->defaultAtts = (DEFAULT_ATTRIBUTE *)MALLOC(type->allocDefaultAtts
5426 1.1 tron * sizeof(DEFAULT_ATTRIBUTE));
5427 1.1 tron if (!type->defaultAtts)
5428 1.1 tron return 0;
5429 1.1 tron }
5430 1.1 tron else {
5431 1.1 tron DEFAULT_ATTRIBUTE *temp;
5432 1.1 tron int count = type->allocDefaultAtts * 2;
5433 1.1 tron temp = (DEFAULT_ATTRIBUTE *)
5434 1.1 tron REALLOC(type->defaultAtts, (count * sizeof(DEFAULT_ATTRIBUTE)));
5435 1.1 tron if (temp == NULL)
5436 1.1 tron return 0;
5437 1.1 tron type->allocDefaultAtts = count;
5438 1.1 tron type->defaultAtts = temp;
5439 1.1 tron }
5440 1.1 tron }
5441 1.1 tron att = type->defaultAtts + type->nDefaultAtts;
5442 1.1 tron att->id = attId;
5443 1.1 tron att->value = value;
5444 1.1 tron att->isCdata = isCdata;
5445 1.1 tron if (!isCdata)
5446 1.1 tron attId->maybeTokenized = XML_TRUE;
5447 1.1 tron type->nDefaultAtts += 1;
5448 1.1 tron return 1;
5449 1.1 tron }
5450 1.1 tron
5451 1.1 tron static int
5452 1.1 tron setElementTypePrefix(XML_Parser parser, ELEMENT_TYPE *elementType)
5453 1.1 tron {
5454 1.1 tron DTD * const dtd = _dtd; /* save one level of indirection */
5455 1.1 tron const XML_Char *name;
5456 1.1 tron for (name = elementType->name; *name; name++) {
5457 1.1 tron if (*name == XML_T(ASCII_COLON)) {
5458 1.1 tron PREFIX *prefix;
5459 1.1 tron const XML_Char *s;
5460 1.1 tron for (s = elementType->name; s != name; s++) {
5461 1.1 tron if (!poolAppendChar(&dtd->pool, *s))
5462 1.1 tron return 0;
5463 1.1 tron }
5464 1.1 tron if (!poolAppendChar(&dtd->pool, XML_T('\0')))
5465 1.1 tron return 0;
5466 1.3 spz prefix = (PREFIX *)lookup(parser, &dtd->prefixes, poolStart(&dtd->pool),
5467 1.1 tron sizeof(PREFIX));
5468 1.1 tron if (!prefix)
5469 1.1 tron return 0;
5470 1.1 tron if (prefix->name == poolStart(&dtd->pool))
5471 1.1 tron poolFinish(&dtd->pool);
5472 1.1 tron else
5473 1.1 tron poolDiscard(&dtd->pool);
5474 1.1 tron elementType->prefix = prefix;
5475 1.1 tron
5476 1.1 tron }
5477 1.1 tron }
5478 1.1 tron return 1;
5479 1.1 tron }
5480 1.1 tron
5481 1.1 tron static ATTRIBUTE_ID *
5482 1.1 tron getAttributeId(XML_Parser parser, const ENCODING *enc,
5483 1.1 tron const char *start, const char *end)
5484 1.1 tron {
5485 1.1 tron DTD * const dtd = _dtd; /* save one level of indirection */
5486 1.1 tron ATTRIBUTE_ID *id;
5487 1.1 tron const XML_Char *name;
5488 1.1 tron if (!poolAppendChar(&dtd->pool, XML_T('\0')))
5489 1.1 tron return NULL;
5490 1.1 tron name = poolStoreString(&dtd->pool, enc, start, end);
5491 1.1 tron if (!name)
5492 1.1 tron return NULL;
5493 1.1 tron /* skip quotation mark - its storage will be re-used (like in name[-1]) */
5494 1.1 tron ++name;
5495 1.3 spz id = (ATTRIBUTE_ID *)lookup(parser, &dtd->attributeIds, name, sizeof(ATTRIBUTE_ID));
5496 1.1 tron if (!id)
5497 1.1 tron return NULL;
5498 1.1 tron if (id->name != name)
5499 1.1 tron poolDiscard(&dtd->pool);
5500 1.1 tron else {
5501 1.1 tron poolFinish(&dtd->pool);
5502 1.1 tron if (!ns)
5503 1.1 tron ;
5504 1.1 tron else if (name[0] == XML_T(ASCII_x)
5505 1.1 tron && name[1] == XML_T(ASCII_m)
5506 1.1 tron && name[2] == XML_T(ASCII_l)
5507 1.1 tron && name[3] == XML_T(ASCII_n)
5508 1.1 tron && name[4] == XML_T(ASCII_s)
5509 1.1 tron && (name[5] == XML_T('\0') || name[5] == XML_T(ASCII_COLON))) {
5510 1.1 tron if (name[5] == XML_T('\0'))
5511 1.1 tron id->prefix = &dtd->defaultPrefix;
5512 1.1 tron else
5513 1.3 spz id->prefix = (PREFIX *)lookup(parser, &dtd->prefixes, name + 6, sizeof(PREFIX));
5514 1.1 tron id->xmlns = XML_TRUE;
5515 1.1 tron }
5516 1.1 tron else {
5517 1.1 tron int i;
5518 1.1 tron for (i = 0; name[i]; i++) {
5519 1.1 tron /* attributes without prefix are *not* in the default namespace */
5520 1.1 tron if (name[i] == XML_T(ASCII_COLON)) {
5521 1.1 tron int j;
5522 1.1 tron for (j = 0; j < i; j++) {
5523 1.1 tron if (!poolAppendChar(&dtd->pool, name[j]))
5524 1.1 tron return NULL;
5525 1.1 tron }
5526 1.1 tron if (!poolAppendChar(&dtd->pool, XML_T('\0')))
5527 1.1 tron return NULL;
5528 1.3 spz id->prefix = (PREFIX *)lookup(parser, &dtd->prefixes, poolStart(&dtd->pool),
5529 1.1 tron sizeof(PREFIX));
5530 1.4 spz if (!id->prefix)
5531 1.4 spz return NULL;
5532 1.1 tron if (id->prefix->name == poolStart(&dtd->pool))
5533 1.1 tron poolFinish(&dtd->pool);
5534 1.1 tron else
5535 1.1 tron poolDiscard(&dtd->pool);
5536 1.1 tron break;
5537 1.1 tron }
5538 1.1 tron }
5539 1.1 tron }
5540 1.1 tron }
5541 1.1 tron return id;
5542 1.1 tron }
5543 1.1 tron
5544 1.1 tron #define CONTEXT_SEP XML_T(ASCII_FF)
5545 1.1 tron
5546 1.1 tron static const XML_Char *
5547 1.1 tron getContext(XML_Parser parser)
5548 1.1 tron {
5549 1.1 tron DTD * const dtd = _dtd; /* save one level of indirection */
5550 1.1 tron HASH_TABLE_ITER iter;
5551 1.1 tron XML_Bool needSep = XML_FALSE;
5552 1.1 tron
5553 1.1 tron if (dtd->defaultPrefix.binding) {
5554 1.1 tron int i;
5555 1.1 tron int len;
5556 1.1 tron if (!poolAppendChar(&tempPool, XML_T(ASCII_EQUALS)))
5557 1.1 tron return NULL;
5558 1.1 tron len = dtd->defaultPrefix.binding->uriLen;
5559 1.1 tron if (namespaceSeparator)
5560 1.1 tron len--;
5561 1.1 tron for (i = 0; i < len; i++)
5562 1.1 tron if (!poolAppendChar(&tempPool, dtd->defaultPrefix.binding->uri[i]))
5563 1.1 tron return NULL;
5564 1.1 tron needSep = XML_TRUE;
5565 1.1 tron }
5566 1.1 tron
5567 1.1 tron hashTableIterInit(&iter, &(dtd->prefixes));
5568 1.1 tron for (;;) {
5569 1.1 tron int i;
5570 1.1 tron int len;
5571 1.1 tron const XML_Char *s;
5572 1.1 tron PREFIX *prefix = (PREFIX *)hashTableIterNext(&iter);
5573 1.1 tron if (!prefix)
5574 1.1 tron break;
5575 1.1 tron if (!prefix->binding)
5576 1.1 tron continue;
5577 1.1 tron if (needSep && !poolAppendChar(&tempPool, CONTEXT_SEP))
5578 1.1 tron return NULL;
5579 1.1 tron for (s = prefix->name; *s; s++)
5580 1.1 tron if (!poolAppendChar(&tempPool, *s))
5581 1.1 tron return NULL;
5582 1.1 tron if (!poolAppendChar(&tempPool, XML_T(ASCII_EQUALS)))
5583 1.1 tron return NULL;
5584 1.1 tron len = prefix->binding->uriLen;
5585 1.1 tron if (namespaceSeparator)
5586 1.1 tron len--;
5587 1.1 tron for (i = 0; i < len; i++)
5588 1.1 tron if (!poolAppendChar(&tempPool, prefix->binding->uri[i]))
5589 1.1 tron return NULL;
5590 1.1 tron needSep = XML_TRUE;
5591 1.1 tron }
5592 1.1 tron
5593 1.1 tron
5594 1.1 tron hashTableIterInit(&iter, &(dtd->generalEntities));
5595 1.1 tron for (;;) {
5596 1.1 tron const XML_Char *s;
5597 1.1 tron ENTITY *e = (ENTITY *)hashTableIterNext(&iter);
5598 1.1 tron if (!e)
5599 1.1 tron break;
5600 1.1 tron if (!e->open)
5601 1.1 tron continue;
5602 1.1 tron if (needSep && !poolAppendChar(&tempPool, CONTEXT_SEP))
5603 1.1 tron return NULL;
5604 1.1 tron for (s = e->name; *s; s++)
5605 1.1 tron if (!poolAppendChar(&tempPool, *s))
5606 1.1 tron return 0;
5607 1.1 tron needSep = XML_TRUE;
5608 1.1 tron }
5609 1.1 tron
5610 1.1 tron if (!poolAppendChar(&tempPool, XML_T('\0')))
5611 1.1 tron return NULL;
5612 1.1 tron return tempPool.start;
5613 1.1 tron }
5614 1.1 tron
5615 1.1 tron static XML_Bool
5616 1.1 tron setContext(XML_Parser parser, const XML_Char *context)
5617 1.1 tron {
5618 1.1 tron DTD * const dtd = _dtd; /* save one level of indirection */
5619 1.1 tron const XML_Char *s = context;
5620 1.1 tron
5621 1.1 tron while (*context != XML_T('\0')) {
5622 1.1 tron if (*s == CONTEXT_SEP || *s == XML_T('\0')) {
5623 1.1 tron ENTITY *e;
5624 1.1 tron if (!poolAppendChar(&tempPool, XML_T('\0')))
5625 1.1 tron return XML_FALSE;
5626 1.3 spz e = (ENTITY *)lookup(parser, &dtd->generalEntities, poolStart(&tempPool), 0);
5627 1.1 tron if (e)
5628 1.1 tron e->open = XML_TRUE;
5629 1.1 tron if (*s != XML_T('\0'))
5630 1.1 tron s++;
5631 1.1 tron context = s;
5632 1.1 tron poolDiscard(&tempPool);
5633 1.1 tron }
5634 1.1 tron else if (*s == XML_T(ASCII_EQUALS)) {
5635 1.1 tron PREFIX *prefix;
5636 1.1 tron if (poolLength(&tempPool) == 0)
5637 1.1 tron prefix = &dtd->defaultPrefix;
5638 1.1 tron else {
5639 1.1 tron if (!poolAppendChar(&tempPool, XML_T('\0')))
5640 1.1 tron return XML_FALSE;
5641 1.3 spz prefix = (PREFIX *)lookup(parser, &dtd->prefixes, poolStart(&tempPool),
5642 1.1 tron sizeof(PREFIX));
5643 1.1 tron if (!prefix)
5644 1.1 tron return XML_FALSE;
5645 1.1 tron if (prefix->name == poolStart(&tempPool)) {
5646 1.1 tron prefix->name = poolCopyString(&dtd->pool, prefix->name);
5647 1.1 tron if (!prefix->name)
5648 1.1 tron return XML_FALSE;
5649 1.1 tron }
5650 1.1 tron poolDiscard(&tempPool);
5651 1.1 tron }
5652 1.1 tron for (context = s + 1;
5653 1.1 tron *context != CONTEXT_SEP && *context != XML_T('\0');
5654 1.1 tron context++)
5655 1.1 tron if (!poolAppendChar(&tempPool, *context))
5656 1.1 tron return XML_FALSE;
5657 1.1 tron if (!poolAppendChar(&tempPool, XML_T('\0')))
5658 1.1 tron return XML_FALSE;
5659 1.1 tron if (addBinding(parser, prefix, NULL, poolStart(&tempPool),
5660 1.1 tron &inheritedBindings) != XML_ERROR_NONE)
5661 1.1 tron return XML_FALSE;
5662 1.1 tron poolDiscard(&tempPool);
5663 1.1 tron if (*context != XML_T('\0'))
5664 1.1 tron ++context;
5665 1.1 tron s = context;
5666 1.1 tron }
5667 1.1 tron else {
5668 1.1 tron if (!poolAppendChar(&tempPool, *s))
5669 1.1 tron return XML_FALSE;
5670 1.1 tron s++;
5671 1.1 tron }
5672 1.1 tron }
5673 1.1 tron return XML_TRUE;
5674 1.1 tron }
5675 1.1 tron
5676 1.1 tron static void FASTCALL
5677 1.1 tron normalizePublicId(XML_Char *publicId)
5678 1.1 tron {
5679 1.1 tron XML_Char *p = publicId;
5680 1.1 tron XML_Char *s;
5681 1.1 tron for (s = publicId; *s; s++) {
5682 1.1 tron switch (*s) {
5683 1.1 tron case 0x20:
5684 1.1 tron case 0xD:
5685 1.1 tron case 0xA:
5686 1.1 tron if (p != publicId && p[-1] != 0x20)
5687 1.1 tron *p++ = 0x20;
5688 1.1 tron break;
5689 1.1 tron default:
5690 1.1 tron *p++ = *s;
5691 1.1 tron }
5692 1.1 tron }
5693 1.1 tron if (p != publicId && p[-1] == 0x20)
5694 1.1 tron --p;
5695 1.1 tron *p = XML_T('\0');
5696 1.1 tron }
5697 1.1 tron
5698 1.1 tron static DTD *
5699 1.1 tron dtdCreate(const XML_Memory_Handling_Suite *ms)
5700 1.1 tron {
5701 1.1 tron DTD *p = (DTD *)ms->malloc_fcn(sizeof(DTD));
5702 1.1 tron if (p == NULL)
5703 1.1 tron return p;
5704 1.1 tron poolInit(&(p->pool), ms);
5705 1.1 tron poolInit(&(p->entityValuePool), ms);
5706 1.1 tron hashTableInit(&(p->generalEntities), ms);
5707 1.1 tron hashTableInit(&(p->elementTypes), ms);
5708 1.1 tron hashTableInit(&(p->attributeIds), ms);
5709 1.1 tron hashTableInit(&(p->prefixes), ms);
5710 1.1 tron #ifdef XML_DTD
5711 1.1 tron p->paramEntityRead = XML_FALSE;
5712 1.1 tron hashTableInit(&(p->paramEntities), ms);
5713 1.1 tron #endif /* XML_DTD */
5714 1.1 tron p->defaultPrefix.name = NULL;
5715 1.1 tron p->defaultPrefix.binding = NULL;
5716 1.1 tron
5717 1.1 tron p->in_eldecl = XML_FALSE;
5718 1.1 tron p->scaffIndex = NULL;
5719 1.1 tron p->scaffold = NULL;
5720 1.1 tron p->scaffLevel = 0;
5721 1.1 tron p->scaffSize = 0;
5722 1.1 tron p->scaffCount = 0;
5723 1.1 tron p->contentStringLen = 0;
5724 1.1 tron
5725 1.1 tron p->keepProcessing = XML_TRUE;
5726 1.1 tron p->hasParamEntityRefs = XML_FALSE;
5727 1.1 tron p->standalone = XML_FALSE;
5728 1.1 tron return p;
5729 1.1 tron }
5730 1.1 tron
5731 1.1 tron static void
5732 1.1 tron dtdReset(DTD *p, const XML_Memory_Handling_Suite *ms)
5733 1.1 tron {
5734 1.1 tron HASH_TABLE_ITER iter;
5735 1.1 tron hashTableIterInit(&iter, &(p->elementTypes));
5736 1.1 tron for (;;) {
5737 1.1 tron ELEMENT_TYPE *e = (ELEMENT_TYPE *)hashTableIterNext(&iter);
5738 1.1 tron if (!e)
5739 1.1 tron break;
5740 1.1 tron if (e->allocDefaultAtts != 0)
5741 1.1 tron ms->free_fcn(e->defaultAtts);
5742 1.1 tron }
5743 1.1 tron hashTableClear(&(p->generalEntities));
5744 1.1 tron #ifdef XML_DTD
5745 1.1 tron p->paramEntityRead = XML_FALSE;
5746 1.1 tron hashTableClear(&(p->paramEntities));
5747 1.1 tron #endif /* XML_DTD */
5748 1.1 tron hashTableClear(&(p->elementTypes));
5749 1.1 tron hashTableClear(&(p->attributeIds));
5750 1.1 tron hashTableClear(&(p->prefixes));
5751 1.1 tron poolClear(&(p->pool));
5752 1.1 tron poolClear(&(p->entityValuePool));
5753 1.1 tron p->defaultPrefix.name = NULL;
5754 1.1 tron p->defaultPrefix.binding = NULL;
5755 1.1 tron
5756 1.1 tron p->in_eldecl = XML_FALSE;
5757 1.1 tron
5758 1.1 tron ms->free_fcn(p->scaffIndex);
5759 1.1 tron p->scaffIndex = NULL;
5760 1.1 tron ms->free_fcn(p->scaffold);
5761 1.1 tron p->scaffold = NULL;
5762 1.1 tron
5763 1.1 tron p->scaffLevel = 0;
5764 1.1 tron p->scaffSize = 0;
5765 1.1 tron p->scaffCount = 0;
5766 1.1 tron p->contentStringLen = 0;
5767 1.1 tron
5768 1.1 tron p->keepProcessing = XML_TRUE;
5769 1.1 tron p->hasParamEntityRefs = XML_FALSE;
5770 1.1 tron p->standalone = XML_FALSE;
5771 1.1 tron }
5772 1.1 tron
5773 1.1 tron static void
5774 1.1 tron dtdDestroy(DTD *p, XML_Bool isDocEntity, const XML_Memory_Handling_Suite *ms)
5775 1.1 tron {
5776 1.1 tron HASH_TABLE_ITER iter;
5777 1.1 tron hashTableIterInit(&iter, &(p->elementTypes));
5778 1.1 tron for (;;) {
5779 1.1 tron ELEMENT_TYPE *e = (ELEMENT_TYPE *)hashTableIterNext(&iter);
5780 1.1 tron if (!e)
5781 1.1 tron break;
5782 1.1 tron if (e->allocDefaultAtts != 0)
5783 1.1 tron ms->free_fcn(e->defaultAtts);
5784 1.1 tron }
5785 1.1 tron hashTableDestroy(&(p->generalEntities));
5786 1.1 tron #ifdef XML_DTD
5787 1.1 tron hashTableDestroy(&(p->paramEntities));
5788 1.1 tron #endif /* XML_DTD */
5789 1.1 tron hashTableDestroy(&(p->elementTypes));
5790 1.1 tron hashTableDestroy(&(p->attributeIds));
5791 1.1 tron hashTableDestroy(&(p->prefixes));
5792 1.1 tron poolDestroy(&(p->pool));
5793 1.1 tron poolDestroy(&(p->entityValuePool));
5794 1.1 tron if (isDocEntity) {
5795 1.1 tron ms->free_fcn(p->scaffIndex);
5796 1.1 tron ms->free_fcn(p->scaffold);
5797 1.1 tron }
5798 1.1 tron ms->free_fcn(p);
5799 1.1 tron }
5800 1.1 tron
5801 1.1 tron /* Do a deep copy of the DTD. Return 0 for out of memory, non-zero otherwise.
5802 1.1 tron The new DTD has already been initialized.
5803 1.1 tron */
5804 1.1 tron static int
5805 1.3 spz dtdCopy(XML_Parser oldParser, DTD *newDtd, const DTD *oldDtd, const XML_Memory_Handling_Suite *ms)
5806 1.1 tron {
5807 1.1 tron HASH_TABLE_ITER iter;
5808 1.1 tron
5809 1.1 tron /* Copy the prefix table. */
5810 1.1 tron
5811 1.1 tron hashTableIterInit(&iter, &(oldDtd->prefixes));
5812 1.1 tron for (;;) {
5813 1.1 tron const XML_Char *name;
5814 1.1 tron const PREFIX *oldP = (PREFIX *)hashTableIterNext(&iter);
5815 1.1 tron if (!oldP)
5816 1.1 tron break;
5817 1.1 tron name = poolCopyString(&(newDtd->pool), oldP->name);
5818 1.1 tron if (!name)
5819 1.1 tron return 0;
5820 1.3 spz if (!lookup(oldParser, &(newDtd->prefixes), name, sizeof(PREFIX)))
5821 1.1 tron return 0;
5822 1.1 tron }
5823 1.1 tron
5824 1.1 tron hashTableIterInit(&iter, &(oldDtd->attributeIds));
5825 1.1 tron
5826 1.1 tron /* Copy the attribute id table. */
5827 1.1 tron
5828 1.1 tron for (;;) {
5829 1.1 tron ATTRIBUTE_ID *newA;
5830 1.1 tron const XML_Char *name;
5831 1.1 tron const ATTRIBUTE_ID *oldA = (ATTRIBUTE_ID *)hashTableIterNext(&iter);
5832 1.1 tron
5833 1.1 tron if (!oldA)
5834 1.1 tron break;
5835 1.1 tron /* Remember to allocate the scratch byte before the name. */
5836 1.1 tron if (!poolAppendChar(&(newDtd->pool), XML_T('\0')))
5837 1.1 tron return 0;
5838 1.1 tron name = poolCopyString(&(newDtd->pool), oldA->name);
5839 1.1 tron if (!name)
5840 1.1 tron return 0;
5841 1.1 tron ++name;
5842 1.3 spz newA = (ATTRIBUTE_ID *)lookup(oldParser, &(newDtd->attributeIds), name,
5843 1.1 tron sizeof(ATTRIBUTE_ID));
5844 1.1 tron if (!newA)
5845 1.1 tron return 0;
5846 1.1 tron newA->maybeTokenized = oldA->maybeTokenized;
5847 1.1 tron if (oldA->prefix) {
5848 1.1 tron newA->xmlns = oldA->xmlns;
5849 1.1 tron if (oldA->prefix == &oldDtd->defaultPrefix)
5850 1.1 tron newA->prefix = &newDtd->defaultPrefix;
5851 1.1 tron else
5852 1.3 spz newA->prefix = (PREFIX *)lookup(oldParser, &(newDtd->prefixes),
5853 1.1 tron oldA->prefix->name, 0);
5854 1.1 tron }
5855 1.1 tron }
5856 1.1 tron
5857 1.1 tron /* Copy the element type table. */
5858 1.1 tron
5859 1.1 tron hashTableIterInit(&iter, &(oldDtd->elementTypes));
5860 1.1 tron
5861 1.1 tron for (;;) {
5862 1.1 tron int i;
5863 1.1 tron ELEMENT_TYPE *newE;
5864 1.1 tron const XML_Char *name;
5865 1.1 tron const ELEMENT_TYPE *oldE = (ELEMENT_TYPE *)hashTableIterNext(&iter);
5866 1.1 tron if (!oldE)
5867 1.1 tron break;
5868 1.1 tron name = poolCopyString(&(newDtd->pool), oldE->name);
5869 1.1 tron if (!name)
5870 1.1 tron return 0;
5871 1.3 spz newE = (ELEMENT_TYPE *)lookup(oldParser, &(newDtd->elementTypes), name,
5872 1.1 tron sizeof(ELEMENT_TYPE));
5873 1.1 tron if (!newE)
5874 1.1 tron return 0;
5875 1.1 tron if (oldE->nDefaultAtts) {
5876 1.1 tron newE->defaultAtts = (DEFAULT_ATTRIBUTE *)
5877 1.1 tron ms->malloc_fcn(oldE->nDefaultAtts * sizeof(DEFAULT_ATTRIBUTE));
5878 1.1 tron if (!newE->defaultAtts) {
5879 1.1 tron ms->free_fcn(newE);
5880 1.1 tron return 0;
5881 1.1 tron }
5882 1.1 tron }
5883 1.1 tron if (oldE->idAtt)
5884 1.1 tron newE->idAtt = (ATTRIBUTE_ID *)
5885 1.3 spz lookup(oldParser, &(newDtd->attributeIds), oldE->idAtt->name, 0);
5886 1.1 tron newE->allocDefaultAtts = newE->nDefaultAtts = oldE->nDefaultAtts;
5887 1.1 tron if (oldE->prefix)
5888 1.3 spz newE->prefix = (PREFIX *)lookup(oldParser, &(newDtd->prefixes),
5889 1.1 tron oldE->prefix->name, 0);
5890 1.1 tron for (i = 0; i < newE->nDefaultAtts; i++) {
5891 1.1 tron newE->defaultAtts[i].id = (ATTRIBUTE_ID *)
5892 1.3 spz lookup(oldParser, &(newDtd->attributeIds), oldE->defaultAtts[i].id->name, 0);
5893 1.1 tron newE->defaultAtts[i].isCdata = oldE->defaultAtts[i].isCdata;
5894 1.1 tron if (oldE->defaultAtts[i].value) {
5895 1.1 tron newE->defaultAtts[i].value
5896 1.1 tron = poolCopyString(&(newDtd->pool), oldE->defaultAtts[i].value);
5897 1.1 tron if (!newE->defaultAtts[i].value)
5898 1.1 tron return 0;
5899 1.1 tron }
5900 1.1 tron else
5901 1.1 tron newE->defaultAtts[i].value = NULL;
5902 1.1 tron }
5903 1.1 tron }
5904 1.1 tron
5905 1.1 tron /* Copy the entity tables. */
5906 1.3 spz if (!copyEntityTable(oldParser,
5907 1.3 spz &(newDtd->generalEntities),
5908 1.1 tron &(newDtd->pool),
5909 1.1 tron &(oldDtd->generalEntities)))
5910 1.1 tron return 0;
5911 1.1 tron
5912 1.1 tron #ifdef XML_DTD
5913 1.3 spz if (!copyEntityTable(oldParser,
5914 1.3 spz &(newDtd->paramEntities),
5915 1.1 tron &(newDtd->pool),
5916 1.1 tron &(oldDtd->paramEntities)))
5917 1.1 tron return 0;
5918 1.1 tron newDtd->paramEntityRead = oldDtd->paramEntityRead;
5919 1.1 tron #endif /* XML_DTD */
5920 1.1 tron
5921 1.1 tron newDtd->keepProcessing = oldDtd->keepProcessing;
5922 1.1 tron newDtd->hasParamEntityRefs = oldDtd->hasParamEntityRefs;
5923 1.1 tron newDtd->standalone = oldDtd->standalone;
5924 1.1 tron
5925 1.1 tron /* Don't want deep copying for scaffolding */
5926 1.1 tron newDtd->in_eldecl = oldDtd->in_eldecl;
5927 1.1 tron newDtd->scaffold = oldDtd->scaffold;
5928 1.1 tron newDtd->contentStringLen = oldDtd->contentStringLen;
5929 1.1 tron newDtd->scaffSize = oldDtd->scaffSize;
5930 1.1 tron newDtd->scaffLevel = oldDtd->scaffLevel;
5931 1.1 tron newDtd->scaffIndex = oldDtd->scaffIndex;
5932 1.1 tron
5933 1.1 tron return 1;
5934 1.1 tron } /* End dtdCopy */
5935 1.1 tron
5936 1.1 tron static int
5937 1.3 spz copyEntityTable(XML_Parser oldParser,
5938 1.3 spz HASH_TABLE *newTable,
5939 1.1 tron STRING_POOL *newPool,
5940 1.1 tron const HASH_TABLE *oldTable)
5941 1.1 tron {
5942 1.1 tron HASH_TABLE_ITER iter;
5943 1.1 tron const XML_Char *cachedOldBase = NULL;
5944 1.1 tron const XML_Char *cachedNewBase = NULL;
5945 1.1 tron
5946 1.1 tron hashTableIterInit(&iter, oldTable);
5947 1.1 tron
5948 1.1 tron for (;;) {
5949 1.1 tron ENTITY *newE;
5950 1.1 tron const XML_Char *name;
5951 1.1 tron const ENTITY *oldE = (ENTITY *)hashTableIterNext(&iter);
5952 1.1 tron if (!oldE)
5953 1.1 tron break;
5954 1.1 tron name = poolCopyString(newPool, oldE->name);
5955 1.1 tron if (!name)
5956 1.1 tron return 0;
5957 1.3 spz newE = (ENTITY *)lookup(oldParser, newTable, name, sizeof(ENTITY));
5958 1.1 tron if (!newE)
5959 1.1 tron return 0;
5960 1.1 tron if (oldE->systemId) {
5961 1.1 tron const XML_Char *tem = poolCopyString(newPool, oldE->systemId);
5962 1.1 tron if (!tem)
5963 1.1 tron return 0;
5964 1.1 tron newE->systemId = tem;
5965 1.1 tron if (oldE->base) {
5966 1.1 tron if (oldE->base == cachedOldBase)
5967 1.1 tron newE->base = cachedNewBase;
5968 1.1 tron else {
5969 1.1 tron cachedOldBase = oldE->base;
5970 1.1 tron tem = poolCopyString(newPool, cachedOldBase);
5971 1.1 tron if (!tem)
5972 1.1 tron return 0;
5973 1.1 tron cachedNewBase = newE->base = tem;
5974 1.1 tron }
5975 1.1 tron }
5976 1.1 tron if (oldE->publicId) {
5977 1.1 tron tem = poolCopyString(newPool, oldE->publicId);
5978 1.1 tron if (!tem)
5979 1.1 tron return 0;
5980 1.1 tron newE->publicId = tem;
5981 1.1 tron }
5982 1.1 tron }
5983 1.1 tron else {
5984 1.1 tron const XML_Char *tem = poolCopyStringN(newPool, oldE->textPtr,
5985 1.1 tron oldE->textLen);
5986 1.1 tron if (!tem)
5987 1.1 tron return 0;
5988 1.1 tron newE->textPtr = tem;
5989 1.1 tron newE->textLen = oldE->textLen;
5990 1.1 tron }
5991 1.1 tron if (oldE->notation) {
5992 1.1 tron const XML_Char *tem = poolCopyString(newPool, oldE->notation);
5993 1.1 tron if (!tem)
5994 1.1 tron return 0;
5995 1.1 tron newE->notation = tem;
5996 1.1 tron }
5997 1.1 tron newE->is_param = oldE->is_param;
5998 1.1 tron newE->is_internal = oldE->is_internal;
5999 1.1 tron }
6000 1.1 tron return 1;
6001 1.1 tron }
6002 1.1 tron
6003 1.1 tron #define INIT_POWER 6
6004 1.1 tron
6005 1.1 tron static XML_Bool FASTCALL
6006 1.1 tron keyeq(KEY s1, KEY s2)
6007 1.1 tron {
6008 1.1 tron for (; *s1 == *s2; s1++, s2++)
6009 1.1 tron if (*s1 == 0)
6010 1.1 tron return XML_TRUE;
6011 1.1 tron return XML_FALSE;
6012 1.1 tron }
6013 1.1 tron
6014 1.1 tron static unsigned long FASTCALL
6015 1.3 spz hash(XML_Parser parser, KEY s)
6016 1.1 tron {
6017 1.3 spz unsigned long h = hash_secret_salt;
6018 1.1 tron while (*s)
6019 1.1 tron h = CHAR_HASH(h, *s++);
6020 1.1 tron return h;
6021 1.1 tron }
6022 1.1 tron
6023 1.1 tron static NAMED *
6024 1.3 spz lookup(XML_Parser parser, HASH_TABLE *table, KEY name, size_t createSize)
6025 1.1 tron {
6026 1.1 tron size_t i;
6027 1.1 tron if (table->size == 0) {
6028 1.1 tron size_t tsize;
6029 1.1 tron if (!createSize)
6030 1.1 tron return NULL;
6031 1.1 tron table->power = INIT_POWER;
6032 1.1 tron /* table->size is a power of 2 */
6033 1.1 tron table->size = (size_t)1 << INIT_POWER;
6034 1.1 tron tsize = table->size * sizeof(NAMED *);
6035 1.1 tron table->v = (NAMED **)table->mem->malloc_fcn(tsize);
6036 1.1 tron if (!table->v) {
6037 1.1 tron table->size = 0;
6038 1.1 tron return NULL;
6039 1.1 tron }
6040 1.1 tron memset(table->v, 0, tsize);
6041 1.3 spz i = hash(parser, name) & ((unsigned long)table->size - 1);
6042 1.1 tron }
6043 1.1 tron else {
6044 1.3 spz unsigned long h = hash(parser, name);
6045 1.1 tron unsigned long mask = (unsigned long)table->size - 1;
6046 1.1 tron unsigned char step = 0;
6047 1.1 tron i = h & mask;
6048 1.1 tron while (table->v[i]) {
6049 1.1 tron if (keyeq(name, table->v[i]->name))
6050 1.1 tron return table->v[i];
6051 1.1 tron if (!step)
6052 1.1 tron step = PROBE_STEP(h, mask, table->power);
6053 1.1 tron i < step ? (i += table->size - step) : (i -= step);
6054 1.1 tron }
6055 1.1 tron if (!createSize)
6056 1.1 tron return NULL;
6057 1.1 tron
6058 1.1 tron /* check for overflow (table is half full) */
6059 1.1 tron if (table->used >> (table->power - 1)) {
6060 1.1 tron unsigned char newPower = table->power + 1;
6061 1.1 tron size_t newSize = (size_t)1 << newPower;
6062 1.1 tron unsigned long newMask = (unsigned long)newSize - 1;
6063 1.1 tron size_t tsize = newSize * sizeof(NAMED *);
6064 1.1 tron NAMED **newV = (NAMED **)table->mem->malloc_fcn(tsize);
6065 1.1 tron if (!newV)
6066 1.1 tron return NULL;
6067 1.1 tron memset(newV, 0, tsize);
6068 1.1 tron for (i = 0; i < table->size; i++)
6069 1.1 tron if (table->v[i]) {
6070 1.3 spz unsigned long newHash = hash(parser, table->v[i]->name);
6071 1.1 tron size_t j = newHash & newMask;
6072 1.1 tron step = 0;
6073 1.1 tron while (newV[j]) {
6074 1.1 tron if (!step)
6075 1.1 tron step = PROBE_STEP(newHash, newMask, newPower);
6076 1.1 tron j < step ? (j += newSize - step) : (j -= step);
6077 1.1 tron }
6078 1.1 tron newV[j] = table->v[i];
6079 1.1 tron }
6080 1.1 tron table->mem->free_fcn(table->v);
6081 1.1 tron table->v = newV;
6082 1.1 tron table->power = newPower;
6083 1.1 tron table->size = newSize;
6084 1.1 tron i = h & newMask;
6085 1.1 tron step = 0;
6086 1.1 tron while (table->v[i]) {
6087 1.1 tron if (!step)
6088 1.1 tron step = PROBE_STEP(h, newMask, newPower);
6089 1.1 tron i < step ? (i += newSize - step) : (i -= step);
6090 1.1 tron }
6091 1.1 tron }
6092 1.1 tron }
6093 1.1 tron table->v[i] = (NAMED *)table->mem->malloc_fcn(createSize);
6094 1.1 tron if (!table->v[i])
6095 1.1 tron return NULL;
6096 1.1 tron memset(table->v[i], 0, createSize);
6097 1.1 tron table->v[i]->name = name;
6098 1.1 tron (table->used)++;
6099 1.1 tron return table->v[i];
6100 1.1 tron }
6101 1.1 tron
6102 1.1 tron static void FASTCALL
6103 1.1 tron hashTableClear(HASH_TABLE *table)
6104 1.1 tron {
6105 1.1 tron size_t i;
6106 1.1 tron for (i = 0; i < table->size; i++) {
6107 1.1 tron table->mem->free_fcn(table->v[i]);
6108 1.1 tron table->v[i] = NULL;
6109 1.1 tron }
6110 1.1 tron table->used = 0;
6111 1.1 tron }
6112 1.1 tron
6113 1.1 tron static void FASTCALL
6114 1.1 tron hashTableDestroy(HASH_TABLE *table)
6115 1.1 tron {
6116 1.1 tron size_t i;
6117 1.1 tron for (i = 0; i < table->size; i++)
6118 1.1 tron table->mem->free_fcn(table->v[i]);
6119 1.1 tron table->mem->free_fcn(table->v);
6120 1.1 tron }
6121 1.1 tron
6122 1.1 tron static void FASTCALL
6123 1.1 tron hashTableInit(HASH_TABLE *p, const XML_Memory_Handling_Suite *ms)
6124 1.1 tron {
6125 1.1 tron p->power = 0;
6126 1.1 tron p->size = 0;
6127 1.1 tron p->used = 0;
6128 1.1 tron p->v = NULL;
6129 1.1 tron p->mem = ms;
6130 1.1 tron }
6131 1.1 tron
6132 1.1 tron static void FASTCALL
6133 1.1 tron hashTableIterInit(HASH_TABLE_ITER *iter, const HASH_TABLE *table)
6134 1.1 tron {
6135 1.1 tron iter->p = table->v;
6136 1.1 tron iter->end = iter->p + table->size;
6137 1.1 tron }
6138 1.1 tron
6139 1.1 tron static NAMED * FASTCALL
6140 1.1 tron hashTableIterNext(HASH_TABLE_ITER *iter)
6141 1.1 tron {
6142 1.1 tron while (iter->p != iter->end) {
6143 1.1 tron NAMED *tem = *(iter->p)++;
6144 1.1 tron if (tem)
6145 1.1 tron return tem;
6146 1.1 tron }
6147 1.1 tron return NULL;
6148 1.1 tron }
6149 1.1 tron
6150 1.1 tron static void FASTCALL
6151 1.1 tron poolInit(STRING_POOL *pool, const XML_Memory_Handling_Suite *ms)
6152 1.1 tron {
6153 1.1 tron pool->blocks = NULL;
6154 1.1 tron pool->freeBlocks = NULL;
6155 1.1 tron pool->start = NULL;
6156 1.1 tron pool->ptr = NULL;
6157 1.1 tron pool->end = NULL;
6158 1.1 tron pool->mem = ms;
6159 1.1 tron }
6160 1.1 tron
6161 1.1 tron static void FASTCALL
6162 1.1 tron poolClear(STRING_POOL *pool)
6163 1.1 tron {
6164 1.1 tron if (!pool->freeBlocks)
6165 1.1 tron pool->freeBlocks = pool->blocks;
6166 1.1 tron else {
6167 1.1 tron BLOCK *p = pool->blocks;
6168 1.1 tron while (p) {
6169 1.1 tron BLOCK *tem = p->next;
6170 1.1 tron p->next = pool->freeBlocks;
6171 1.1 tron pool->freeBlocks = p;
6172 1.1 tron p = tem;
6173 1.1 tron }
6174 1.1 tron }
6175 1.1 tron pool->blocks = NULL;
6176 1.1 tron pool->start = NULL;
6177 1.1 tron pool->ptr = NULL;
6178 1.1 tron pool->end = NULL;
6179 1.1 tron }
6180 1.1 tron
6181 1.1 tron static void FASTCALL
6182 1.1 tron poolDestroy(STRING_POOL *pool)
6183 1.1 tron {
6184 1.1 tron BLOCK *p = pool->blocks;
6185 1.1 tron while (p) {
6186 1.1 tron BLOCK *tem = p->next;
6187 1.1 tron pool->mem->free_fcn(p);
6188 1.1 tron p = tem;
6189 1.1 tron }
6190 1.1 tron p = pool->freeBlocks;
6191 1.1 tron while (p) {
6192 1.1 tron BLOCK *tem = p->next;
6193 1.1 tron pool->mem->free_fcn(p);
6194 1.1 tron p = tem;
6195 1.1 tron }
6196 1.1 tron }
6197 1.1 tron
6198 1.1 tron static XML_Char *
6199 1.1 tron poolAppend(STRING_POOL *pool, const ENCODING *enc,
6200 1.1 tron const char *ptr, const char *end)
6201 1.1 tron {
6202 1.1 tron if (!pool->ptr && !poolGrow(pool))
6203 1.1 tron return NULL;
6204 1.1 tron for (;;) {
6205 1.5 spz const enum XML_Convert_Result convert_res = XmlConvert(enc, &ptr, end, (ICHAR **)&(pool->ptr), (ICHAR *)pool->end);
6206 1.5 spz if ((convert_res == XML_CONVERT_COMPLETED) || (convert_res == XML_CONVERT_INPUT_INCOMPLETE))
6207 1.1 tron break;
6208 1.1 tron if (!poolGrow(pool))
6209 1.1 tron return NULL;
6210 1.1 tron }
6211 1.1 tron return pool->start;
6212 1.1 tron }
6213 1.1 tron
6214 1.1 tron static const XML_Char * FASTCALL
6215 1.1 tron poolCopyString(STRING_POOL *pool, const XML_Char *s)
6216 1.1 tron {
6217 1.1 tron do {
6218 1.1 tron if (!poolAppendChar(pool, *s))
6219 1.1 tron return NULL;
6220 1.1 tron } while (*s++);
6221 1.1 tron s = pool->start;
6222 1.1 tron poolFinish(pool);
6223 1.1 tron return s;
6224 1.1 tron }
6225 1.1 tron
6226 1.1 tron static const XML_Char *
6227 1.1 tron poolCopyStringN(STRING_POOL *pool, const XML_Char *s, int n)
6228 1.1 tron {
6229 1.1 tron if (!pool->ptr && !poolGrow(pool))
6230 1.1 tron return NULL;
6231 1.1 tron for (; n > 0; --n, s++) {
6232 1.1 tron if (!poolAppendChar(pool, *s))
6233 1.1 tron return NULL;
6234 1.1 tron }
6235 1.1 tron s = pool->start;
6236 1.1 tron poolFinish(pool);
6237 1.1 tron return s;
6238 1.1 tron }
6239 1.1 tron
6240 1.1 tron static const XML_Char * FASTCALL
6241 1.1 tron poolAppendString(STRING_POOL *pool, const XML_Char *s)
6242 1.1 tron {
6243 1.1 tron while (*s) {
6244 1.1 tron if (!poolAppendChar(pool, *s))
6245 1.1 tron return NULL;
6246 1.1 tron s++;
6247 1.1 tron }
6248 1.1 tron return pool->start;
6249 1.1 tron }
6250 1.1 tron
6251 1.1 tron static XML_Char *
6252 1.1 tron poolStoreString(STRING_POOL *pool, const ENCODING *enc,
6253 1.1 tron const char *ptr, const char *end)
6254 1.1 tron {
6255 1.1 tron if (!poolAppend(pool, enc, ptr, end))
6256 1.1 tron return NULL;
6257 1.1 tron if (pool->ptr == pool->end && !poolGrow(pool))
6258 1.1 tron return NULL;
6259 1.1 tron *(pool->ptr)++ = 0;
6260 1.1 tron return pool->start;
6261 1.1 tron }
6262 1.1 tron
6263 1.1 tron static XML_Bool FASTCALL
6264 1.1 tron poolGrow(STRING_POOL *pool)
6265 1.1 tron {
6266 1.1 tron if (pool->freeBlocks) {
6267 1.1 tron if (pool->start == 0) {
6268 1.1 tron pool->blocks = pool->freeBlocks;
6269 1.1 tron pool->freeBlocks = pool->freeBlocks->next;
6270 1.1 tron pool->blocks->next = NULL;
6271 1.1 tron pool->start = pool->blocks->s;
6272 1.1 tron pool->end = pool->start + pool->blocks->size;
6273 1.1 tron pool->ptr = pool->start;
6274 1.1 tron return XML_TRUE;
6275 1.1 tron }
6276 1.1 tron if (pool->end - pool->start < pool->freeBlocks->size) {
6277 1.1 tron BLOCK *tem = pool->freeBlocks->next;
6278 1.1 tron pool->freeBlocks->next = pool->blocks;
6279 1.1 tron pool->blocks = pool->freeBlocks;
6280 1.1 tron pool->freeBlocks = tem;
6281 1.1 tron memcpy(pool->blocks->s, pool->start,
6282 1.1 tron (pool->end - pool->start) * sizeof(XML_Char));
6283 1.1 tron pool->ptr = pool->blocks->s + (pool->ptr - pool->start);
6284 1.1 tron pool->start = pool->blocks->s;
6285 1.1 tron pool->end = pool->start + pool->blocks->size;
6286 1.1 tron return XML_TRUE;
6287 1.1 tron }
6288 1.1 tron }
6289 1.1 tron if (pool->blocks && pool->start == pool->blocks->s) {
6290 1.5 spz BLOCK *temp;
6291 1.5 spz int blockSize = (int)((unsigned)(pool->end - pool->start)*2U);
6292 1.5 spz
6293 1.5 spz if (blockSize < 0)
6294 1.5 spz return XML_FALSE;
6295 1.5 spz
6296 1.5 spz temp = (BLOCK *)
6297 1.1 tron pool->mem->realloc_fcn(pool->blocks,
6298 1.1 tron (offsetof(BLOCK, s)
6299 1.1 tron + blockSize * sizeof(XML_Char)));
6300 1.3 spz if (temp == NULL)
6301 1.1 tron return XML_FALSE;
6302 1.3 spz pool->blocks = temp;
6303 1.1 tron pool->blocks->size = blockSize;
6304 1.1 tron pool->ptr = pool->blocks->s + (pool->ptr - pool->start);
6305 1.1 tron pool->start = pool->blocks->s;
6306 1.1 tron pool->end = pool->start + blockSize;
6307 1.1 tron }
6308 1.1 tron else {
6309 1.1 tron BLOCK *tem;
6310 1.1 tron int blockSize = (int)(pool->end - pool->start);
6311 1.5 spz
6312 1.5 spz if (blockSize < 0)
6313 1.5 spz return XML_FALSE;
6314 1.5 spz
6315 1.1 tron if (blockSize < INIT_BLOCK_SIZE)
6316 1.1 tron blockSize = INIT_BLOCK_SIZE;
6317 1.1 tron else
6318 1.1 tron blockSize *= 2;
6319 1.1 tron tem = (BLOCK *)pool->mem->malloc_fcn(offsetof(BLOCK, s)
6320 1.1 tron + blockSize * sizeof(XML_Char));
6321 1.1 tron if (!tem)
6322 1.1 tron return XML_FALSE;
6323 1.1 tron tem->size = blockSize;
6324 1.1 tron tem->next = pool->blocks;
6325 1.1 tron pool->blocks = tem;
6326 1.1 tron if (pool->ptr != pool->start)
6327 1.1 tron memcpy(tem->s, pool->start,
6328 1.1 tron (pool->ptr - pool->start) * sizeof(XML_Char));
6329 1.1 tron pool->ptr = tem->s + (pool->ptr - pool->start);
6330 1.1 tron pool->start = tem->s;
6331 1.1 tron pool->end = tem->s + blockSize;
6332 1.1 tron }
6333 1.1 tron return XML_TRUE;
6334 1.1 tron }
6335 1.1 tron
6336 1.1 tron static int FASTCALL
6337 1.1 tron nextScaffoldPart(XML_Parser parser)
6338 1.1 tron {
6339 1.1 tron DTD * const dtd = _dtd; /* save one level of indirection */
6340 1.1 tron CONTENT_SCAFFOLD * me;
6341 1.1 tron int next;
6342 1.1 tron
6343 1.1 tron if (!dtd->scaffIndex) {
6344 1.1 tron dtd->scaffIndex = (int *)MALLOC(groupSize * sizeof(int));
6345 1.1 tron if (!dtd->scaffIndex)
6346 1.1 tron return -1;
6347 1.1 tron dtd->scaffIndex[0] = 0;
6348 1.1 tron }
6349 1.1 tron
6350 1.1 tron if (dtd->scaffCount >= dtd->scaffSize) {
6351 1.1 tron CONTENT_SCAFFOLD *temp;
6352 1.1 tron if (dtd->scaffold) {
6353 1.1 tron temp = (CONTENT_SCAFFOLD *)
6354 1.1 tron REALLOC(dtd->scaffold, dtd->scaffSize * 2 * sizeof(CONTENT_SCAFFOLD));
6355 1.1 tron if (temp == NULL)
6356 1.1 tron return -1;
6357 1.1 tron dtd->scaffSize *= 2;
6358 1.1 tron }
6359 1.1 tron else {
6360 1.1 tron temp = (CONTENT_SCAFFOLD *)MALLOC(INIT_SCAFFOLD_ELEMENTS
6361 1.1 tron * sizeof(CONTENT_SCAFFOLD));
6362 1.1 tron if (temp == NULL)
6363 1.1 tron return -1;
6364 1.1 tron dtd->scaffSize = INIT_SCAFFOLD_ELEMENTS;
6365 1.1 tron }
6366 1.1 tron dtd->scaffold = temp;
6367 1.1 tron }
6368 1.1 tron next = dtd->scaffCount++;
6369 1.1 tron me = &dtd->scaffold[next];
6370 1.1 tron if (dtd->scaffLevel) {
6371 1.1 tron CONTENT_SCAFFOLD *parent = &dtd->scaffold[dtd->scaffIndex[dtd->scaffLevel-1]];
6372 1.1 tron if (parent->lastchild) {
6373 1.1 tron dtd->scaffold[parent->lastchild].nextsib = next;
6374 1.1 tron }
6375 1.1 tron if (!parent->childcnt)
6376 1.1 tron parent->firstchild = next;
6377 1.1 tron parent->lastchild = next;
6378 1.1 tron parent->childcnt++;
6379 1.1 tron }
6380 1.1 tron me->firstchild = me->lastchild = me->childcnt = me->nextsib = 0;
6381 1.1 tron return next;
6382 1.1 tron }
6383 1.1 tron
6384 1.1 tron static void
6385 1.1 tron build_node(XML_Parser parser,
6386 1.1 tron int src_node,
6387 1.1 tron XML_Content *dest,
6388 1.1 tron XML_Content **contpos,
6389 1.1 tron XML_Char **strpos)
6390 1.1 tron {
6391 1.1 tron DTD * const dtd = _dtd; /* save one level of indirection */
6392 1.1 tron dest->type = dtd->scaffold[src_node].type;
6393 1.1 tron dest->quant = dtd->scaffold[src_node].quant;
6394 1.1 tron if (dest->type == XML_CTYPE_NAME) {
6395 1.1 tron const XML_Char *src;
6396 1.1 tron dest->name = *strpos;
6397 1.1 tron src = dtd->scaffold[src_node].name;
6398 1.1 tron for (;;) {
6399 1.1 tron *(*strpos)++ = *src;
6400 1.1 tron if (!*src)
6401 1.1 tron break;
6402 1.1 tron src++;
6403 1.1 tron }
6404 1.1 tron dest->numchildren = 0;
6405 1.1 tron dest->children = NULL;
6406 1.1 tron }
6407 1.1 tron else {
6408 1.1 tron unsigned int i;
6409 1.1 tron int cn;
6410 1.1 tron dest->numchildren = dtd->scaffold[src_node].childcnt;
6411 1.1 tron dest->children = *contpos;
6412 1.1 tron *contpos += dest->numchildren;
6413 1.1 tron for (i = 0, cn = dtd->scaffold[src_node].firstchild;
6414 1.1 tron i < dest->numchildren;
6415 1.1 tron i++, cn = dtd->scaffold[cn].nextsib) {
6416 1.1 tron build_node(parser, cn, &(dest->children[i]), contpos, strpos);
6417 1.1 tron }
6418 1.1 tron dest->name = NULL;
6419 1.1 tron }
6420 1.1 tron }
6421 1.1 tron
6422 1.1 tron static XML_Content *
6423 1.1 tron build_model (XML_Parser parser)
6424 1.1 tron {
6425 1.1 tron DTD * const dtd = _dtd; /* save one level of indirection */
6426 1.1 tron XML_Content *ret;
6427 1.1 tron XML_Content *cpos;
6428 1.1 tron XML_Char * str;
6429 1.1 tron int allocsize = (dtd->scaffCount * sizeof(XML_Content)
6430 1.1 tron + (dtd->contentStringLen * sizeof(XML_Char)));
6431 1.1 tron
6432 1.1 tron ret = (XML_Content *)MALLOC(allocsize);
6433 1.1 tron if (!ret)
6434 1.1 tron return NULL;
6435 1.1 tron
6436 1.1 tron str = (XML_Char *) (&ret[dtd->scaffCount]);
6437 1.1 tron cpos = &ret[1];
6438 1.1 tron
6439 1.1 tron build_node(parser, 0, ret, &cpos, &str);
6440 1.1 tron return ret;
6441 1.1 tron }
6442 1.1 tron
6443 1.1 tron static ELEMENT_TYPE *
6444 1.1 tron getElementType(XML_Parser parser,
6445 1.1 tron const ENCODING *enc,
6446 1.1 tron const char *ptr,
6447 1.1 tron const char *end)
6448 1.1 tron {
6449 1.1 tron DTD * const dtd = _dtd; /* save one level of indirection */
6450 1.1 tron const XML_Char *name = poolStoreString(&dtd->pool, enc, ptr, end);
6451 1.1 tron ELEMENT_TYPE *ret;
6452 1.1 tron
6453 1.1 tron if (!name)
6454 1.1 tron return NULL;
6455 1.3 spz ret = (ELEMENT_TYPE *) lookup(parser, &dtd->elementTypes, name, sizeof(ELEMENT_TYPE));
6456 1.1 tron if (!ret)
6457 1.1 tron return NULL;
6458 1.1 tron if (ret->name != name)
6459 1.1 tron poolDiscard(&dtd->pool);
6460 1.1 tron else {
6461 1.1 tron poolFinish(&dtd->pool);
6462 1.1 tron if (!setElementTypePrefix(parser, ret))
6463 1.1 tron return NULL;
6464 1.1 tron }
6465 1.1 tron return ret;
6466 1.1 tron }
6467