|
@@ -537,6 +537,25 @@ static bool is_in_static_list(
|
|
|
return false;
|
|
return false;
|
|
|
}
|
|
}
|
|
|
|
|
|
|
|
|
|
+static void push_template_insertion_mode(
|
|
|
|
|
+ GumboParser* parser, GumboInsertionMode mode) {
|
|
|
|
|
+ gumbo_vector_add(
|
|
|
|
|
+ parser, (void*) mode, &parser->_parser_state->_template_insertion_modes);
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+static void pop_template_insertion_mode(GumboParser* parser) {
|
|
|
|
|
+ gumbo_vector_pop(parser, &parser->_parser_state->_template_insertion_modes);
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
|
|
+static GumboInsertionMode get_current_template_insertion_mode(
|
|
|
|
|
+ GumboParser* parser) {
|
|
|
|
|
+ GumboVector* template_insertion_modes =
|
|
|
|
|
+ &parser->_parser_state->_template_insertion_modes;
|
|
|
|
|
+ assert(template_insertion_modes->length > 0);
|
|
|
|
|
+ return (GumboInsertionMode) template_insertion_modes->data[
|
|
|
|
|
+ template_insertion_modes->length - 1];
|
|
|
|
|
+}
|
|
|
|
|
+
|
|
|
static void set_insertion_mode(GumboParser* parser, GumboInsertionMode mode) {
|
|
static void set_insertion_mode(GumboParser* parser, GumboInsertionMode mode) {
|
|
|
parser->_parser_state->_insertion_mode = mode;
|
|
parser->_parser_state->_insertion_mode = mode;
|
|
|
}
|
|
}
|
|
@@ -1716,10 +1735,10 @@ static bool maybe_add_doctype_error(
|
|
|
GumboParser* parser, const GumboToken* token) {
|
|
GumboParser* parser, const GumboToken* token) {
|
|
|
const GumboTokenDocType* doctype = &token->v.doc_type;
|
|
const GumboTokenDocType* doctype = &token->v.doc_type;
|
|
|
bool html_doctype = !strcmp(doctype->name, kDoctypeHtml.data);
|
|
bool html_doctype = !strcmp(doctype->name, kDoctypeHtml.data);
|
|
|
- if ((!html_doctype ||
|
|
|
|
|
- doctype->has_public_identifier ||
|
|
|
|
|
- (doctype->has_system_identifier && !strcmp(
|
|
|
|
|
- doctype->system_identifier, kSystemIdLegacyCompat.data))) &&
|
|
|
|
|
|
|
+ if (!html_doctype ||
|
|
|
|
|
+ doctype->has_public_identifier ||
|
|
|
|
|
+ (doctype->has_system_identifier && !strcmp(
|
|
|
|
|
+ doctype->system_identifier, kSystemIdLegacyCompat.data)) ||
|
|
|
!(html_doctype && (
|
|
!(html_doctype && (
|
|
|
doctype_matches(doctype, &kPublicIdHtml4_0,
|
|
doctype_matches(doctype, &kPublicIdHtml4_0,
|
|
|
&kSystemIdRecHtml4_0, true) ||
|
|
&kSystemIdRecHtml4_0, true) ||
|
|
@@ -2353,13 +2372,6 @@ static bool handle_in_body(GumboParser* parser, GumboToken* token) {
|
|
|
node = pop_current_node(parser);
|
|
node = pop_current_node(parser);
|
|
|
} while (node != state->_open_elements.data[1]);
|
|
} while (node != state->_open_elements.data[1]);
|
|
|
|
|
|
|
|
- // Removing & destroying the body node is going to kill any nodes that have
|
|
|
|
|
- // been added to the list of active formatting elements, and so we should
|
|
|
|
|
- // clear it to prevent a use-after-free if the list of active formatting
|
|
|
|
|
- // elements is reconstructed afterwards. This may happen if whitespace
|
|
|
|
|
- // follows the </frameset>.
|
|
|
|
|
- clear_active_formatting_elements(parser);
|
|
|
|
|
-
|
|
|
|
|
// Remove the body node. We may want to factor this out into a generic
|
|
// Remove the body node. We may want to factor this out into a generic
|
|
|
// helper, but right now this is the only code that needs to do this.
|
|
// helper, but right now this is the only code that needs to do this.
|
|
|
GumboVector* children = &parser->_output->root->v.element.children;
|
|
GumboVector* children = &parser->_output->root->v.element.children;
|
|
@@ -3531,10 +3543,6 @@ static bool handle_after_frameset(GumboParser* parser, GumboToken* token) {
|
|
|
} else if (tag_is(token, kStartTag, GUMBO_TAG_HTML)) {
|
|
} else if (tag_is(token, kStartTag, GUMBO_TAG_HTML)) {
|
|
|
return handle_in_body(parser, token);
|
|
return handle_in_body(parser, token);
|
|
|
} else if (tag_is(token, kEndTag, GUMBO_TAG_HTML)) {
|
|
} else if (tag_is(token, kEndTag, GUMBO_TAG_HTML)) {
|
|
|
- GumboNode* html = parser->_parser_state->_open_elements.data[0];
|
|
|
|
|
- assert(node_tag_is(html, GUMBO_TAG_HTML));
|
|
|
|
|
- record_end_of_element(
|
|
|
|
|
- parser->_parser_state->_current_token, &html->v.element);
|
|
|
|
|
set_insertion_mode(parser, GUMBO_INSERTION_MODE_AFTER_AFTER_FRAMESET);
|
|
set_insertion_mode(parser, GUMBO_INSERTION_MODE_AFTER_AFTER_FRAMESET);
|
|
|
return true;
|
|
return true;
|
|
|
} else if (tag_is(token, kStartTag, GUMBO_TAG_NOFRAMES)) {
|
|
} else if (tag_is(token, kStartTag, GUMBO_TAG_NOFRAMES)) {
|