void svgtiny_parse_paint_attributes(dom_element *node, struct svgtiny_parse_state *state) { dom_string *attr; dom_exception exc; exc = dom_element_get_attribute(node, state->interned_fill, &attr); if (exc == DOM_NO_ERR && attr != NULL) { svgtiny_parse_color(attr, &state->fill, state); dom_string_unref(attr); } exc = dom_element_get_attribute(node, state->interned_stroke, &attr); if (exc == DOM_NO_ERR && attr != NULL) { svgtiny_parse_color(attr, &state->stroke, state); dom_string_unref(attr); } exc = dom_element_get_attribute(node, state->interned_stroke_width, &attr); if (exc == DOM_NO_ERR && attr != NULL) { state->stroke_width = svgtiny_parse_length(attr, state->viewport_width, *state); dom_string_unref(attr); } exc = dom_element_get_attribute(node, state->interned_style, &attr); if (exc == DOM_NO_ERR && attr != NULL) { char *style = strndup(dom_string_data(attr), dom_string_byte_length(attr)); const char *s; char *value; if ((s = strstr(style, "fill:"))) { s += 5; while (*s == ' ') s++; value = strndup(s, strcspn(s, "; ")); _svgtiny_parse_color(value, &state->fill, state); free(value); } if ((s = strstr(style, "stroke:"))) { s += 7; while (*s == ' ') s++; value = strndup(s, strcspn(s, "; ")); _svgtiny_parse_color(value, &state->stroke, state); free(value); } if ((s = strstr(style, "stroke-width:"))) { s += 13; while (*s == ' ') s++; value = strndup(s, strcspn(s, "; ")); state->stroke_width = _svgtiny_parse_length(value, state->viewport_width, *state); free(value); } free(style); dom_string_unref(attr); } }
/* Finalise the document */ bool _dom_document_finalise(dom_document *doc) { /* Finalise base class, delete the tree in force */ _dom_node_finalise(&doc->base); /* Now, the first_child and last_child should be null */ doc->base.first_child = NULL; doc->base.last_child = NULL; /* Ensure list of nodes pending deletion is empty. If not, * then we can't yet destroy the document (its destruction will * have to wait until the pending nodes are destroyed) */ if (doc->pending_nodes.next != &doc->pending_nodes) return false; /* Ok, the document tree is empty, as is the list of nodes pending * deletion. Therefore, it is safe to destroy the document. */ /* This is paranoia -- if there are any remaining nodelists, * then the document's reference count will be * non-zero as these data structures reference the document because * they are held by the client. */ doc->nodelists = NULL; if (doc->id_name != NULL) dom_string_unref(doc->id_name); dom_string_unref(doc->class_string); _dom_document_event_internal_finalise(doc, &doc->dei); return true; }
/*--------------------- The callbacks definitions --------------------*/ static hubbub_error create_comment(void *parser, const hubbub_string *data, void **result) { dom_hubbub_parser *dom_parser = (dom_hubbub_parser *) parser; dom_exception err; dom_string *str; struct dom_comment *comment; *result = NULL; err = dom_string_create(data->ptr, data->len, &str); if (err != DOM_NO_ERR) { dom_parser->msg(DOM_MSG_CRITICAL, dom_parser->mctx, "Can't create comment node text"); return HUBBUB_UNKNOWN; } err = dom_document_create_comment(dom_parser->doc, str, &comment); if (err != DOM_NO_ERR) { dom_string_unref(str); dom_parser->msg(DOM_MSG_CRITICAL, dom_parser->mctx, "Can't create comment node with text '%.*s'", data->len, data->ptr); return HUBBUB_UNKNOWN; } *result = comment; dom_string_unref(str); return HUBBUB_OK; }
/** * Callback to determine if a node is a linking element whose target has been * visited. * * \param pw HTML document * \param node DOM node * \param match Pointer to location to receive result * \return CSS_OK. * * \post \a match will contain true if the node matches and false otherwise. */ css_error node_is_visited(void *pw, void *node, bool *match) { nscss_select_ctx *ctx = pw; nsurl *url; nserror error; const struct url_data *data; dom_exception exc; dom_node *n = node; dom_string *s = NULL; *match = false; exc = dom_node_get_node_name(n, &s); if ((exc != DOM_NO_ERR) || (s == NULL)) { return CSS_NOMEM; } if (!dom_string_caseless_lwc_isequal(s, corestring_lwc_a)) { /* Can't be visited; not ancher element */ dom_string_unref(s); return CSS_OK; } /* Finished with node name string */ dom_string_unref(s); s = NULL; exc = dom_element_get_attribute(n, corestring_dom_href, &s); if ((exc != DOM_NO_ERR) || (s == NULL)) { /* Can't be visited; not got a URL */ return CSS_OK; } /* Make href absolute */ /* TODO: this duplicates what we do for box->href * should we put the absolute URL on the dom node? */ error = nsurl_join(ctx->base_url, dom_string_data(s), &url); /* Finished with href string */ dom_string_unref(s); if (error != NSERROR_OK) { /* Couldn't make nsurl object */ return CSS_NOMEM; } data = urldb_get_url_data(url); /* Visited if in the db and has * non-zero visit count */ if (data != NULL && data->visits > 0) *match = true; nsurl_unref(url); return CSS_OK; }
static hubbub_error add_attributes(void *parser, void *node, const hubbub_attribute *attributes, uint32_t n_attributes) { dom_hubbub_parser *dom_parser = (dom_hubbub_parser *) parser; dom_exception err; uint32_t i; for (i = 0; i < n_attributes; i++) { dom_string *name, *value; err = dom_string_create_interned(attributes[i].name.ptr, attributes[i].name.len, &name); if (err != DOM_NO_ERR) { dom_parser->msg(DOM_MSG_CRITICAL, dom_parser->mctx, "Can't create attribute name"); goto fail; } err = dom_string_create(attributes[i].value.ptr, attributes[i].value.len, &value); if (err != DOM_NO_ERR) { dom_parser->msg(DOM_MSG_CRITICAL, dom_parser->mctx, "Can't create attribute value"); dom_string_unref(name); goto fail; } if (attributes[i].ns == HUBBUB_NS_NULL) { err = dom_element_set_attribute( (struct dom_element *) node, name, value); dom_string_unref(name); dom_string_unref(value); if (err != DOM_NO_ERR) { dom_parser->msg(DOM_MSG_CRITICAL, dom_parser->mctx, "Can't add attribute"); } } else { err = dom_element_set_attribute_ns( (struct dom_element *) node, dom_namespaces[attributes[i].ns], name, value); dom_string_unref(name); dom_string_unref(value); if (err != DOM_NO_ERR) { dom_parser->msg(DOM_MSG_CRITICAL, dom_parser->mctx, "Can't add attribute ns"); } } } return HUBBUB_OK; fail: return HUBBUB_UNKNOWN; }
/** * Callback to determine if a node has an attribute with the given name whose * value contains the substring given. * * \param pw HTML document * \param node DOM node * \param qname Name to match * \param value Value to match * \param match Pointer to location to receive result * \return CSS_OK on success, * CSS_NOMEM on memory exhaustion. * * \post \a match will contain true if the node matches and false otherwise. */ css_error node_has_attribute_substring(void *pw, void *node, const css_qname *qname, lwc_string *value, bool *match) { dom_node *n = node; dom_string *name; dom_string *atr_val; dom_exception err; size_t vlen = lwc_string_length(value); if (vlen == 0) { *match = false; return CSS_OK; } err = dom_string_create_interned( (const uint8_t *) lwc_string_data(qname->name), lwc_string_length(qname->name), &name); if (err != DOM_NO_ERR) return CSS_NOMEM; err = dom_element_get_attribute(n, name, &atr_val); if ((err != DOM_NO_ERR) || (atr_val == NULL)) { dom_string_unref(name); *match = false; return CSS_OK; } dom_string_unref(name); /* check for exact match */ *match = dom_string_caseless_lwc_isequal(atr_val, value); /* check for prefix match */ if (*match == false) { const char *vdata = lwc_string_data(value); const char *start = (const char *) dom_string_data(atr_val); size_t len = dom_string_byte_length(atr_val); const char *last_start = start + len - vlen; if (len >= vlen) { while (start <= last_start) { if (strncasecmp(start, vdata, vlen) == 0) { *match = true; break; } start++; } } } dom_string_unref(atr_val); return CSS_OK; }
/** * Callback to determine if a node has an attribute with the given name whose * value includes that given. * * \param pw HTML document * \param node DOM node * \param qname Name to match * \param value Value to match * \param match Pointer to location to receive result * \return CSS_OK on success, * CSS_NOMEM on memory exhaustion. * * \post \a match will contain true if the node matches and false otherwise. */ css_error node_has_attribute_includes(void *pw, void *node, const css_qname *qname, lwc_string *value, bool *match) { dom_node *n = node; dom_string *name; dom_string *atr_val; dom_exception err; size_t vlen = lwc_string_length(value); const char *p; const char *start; const char *end; *match = false; if (vlen == 0) { return CSS_OK; } err = dom_string_create_interned( (const uint8_t *) lwc_string_data(qname->name), lwc_string_length(qname->name), &name); if (err != DOM_NO_ERR) return CSS_NOMEM; err = dom_element_get_attribute(n, name, &atr_val); if ((err != DOM_NO_ERR) || (atr_val == NULL)) { dom_string_unref(name); *match = false; return CSS_OK; } dom_string_unref(name); /* check for match */ start = (const char *) dom_string_data(atr_val); end = start + dom_string_byte_length(atr_val); for (p = start; p <= end; p++) { if (*p == ' ' || *p == '\0') { if ((size_t) (p - start) == vlen && strncasecmp(start, lwc_string_data(value), vlen) == 0) { *match = true; break; } start = p + 1; } } dom_string_unref(atr_val); return CSS_OK; }
/** * Get the node in the collection according name * * \param col The collection * \param name The name of target node * \param node The returned node object * \return DOM_NO_ERR on success. */ dom_exception dom_html_collection_named_item(dom_html_collection *col, dom_string *name, struct dom_node **node) { struct dom_node_internal *n = col->root; dom_exception err; while (n != NULL) { if (n->type == DOM_ELEMENT_NODE && col->ic(n, col->ctx) == true) { dom_string *id = NULL; err = _dom_element_get_id((struct dom_element *) n, &id); if (err != DOM_NO_ERR) { return err; } if (id != NULL && dom_string_isequal(name, id)) { *node = (struct dom_node *) n; dom_node_ref(n); dom_string_unref(id); return DOM_NO_ERR; } if (id != NULL) dom_string_unref(id); } /* Depth first iterating */ if (n->first_child != NULL) { n = n->first_child; } else if (n->next != NULL) { n = n->next; } else { /* No children and siblings */ struct dom_node_internal *parent = n->parent; while (parent != col->root && n == parent->last_child) { n = parent; parent = parent->parent; } if (parent == col->root) n = NULL; else n = n->next; } } /* Not found the target node */ *node = NULL; return DOM_NO_ERR; }
static nserror html_stylesheet_from_domnode(html_content *c, dom_node *node, hlcache_handle **sheet) { hlcache_child_context child; dom_string *style; nsurl *url; dom_exception exc; nserror error; uint32_t key; char urlbuf[64]; child.charset = c->encoding; child.quirks = c->base.quirks; exc = dom_node_get_text_content(node, &style); if ((exc != DOM_NO_ERR) || (style == NULL)) { LOG("No text content"); return NSERROR_OK; } error = html_css_fetcher_add_item(style, c->base_url, &key); if (error != NSERROR_OK) { dom_string_unref(style); return error; } dom_string_unref(style); snprintf(urlbuf, sizeof(urlbuf), "x-ns-css:%u", key); error = nsurl_create(urlbuf, &url); if (error != NSERROR_OK) { return error; } error = hlcache_handle_retrieve(url, 0, content_get_url(&c->base), NULL, html_convert_css_callback, c, &child, CONTENT_CSS, sheet); if (error != NSERROR_OK) { nsurl_unref(url); return error; } nsurl_unref(url); c->base.active++; LOG("%d fetches active", c->base.active); return NSERROR_OK; }
/** * Callback to find a named generic sibling node. * * \param pw HTML document * \param node DOM node * \param qname Node name to search for * \param sibling Pointer to location to receive ancestor * \return CSS_OK. * * \post \a sibling will contain the result, or NULL if there is no match */ css_error named_generic_sibling_node(void *pw, void *node, const css_qname *qname, void **sibling) { dom_node *n = node; dom_node *prev; dom_exception err; *sibling = NULL; err = dom_node_get_previous_sibling(n, &n); if (err != DOM_NO_ERR) return CSS_OK; while (n != NULL) { dom_node_type type; dom_string *name; err = dom_node_get_node_type(n, &type); if (err != DOM_NO_ERR) { dom_node_unref(n); return CSS_OK; } if (type == DOM_ELEMENT_NODE) { err = dom_node_get_node_name(n, &name); if (err != DOM_NO_ERR) { dom_node_unref(n); return CSS_OK; } if (dom_string_caseless_lwc_isequal(name, qname->name)) { dom_string_unref(name); dom_node_unref(n); *sibling = n; break; } dom_string_unref(name); } err = dom_node_get_previous_sibling(n, &prev); if (err != DOM_NO_ERR) { dom_node_unref(n); return CSS_OK; } dom_node_unref(n); n = prev; } return CSS_OK; }
/** * Callback to determine if a node has an attribute with the given name whose * value dashmatches that given. * * \param pw HTML document * \param node DOM node * \param qname Name to match * \param value Value to match * \param match Pointer to location to receive result * \return CSS_OK on success, * CSS_NOMEM on memory exhaustion. * * \post \a match will contain true if the node matches and false otherwise. */ css_error node_has_attribute_dashmatch(void *pw, void *node, const css_qname *qname, lwc_string *value, bool *match) { dom_node *n = node; dom_string *name; dom_string *atr_val; dom_exception err; size_t vlen = lwc_string_length(value); if (vlen == 0) { *match = false; return CSS_OK; } err = dom_string_create_interned( (const uint8_t *) lwc_string_data(qname->name), lwc_string_length(qname->name), &name); if (err != DOM_NO_ERR) return CSS_NOMEM; err = dom_element_get_attribute(n, name, &atr_val); if ((err != DOM_NO_ERR) || (atr_val == NULL)) { dom_string_unref(name); *match = false; return CSS_OK; } dom_string_unref(name); /* check for exact match */ *match = dom_string_caseless_lwc_isequal(atr_val, value); /* check for dashmatch */ if (*match == false) { const char *vdata = lwc_string_data(value); const char *data = (const char *) dom_string_data(atr_val); size_t len = dom_string_byte_length(atr_val); if (len > vlen && data[vlen] == '-' && strncasecmp(data, vdata, vlen) == 0) { *match = true; } } dom_string_unref(atr_val); return CSS_OK; }
static struct html_stylesheet * html_create_style_element(html_content *c, dom_node *style) { dom_string *val; dom_exception exc; struct html_stylesheet *stylesheets; /* type='text/css', or not present (invalid but common) */ exc = dom_element_get_attribute(style, corestring_dom_type, &val); if (exc == DOM_NO_ERR && val != NULL) { if (!dom_string_caseless_lwc_isequal(val, corestring_lwc_text_css)) { dom_string_unref(val); return NULL; } dom_string_unref(val); } /* media contains 'screen' or 'all' or not present */ exc = dom_element_get_attribute(style, corestring_dom_media, &val); if (exc == DOM_NO_ERR && val != NULL) { if (strcasestr(dom_string_data(val), "screen") == NULL && strcasestr(dom_string_data(val), "all") == NULL) { dom_string_unref(val); return NULL; } dom_string_unref(val); } /* Extend array */ stylesheets = realloc(c->stylesheets, sizeof(struct html_stylesheet) * (c->stylesheet_count + 1)); if (stylesheets == NULL) { content_broadcast_errorcode(&c->base, NSERROR_NOMEM); return false; } c->stylesheets = stylesheets; c->stylesheets[c->stylesheet_count].node = dom_node_ref(style); c->stylesheets[c->stylesheet_count].sheet = NULL; c->stylesheets[c->stylesheet_count].modified = false; c->stylesheet_count++; return c->stylesheets + (c->stylesheet_count - 1); }
/** * Callback to determine if a node is a linking element. * * \param pw HTML document * \param n DOM node * \param match Pointer to location to receive result * \return CSS_OK. * * \post \a match will contain true if the node matches and false otherwise. */ css_error node_is_link(void *pw, void *n, bool *match) { dom_node *node = n; dom_exception exc; dom_string *node_name = NULL; exc = dom_node_get_node_name(node, &node_name); if ((exc != DOM_NO_ERR) || (node_name == NULL)) { return CSS_NOMEM; } if (dom_string_caseless_lwc_isequal(node_name, corestring_lwc_a)) { bool has_href; exc = dom_element_has_attribute(node, corestring_dom_href, &has_href); if ((exc == DOM_NO_ERR) && (has_href)) { *match = true; } else { *match = false; } } else { *match = false; } dom_string_unref(node_name); return CSS_OK; }
static int node_count_siblings_check(dom_node *node, bool check_name, dom_string *name) { dom_node_type type; int ret = 0; dom_exception exc; if (node == NULL) return 0; exc = dom_node_get_node_type(node, &type); if ((exc != DOM_NO_ERR) || (type != DOM_ELEMENT_NODE)) { return 0; } if (check_name) { dom_string *node_name = NULL; exc = dom_node_get_node_name(node, &node_name); if ((exc == DOM_NO_ERR) && (node_name != NULL)) { if (dom_string_caseless_isequal(name, node_name)) { ret = 1; } dom_string_unref(node_name); } } else { ret = 1; } return ret; }
/** * Dispatch a DOMNodeInsertedIntoDocument/DOMNodeRemovedFromDocument event * * \param doc The document object * \param et The EventTarget object * \param type "DOMNodeInserted" or "DOMNodeRemoved" * \param success Whether this event's default action get called * \return DOM_NO_ERR on success, appropriate dom_exception on failure. */ dom_exception __dom_dispatch_node_change_document_event(dom_document *doc, dom_event_target *et, dom_mutation_type change, bool *success) { struct dom_mutation_event *evt; dom_string *type = NULL; dom_exception err; err = _dom_mutation_event_create(doc, &evt); if (err != DOM_NO_ERR) return err; if (change == DOM_MUTATION_ADDITION) { type = dom_string_ref(doc->_memo_domnodeinsertedintodocument); } else if (change == DOM_MUTATION_REMOVAL) { type = dom_string_ref(doc->_memo_domnoderemovedfromdocument); } else { assert("Should never be here" == NULL); } /* Initialise the event with corresponding parameters */ err = dom_mutation_event_init(evt, type, true, false, NULL, NULL, NULL, NULL, change); dom_string_unref(type); if (err != DOM_NO_ERR) goto cleanup; err = dom_event_target_dispatch_event(et, evt, success); if (err != DOM_NO_ERR) goto cleanup; cleanup: _dom_mutation_event_destroy(evt); return err; }
/* Initialise the document */ dom_exception _dom_document_initialise(dom_document *doc, dom_events_default_action_fetcher daf) { dom_exception err; dom_string *name; err = dom_string_create((const uint8_t *) "#document", SLEN("#document"), &name); if (err != DOM_NO_ERR) return err; doc->nodelists = NULL; err = _dom_node_initialise(&doc->base, doc, DOM_DOCUMENT_NODE, name, NULL, NULL, NULL); dom_string_unref(name); if (err != DOM_NO_ERR) return err; list_init(&doc->pending_nodes); doc->id_name = NULL; doc->quirks = DOM_DOCUMENT_QUIRKS_MODE_NONE; err = dom_string_create_interned((const uint8_t *) "class", SLEN("class"), &doc->class_string); if (err != DOM_NO_ERR) return err; /* We should not pass a NULL when all things hook up */ return _dom_document_event_internal_initialise(doc, &doc->dei, daf); }
static duk_ret_t dukky_html_anchor_element_target_getter(duk_context *ctx) { /* Get private data for method */ html_anchor_element_private_t *priv = NULL; duk_push_this(ctx); duk_get_prop_string(ctx, -1, dukky_magic_string_private); priv = duk_get_pointer(ctx, -1); duk_pop_2(ctx); if (priv == NULL) { return 0; /* can do? No can do. */ } #line 34 "HTMLAnchorElement.bnd" dom_exception exc; dom_string *str; exc = dom_html_anchor_element_get_target((struct dom_html_anchor_element *)((node_private_t*)priv)->node, &str); if (exc != DOM_NO_ERR) { return 0; } if (str != NULL) { duk_push_lstring(ctx, dom_string_data(str), dom_string_length(str)); dom_string_unref(str); } else { duk_push_lstring(ctx, NULL, 0); } return 1; }
static duk_ret_t dukky_html_anchor_element_shape_setter(duk_context *ctx) { /* Get private data for method */ html_anchor_element_private_t *priv = NULL; duk_push_this(ctx); duk_get_prop_string(ctx, -1, dukky_magic_string_private); priv = duk_get_pointer(ctx, -1); duk_pop_2(ctx); if (priv == NULL) { return 0; /* can do? No can do. */ } #line 32 "HTMLAnchorElement.bnd" dom_exception exc; dom_string *str; duk_size_t slen; const char *s; s = duk_safe_to_lstring(ctx, 0, &slen); exc = dom_string_create((const uint8_t *)s, slen, &str); if (exc != DOM_NO_ERR) { return 0; } exc = dom_html_anchor_element_set_shape((struct dom_html_anchor_element *)((node_private_t*)priv)->node, str); dom_string_unref(str); if (exc != DOM_NO_ERR) { return 0; } return 0; }
/** * Cleanup the local externally-stored parts of a parse state. * Call this in functions that made a new state on the stack. * Doesn't cleanup global state, such as the interned string list. */ static void svgtiny_cleanup_state_local(struct svgtiny_parse_state *state) { if (state->gradient_x1 != NULL) { dom_string_unref(state->gradient_x1); state->gradient_x1 = NULL; } if (state->gradient_y1 != NULL) { dom_string_unref(state->gradient_y1); state->gradient_y1 = NULL; } if (state->gradient_x2 != NULL) { dom_string_unref(state->gradient_x2); state->gradient_x2 = NULL; } if (state->gradient_y2 != NULL) { dom_string_unref(state->gradient_y2); state->gradient_y2 = NULL; } }
static bool save_complete_handle_attr(save_complete_ctx *ctx, dom_string *node_name, dom_attr *attr) { dom_string *name; const char *name_data; size_t name_len; dom_string *value; dom_exception error; error = dom_attr_get_name(attr, &name); if (error != DOM_NO_ERR) return false; if (name == NULL) return true; error = dom_attr_get_value(attr, &value); if (error != DOM_NO_ERR) { dom_string_unref(name); return false; } name_data = dom_string_data(name); name_len = dom_string_byte_length(name); fputc(' ', ctx->fp); fwrite(name_data, sizeof(*name_data), name_len, ctx->fp); if (value != NULL) { fputc('=', ctx->fp); if (save_complete_handle_attr_value(ctx, node_name, name, value) == false) { dom_string_unref(value); dom_string_unref(name); return false; } } dom_string_unref(name); return true; }
static hubbub_error create_element(void *parser, const hubbub_tag *tag, void **result) { dom_hubbub_parser *dom_parser = (dom_hubbub_parser *) parser; dom_exception err; dom_string *name; struct dom_element *element = NULL; hubbub_error herr; *result = NULL; err = dom_string_create_interned(tag->name.ptr, tag->name.len, &name); if (err != DOM_NO_ERR) { dom_parser->msg(DOM_MSG_CRITICAL, dom_parser->mctx, "Can't create element name"); goto fail; } if (tag->ns == HUBBUB_NS_NULL) { err = dom_document_create_element(dom_parser->doc, name, &element); if (err != DOM_NO_ERR) { dom_parser->msg(DOM_MSG_CRITICAL, dom_parser->mctx, "Can't create the DOM element"); goto clean1; } } else { err = dom_document_create_element_ns(dom_parser->doc, dom_namespaces[tag->ns], name, &element); if (err != DOM_NO_ERR) { dom_parser->msg(DOM_MSG_CRITICAL, dom_parser->mctx, "Can't create the DOM element"); goto clean1; } } if (element != NULL && tag->n_attributes > 0) { herr = add_attributes(parser, element, tag->attributes, tag->n_attributes); if (herr != HUBBUB_OK) goto clean1; } *result = element; clean1: dom_string_unref(name); fail: if (*result == NULL) return HUBBUB_UNKNOWN; else return HUBBUB_OK; }
/** * Callback to count a node's siblings. * * \param pw HTML document * \param n DOM node * \param same_name Only count siblings with the same name, or all * \param after Count anteceding instead of preceding siblings * \param count Pointer to location to receive result * \return CSS_OK. * * \post \a count will contain the number of siblings */ css_error node_count_siblings(void *pw, void *n, bool same_name, bool after, int32_t *count) { int32_t cnt = 0; dom_exception exc; dom_string *node_name = NULL; if (same_name) { dom_node *node = n; exc = dom_node_get_node_name(node, &node_name); if ((exc != DOM_NO_ERR) || (node_name == NULL)) { return CSS_NOMEM; } } if (after) { dom_node *node = dom_node_ref(n); dom_node *next; do { exc = dom_node_get_next_sibling(node, &next); if ((exc != DOM_NO_ERR)) break; dom_node_unref(node); node = next; cnt += node_count_siblings_check(node, same_name, node_name); } while (node != NULL); } else { dom_node *node = dom_node_ref(n); dom_node *next; do { exc = dom_node_get_previous_sibling(node, &next); if ((exc != DOM_NO_ERR)) break; dom_node_unref(node); node = next; cnt += node_count_siblings_check(node, same_name, node_name); } while (node != NULL); } if (node_name != NULL) { dom_string_unref(node_name); } *count = cnt; return CSS_OK; }
/** * process script node parser callback * * */ dom_hubbub_error html_process_script(void *ctx, dom_node *node) { html_content *c = (html_content *)ctx; dom_exception exc; /* returned by libdom functions */ dom_string *src, *mimetype; dom_hubbub_error err = DOM_HUBBUB_OK; /* ensure javascript context is available */ if (c->jscontext == NULL) { union content_msg_data msg_data; msg_data.jscontext = &c->jscontext; content_broadcast(&c->base, CONTENT_MSG_GETCTX, msg_data); LOG(("javascript context %p ", c->jscontext)); if (c->jscontext == NULL) { /* no context and it could not be created, abort */ return DOM_HUBBUB_OK; } } LOG(("content %p parser %p node %p", c, c->parser, node)); exc = dom_element_get_attribute(node, corestring_dom_type, &mimetype); if (exc != DOM_NO_ERR || mimetype == NULL) { mimetype = dom_string_ref(corestring_dom_text_javascript); } exc = dom_element_get_attribute(node, corestring_dom_src, &src); if (exc != DOM_NO_ERR || src == NULL) { err = exec_inline_script(c, node, mimetype); } else { err = exec_src_script(c, node, mimetype, src); dom_string_unref(src); } dom_string_unref(mimetype); return err; }
/* Finalise a HTMLDocument */ bool _dom_html_document_finalise(dom_html_document *doc) { int sidx; if (doc->cookie != NULL) dom_string_unref(doc->cookie); if (doc->url != NULL) dom_string_unref(doc->url); if (doc->domain != NULL) dom_string_unref(doc->domain); if (doc->referrer != NULL) dom_string_unref(doc->referrer); if (doc->title != NULL) dom_string_unref(doc->title); if (doc->memoised != NULL) { for(sidx = 0; sidx < hds_COUNT; ++sidx) { if (doc->memoised[sidx] != NULL) { dom_string_unref(doc->memoised[sidx]); } } free(doc->memoised); doc->memoised = NULL; } return _dom_document_finalise(&doc->base); }
/** * Callback to retrieve a node's name. * * \param pw HTML document * \param node DOM node * \param qname Pointer to location to receive node name * \return CSS_OK on success, * CSS_NOMEM on memory exhaustion. */ css_error node_name(void *pw, void *node, css_qname *qname) { dom_node *n = node; dom_string *name; dom_exception err; err = dom_node_get_node_name(n, &name); if (err != DOM_NO_ERR) return CSS_NOMEM; qname->ns = NULL; err = dom_string_intern(name, &qname->name); if (err != DOM_NO_ERR) { dom_string_unref(name); return CSS_NOMEM; } dom_string_unref(name); return CSS_OK; }
void svgtiny_parse_position_attributes(dom_element *node, const struct svgtiny_parse_state state, float *x, float *y, float *width, float *height) { dom_string *attr; dom_exception exc; *x = 0; *y = 0; *width = state.viewport_width; *height = state.viewport_height; exc = dom_element_get_attribute(node, state.interned_x, &attr); if (exc == DOM_NO_ERR && attr != NULL) { *x = svgtiny_parse_length(attr, state.viewport_width, state); dom_string_unref(attr); } exc = dom_element_get_attribute(node, state.interned_y, &attr); if (exc == DOM_NO_ERR && attr != NULL) { *y = svgtiny_parse_length(attr, state.viewport_height, state); dom_string_unref(attr); } exc = dom_element_get_attribute(node, state.interned_width, &attr); if (exc == DOM_NO_ERR && attr != NULL) { *width = svgtiny_parse_length(attr, state.viewport_width, state); dom_string_unref(attr); } exc = dom_element_get_attribute(node, state.interned_height, &attr); if (exc == DOM_NO_ERR && attr != NULL) { *height = svgtiny_parse_length(attr, state.viewport_height, state); dom_string_unref(attr); } }
/** * Finalise the namespace component * * \return DOM_NO_ERR on success. */ dom_exception _dom_namespace_finalise(void) { int i; if (xmlns != NULL) { dom_string_unref(xmlns); xmlns = NULL; } if (xml != NULL) { dom_string_unref(xml); xml = NULL; } for (i = 1; i < DOM_NAMESPACE_COUNT; i++) { if (dom_namespaces[i] != NULL) { dom_string_unref(dom_namespaces[i]); dom_namespaces[i] = NULL; } } return DOM_NO_ERR; }
void list_destroy(struct list* list) { struct list_elt* elt = list->head; while (elt != NULL) { if (list->type == DOM_STRING) dom_string_unref((dom_string *) elt->data); if (list->type == NODE) dom_node_unref(elt->data); struct list_elt* nextElt = elt->next; free(elt); elt = nextElt; } free(list); }
/** * Callback to determine if a node has an attribute with the given name. * * \param pw HTML document * \param node DOM node * \param qname Name to match * \param match Pointer to location to receive result * \return CSS_OK on success, * CSS_NOMEM on memory exhaustion. * * \post \a match will contain true if the node matches and false otherwise. */ css_error node_has_attribute(void *pw, void *node, const css_qname *qname, bool *match) { dom_node *n = node; dom_string *name; dom_exception err; err = dom_string_create_interned( (const uint8_t *) lwc_string_data(qname->name), lwc_string_length(qname->name), &name); if (err != DOM_NO_ERR) return CSS_NOMEM; err = dom_element_has_attribute(n, name, match); if (err != DOM_NO_ERR) { dom_string_unref(name); return CSS_OK; } dom_string_unref(name); return CSS_OK; }
void html_free_scripts(html_content *html) { unsigned int i; for (i = 0; i != html->scripts_count; i++) { if (html->scripts[i].mimetype != NULL) { dom_string_unref(html->scripts[i].mimetype); } if ((html->scripts[i].type == HTML_SCRIPT_INLINE) && (html->scripts[i].data.string != NULL)) { dom_string_unref(html->scripts[i].data.string); } else if ((html->scripts[i].type == HTML_SCRIPT_SYNC) && (html->scripts[i].data.handle != NULL)) { hlcache_handle_release(html->scripts[i].data.handle); } } free(html->scripts); }