summaryrefslogtreecommitdiff
path: root/src/treebuilder/treebuilder.c
diff options
context:
space:
mode:
authorRupinder Singh Khokhar <rsk1coder99@gmail.com>2014-07-20 08:06:39 +0530
committerRupinder Singh Khokhar <rsk1coder99@gmail.com>2014-08-01 21:44:34 +0530
commit128ff208119c9ee95727a7df00607f024d573e91 (patch)
treea6dc6a3a5f033b3664ad6e9470989fd5de0be9af /src/treebuilder/treebuilder.c
parentd5c1b55f5a0a6f06280d33a6555e50330b676e2c (diff)
downloadlibhubbub-128ff208119c9ee95727a7df00607f024d573e91.tar.gz
libhubbub-128ff208119c9ee95727a7df00607f024d573e91.tar.bz2
template insertion mode stack implemented
Diffstat (limited to 'src/treebuilder/treebuilder.c')
-rw-r--r--src/treebuilder/treebuilder.c71
1 files changed, 70 insertions, 1 deletions
diff --git a/src/treebuilder/treebuilder.c b/src/treebuilder/treebuilder.c
index eb6bb51..8f0e7e3 100644
--- a/src/treebuilder/treebuilder.c
+++ b/src/treebuilder/treebuilder.c
@@ -138,6 +138,16 @@ hubbub_error hubbub_treebuilder_create(hubbub_tokeniser *tokeniser,
free(tb);
return HUBBUB_NOMEM;
}
+
+ tb->context.template_stack = malloc(
+ TEMPLATE_STACK_CHUNK * sizeof(insertion_mode));
+ if (tb->context.template_stack == NULL) {
+ free(tb);
+ return HUBBUB_NOMEM;
+ }
+ tb->context.template_stack_alloc = TEMPLATE_STACK_CHUNK;
+ tb->context.current_template_mode = -1;
+
tb->context.stack_alloc = ELEMENT_STACK_CHUNK;
/* We rely on HTML not being equal to zero to determine
* if the first item in the stack is in use. Assert this here. */
@@ -160,6 +170,7 @@ hubbub_error hubbub_treebuilder_create(hubbub_tokeniser *tokeniser,
HUBBUB_TOKENISER_TOKEN_HANDLER, &tokparams);
if (error != HUBBUB_OK) {
free(tb->context.element_stack);
+ free(tb->context.template_stack);
free(tb);
return error;
}
@@ -216,16 +227,21 @@ hubbub_error hubbub_treebuilder_destroy(hubbub_treebuilder *treebuilder)
treebuilder->tree_handler->unref_node(
treebuilder->tree_handler->ctx,
treebuilder->context.element_stack[n].node);
+
}
if (treebuilder->context.element_stack[0].type == HTML) {
treebuilder->tree_handler->unref_node(
treebuilder->tree_handler->ctx,
treebuilder->context.element_stack[0].node);
}
+ /*\todo free attributes?*/
}
free(treebuilder->context.element_stack);
treebuilder->context.element_stack = NULL;
+ free(treebuilder->context.template_stack);
+ treebuilder->context.template_stack = NULL;
+
for (entry = treebuilder->context.formatting_list; entry != NULL;
entry = next) {
next = entry->next;
@@ -235,7 +251,7 @@ hubbub_error hubbub_treebuilder_destroy(hubbub_treebuilder *treebuilder)
treebuilder->tree_handler->ctx,
entry->details.node);
}
-
+ /*\todo free attributes? */
free(entry);
}
@@ -1291,6 +1307,59 @@ hubbub_error element_stack_pop(hubbub_treebuilder *treebuilder,
}
/**
+ * Push an element onto the stack of Template Insertion Modes
+ *
+ * \param treebuilder The treebuilder instance containing the stack
+ * \param mode The insertion mode being pushed
+ * \return HUBBUB_OK on success, appropriate error otherwise.
+ */
+hubbub_error template_stack_push(hubbub_treebuilder *treebuilder,
+ insertion_mode mode)
+{
+ int32_t slot = treebuilder->context.current_template_mode + 1;
+
+ if (slot >= (signed)treebuilder->context.template_stack_alloc) {
+ insertion_mode *temp = realloc(
+ treebuilder->context.template_stack,
+ (treebuilder->context.template_stack_alloc +
+ TEMPLATE_STACK_CHUNK) *
+ sizeof(insertion_mode));
+
+ if (temp == NULL)
+ return HUBBUB_NOMEM;
+
+ treebuilder->context.template_stack = temp;
+ treebuilder->context.template_stack_alloc += TEMPLATE_STACK_CHUNK;
+ }
+
+ treebuilder->context.template_stack[slot] = mode;
+
+ treebuilder->context.current_template_mode = slot;
+
+ return HUBBUB_OK;
+}
+
+/**
+ * Pop an element off the stack of Template Insertion Modes
+ *
+ * \param ns Pointer to location to receive insertion mode
+ * \return HUBBUB_OK on success, appropriate error otherwise.
+ */
+hubbub_error template_stack_pop(hubbub_treebuilder *treebuilder,
+ insertion_mode *mode)
+{
+ int32_t stack =
+ treebuilder->context.current_template_mode;
+ *mode = treebuilder->context.template_stack[stack];
+
+ treebuilder->context.current_template_mode -= 1;
+
+ assert( treebuilder->context.current_template_mode >= -1);
+
+ return HUBBUB_OK;
+}
+
+/**
* Pop elements until an element of type "element" has been popped.
*
* \return HUBBUB_OK on success, appropriate error otherwise.