mirror of
https://github.com/RGBCube/serenity
synced 2025-05-16 18:05:07 +00:00
LibWeb: Bring up basic external script execution in the new parser
This only works in some narrow cases, but should be enough for our own welcome.html at least. :^)
This commit is contained in:
parent
2cb50f6750
commit
4c9c6b3a7b
7 changed files with 60 additions and 3 deletions
|
@ -424,4 +424,9 @@ void Document::set_pending_parsing_blocking_script(Badge<HTMLScriptElement>, HTM
|
||||||
m_pending_parsing_blocking_script = script;
|
m_pending_parsing_blocking_script = script;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
NonnullRefPtr<HTMLScriptElement> Document::take_pending_parsing_blocking_script(Badge<HTMLDocumentParser>)
|
||||||
|
{
|
||||||
|
return m_pending_parsing_blocking_script.release_nonnull();
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -130,6 +130,8 @@ public:
|
||||||
NonnullRefPtr<Text> create_text_node(const String& data);
|
NonnullRefPtr<Text> create_text_node(const String& data);
|
||||||
|
|
||||||
void set_pending_parsing_blocking_script(Badge<HTMLScriptElement>, HTMLScriptElement*);
|
void set_pending_parsing_blocking_script(Badge<HTMLScriptElement>, HTMLScriptElement*);
|
||||||
|
HTMLScriptElement* pending_parsing_blocking_script() { return m_pending_parsing_blocking_script; }
|
||||||
|
NonnullRefPtr<HTMLScriptElement> take_pending_parsing_blocking_script(Badge<HTMLDocumentParser>);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
virtual RefPtr<LayoutNode> create_layout_node(const StyleProperties* parent_style) const override;
|
virtual RefPtr<LayoutNode> create_layout_node(const StyleProperties* parent_style) const override;
|
||||||
|
|
|
@ -189,7 +189,8 @@ void HTMLScriptElement::prepare_script(Badge<HTMLDocumentParser>)
|
||||||
|
|
||||||
// FIXME: Check classic vs. module script type
|
// FIXME: Check classic vs. module script type
|
||||||
|
|
||||||
ResourceLoader::the().load(url, [this, url](auto& data, auto&) {
|
// FIXME: This load should be made asynchronous and the parser should spin an event loop etc.
|
||||||
|
ResourceLoader::the().load_sync(url, [this, url](auto& data, auto&) {
|
||||||
if (data.is_null()) {
|
if (data.is_null()) {
|
||||||
dbg() << "HTMLScriptElement: Failed to load " << url;
|
dbg() << "HTMLScriptElement: Failed to load " << url;
|
||||||
return;
|
return;
|
||||||
|
@ -212,6 +213,7 @@ void HTMLScriptElement::prepare_script(Badge<HTMLDocumentParser>)
|
||||||
}
|
}
|
||||||
|
|
||||||
else if (has_attribute("src") && m_parser_inserted && !has_attribute("async")) {
|
else if (has_attribute("src") && m_parser_inserted && !has_attribute("async")) {
|
||||||
|
|
||||||
document().set_pending_parsing_blocking_script({}, this);
|
document().set_pending_parsing_blocking_script({}, this);
|
||||||
when_the_script_is_ready([this] {
|
when_the_script_is_ready([this] {
|
||||||
m_ready_to_be_parser_executed = true;
|
m_ready_to_be_parser_executed = true;
|
||||||
|
@ -234,6 +236,7 @@ void HTMLScriptElement::prepare_script(Badge<HTMLDocumentParser>)
|
||||||
|
|
||||||
void HTMLScriptElement::script_became_ready()
|
void HTMLScriptElement::script_became_ready()
|
||||||
{
|
{
|
||||||
|
m_script_ready = true;
|
||||||
if (!m_script_ready_callback)
|
if (!m_script_ready_callback)
|
||||||
return;
|
return;
|
||||||
m_script_ready_callback();
|
m_script_ready_callback();
|
||||||
|
|
|
@ -40,15 +40,16 @@ public:
|
||||||
virtual void children_changed() override;
|
virtual void children_changed() override;
|
||||||
|
|
||||||
bool is_non_blocking() const { return m_non_blocking; }
|
bool is_non_blocking() const { return m_non_blocking; }
|
||||||
|
bool is_ready_to_be_parser_executed() const { return m_ready_to_be_parser_executed; }
|
||||||
|
|
||||||
void set_parser_document(Badge<HTMLDocumentParser>, Document&);
|
void set_parser_document(Badge<HTMLDocumentParser>, Document&);
|
||||||
void set_non_blocking(Badge<HTMLDocumentParser>, bool);
|
void set_non_blocking(Badge<HTMLDocumentParser>, bool);
|
||||||
void prepare_script(Badge<HTMLDocumentParser>);
|
void prepare_script(Badge<HTMLDocumentParser>);
|
||||||
|
void execute_script();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void script_became_ready();
|
void script_became_ready();
|
||||||
void when_the_script_is_ready(Function<void()>);
|
void when_the_script_is_ready(Function<void()>);
|
||||||
void execute_script();
|
|
||||||
|
|
||||||
WeakPtr<Document> m_parser_document;
|
WeakPtr<Document> m_parser_document;
|
||||||
WeakPtr<Document> m_preparation_time_document;
|
WeakPtr<Document> m_preparation_time_document;
|
||||||
|
|
|
@ -704,8 +704,48 @@ void HTMLDocumentParser::handle_text(HTMLToken& token)
|
||||||
if (script_nesting_level() == 0)
|
if (script_nesting_level() == 0)
|
||||||
m_parser_pause_flag = false;
|
m_parser_pause_flag = false;
|
||||||
// FIXME: Handle tokenizer insertion point stuff here too.
|
// FIXME: Handle tokenizer insertion point stuff here too.
|
||||||
|
|
||||||
|
while (document().pending_parsing_blocking_script()) {
|
||||||
|
if (script_nesting_level() != 0) {
|
||||||
|
m_parser_pause_flag = true;
|
||||||
|
// FIXME: Abort the processing of any nested invocations of the tokenizer,
|
||||||
|
// yielding control back to the caller. (Tokenization will resume when
|
||||||
|
// the caller returns to the "outer" tree construction stage.)
|
||||||
|
TODO();
|
||||||
|
} else {
|
||||||
|
auto the_script = document().take_pending_parsing_blocking_script({});
|
||||||
|
m_tokenizer.set_blocked(true);
|
||||||
|
|
||||||
|
// FIXME: If the parser's Document has a style sheet that is blocking scripts
|
||||||
|
// or the script's "ready to be parser-executed" flag is not set:
|
||||||
|
// spin the event loop until the parser's Document has no style sheet
|
||||||
|
// that is blocking scripts and the script's "ready to be parser-executed"
|
||||||
|
// flag is set.
|
||||||
|
|
||||||
|
ASSERT(the_script->is_ready_to_be_parser_executed());
|
||||||
|
|
||||||
|
if (m_aborted)
|
||||||
|
return;
|
||||||
|
|
||||||
|
m_tokenizer.set_blocked(false);
|
||||||
|
|
||||||
|
// FIXME: Handle tokenizer insertion point stuff here too.
|
||||||
|
|
||||||
|
ASSERT(script_nesting_level() == 0);
|
||||||
|
increment_script_nesting_level();
|
||||||
|
|
||||||
|
the_script->execute_script();
|
||||||
|
|
||||||
|
decrement_script_nesting_level();
|
||||||
|
ASSERT(script_nesting_level() == 0);
|
||||||
|
m_parser_pause_flag = false;
|
||||||
|
|
||||||
|
// FIXME: Handle tokenizer insertion point stuff here too.
|
||||||
|
}
|
||||||
|
}
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (token.is_end_tag()) {
|
if (token.is_end_tag()) {
|
||||||
m_stack_of_open_elements.pop();
|
m_stack_of_open_elements.pop();
|
||||||
m_insertion_mode = m_original_insertion_mode;
|
m_insertion_mode = m_original_insertion_mode;
|
||||||
|
|
|
@ -121,7 +121,7 @@ private:
|
||||||
bool m_parsing_fragment { false };
|
bool m_parsing_fragment { false };
|
||||||
bool m_scripting_enabled { true };
|
bool m_scripting_enabled { true };
|
||||||
bool m_invoked_via_document_write { false };
|
bool m_invoked_via_document_write { false };
|
||||||
|
bool m_aborted { false };
|
||||||
bool m_parser_pause_flag { false };
|
bool m_parser_pause_flag { false };
|
||||||
size_t m_script_nesting_level { 0 };
|
size_t m_script_nesting_level { 0 };
|
||||||
|
|
||||||
|
|
|
@ -130,6 +130,9 @@ public:
|
||||||
|
|
||||||
void switch_to(Badge<HTMLDocumentParser>, State new_state);
|
void switch_to(Badge<HTMLDocumentParser>, State new_state);
|
||||||
|
|
||||||
|
void set_blocked(bool b) { m_blocked = b; }
|
||||||
|
bool is_blocked() const { return m_blocked; }
|
||||||
|
|
||||||
private:
|
private:
|
||||||
Optional<u32> next_codepoint();
|
Optional<u32> next_codepoint();
|
||||||
Optional<u32> peek_codepoint(size_t offset) const;
|
Optional<u32> peek_codepoint(size_t offset) const;
|
||||||
|
@ -172,5 +175,8 @@ private:
|
||||||
Queue<HTMLToken> m_queued_tokens;
|
Queue<HTMLToken> m_queued_tokens;
|
||||||
|
|
||||||
u32 m_character_reference_code { 0 };
|
u32 m_character_reference_code { 0 };
|
||||||
|
|
||||||
|
bool m_blocked { false };
|
||||||
};
|
};
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue