From 9fa0aacebdc0c4c8280b69df0133e4b819454171 Mon Sep 17 00:00:00 2001 From: John Mark Bell Date: Sun, 23 Sep 2007 22:54:22 +0000 Subject: Add dom_entity_reference_get_textual_representation() as an internal library function. Implement dom_attr_get_value() svn path=/trunk/dom/; revision=3588 --- src/core/attr.c | 120 ++++++++++++++++++++++++++++++++++++++++++++++++-- src/core/entity_ref.c | 22 +++++++++ src/core/entity_ref.h | 3 ++ 3 files changed, 142 insertions(+), 3 deletions(-) (limited to 'src') diff --git a/src/core/attr.c b/src/core/attr.c index 31c9d94..6200ab1 100644 --- a/src/core/attr.c +++ b/src/core/attr.c @@ -6,6 +6,7 @@ */ #include +#include #include #include @@ -13,6 +14,7 @@ #include "core/attr.h" #include "core/document.h" +#include "core/entity_ref.h" #include "core/node.h" #include "utils/utils.h" @@ -176,12 +178,124 @@ dom_exception dom_attr_get_specified(struct dom_attr *attr, bool *result) dom_exception dom_attr_get_value(struct dom_attr *attr, struct dom_string **result) { - UNUSED(attr); - UNUSED(result); + struct dom_node *a = (struct dom_node *) attr; + struct dom_node *c; + uint8_t *rep; + size_t rep_len; + size_t rep_alloc; + dom_exception err; + +#define CHUNK 128 + + rep = dom_document_alloc(a->owner, NULL, CHUNK); + if (rep == NULL) + return DOM_NO_MEM_ERR; + + rep_len = 0; + rep_alloc = CHUNK; /* Traverse children, building a string representation as we go */ + for (c = a->first_child; c != NULL; c = c->next) { + if (c->type == DOM_TEXT_NODE && c->value != NULL) { + const uint8_t *data; + size_t len; + + err = dom_string_get_data(c->value, &data, &len); + if (err != DOM_NO_ERR) { + dom_document_alloc(a->owner, rep, 0); + return err; + } + + /* Extend buffer, if necessary */ + if (rep_len + len >= rep_alloc) { + uint8_t *temp; + size_t required = (rep_len + len) - rep_alloc; + + /* Round required up to a chunk boundary */ + required = + (required + CHUNK - 1) & ~(CHUNK - 1); + + temp = dom_document_alloc(a->owner, rep, + rep_alloc + required); + if (temp == NULL) { + dom_document_alloc(a->owner, rep, 0); + return DOM_NO_MEM_ERR; + } + + rep = temp; + rep_alloc += required; + } + + /* Copy text into buffer */ + memcpy(rep + rep_len, data, len); + + /* And fix up length information */ + rep_len += len; + } else if (c->type == DOM_ENTITY_REFERENCE_NODE) { + struct dom_string *tr; + const uint8_t *data; + size_t len; + + /* Get textual representation of entity */ + err = dom_entity_reference_get_textual_representation( + (struct dom_entity_reference *) c, + &tr); + if (err != DOM_NO_ERR) { + dom_document_alloc(a->owner, rep, 0); + return err; + } + + err = dom_string_get_data(tr, &data, &len); + if (err != DOM_NO_ERR) { + dom_string_unref(tr); + dom_document_alloc(a->owner, rep, 0); + return err; + } + + /* Extend buffer, if necessary */ + if (rep_len + len >= rep_alloc) { + uint8_t *temp; + size_t required = (rep_len + len) - rep_alloc; + + /* Round required up to a chunk boundary */ + required = + (required + CHUNK - 1) & ~(CHUNK - 1); + + temp = dom_document_alloc(a->owner, rep, + rep_alloc + required); + if (temp == NULL) { + dom_document_alloc(a->owner, rep, 0); + return DOM_NO_MEM_ERR; + } + + rep = temp; + rep_alloc += required; + } + + /* Copy text into buffer */ + memcpy(rep + rep_len, data, len); + + /* And fix up length information */ + rep_len += len; + + /* No longer need textual representation */ + dom_string_unref(tr); + } + } - return DOM_NOT_SUPPORTED_ERR; +#undef CHUNK + + /* Create DOMString */ + err = dom_string_create_from_ptr(a->owner, rep, rep_len, result); + if (err != DOM_NO_ERR) { + dom_document_alloc(a->owner, rep, 0); + return err; + } + + /* Cleanup */ + dom_document_alloc(a->owner, rep, 0); + + return DOM_NO_ERR; } /** diff --git a/src/core/entity_ref.c b/src/core/entity_ref.c index 8382249..bf4868b 100644 --- a/src/core/entity_ref.c +++ b/src/core/entity_ref.c @@ -8,6 +8,7 @@ #include "core/document.h" #include "core/entity_ref.h" #include "core/node.h" +#include "utils/utils.h" /** * A DOM entity reference @@ -97,3 +98,24 @@ void dom_entity_reference_destroy(struct dom_document *doc, /* Destroy fragment */ dom_document_alloc(doc, entity, 0); } + +/** + * Get the textual representation of an EntityReference + * + * \param entity The entity reference to get the textual representation of + * \param result Pointer to location to receive result + * \return DOM_NO_ERR on success. + * + * The returned string will have its reference count increased. It is + * the responsibility of the caller to unref the string once it has + * finished with it. + */ +dom_exception dom_entity_reference_get_textual_representation( + struct dom_entity_reference *entity, struct dom_string **result) +{ + UNUSED(entity); + UNUSED(result); + + return DOM_NOT_SUPPORTED_ERR; +} + diff --git a/src/core/entity_ref.h b/src/core/entity_ref.h index 047ff30..fa03737 100644 --- a/src/core/entity_ref.h +++ b/src/core/entity_ref.h @@ -21,4 +21,7 @@ dom_exception dom_entity_reference_create(struct dom_document *doc, void dom_entity_reference_destroy(struct dom_document *doc, struct dom_entity_reference *entity); +dom_exception dom_entity_reference_get_textual_representation( + struct dom_entity_reference *entity, + struct dom_string **result); #endif -- cgit v1.2.3