blob: c61f81db9534679297fcf0a4b33032f5eb895773 [file] [log] [blame]
Daniel Veillard260a68f1998-08-13 03:39:55 +00001/*
2 * entities.c : implementation for the XML entities handking
3 *
4 * See Copyright for the status of this software.
5 *
Daniel Veillard39a1f9a1999-01-17 19:11:59 +00006 * Daniel.Veillard@w3.org
Daniel Veillard260a68f1998-08-13 03:39:55 +00007 */
8
9#include <stdio.h>
Seth Alvese7f12e61998-10-01 20:51:15 +000010#include <stdlib.h>
Daniel Veillard260a68f1998-08-13 03:39:55 +000011#include <string.h>
12#include "entities.h"
13
14/*
15 * The XML predefined entities.
16 */
17
18struct xmlPredefinedEntityValue {
19 const char *name;
20 const char *value;
21};
22struct xmlPredefinedEntityValue xmlPredefinedEntityValues[] = {
23 { "lt", "<" },
24 { "gt", ">" },
25 { "apos", "'" },
26 { "quot", "\"" },
27 { "amp", "&" }
28};
29
30xmlEntitiesTablePtr xmlPredefinedEntities = NULL;
31
32/*
Daniel Veillard011b63c1999-06-02 17:44:04 +000033 * Macro used to grow the current buffer.
Daniel Veillard260a68f1998-08-13 03:39:55 +000034 */
Daniel Veillard011b63c1999-06-02 17:44:04 +000035#define growBuffer() { \
36 buffer_size *= 2; \
37 buffer = (CHAR *) realloc(buffer, buffer_size * sizeof(CHAR)); \
38 if (buffer == NULL) { \
39 perror("realloc failed"); \
40 exit(1); \
41 } \
Daniel Veillard260a68f1998-08-13 03:39:55 +000042}
43
Daniel Veillard011b63c1999-06-02 17:44:04 +000044
Daniel Veillard260a68f1998-08-13 03:39:55 +000045/*
46 * xmlFreeEntity : clean-up an entity record.
47 */
Daniel Veillard260a68f1998-08-13 03:39:55 +000048void xmlFreeEntity(xmlEntityPtr entity) {
49 if (entity == NULL) return;
50
51 if (entity->name != NULL)
52 free((char *) entity->name);
53 if (entity->ExternalID != NULL)
54 free((char *) entity->ExternalID);
55 if (entity->SystemID != NULL)
56 free((char *) entity->SystemID);
57 if (entity->content != NULL)
58 free((char *) entity->content);
Daniel Veillard011b63c1999-06-02 17:44:04 +000059 if (entity->orig != NULL)
60 free((char *) entity->orig);
Daniel Veillard260a68f1998-08-13 03:39:55 +000061 memset(entity, -1, sizeof(xmlEntity));
62}
63
64/*
Daniel Veillardbe36afe1998-11-27 06:39:50 +000065 * xmlAddEntity : register a new entity for an entities table.
Daniel Veillard260a68f1998-08-13 03:39:55 +000066 *
67 * TODO !!! We should check here that the combination of type
68 * ExternalID and SystemID is valid.
69 */
Daniel Veillardbe36afe1998-11-27 06:39:50 +000070static void
71xmlAddEntity(xmlEntitiesTablePtr table, const CHAR *name, int type,
Daniel Veillard260a68f1998-08-13 03:39:55 +000072 const CHAR *ExternalID, const CHAR *SystemID, CHAR *content) {
73 int i;
74 xmlEntityPtr cur;
75 int len;
76
77 for (i = 0;i < table->nb_entities;i++) {
78 cur = &table->table[i];
79 if (!xmlStrcmp(cur->name, name)) {
80 /*
81 * The entity is already defined in this Dtd, the spec says to NOT
82 * override it ... Is it worth a Warning ??? !!!
83 */
84 return;
85 }
86 }
87 if (table->nb_entities >= table->max_entities) {
88 /*
89 * need more elements.
90 */
91 table->max_entities *= 2;
92 table->table = (xmlEntityPtr)
93 realloc(table->table, table->max_entities * sizeof(xmlEntity));
94 if (table->table) {
95 perror("realloc failed");
96 exit(1);
97 }
98 }
99 cur = &table->table[table->nb_entities];
100 cur->name = xmlStrdup(name);
101 for (len = 0;name[0] != 0;name++)len++;
102 cur->len = len;
103 cur->type = type;
104 if (ExternalID != NULL)
105 cur->ExternalID = xmlStrdup(ExternalID);
106 else
107 cur->ExternalID = NULL;
108 if (SystemID != NULL)
109 cur->SystemID = xmlStrdup(SystemID);
110 else
111 cur->SystemID = NULL;
112 if (content != NULL)
113 cur->content = xmlStrdup(content);
114 else
115 cur->content = NULL;
Daniel Veillard011b63c1999-06-02 17:44:04 +0000116 cur->orig = NULL;
Daniel Veillard260a68f1998-08-13 03:39:55 +0000117 table->nb_entities++;
118}
119
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000120/**
121 * xmlInitializePredefinedEntities:
122 *
123 * Set up the predefined entities.
Daniel Veillard260a68f1998-08-13 03:39:55 +0000124 */
125void xmlInitializePredefinedEntities(void) {
126 int i;
127 CHAR name[50];
128 CHAR value[50];
129 const char *in;
130 CHAR *out;
131
132 if (xmlPredefinedEntities != NULL) return;
133
134 xmlPredefinedEntities = xmlCreateEntitiesTable();
135 for (i = 0;i < sizeof(xmlPredefinedEntityValues) /
136 sizeof(xmlPredefinedEntityValues[0]);i++) {
137 in = xmlPredefinedEntityValues[i].name;
138 out = &name[0];
139 for (;(*out++ = (CHAR) *in);)in++;
140 in = xmlPredefinedEntityValues[i].value;
141 out = &value[0];
142 for (;(*out++ = (CHAR) *in);)in++;
143 xmlAddEntity(xmlPredefinedEntities, (const CHAR *) &name[0],
Daniel Veillard25940b71998-10-29 05:51:30 +0000144 XML_INTERNAL_PREDEFINED_ENTITY, NULL, NULL,
Daniel Veillard260a68f1998-08-13 03:39:55 +0000145 &value[0]);
146 }
147}
148
Daniel Veillardccb09631998-10-27 06:21:04 +0000149/**
150 * xmlGetPredefinedEntity:
151 * @name: the entity name
152 *
153 * Check whether this name is an predefined entity.
154 *
Daniel Veillard1e346af1999-02-22 10:33:01 +0000155 * Returns NULL if not, othervise the entity
Daniel Veillardccb09631998-10-27 06:21:04 +0000156 */
157xmlEntityPtr
158xmlGetPredefinedEntity(const CHAR *name) {
159 int i;
160 xmlEntityPtr cur;
161
162 if (xmlPredefinedEntities == NULL)
163 xmlInitializePredefinedEntities();
164 for (i = 0;i < xmlPredefinedEntities->nb_entities;i++) {
165 cur = &xmlPredefinedEntities->table[i];
166 if (!xmlStrcmp(cur->name, name)) return(cur);
167 }
168 return(NULL);
169}
170
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000171/**
172 * xmlAddDtdEntity:
173 * @doc: the document
174 * @name: the entity name
175 * @type: the entity type XML_xxx_yyy_ENTITY
176 * @ExternalID: the entity external ID if available
177 * @SystemID: the entity system ID if available
178 * @content: the entity content
179 *
180 * Register a new entity for this document DTD.
Daniel Veillard260a68f1998-08-13 03:39:55 +0000181 */
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000182void
183xmlAddDtdEntity(xmlDocPtr doc, const CHAR *name, int type,
Daniel Veillard260a68f1998-08-13 03:39:55 +0000184 const CHAR *ExternalID, const CHAR *SystemID, CHAR *content) {
185 xmlEntitiesTablePtr table;
186
Daniel Veillard39a1f9a1999-01-17 19:11:59 +0000187 if (doc->extSubset == NULL) {
188 fprintf(stderr,
189 "xmlAddDtdEntity: document without external subset !\n");
Daniel Veillard260a68f1998-08-13 03:39:55 +0000190 return;
191 }
Daniel Veillard39a1f9a1999-01-17 19:11:59 +0000192 table = (xmlEntitiesTablePtr) doc->extSubset->entities;
Daniel Veillard260a68f1998-08-13 03:39:55 +0000193 if (table == NULL) {
194 table = xmlCreateEntitiesTable();
Daniel Veillard39a1f9a1999-01-17 19:11:59 +0000195 doc->extSubset->entities = table;
Daniel Veillard260a68f1998-08-13 03:39:55 +0000196 }
197 xmlAddEntity(table, name, type, ExternalID, SystemID, content);
198}
199
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000200/**
201 * xmlAddDocEntity:
202 * @doc: the document
203 * @name: the entity name
204 * @type: the entity type XML_xxx_yyy_ENTITY
205 * @ExternalID: the entity external ID if available
206 * @SystemID: the entity system ID if available
207 * @content: the entity content
208 *
209 * Register a new entity for this document.
Daniel Veillard260a68f1998-08-13 03:39:55 +0000210 */
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000211void
212xmlAddDocEntity(xmlDocPtr doc, const CHAR *name, int type,
Daniel Veillard260a68f1998-08-13 03:39:55 +0000213 const CHAR *ExternalID, const CHAR *SystemID, CHAR *content) {
214 xmlEntitiesTablePtr table;
215
Daniel Veillard39a1f9a1999-01-17 19:11:59 +0000216 if (doc == NULL) {
217 fprintf(stderr,
218 "xmlAddDocEntity: document is NULL !\n");
219 return;
220 }
221 if (doc->intSubset == NULL) {
222 fprintf(stderr,
223 "xmlAddDtdEntity: document without internal subset !\n");
224 return;
225 }
226 table = (xmlEntitiesTablePtr) doc->intSubset->entities;
Daniel Veillard260a68f1998-08-13 03:39:55 +0000227 if (table == NULL) {
228 table = xmlCreateEntitiesTable();
Daniel Veillard39a1f9a1999-01-17 19:11:59 +0000229 doc->intSubset->entities = table;
Daniel Veillard260a68f1998-08-13 03:39:55 +0000230 }
Daniel Veillard39a1f9a1999-01-17 19:11:59 +0000231 xmlAddEntity(table, name, type, ExternalID, SystemID, content);
Daniel Veillard260a68f1998-08-13 03:39:55 +0000232}
233
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000234/**
235 * xmlGetDtdEntity:
236 * @doc: the document referencing the entity
237 * @name: the entity name
238 *
239 * Do an entity lookup in the Dtd entity hash table and
240 * returns the corresponding entity, if found.
241 *
Daniel Veillard1e346af1999-02-22 10:33:01 +0000242 * Returns A pointer to the entity structure or NULL if not found.
Daniel Veillard260a68f1998-08-13 03:39:55 +0000243 */
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000244xmlEntityPtr
245xmlGetDtdEntity(xmlDocPtr doc, const CHAR *name) {
Daniel Veillard260a68f1998-08-13 03:39:55 +0000246 int i;
247 xmlEntityPtr cur;
248 xmlEntitiesTablePtr table;
249
Daniel Veillard39a1f9a1999-01-17 19:11:59 +0000250 if ((doc->extSubset != NULL) && (doc->extSubset->entities != NULL)) {
251 table = (xmlEntitiesTablePtr) doc->extSubset->entities;
Daniel Veillard260a68f1998-08-13 03:39:55 +0000252 for (i = 0;i < table->nb_entities;i++) {
253 cur = &table->table[i];
254 if (!xmlStrcmp(cur->name, name)) return(cur);
255 }
256 }
257 return(NULL);
258}
259
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000260/**
261 * xmlGetDocEntity:
262 * @doc: the document referencing the entity
263 * @name: the entity name
264 *
265 * Do an entity lookup in the document entity hash table and
266 * returns the corrsponding entity, otherwise a lookup is done
267 * in the predefined entities too.
268 *
Daniel Veillard1e346af1999-02-22 10:33:01 +0000269 * Returns A pointer to the entity structure or NULL if not found.
Daniel Veillard260a68f1998-08-13 03:39:55 +0000270 */
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000271xmlEntityPtr
272xmlGetDocEntity(xmlDocPtr doc, const CHAR *name) {
Daniel Veillard260a68f1998-08-13 03:39:55 +0000273 int i;
274 xmlEntityPtr cur;
275 xmlEntitiesTablePtr table;
276
Daniel Veillard39a1f9a1999-01-17 19:11:59 +0000277 if ((doc->intSubset != NULL) && (doc->intSubset->entities != NULL)) {
278 table = (xmlEntitiesTablePtr) doc->intSubset->entities;
Daniel Veillard260a68f1998-08-13 03:39:55 +0000279 for (i = 0;i < table->nb_entities;i++) {
280 cur = &table->table[i];
281 if (!xmlStrcmp(cur->name, name)) return(cur);
282 }
283 }
284 if (xmlPredefinedEntities == NULL)
285 xmlInitializePredefinedEntities();
286 table = xmlPredefinedEntities;
287 for (i = 0;i < table->nb_entities;i++) {
288 cur = &table->table[i];
289 if (!xmlStrcmp(cur->name, name)) return(cur);
290 }
291
292 return(NULL);
293}
294
295/*
Daniel Veillard8cc0d1f1998-11-16 01:04:26 +0000296 * [2] Char ::= #x9 | #xA | #xD | [#x20-#xD7FF] | [#xE000-#xFFFD]
297 * | [#x10000-#x10FFFF]
298 * any Unicode character, excluding the surrogate blocks, FFFE, and FFFF.
299 */
300#define IS_CHAR(c) \
301 (((c) == 0x09) || ((c) == 0x0a) || ((c) == 0x0d) || \
302 (((c) >= 0x20) && ((c) != 0xFFFE) && ((c) != 0xFFFF)))
303
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000304/**
305 * xmlEncodeEntities:
306 * @doc: the document containing the string
307 * @input: A string to convert to XML.
308 *
309 * Do a global encoding of a string, replacing the predefined entities
310 * and non ASCII values with their entities and CharRef counterparts.
311 *
Daniel Veillard0ba4d531998-11-01 19:34:31 +0000312 * TODO !!!! Once moved to UTF-8 internal encoding, the encoding of non-ascii
313 * get erroneous.
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000314 *
Daniel Veillard1e346af1999-02-22 10:33:01 +0000315 * Returns A newly allocated string with the substitution done.
Daniel Veillard260a68f1998-08-13 03:39:55 +0000316 */
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000317CHAR *
318xmlEncodeEntities(xmlDocPtr doc, const CHAR *input) {
Daniel Veillard260a68f1998-08-13 03:39:55 +0000319 const CHAR *cur = input;
Daniel Veillard011b63c1999-06-02 17:44:04 +0000320 CHAR *buffer = NULL;
321 CHAR *out = NULL;
322 int buffer_size = 0;
Daniel Veillard260a68f1998-08-13 03:39:55 +0000323
Daniel Veillard242590e1998-11-13 18:04:35 +0000324 if (input == NULL) return(NULL);
Daniel Veillard011b63c1999-06-02 17:44:04 +0000325
326 /*
327 * allocate an translation buffer.
328 */
329 buffer_size = 1000;
330 buffer = (CHAR *) malloc(buffer_size * sizeof(CHAR));
Daniel Veillard260a68f1998-08-13 03:39:55 +0000331 if (buffer == NULL) {
Daniel Veillard011b63c1999-06-02 17:44:04 +0000332 perror("malloc failed");
333 exit(1);
Daniel Veillard260a68f1998-08-13 03:39:55 +0000334 }
Daniel Veillard011b63c1999-06-02 17:44:04 +0000335 out = buffer;
336
Daniel Veillard260a68f1998-08-13 03:39:55 +0000337 while (*cur != '\0') {
338 if (out - buffer > buffer_size - 100) {
339 int index = out - buffer;
340
341 growBuffer();
342 out = &buffer[index];
343 }
344
345 /*
346 * By default one have to encode at least '<', '>', '"' and '&' !
Daniel Veillard260a68f1998-08-13 03:39:55 +0000347 */
348 if (*cur == '<') {
349 *out++ = '&';
350 *out++ = 'l';
351 *out++ = 't';
352 *out++ = ';';
353 } else if (*cur == '>') {
354 *out++ = '&';
355 *out++ = 'g';
356 *out++ = 't';
357 *out++ = ';';
358 } else if (*cur == '&') {
359 *out++ = '&';
360 *out++ = 'a';
361 *out++ = 'm';
362 *out++ = 'p';
363 *out++ = ';';
364 } else if (*cur == '"') {
365 *out++ = '&';
366 *out++ = 'q';
367 *out++ = 'u';
368 *out++ = 'o';
369 *out++ = 't';
370 *out++ = ';';
371 } else if (*cur == '\'') {
372 *out++ = '&';
373 *out++ = 'a';
374 *out++ = 'p';
375 *out++ = 'o';
376 *out++ = 's';
377 *out++ = ';';
Daniel Veillard8cc0d1f1998-11-16 01:04:26 +0000378 } else if (((*cur >= 0x20) && (*cur < 0x80)) ||
379 (*cur == '\n') || (*cur == '\r') || (*cur == '\t')) {
380 /*
381 * default case, just copy !
382 */
383 *out++ = *cur;
Daniel Veillard0ba4d531998-11-01 19:34:31 +0000384#ifndef USE_UTF_8
385 } else if ((sizeof(CHAR) == 1) && (*cur >= 0x80)) {
386 char buf[10], *ptr;
Daniel Veillardda4d3c41998-11-04 20:07:05 +0000387#ifdef HAVE_SNPRINTF
388 snprintf(buf, 9, "&#%d;", *cur);
389#else
390 sprintf(buf, "&#%d;", *cur);
391#endif
Daniel Veillard0ba4d531998-11-01 19:34:31 +0000392 ptr = buf;
393 while (*ptr != 0) *out++ = *ptr++;
394#endif
Daniel Veillard8cc0d1f1998-11-16 01:04:26 +0000395 } else if (IS_CHAR(*cur)) {
396 char buf[10], *ptr;
397
398#ifdef HAVE_SNPRINTF
399 snprintf(buf, 9, "&#%d;", *cur);
400#else
401 sprintf(buf, "&#%d;", *cur);
402#endif
403 ptr = buf;
404 while (*ptr != 0) *out++ = *ptr++;
Daniel Veillard260a68f1998-08-13 03:39:55 +0000405 }
Daniel Veillard8cc0d1f1998-11-16 01:04:26 +0000406#if 0
407 else {
408 /*
409 * default case, this is not a valid char !
410 * Skip it...
411 */
412 fprintf(stderr, "xmlEncodeEntities: invalid char %d\n", (int) *cur);
413 }
414#endif
Daniel Veillard260a68f1998-08-13 03:39:55 +0000415 cur++;
416 }
417 *out++ = 0;
418 return(buffer);
419}
420
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000421/**
422 * xmlCreateEntitiesTable:
423 *
424 * create and initialize an empty entities hash table.
425 *
Daniel Veillard1e346af1999-02-22 10:33:01 +0000426 * Returns the xmlEntitiesTablePtr just created or NULL in case of error.
Daniel Veillard260a68f1998-08-13 03:39:55 +0000427 */
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000428xmlEntitiesTablePtr
429xmlCreateEntitiesTable(void) {
Daniel Veillard260a68f1998-08-13 03:39:55 +0000430 xmlEntitiesTablePtr ret;
431
432 ret = (xmlEntitiesTablePtr)
433 malloc(sizeof(xmlEntitiesTable));
434 if (ret == NULL) {
435 fprintf(stderr, "xmlCreateEntitiesTable : malloc(%d) failed\n",
436 sizeof(xmlEntitiesTable));
437 return(NULL);
438 }
439 ret->max_entities = XML_MIN_ENTITIES_TABLE;
440 ret->nb_entities = 0;
441 ret->table = (xmlEntityPtr )
442 malloc(ret->max_entities * sizeof(xmlEntity));
443 if (ret == NULL) {
444 fprintf(stderr, "xmlCreateEntitiesTable : malloc(%d) failed\n",
445 ret->max_entities * sizeof(xmlEntity));
446 free(ret);
447 return(NULL);
448 }
449 return(ret);
450}
451
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000452/**
453 * xmlFreeEntitiesTable:
454 * @table: An entity table
455 *
456 * Deallocate the memory used by an entities hash table.
Daniel Veillard260a68f1998-08-13 03:39:55 +0000457 */
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000458void
459xmlFreeEntitiesTable(xmlEntitiesTablePtr table) {
Daniel Veillard260a68f1998-08-13 03:39:55 +0000460 int i;
461
462 if (table == NULL) return;
463
464 for (i = 0;i < table->nb_entities;i++) {
465 xmlFreeEntity(&table->table[i]);
466 }
467 free(table->table);
468 free(table);
469}
470
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000471/**
472 * xmlCopyEntitiesTable:
473 * @table: An entity table
474 *
475 * Build a copy of an entity table.
476 *
Daniel Veillard1e346af1999-02-22 10:33:01 +0000477 * Returns the new xmlEntitiesTablePtr or NULL in case of error.
Daniel Veillard260a68f1998-08-13 03:39:55 +0000478 */
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000479xmlEntitiesTablePtr
480xmlCopyEntitiesTable(xmlEntitiesTablePtr table) {
481 xmlEntitiesTablePtr ret;
482 xmlEntityPtr cur, ent;
483 int i;
484
485 ret = (xmlEntitiesTablePtr) malloc(sizeof(xmlEntitiesTable));
486 if (ret == NULL) {
487 fprintf(stderr, "xmlCopyEntitiesTable: out of memory !\n");
488 return(NULL);
489 }
490 ret->table = (xmlEntityPtr) malloc(table->max_entities *
491 sizeof(xmlEntity));
492 if (ret->table == NULL) {
493 fprintf(stderr, "xmlCopyEntitiesTable: out of memory !\n");
494 free(ret);
495 return(NULL);
496 }
497 ret->max_entities = table->max_entities;
498 ret->nb_entities = table->nb_entities;
499 for (i = 0;i < ret->nb_entities;i++) {
500 cur = &ret->table[i];
501 ent = &table->table[i];
502 cur->len = ent->len;
503 cur->type = ent->type;
504 if (ent->name != NULL)
505 cur->name = xmlStrdup(ent->name);
506 else
507 cur->name = NULL;
508 if (ent->ExternalID != NULL)
509 cur->ExternalID = xmlStrdup(ent->ExternalID);
510 else
511 cur->ExternalID = NULL;
512 if (ent->SystemID != NULL)
513 cur->SystemID = xmlStrdup(ent->SystemID);
514 else
515 cur->SystemID = NULL;
516 if (ent->content != NULL)
517 cur->content = xmlStrdup(ent->content);
518 else
519 cur->content = NULL;
Daniel Veillard011b63c1999-06-02 17:44:04 +0000520 if (ent->orig != NULL)
521 cur->orig = xmlStrdup(ent->orig);
522 else
523 cur->orig = NULL;
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000524 }
525 return(ret);
526}
527
528/**
529 * xmlDumpEntitiesTable:
Daniel Veillard5099ae81999-04-21 20:12:07 +0000530 * @buf: An XML buffer.
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000531 * @table: An entity table
532 *
533 * This will dump the content of the entity table as an XML DTD definition
Daniel Veillardbe36afe1998-11-27 06:39:50 +0000534 */
535void
Daniel Veillard5099ae81999-04-21 20:12:07 +0000536xmlDumpEntitiesTable(xmlBufferPtr buf, xmlEntitiesTablePtr table) {
Daniel Veillard260a68f1998-08-13 03:39:55 +0000537 int i;
538 xmlEntityPtr cur;
539
540 if (table == NULL) return;
541
542 for (i = 0;i < table->nb_entities;i++) {
543 cur = &table->table[i];
544 switch (cur->type) {
545 case XML_INTERNAL_GENERAL_ENTITY:
Daniel Veillard5099ae81999-04-21 20:12:07 +0000546 xmlBufferWriteChar(buf, "<!ENTITY ");
547 xmlBufferWriteCHAR(buf, cur->name);
Daniel Veillard011b63c1999-06-02 17:44:04 +0000548 xmlBufferWriteChar(buf, " ");
549 if (cur->orig != NULL)
550 xmlBufferWriteQuotedString(buf, cur->orig);
551 else
552 xmlBufferWriteQuotedString(buf, cur->content);
553 xmlBufferWriteChar(buf, ">\n");
Daniel Veillard260a68f1998-08-13 03:39:55 +0000554 break;
555 case XML_EXTERNAL_GENERAL_PARSED_ENTITY:
Daniel Veillard5099ae81999-04-21 20:12:07 +0000556 xmlBufferWriteChar(buf, "<!ENTITY ");
557 xmlBufferWriteCHAR(buf, cur->name);
Daniel Veillard260a68f1998-08-13 03:39:55 +0000558 if (cur->ExternalID != NULL) {
Daniel Veillard011b63c1999-06-02 17:44:04 +0000559 xmlBufferWriteChar(buf, " PUBLIC ");
560 xmlBufferWriteQuotedString(buf, cur->ExternalID);
561 xmlBufferWriteChar(buf, " ");
562 xmlBufferWriteQuotedString(buf, cur->SystemID);
Daniel Veillard260a68f1998-08-13 03:39:55 +0000563 } else {
Daniel Veillard011b63c1999-06-02 17:44:04 +0000564 xmlBufferWriteChar(buf, " SYSTEM ");
565 xmlBufferWriteQuotedString(buf, cur->SystemID);
Daniel Veillard260a68f1998-08-13 03:39:55 +0000566 }
Daniel Veillard5099ae81999-04-21 20:12:07 +0000567 xmlBufferWriteChar(buf, ">\n");
Daniel Veillard260a68f1998-08-13 03:39:55 +0000568 break;
569 case XML_EXTERNAL_GENERAL_UNPARSED_ENTITY:
Daniel Veillard5099ae81999-04-21 20:12:07 +0000570 xmlBufferWriteChar(buf, "<!ENTITY ");
571 xmlBufferWriteCHAR(buf, cur->name);
Daniel Veillard260a68f1998-08-13 03:39:55 +0000572 if (cur->ExternalID != NULL) {
Daniel Veillard011b63c1999-06-02 17:44:04 +0000573 xmlBufferWriteChar(buf, " PUBLIC ");
574 xmlBufferWriteQuotedString(buf, cur->ExternalID);
575 xmlBufferWriteChar(buf, " ");
576 xmlBufferWriteQuotedString(buf, cur->SystemID);
Daniel Veillard260a68f1998-08-13 03:39:55 +0000577 } else {
Daniel Veillard011b63c1999-06-02 17:44:04 +0000578 xmlBufferWriteChar(buf, " SYSTEM ");
579 xmlBufferWriteQuotedString(buf, cur->SystemID);
Daniel Veillard260a68f1998-08-13 03:39:55 +0000580 }
581 if (cur->content != NULL) { /* Should be true ! */
Daniel Veillard5099ae81999-04-21 20:12:07 +0000582 xmlBufferWriteChar(buf, " NDATA ");
Daniel Veillard011b63c1999-06-02 17:44:04 +0000583 if (cur->orig != NULL)
584 xmlBufferWriteCHAR(buf, cur->orig);
585 else
586 xmlBufferWriteCHAR(buf, cur->content);
Daniel Veillard260a68f1998-08-13 03:39:55 +0000587 }
Daniel Veillard5099ae81999-04-21 20:12:07 +0000588 xmlBufferWriteChar(buf, ">\n");
Daniel Veillard260a68f1998-08-13 03:39:55 +0000589 break;
590 case XML_INTERNAL_PARAMETER_ENTITY:
Daniel Veillard5099ae81999-04-21 20:12:07 +0000591 xmlBufferWriteChar(buf, "<!ENTITY % ");
592 xmlBufferWriteCHAR(buf, cur->name);
Daniel Veillard011b63c1999-06-02 17:44:04 +0000593 xmlBufferWriteChar(buf, " ");
594 if (cur->orig == NULL)
595 xmlBufferWriteQuotedString(buf, cur->content);
596 else
597 xmlBufferWriteQuotedString(buf, cur->orig);
598 xmlBufferWriteChar(buf, ">\n");
Daniel Veillard260a68f1998-08-13 03:39:55 +0000599 break;
600 case XML_EXTERNAL_PARAMETER_ENTITY:
Daniel Veillard5099ae81999-04-21 20:12:07 +0000601 xmlBufferWriteChar(buf, "<!ENTITY % ");
602 xmlBufferWriteCHAR(buf, cur->name);
Daniel Veillard260a68f1998-08-13 03:39:55 +0000603 if (cur->ExternalID != NULL) {
Daniel Veillard011b63c1999-06-02 17:44:04 +0000604 xmlBufferWriteChar(buf, " PUBLIC ");
605 xmlBufferWriteQuotedString(buf, cur->ExternalID);
606 xmlBufferWriteChar(buf, " ");
607 xmlBufferWriteQuotedString(buf, cur->SystemID);
Daniel Veillard260a68f1998-08-13 03:39:55 +0000608 } else {
Daniel Veillard011b63c1999-06-02 17:44:04 +0000609 xmlBufferWriteChar(buf, " SYSTEM ");
610 xmlBufferWriteQuotedString(buf, cur->SystemID);
Daniel Veillard260a68f1998-08-13 03:39:55 +0000611 }
Daniel Veillard5099ae81999-04-21 20:12:07 +0000612 xmlBufferWriteChar(buf, ">\n");
Daniel Veillard260a68f1998-08-13 03:39:55 +0000613 break;
614 default:
615 fprintf(stderr,
616 "xmlDumpEntitiesTable: internal: unknown type %d\n",
617 cur->type);
618 }
619 }
620}