2
* entities.c : implementation for the XML entities handling
4
* See Copyright for the status of this software.
16
#include <libxml/xmlmemory.h>
17
#include <libxml/hash.h>
18
#include <libxml/entities.h>
19
#include <libxml/parser.h>
20
#include <libxml/parserInternals.h>
21
#include <libxml/xmlerror.h>
22
#include <libxml/globals.h>
23
#include <libxml/dict.h>
26
* The XML predefined entities.
29
static xmlEntity xmlEntityLt = {
30
NULL, XML_ENTITY_DECL, BAD_CAST "lt",
31
NULL, NULL, NULL, NULL, NULL, NULL,
32
BAD_CAST "<", BAD_CAST "<", 1,
33
XML_INTERNAL_PREDEFINED_ENTITY,
34
NULL, NULL, NULL, NULL, 0, 1
36
static xmlEntity xmlEntityGt = {
37
NULL, XML_ENTITY_DECL, BAD_CAST "gt",
38
NULL, NULL, NULL, NULL, NULL, NULL,
39
BAD_CAST ">", BAD_CAST ">", 1,
40
XML_INTERNAL_PREDEFINED_ENTITY,
41
NULL, NULL, NULL, NULL, 0, 1
43
static xmlEntity xmlEntityAmp = {
44
NULL, XML_ENTITY_DECL, BAD_CAST "amp",
45
NULL, NULL, NULL, NULL, NULL, NULL,
46
BAD_CAST "&", BAD_CAST "&", 1,
47
XML_INTERNAL_PREDEFINED_ENTITY,
48
NULL, NULL, NULL, NULL, 0, 1
50
static xmlEntity xmlEntityQuot = {
51
NULL, XML_ENTITY_DECL, BAD_CAST "quot",
52
NULL, NULL, NULL, NULL, NULL, NULL,
53
BAD_CAST "\"", BAD_CAST "\"", 1,
54
XML_INTERNAL_PREDEFINED_ENTITY,
55
NULL, NULL, NULL, NULL, 0, 1
57
static xmlEntity xmlEntityApos = {
58
NULL, XML_ENTITY_DECL, BAD_CAST "apos",
59
NULL, NULL, NULL, NULL, NULL, NULL,
60
BAD_CAST "'", BAD_CAST "'", 1,
61
XML_INTERNAL_PREDEFINED_ENTITY,
62
NULL, NULL, NULL, NULL, 0, 1
66
* xmlEntitiesErrMemory:
67
* @extra: extra informations
69
* Handle an out of memory condition
72
xmlEntitiesErrMemory(const char *extra)
74
__xmlSimpleError(XML_FROM_TREE, XML_ERR_NO_MEMORY, NULL, NULL, extra);
79
* @code: the error code
82
* Handle an out of memory condition
85
xmlEntitiesErr(xmlParserErrors code, const char *msg)
87
__xmlSimpleError(XML_FROM_TREE, code, NULL, msg, NULL);
91
* xmlFreeEntity : clean-up an entity record.
94
xmlFreeEntity(xmlEntityPtr entity)
96
xmlDictPtr dict = NULL;
101
if (entity->doc != NULL)
102
dict = entity->doc->dict;
105
if ((entity->children) && (entity->owner == 1) &&
106
(entity == (xmlEntityPtr) entity->children->parent))
107
xmlFreeNodeList(entity->children);
109
if ((entity->name != NULL) && (!xmlDictOwns(dict, entity->name)))
110
xmlFree((char *) entity->name);
111
if ((entity->ExternalID != NULL) &&
112
(!xmlDictOwns(dict, entity->ExternalID)))
113
xmlFree((char *) entity->ExternalID);
114
if ((entity->SystemID != NULL) &&
115
(!xmlDictOwns(dict, entity->SystemID)))
116
xmlFree((char *) entity->SystemID);
117
if ((entity->URI != NULL) && (!xmlDictOwns(dict, entity->URI)))
118
xmlFree((char *) entity->URI);
119
if ((entity->content != NULL)
120
&& (!xmlDictOwns(dict, entity->content)))
121
xmlFree((char *) entity->content);
122
if ((entity->orig != NULL) && (!xmlDictOwns(dict, entity->orig)))
123
xmlFree((char *) entity->orig);
125
if (entity->name != NULL)
126
xmlFree((char *) entity->name);
127
if (entity->ExternalID != NULL)
128
xmlFree((char *) entity->ExternalID);
129
if (entity->SystemID != NULL)
130
xmlFree((char *) entity->SystemID);
131
if (entity->URI != NULL)
132
xmlFree((char *) entity->URI);
133
if (entity->content != NULL)
134
xmlFree((char *) entity->content);
135
if (entity->orig != NULL)
136
xmlFree((char *) entity->orig);
144
* internal routine doing the entity node strutures allocations
147
xmlCreateEntity(xmlDictPtr dict, const xmlChar *name, int type,
148
const xmlChar *ExternalID, const xmlChar *SystemID,
149
const xmlChar *content) {
152
ret = (xmlEntityPtr) xmlMalloc(sizeof(xmlEntity));
154
xmlEntitiesErrMemory("xmlCreateEntity: malloc failed");
157
memset(ret, 0, sizeof(xmlEntity));
158
ret->type = XML_ENTITY_DECL;
162
* fill the structure.
164
ret->etype = (xmlEntityType) type;
166
ret->name = xmlStrdup(name);
167
if (ExternalID != NULL)
168
ret->ExternalID = xmlStrdup(ExternalID);
169
if (SystemID != NULL)
170
ret->SystemID = xmlStrdup(SystemID);
172
ret->name = xmlDictLookup(dict, name, -1);
173
if (ExternalID != NULL)
174
ret->ExternalID = xmlDictLookup(dict, ExternalID, -1);
175
if (SystemID != NULL)
176
ret->SystemID = xmlDictLookup(dict, SystemID, -1);
178
if (content != NULL) {
179
ret->length = xmlStrlen(content);
180
if ((dict != NULL) && (ret->length < 5))
181
ret->content = (xmlChar *)
182
xmlDictLookup(dict, content, ret->length);
184
ret->content = xmlStrndup(content, ret->length);
189
ret->URI = NULL; /* to be computed by the layer knowing
190
the defining entity */
198
* xmlAddEntity : register a new entity for an entities table.
201
xmlAddEntity(xmlDtdPtr dtd, const xmlChar *name, int type,
202
const xmlChar *ExternalID, const xmlChar *SystemID,
203
const xmlChar *content) {
204
xmlDictPtr dict = NULL;
205
xmlEntitiesTablePtr table = NULL;
212
if (dtd->doc != NULL)
213
dict = dtd->doc->dict;
216
case XML_INTERNAL_GENERAL_ENTITY:
217
case XML_EXTERNAL_GENERAL_PARSED_ENTITY:
218
case XML_EXTERNAL_GENERAL_UNPARSED_ENTITY:
219
if (dtd->entities == NULL)
220
dtd->entities = xmlHashCreateDict(0, dict);
221
table = dtd->entities;
223
case XML_INTERNAL_PARAMETER_ENTITY:
224
case XML_EXTERNAL_PARAMETER_ENTITY:
225
if (dtd->pentities == NULL)
226
dtd->pentities = xmlHashCreateDict(0, dict);
227
table = dtd->pentities;
229
case XML_INTERNAL_PREDEFINED_ENTITY:
234
ret = xmlCreateEntity(dict, name, type, ExternalID, SystemID, content);
239
if (xmlHashAddEntry(table, name, ret)) {
241
* entity was already defined at another level.
250
* xmlGetPredefinedEntity:
251
* @name: the entity name
253
* Check whether this name is an predefined entity.
255
* Returns NULL if not, otherwise the entity
258
xmlGetPredefinedEntity(const xmlChar *name) {
259
if (name == NULL) return(NULL);
262
if (xmlStrEqual(name, BAD_CAST "lt"))
263
return(&xmlEntityLt);
266
if (xmlStrEqual(name, BAD_CAST "gt"))
267
return(&xmlEntityGt);
270
if (xmlStrEqual(name, BAD_CAST "amp"))
271
return(&xmlEntityAmp);
272
if (xmlStrEqual(name, BAD_CAST "apos"))
273
return(&xmlEntityApos);
276
if (xmlStrEqual(name, BAD_CAST "quot"))
277
return(&xmlEntityQuot);
288
* @name: the entity name
289
* @type: the entity type XML_xxx_yyy_ENTITY
290
* @ExternalID: the entity external ID if available
291
* @SystemID: the entity system ID if available
292
* @content: the entity content
294
* Register a new entity for this document DTD external subset.
296
* Returns a pointer to the entity or NULL in case of error
299
xmlAddDtdEntity(xmlDocPtr doc, const xmlChar *name, int type,
300
const xmlChar *ExternalID, const xmlChar *SystemID,
301
const xmlChar *content) {
306
xmlEntitiesErr(XML_DTD_NO_DOC,
307
"xmlAddDtdEntity: document is NULL");
310
if (doc->extSubset == NULL) {
311
xmlEntitiesErr(XML_DTD_NO_DTD,
312
"xmlAddDtdEntity: document without external subset");
315
dtd = doc->extSubset;
316
ret = xmlAddEntity(dtd, name, type, ExternalID, SystemID, content);
317
if (ret == NULL) return(NULL);
324
if (dtd->last == NULL) {
325
dtd->children = dtd->last = (xmlNodePtr) ret;
327
dtd->last->next = (xmlNodePtr) ret;
328
ret->prev = dtd->last;
329
dtd->last = (xmlNodePtr) ret;
337
* @name: the entity name
338
* @type: the entity type XML_xxx_yyy_ENTITY
339
* @ExternalID: the entity external ID if available
340
* @SystemID: the entity system ID if available
341
* @content: the entity content
343
* Register a new entity for this document.
345
* Returns a pointer to the entity or NULL in case of error
348
xmlAddDocEntity(xmlDocPtr doc, const xmlChar *name, int type,
349
const xmlChar *ExternalID, const xmlChar *SystemID,
350
const xmlChar *content) {
355
xmlEntitiesErr(XML_DTD_NO_DOC,
356
"xmlAddDocEntity: document is NULL");
359
if (doc->intSubset == NULL) {
360
xmlEntitiesErr(XML_DTD_NO_DTD,
361
"xmlAddDocEntity: document without internal subset");
364
dtd = doc->intSubset;
365
ret = xmlAddEntity(dtd, name, type, ExternalID, SystemID, content);
366
if (ret == NULL) return(NULL);
373
if (dtd->last == NULL) {
374
dtd->children = dtd->last = (xmlNodePtr) ret;
376
dtd->last->next = (xmlNodePtr) ret;
377
ret->prev = dtd->last;
378
dtd->last = (xmlNodePtr) ret;
386
* @name: the entity name
387
* @type: the entity type XML_xxx_yyy_ENTITY
388
* @ExternalID: the entity external ID if available
389
* @SystemID: the entity system ID if available
390
* @content: the entity content
392
* Create a new entity, this differs from xmlAddDocEntity() that if
393
* the document is NULL or has no internal subset defined, then an
394
* unlinked entity structure will be returned, it is then the responsability
395
* of the caller to link it to the document later or free it when not needed
398
* Returns a pointer to the entity or NULL in case of error
401
xmlNewEntity(xmlDocPtr doc, const xmlChar *name, int type,
402
const xmlChar *ExternalID, const xmlChar *SystemID,
403
const xmlChar *content) {
407
if ((doc != NULL) && (doc->intSubset != NULL)) {
408
return(xmlAddDocEntity(doc, name, type, ExternalID, SystemID, content));
414
ret = xmlCreateEntity(dict, name, type, ExternalID, SystemID, content);
422
* xmlGetEntityFromTable:
423
* @table: an entity table
424
* @name: the entity name
425
* @parameter: look for parameter entities
427
* Do an entity lookup in the table.
428
* returns the corresponding parameter entity, if found.
430
* Returns A pointer to the entity structure or NULL if not found.
433
xmlGetEntityFromTable(xmlEntitiesTablePtr table, const xmlChar *name) {
434
return((xmlEntityPtr) xmlHashLookup(table, name));
438
* xmlGetParameterEntity:
439
* @doc: the document referencing the entity
440
* @name: the entity name
442
* Do an entity lookup in the internal and external subsets and
443
* returns the corresponding parameter entity, if found.
445
* Returns A pointer to the entity structure or NULL if not found.
448
xmlGetParameterEntity(xmlDocPtr doc, const xmlChar *name) {
449
xmlEntitiesTablePtr table;
454
if ((doc->intSubset != NULL) && (doc->intSubset->pentities != NULL)) {
455
table = (xmlEntitiesTablePtr) doc->intSubset->pentities;
456
ret = xmlGetEntityFromTable(table, name);
460
if ((doc->extSubset != NULL) && (doc->extSubset->pentities != NULL)) {
461
table = (xmlEntitiesTablePtr) doc->extSubset->pentities;
462
return(xmlGetEntityFromTable(table, name));
469
* @doc: the document referencing the entity
470
* @name: the entity name
472
* Do an entity lookup in the DTD entity hash table and
473
* returns the corresponding entity, if found.
474
* Note: the first argument is the document node, not the DTD node.
476
* Returns A pointer to the entity structure or NULL if not found.
479
xmlGetDtdEntity(xmlDocPtr doc, const xmlChar *name) {
480
xmlEntitiesTablePtr table;
484
if ((doc->extSubset != NULL) && (doc->extSubset->entities != NULL)) {
485
table = (xmlEntitiesTablePtr) doc->extSubset->entities;
486
return(xmlGetEntityFromTable(table, name));
493
* @doc: the document referencing the entity
494
* @name: the entity name
496
* Do an entity lookup in the document entity hash table and
497
* returns the corresponding entity, otherwise a lookup is done
498
* in the predefined entities too.
500
* Returns A pointer to the entity structure or NULL if not found.
503
xmlGetDocEntity(xmlDocPtr doc, const xmlChar *name) {
505
xmlEntitiesTablePtr table;
508
if ((doc->intSubset != NULL) && (doc->intSubset->entities != NULL)) {
509
table = (xmlEntitiesTablePtr) doc->intSubset->entities;
510
cur = xmlGetEntityFromTable(table, name);
514
if (doc->standalone != 1) {
515
if ((doc->extSubset != NULL) &&
516
(doc->extSubset->entities != NULL)) {
517
table = (xmlEntitiesTablePtr) doc->extSubset->entities;
518
cur = xmlGetEntityFromTable(table, name);
524
return(xmlGetPredefinedEntity(name));
528
* Macro used to grow the current buffer.
530
#define growBufferReentrant() { \
532
buffer = (xmlChar *) \
533
xmlRealloc(buffer, buffer_size * sizeof(xmlChar)); \
534
if (buffer == NULL) { \
535
xmlEntitiesErrMemory("xmlEncodeEntitiesReentrant: realloc failed");\
542
* xmlEncodeEntitiesReentrant:
543
* @doc: the document containing the string
544
* @input: A string to convert to XML.
546
* Do a global encoding of a string, replacing the predefined entities
547
* and non ASCII values with their entities and CharRef counterparts.
548
* Contrary to xmlEncodeEntities, this routine is reentrant, and result
549
* must be deallocated.
551
* Returns A newly allocated string with the substitution done.
554
xmlEncodeEntitiesReentrant(xmlDocPtr doc, const xmlChar *input) {
555
const xmlChar *cur = input;
556
xmlChar *buffer = NULL;
561
if (input == NULL) return(NULL);
563
html = (doc->type == XML_HTML_DOCUMENT_NODE);
566
* allocate an translation buffer.
569
buffer = (xmlChar *) xmlMalloc(buffer_size * sizeof(xmlChar));
570
if (buffer == NULL) {
571
xmlEntitiesErrMemory("xmlEncodeEntitiesReentrant: malloc failed");
576
while (*cur != '\0') {
577
if (out - buffer > buffer_size - 100) {
578
int indx = out - buffer;
580
growBufferReentrant();
585
* By default one have to encode at least '<', '>', '"' and '&' !
592
} else if (*cur == '>') {
597
} else if (*cur == '&') {
603
} else if (((*cur >= 0x20) && (*cur < 0x80)) ||
604
(*cur == '\n') || (*cur == '\t') || ((html) && (*cur == '\r'))) {
606
* default case, just copy !
609
} else if (*cur >= 0x80) {
610
if (((doc != NULL) && (doc->encoding != NULL)) || (html)) {
612
* Bj�rn Reese <br@sseusa.com> provided the patch
614
xc = (*cur & 0x3F) << 6;
616
xc += *(++cur) & 0x3F;
623
* We assume we have UTF-8 input.
629
xmlEntitiesErr(XML_CHECK_NOT_UTF8,
630
"xmlEncodeEntitiesReentrant : input not UTF-8");
632
doc->encoding = xmlStrdup(BAD_CAST "ISO-8859-1");
633
snprintf(buf, sizeof(buf), "&#%d;", *cur);
634
buf[sizeof(buf) - 1] = 0;
636
while (*ptr != 0) *out++ = *ptr++;
639
} else if (*cur < 0xE0) {
640
val = (cur[0]) & 0x1F;
642
val |= (cur[1]) & 0x3F;
644
} else if (*cur < 0xF0) {
645
val = (cur[0]) & 0x0F;
647
val |= (cur[1]) & 0x3F;
649
val |= (cur[2]) & 0x3F;
651
} else if (*cur < 0xF8) {
652
val = (cur[0]) & 0x07;
654
val |= (cur[1]) & 0x3F;
656
val |= (cur[2]) & 0x3F;
658
val |= (cur[3]) & 0x3F;
661
if ((l == 1) || (!IS_CHAR(val))) {
662
xmlEntitiesErr(XML_ERR_INVALID_CHAR,
663
"xmlEncodeEntitiesReentrant : char out of range\n");
665
doc->encoding = xmlStrdup(BAD_CAST "ISO-8859-1");
666
snprintf(buf, sizeof(buf), "&#%d;", *cur);
667
buf[sizeof(buf) - 1] = 0;
669
while (*ptr != 0) *out++ = *ptr++;
674
* We could do multiple things here. Just save as a char ref
676
snprintf(buf, sizeof(buf), "&#x%X;", val);
677
buf[sizeof(buf) - 1] = 0;
679
while (*ptr != 0) *out++ = *ptr++;
683
} else if (IS_BYTE_CHAR(*cur)) {
686
snprintf(buf, sizeof(buf), "&#%d;", *cur);
687
buf[sizeof(buf) - 1] = 0;
689
while (*ptr != 0) *out++ = *ptr++;
698
* xmlEncodeSpecialChars:
699
* @doc: the document containing the string
700
* @input: A string to convert to XML.
702
* Do a global encoding of a string, replacing the predefined entities
703
* this routine is reentrant, and result must be deallocated.
705
* Returns A newly allocated string with the substitution done.
708
xmlEncodeSpecialChars(xmlDocPtr doc ATTRIBUTE_UNUSED, const xmlChar *input) {
709
const xmlChar *cur = input;
710
xmlChar *buffer = NULL;
713
if (input == NULL) return(NULL);
716
* allocate an translation buffer.
719
buffer = (xmlChar *) xmlMalloc(buffer_size * sizeof(xmlChar));
720
if (buffer == NULL) {
721
xmlEntitiesErrMemory("xmlEncodeSpecialChars: malloc failed");
726
while (*cur != '\0') {
727
if (out - buffer > buffer_size - 10) {
728
int indx = out - buffer;
730
growBufferReentrant();
735
* By default one have to encode at least '<', '>', '"' and '&' !
742
} else if (*cur == '>') {
747
} else if (*cur == '&') {
753
} else if (*cur == '"') {
760
} else if (*cur == '\r') {
768
* Works because on UTF-8, all extended sequences cannot
769
* result in bytes in the ASCII range.
780
* xmlCreateEntitiesTable:
782
* create and initialize an empty entities hash table.
783
* This really doesn't make sense and should be deprecated
785
* Returns the xmlEntitiesTablePtr just created or NULL in case of error.
788
xmlCreateEntitiesTable(void) {
789
return((xmlEntitiesTablePtr) xmlHashCreate(0));
793
* xmlFreeEntityWrapper:
797
* Deallocate the memory used by an entities in the hash table.
800
xmlFreeEntityWrapper(xmlEntityPtr entity,
801
const xmlChar *name ATTRIBUTE_UNUSED) {
803
xmlFreeEntity(entity);
807
* xmlFreeEntitiesTable:
808
* @table: An entity table
810
* Deallocate the memory used by an entities hash table.
813
xmlFreeEntitiesTable(xmlEntitiesTablePtr table) {
814
xmlHashFree(table, (xmlHashDeallocator) xmlFreeEntityWrapper);
817
#ifdef LIBXML_TREE_ENABLED
822
* Build a copy of an entity
824
* Returns the new xmlEntitiesPtr or NULL in case of error.
827
xmlCopyEntity(xmlEntityPtr ent) {
830
cur = (xmlEntityPtr) xmlMalloc(sizeof(xmlEntity));
832
xmlEntitiesErrMemory("xmlCopyEntity:: malloc failed");
835
memset(cur, 0, sizeof(xmlEntity));
836
cur->type = XML_ENTITY_DECL;
838
cur->etype = ent->etype;
839
if (ent->name != NULL)
840
cur->name = xmlStrdup(ent->name);
841
if (ent->ExternalID != NULL)
842
cur->ExternalID = xmlStrdup(ent->ExternalID);
843
if (ent->SystemID != NULL)
844
cur->SystemID = xmlStrdup(ent->SystemID);
845
if (ent->content != NULL)
846
cur->content = xmlStrdup(ent->content);
847
if (ent->orig != NULL)
848
cur->orig = xmlStrdup(ent->orig);
849
if (ent->URI != NULL)
850
cur->URI = xmlStrdup(ent->URI);
855
* xmlCopyEntitiesTable:
856
* @table: An entity table
858
* Build a copy of an entity table.
860
* Returns the new xmlEntitiesTablePtr or NULL in case of error.
863
xmlCopyEntitiesTable(xmlEntitiesTablePtr table) {
864
return(xmlHashCopy(table, (xmlHashCopier) xmlCopyEntity));
866
#endif /* LIBXML_TREE_ENABLED */
868
#ifdef LIBXML_OUTPUT_ENABLED
871
* xmlDumpEntityContent:
872
* @buf: An XML buffer.
873
* @content: The entity content.
875
* This will dump the quoted string value, taking care of the special
876
* treatment required by %
879
xmlDumpEntityContent(xmlBufferPtr buf, const xmlChar *content) {
880
if (buf->alloc == XML_BUFFER_ALLOC_IMMUTABLE) return;
881
if (xmlStrchr(content, '%')) {
882
const xmlChar * base, *cur;
884
xmlBufferCCat(buf, "\"");
885
base = cur = content;
889
xmlBufferAdd(buf, base, cur - base);
890
xmlBufferAdd(buf, BAD_CAST """, 6);
893
} else if (*cur == '%') {
895
xmlBufferAdd(buf, base, cur - base);
896
xmlBufferAdd(buf, BAD_CAST "%", 6);
904
xmlBufferAdd(buf, base, cur - base);
905
xmlBufferCCat(buf, "\"");
907
xmlBufferWriteQuotedString(buf, content);
913
* @buf: An XML buffer.
914
* @ent: An entity table
916
* This will dump the content of the entity table as an XML DTD definition
919
xmlDumpEntityDecl(xmlBufferPtr buf, xmlEntityPtr ent) {
920
if ((buf == NULL) || (ent == NULL)) return;
921
switch (ent->etype) {
922
case XML_INTERNAL_GENERAL_ENTITY:
923
xmlBufferWriteChar(buf, "<!ENTITY ");
924
xmlBufferWriteCHAR(buf, ent->name);
925
xmlBufferWriteChar(buf, " ");
926
if (ent->orig != NULL)
927
xmlBufferWriteQuotedString(buf, ent->orig);
929
xmlDumpEntityContent(buf, ent->content);
930
xmlBufferWriteChar(buf, ">\n");
932
case XML_EXTERNAL_GENERAL_PARSED_ENTITY:
933
xmlBufferWriteChar(buf, "<!ENTITY ");
934
xmlBufferWriteCHAR(buf, ent->name);
935
if (ent->ExternalID != NULL) {
936
xmlBufferWriteChar(buf, " PUBLIC ");
937
xmlBufferWriteQuotedString(buf, ent->ExternalID);
938
xmlBufferWriteChar(buf, " ");
939
xmlBufferWriteQuotedString(buf, ent->SystemID);
941
xmlBufferWriteChar(buf, " SYSTEM ");
942
xmlBufferWriteQuotedString(buf, ent->SystemID);
944
xmlBufferWriteChar(buf, ">\n");
946
case XML_EXTERNAL_GENERAL_UNPARSED_ENTITY:
947
xmlBufferWriteChar(buf, "<!ENTITY ");
948
xmlBufferWriteCHAR(buf, ent->name);
949
if (ent->ExternalID != NULL) {
950
xmlBufferWriteChar(buf, " PUBLIC ");
951
xmlBufferWriteQuotedString(buf, ent->ExternalID);
952
xmlBufferWriteChar(buf, " ");
953
xmlBufferWriteQuotedString(buf, ent->SystemID);
955
xmlBufferWriteChar(buf, " SYSTEM ");
956
xmlBufferWriteQuotedString(buf, ent->SystemID);
958
if (ent->content != NULL) { /* Should be true ! */
959
xmlBufferWriteChar(buf, " NDATA ");
960
if (ent->orig != NULL)
961
xmlBufferWriteCHAR(buf, ent->orig);
963
xmlBufferWriteCHAR(buf, ent->content);
965
xmlBufferWriteChar(buf, ">\n");
967
case XML_INTERNAL_PARAMETER_ENTITY:
968
xmlBufferWriteChar(buf, "<!ENTITY % ");
969
xmlBufferWriteCHAR(buf, ent->name);
970
xmlBufferWriteChar(buf, " ");
971
if (ent->orig == NULL)
972
xmlDumpEntityContent(buf, ent->content);
974
xmlBufferWriteQuotedString(buf, ent->orig);
975
xmlBufferWriteChar(buf, ">\n");
977
case XML_EXTERNAL_PARAMETER_ENTITY:
978
xmlBufferWriteChar(buf, "<!ENTITY % ");
979
xmlBufferWriteCHAR(buf, ent->name);
980
if (ent->ExternalID != NULL) {
981
xmlBufferWriteChar(buf, " PUBLIC ");
982
xmlBufferWriteQuotedString(buf, ent->ExternalID);
983
xmlBufferWriteChar(buf, " ");
984
xmlBufferWriteQuotedString(buf, ent->SystemID);
986
xmlBufferWriteChar(buf, " SYSTEM ");
987
xmlBufferWriteQuotedString(buf, ent->SystemID);
989
xmlBufferWriteChar(buf, ">\n");
992
xmlEntitiesErr(XML_DTD_UNKNOWN_ENTITY,
993
"xmlDumpEntitiesDecl: internal: unknown type entity type");
998
* xmlDumpEntityDeclScan:
999
* @ent: An entity table
1000
* @buf: An XML buffer.
1002
* When using the hash table scan function, arguments need to be reversed
1005
xmlDumpEntityDeclScan(xmlEntityPtr ent, xmlBufferPtr buf) {
1006
xmlDumpEntityDecl(buf, ent);
1010
* xmlDumpEntitiesTable:
1011
* @buf: An XML buffer.
1012
* @table: An entity table
1014
* This will dump the content of the entity table as an XML DTD definition
1017
xmlDumpEntitiesTable(xmlBufferPtr buf, xmlEntitiesTablePtr table) {
1018
xmlHashScan(table, (xmlHashScanner)xmlDumpEntityDeclScan, buf);
1020
#endif /* LIBXML_OUTPUT_ENABLED */
1021
#define bottom_entities
1022
#include "elfgcchack.h"