19 #include "lt-memory.h"
23 #define Realloc srealloc
37 const char8 *DefaultTypeName[DT_enum_count] = {
46 const char8 *ContentTypeName[CT_enum_count] = {
55 const char8 *AttributeTypeName[AT_enum_count] = {
74 const char8 *StandaloneDeclarationName[SDD_enum_count] = {
75 "unspecified",
"no",
"yes"
78 static Char *Strndup(
const Char *old,
int len)
80 Char *
new = Malloc((len+1) *
sizeof(Char));
85 memcpy(
new, old, len *
sizeof(Char));
97 if(!(d = Malloc(
sizeof(*d))))
101 d->internal_part = 0;
102 d->external_part = 0;
104 d->parameter_entities = 0;
105 d->predefined_entities = 0;
118 void FreeDtd(Dtd
dtd)
122 ElementDefinition elem, elem1;
124 NotationDefinition not, not1;
131 Free((Char *)dtd->name);
135 FreeEntity(dtd->internal_part);
136 FreeEntity(dtd->external_part);
138 for(ent = dtd->entities; ent; ent = ent1)
144 for(ent = dtd->parameter_entities; ent; ent = ent1)
155 for(elem = dtd->elements; elem; elem = elem1)
158 FreeElementDefinition(elem);
164 for(not = dtd->notations; not; not = not1)
167 FreeNotationDefinition(not);
182 Entity NewExternalEntityN(
const Char *name,
int namelen,
const char8 *publicid,
183 const char8 *systemid, NotationDefinition notation,
188 if(!(e = Malloc(
sizeof(*e))))
190 if(name && !(name = Strndup(name, namelen)))
193 e->type = ET_external;
196 e->encoding = CE_unknown;
200 e->publicid = publicid;
201 e->systemid = systemid;
202 e->notation = notation;
205 e->encoding_decl = CE_unknown;
206 e->standalone_decl = SDD_unspecified;
214 Entity NewInternalEntityN(
const Char *name,
int namelen,
215 const Char *text, Entity parent,
216 int line_offset,
int line1_char_offset,
217 int matches_parent_text)
221 if(!(e = Malloc(
sizeof(*e))))
224 if(!(name = Strndup(name, namelen)))
227 e->type = ET_internal;
230 e->encoding = InternalCharacterEncoding;
235 e->line_offset = line_offset;
236 e->line1_char_offset = line1_char_offset;
237 e->matches_parent_text = matches_parent_text;
244 void FreeEntity(Entity e)
249 Free((
void *)e->name);
250 Free((
void *)e->base_url);
251 Free((
void *)e->url);
256 Free((
void *)e->text);
259 Free((
void *)e->systemid);
260 Free((
void *)e->publicid);
261 Free((
void *)e->version_decl);
262 Free((
void *)e->ddb_filename);
269 const char8 *EntityURL(Entity e)
276 if(e->type == ET_internal)
280 const char8 *url = EntityURL(e->parent);
282 e->url = strdup8(url);
286 e->url = url_merge(e->systemid,
287 e->parent ? EntityBaseURL(e->parent) : 0,
297 const char8 *EntityDescription(Entity e)
302 if(e->type == ET_external)
306 return EntityDescription(e->parent);
311 void EntitySetBaseURL(Entity e,
const char8 *url)
316 const char8 *EntityBaseURL(Entity e)
321 if(e->type == ET_internal)
324 return EntityBaseURL(e->parent);
332 Entity DefineEntity(Dtd dtd, Entity e,
int pe)
336 e->next = dtd->parameter_entities;
337 dtd->parameter_entities = e;
341 e->next = dtd->entities;
348 Entity FindEntityN(Dtd dtd,
const Char *name,
int namelen,
int pe)
353 for(e = dtd->predefined_entities; e; e = e->next)
354 if(Strncmp(name, e->name, namelen) == 0 && e->name[namelen] == 0)
358 for(e = pe ? dtd->parameter_entities : dtd->entities; e; e=e->next)
359 if(Strncmp(name, e->name, namelen) == 0 && e->name[namelen] == 0)
372 ElementDefinition DefineElementN(Dtd dtd,
const Char *name,
int namelen,
373 ContentType type, Char *content)
378 struct element_content *c;
380 if (!(entry = DeclareElement(dtd->doctype, name, namelen, 0,
385 e.doctype = dtd->doctype;
386 e.name = (Char *)dtd->doctype->elements+entry->keyptr;
387 e.elsum = (NSL_ElementSummary_I *)(dtd->doctype->permanentBase+entry->eval);
389 if(type == CT_element || type == CT_mixed)
391 if(!(c = Malloc(
sizeof(*c))))
394 c->content = content;
395 c->next = e.doctype->element_content;
396 e.doctype->element_content = c;
403 if(!(e = Malloc(
sizeof(*e))) || !(name = Strndup(name, namelen)))
408 e->namelen = namelen;
410 e->content = content;
412 e->next = dtd->elements;
419 ElementDefinition TentativelyDefineElementN(Dtd dtd,
420 const Char *name,
int namelen)
426 if (!(entry = DeclareElement(dtd->doctype, name, namelen, 0, (ctVals)CT_any))) {
429 e.doctype = dtd->doctype;
430 e.name = (Char *)dtd->doctype->elements+entry->keyptr;
431 e.elsum = (NSL_ElementSummary_I *)(dtd->doctype->permanentBase+entry->eval);
433 e.elsum->omitStart |= 2;
438 if(!(e = Malloc(
sizeof(*e))) || !(name = Strndup(name, namelen)))
443 e->namelen = namelen;
447 e->next = dtd->elements;
454 ElementDefinition RedefineElement(ElementDefinition e, ContentType type,
458 struct element_content *c;
460 e->elsum->contentType = type;
461 e->elsum->omitStart &= ~2;
462 if(type == CT_element)
464 if(!(c = Malloc(
sizeof(*c))))
467 c->content = content;
468 c->next = e->doctype->element_content;
469 e->doctype->element_content = c;
474 e->content = content;
479 ElementDefinition FindElementN(Dtd dtd,
const Char *name,
int namelen)
486 NSL_ElementSummary_I *elsum;
491 entry = rsearch(name, namelen, dtd->doctype->elements);
495 elsum = (NSL_ElementSummary_I *)(dtd->doctype->permanentBase+entry->eval);
497 e.doctype = dtd->doctype;
498 e.name = (Char *)dtd->doctype->elements+entry->keyptr;
501 e.namelen = Strlen(e.name);
504 e.tentative = ((e.elsum->omitStart & 2) != 0);
508 ElementDefinition e, *p;
510 for(p = &dtd->elements, e = *p; e; p = &e->next, e = *p)
511 if(namelen == e->namelen && *name == *e->name &&
512 memcmp(name, e->name, namelen*
sizeof(Char)) == 0)
515 e->next = dtd->elements;
526 void FreeElementDefinition(ElementDefinition e)
529 AttributeDefinition a, a1;
537 Free((
void *)e->name);
546 for(a = e->attributes; a; a = a1)
549 FreeAttributeDefinition(a);
566 DefineAttributeN(ElementDefinition element,
const Char *name,
int namelen,
567 AttributeType type, Char **allowed_values,
568 DefaultType default_type,
const Char *default_value)
572 Char *av = allowed_values ? allowed_values[0] : 0;
574 NSL_Doctype_I *doctype = element->doctype;
581 for(avp = allowed_values; *avp; avp++)
583 Free(allowed_values);
586 if (!(name = DeclareAttr(doctype, name, namelen,
587 (NSL_Attr_Declared_Value)type,
589 (NSL_ADefType)default_type, default_value,
590 &element->elsum, element->name))) {
594 return (AttributeDefinition)FindAttrSpec(element->elsum,
598 AttributeDefinition a;
600 if(!(a= Malloc(
sizeof(*a))) || !(name = Strndup(name, namelen)))
604 a->namelen = namelen;
606 a->allowed_values = allowed_values;
607 a->default_type = default_type;
608 a->default_value = default_value;
609 a->next = element->attributes;
610 element->attributes = a;
616 AttributeDefinition FindAttributeN(ElementDefinition element,
617 const Char *name,
int namelen)
620 if(!element->doctype)
623 if(!(name = AttrUniqueName(element->doctype, name, namelen)))
625 return (AttributeDefinition)FindAttrSpec(element->elsum,
629 AttributeDefinition a;
631 for(a = element->attributes; a; a = a->next)
632 if(namelen == a->namelen &&
633 memcmp(name, a->name, namelen *
sizeof(Char)) == 0)
640 AttributeDefinition NextAttributeDefinition(ElementDefinition element,
641 AttributeDefinition previous)
647 return previous->next;
649 return element->attributes;
655 void FreeAttributeDefinition(AttributeDefinition a)
665 Free((
void *)a->name);
670 if(a->allowed_values)
671 Free(a->allowed_values[0]);
672 Free(a->allowed_values);
676 Free((
void *)a->default_value);
691 NotationDefinition DefineNotationN(Dtd dtd,
const Char *name,
int namelen,
692 const char8 *publicid,
const char8 *systemid)
694 NotationDefinition n;
696 if(!(n = Malloc(
sizeof(*n))) || !(name = Strndup(name, namelen)))
701 n->systemid = systemid;
702 n->publicid = publicid;
703 n->next = dtd->notations;
709 NotationDefinition TentativelyDefineNotationN(Dtd dtd,
710 const Char *name,
int namelen)
712 NotationDefinition n;
714 if(!(n = Malloc(
sizeof(*n))) || !(name = Strndup(name, namelen)))
721 n->next = dtd->notations;
727 NotationDefinition RedefineNotation(NotationDefinition n,
728 const char8 *publicid,
const char8 *systemid)
731 n->systemid = systemid;
732 n->publicid = publicid;
737 NotationDefinition FindNotationN(Dtd dtd,
const Char *name,
int namelen)
739 NotationDefinition n;
741 for(n = dtd->notations; n; n = n->next)
742 if(Strncmp(name, n->name, namelen) == 0 && n->name[namelen] == 0)
748 void FreeNotationDefinition(NotationDefinition n)
755 Free((
void *)n->name);
759 Free((
void *)n->systemid);
760 Free((
void *)n->publicid);