LibWeb: Return a representation of an 'Agent' in 'relevant agent'

This makes it more convenient to use the 'relvant agent' concept,
instead of the awkward dynamic casts we needed to do for every call
site.

mutation_observers is also changed to hold a GC::Root instead of raw
GC::Ptr. Somehow this was not causing problems before, but trips up CI
after these changes.
This commit is contained in:
Shannon Booth 2025-01-04 23:12:55 +13:00 committed by Tim Flynn
commit 64eeda6450
Notes: github-actions[bot] 2025-01-11 15:40:39 +00:00
15 changed files with 140 additions and 98 deletions

View file

@ -0,0 +1,21 @@
/*
* Copyright (c) 2025, Shannon Booth <shannon@serenityos.org>
*
* SPDX-License-Identifier: BSD-2-Clause
*/
#include <LibWeb/Bindings/MainThreadVM.h>
#include <LibWeb/HTML/Scripting/Agent.h>
#include <LibWeb/HTML/Scripting/Environments.h>
namespace Web::HTML {
// https://html.spec.whatwg.org/multipage/webappapis.html#relevant-agent
Agent& relevant_agent(JS::Object const& object)
{
// The relevant agent for a platform object platformObject is platformObject's relevant Realm's agent.
// Spec Note: This pointer is not yet defined in the JavaScript specification; see tc39/ecma262#1357.
return verify_cast<Bindings::WebEngineCustomData>(relevant_realm(object).vm().custom_data())->agent;
}
}

View file

@ -0,0 +1,43 @@
/*
* Copyright (c) 2025, Shannon Booth <shannon@serenityos.org>
*
* SPDX-License-Identifier: BSD-2-Clause
*/
#pragma once
#include <AK/OwnPtr.h>
#include <AK/Vector.h>
#include <LibGC/Root.h>
#include <LibJS/Forward.h>
#include <LibWeb/Forward.h>
#include <LibWeb/HTML/CustomElements/CustomElementReactionsStack.h>
namespace Web::HTML {
// https://html.spec.whatwg.org/multipage/webappapis.html#similar-origin-window-agent
struct Agent {
GC::Root<HTML::EventLoop> event_loop;
// FIXME: These should only be on similar-origin window agents, but we don't currently differentiate agent types.
// https://dom.spec.whatwg.org/#mutation-observer-compound-microtask-queued-flag
bool mutation_observer_microtask_queued { false };
// https://dom.spec.whatwg.org/#mutation-observer-list
// FIXME: This should be a set.
Vector<GC::Root<DOM::MutationObserver>> mutation_observers;
// https://html.spec.whatwg.org/multipage/custom-elements.html#custom-element-reactions-stack
// Each similar-origin window agent has a custom element reactions stack, which is initially empty.
CustomElementReactionsStack custom_element_reactions_stack {};
// https://html.spec.whatwg.org/multipage/custom-elements.html#current-element-queue
// A similar-origin window agent's current element queue is the element queue at the top of its custom element reactions stack.
Vector<GC::Root<DOM::Element>>& current_element_queue() { return custom_element_reactions_stack.element_queue_stack.last(); }
Vector<GC::Root<DOM::Element>> const& current_element_queue() const { return custom_element_reactions_stack.element_queue_stack.last(); }
};
Agent& relevant_agent(JS::Object const&);
}

View file

@ -13,6 +13,7 @@
#include <LibWeb/DOM/Document.h>
#include <LibWeb/DOMURL/DOMURL.h>
#include <LibWeb/Fetch/Infrastructure/FetchRecord.h>
#include <LibWeb/HTML/Scripting/Agent.h>
#include <LibWeb/HTML/Scripting/Environments.h>
#include <LibWeb/HTML/Scripting/ExceptionReporter.h>
#include <LibWeb/HTML/Scripting/WindowEnvironmentSettingsObject.h>
@ -102,10 +103,8 @@ EventLoop& EnvironmentSettingsObject::responsible_event_loop()
if (m_responsible_event_loop)
return *m_responsible_event_loop;
auto& vm = global_object().vm();
auto& event_loop = verify_cast<Bindings::WebEngineCustomData>(vm.custom_data())->event_loop;
m_responsible_event_loop = event_loop;
return *event_loop;
m_responsible_event_loop = relevant_agent(global_object()).event_loop;
return *m_responsible_event_loop;
}
// https://html.spec.whatwg.org/multipage/webappapis.html#check-if-we-can-run-script
@ -513,13 +512,6 @@ JS::Object& entry_global_object()
return entry_realm().global_object();
}
JS::VM& relevant_agent(JS::Object const& object)
{
// The relevant agent for a platform object platformObject is platformObject's relevant Realm's agent.
// Spec Note: This pointer is not yet defined in the JavaScript specification; see tc39/ecma262#1357.
return relevant_realm(object).vm();
}
// https://html.spec.whatwg.org/multipage/webappapis.html#secure-context
bool is_secure_context(Environment const& environment)
{

View file

@ -168,7 +168,6 @@ JS::Object& relevant_principal_global_object(JS::Object const&);
JS::Realm& entry_realm();
EnvironmentSettingsObject& entry_settings_object();
JS::Object& entry_global_object();
JS::VM& relevant_agent(JS::Object const&);
[[nodiscard]] bool is_secure_context(Environment const&);
[[nodiscard]] bool is_non_secure_context(Environment const&);