From 50d951aea24af43256e138d60fe0c48770570919 Mon Sep 17 00:00:00 2001 From: Andreas Kling Date: Mon, 1 Aug 2022 20:27:20 +0200 Subject: [PATCH] LibJS: Let Shape store a Realm instead of a GlobalObject This is a cautious first step towards being able to create JS objects before a global object has been instantiated. --- Meta/Lagom/Fuzzers/FuzzilliJs.cpp | 5 ++- .../Spreadsheet/JSIntegration.cpp | 5 ++- .../Applications/Spreadsheet/JSIntegration.h | 2 +- .../LibJS/Contrib/Test262/$262Object.cpp | 3 +- .../LibJS/Contrib/Test262/GlobalObject.h | 5 ++- Userland/Libraries/LibJS/Interpreter.h | 4 +- .../Libraries/LibJS/Runtime/GlobalObject.cpp | 15 ++++--- .../Libraries/LibJS/Runtime/GlobalObject.h | 45 ++++++++++++++----- Userland/Libraries/LibJS/Runtime/Object.cpp | 12 +++-- Userland/Libraries/LibJS/Runtime/Object.h | 4 +- Userland/Libraries/LibJS/Runtime/Realm.cpp | 2 +- .../LibJS/Runtime/ShadowRealmConstructor.cpp | 4 +- Userland/Libraries/LibJS/Runtime/Shape.cpp | 13 +++--- Userland/Libraries/LibJS/Runtime/Shape.h | 5 ++- .../Libraries/LibTest/JavaScriptTestRunner.h | 6 ++- .../LibWeb/Bindings/WindowObject.cpp | 5 ++- .../Libraries/LibWeb/Bindings/WindowObject.h | 2 +- Userland/Libraries/LibWeb/HTML/Worker.cpp | 2 +- .../WebContent/ConsoleGlobalObject.cpp | 5 ++- .../Services/WebContent/ConsoleGlobalObject.h | 2 +- .../WebContent/WebContentConsoleClient.cpp | 3 +- Userland/Utilities/js.cpp | 10 ++++- 22 files changed, 104 insertions(+), 55 deletions(-) diff --git a/Meta/Lagom/Fuzzers/FuzzilliJs.cpp b/Meta/Lagom/Fuzzers/FuzzilliJs.cpp index b0a8b221a9..eb00d01d54 100644 --- a/Meta/Lagom/Fuzzers/FuzzilliJs.cpp +++ b/Meta/Lagom/Fuzzers/FuzzilliJs.cpp @@ -119,7 +119,7 @@ class TestRunnerGlobalObject final : public JS::GlobalObject { JS_OBJECT(TestRunnerGlobalObject, JS::GlobalObject); public: - TestRunnerGlobalObject(); + TestRunnerGlobalObject(JS::Realm&); virtual ~TestRunnerGlobalObject() override; virtual void initialize_global_object() override; @@ -128,7 +128,8 @@ private: JS_DECLARE_NATIVE_FUNCTION(fuzzilli); }; -TestRunnerGlobalObject::TestRunnerGlobalObject() +TestRunnerGlobalObject::TestRunnerGlobalObject(JS::Realm& realm) + : GlobalObject(realm) { } diff --git a/Userland/Applications/Spreadsheet/JSIntegration.cpp b/Userland/Applications/Spreadsheet/JSIntegration.cpp index febae065de..2512f8b324 100644 --- a/Userland/Applications/Spreadsheet/JSIntegration.cpp +++ b/Userland/Applications/Spreadsheet/JSIntegration.cpp @@ -92,8 +92,9 @@ Optional get_function_and_argument_index(StringView so return {}; } -SheetGlobalObject::SheetGlobalObject(Sheet& sheet) - : m_sheet(sheet) +SheetGlobalObject::SheetGlobalObject(JS::Realm& realm, Sheet& sheet) + : JS::GlobalObject(realm) + , m_sheet(sheet) { } diff --git a/Userland/Applications/Spreadsheet/JSIntegration.h b/Userland/Applications/Spreadsheet/JSIntegration.h index 15c237634d..f879c99880 100644 --- a/Userland/Applications/Spreadsheet/JSIntegration.h +++ b/Userland/Applications/Spreadsheet/JSIntegration.h @@ -23,7 +23,7 @@ class SheetGlobalObject final : public JS::GlobalObject { JS_OBJECT(SheetGlobalObject, JS::GlobalObject); public: - SheetGlobalObject(Sheet&); + SheetGlobalObject(JS::Realm&, Sheet&); virtual ~SheetGlobalObject() override = default; diff --git a/Userland/Libraries/LibJS/Contrib/Test262/$262Object.cpp b/Userland/Libraries/LibJS/Contrib/Test262/$262Object.cpp index 183dae07c4..e9a38e2cbc 100644 --- a/Userland/Libraries/LibJS/Contrib/Test262/$262Object.cpp +++ b/Userland/Libraries/LibJS/Contrib/Test262/$262Object.cpp @@ -57,7 +57,8 @@ JS_DEFINE_NATIVE_FUNCTION($262Object::clear_kept_objects) JS_DEFINE_NATIVE_FUNCTION($262Object::create_realm) { - auto realm = vm.heap().allocate_without_global_object(); + // FIXME: This doesn't look right. + auto realm = vm.heap().allocate_without_global_object(*global_object.associated_realm()); realm->initialize_global_object(); return Value(realm->$262()); } diff --git a/Userland/Libraries/LibJS/Contrib/Test262/GlobalObject.h b/Userland/Libraries/LibJS/Contrib/Test262/GlobalObject.h index 5729f9021f..359f5b5036 100644 --- a/Userland/Libraries/LibJS/Contrib/Test262/GlobalObject.h +++ b/Userland/Libraries/LibJS/Contrib/Test262/GlobalObject.h @@ -15,7 +15,10 @@ class GlobalObject final : public JS::GlobalObject { JS_OBJECT(GlobalObject, JS::GlobalObject); public: - GlobalObject() = default; + GlobalObject(JS::Realm& realm) + : JS::GlobalObject(realm) + { + } virtual void initialize_global_object() override; virtual ~GlobalObject() override = default; diff --git a/Userland/Libraries/LibJS/Interpreter.h b/Userland/Libraries/LibJS/Interpreter.h index c8e5eed82d..2e1988e115 100644 --- a/Userland/Libraries/LibJS/Interpreter.h +++ b/Userland/Libraries/LibJS/Interpreter.h @@ -64,7 +64,7 @@ public: // 7. If the host requires use of an exotic object to serve as realm's global object, let global be such an object created in a host-defined manner. // Otherwise, let global be undefined, indicating that an ordinary object should be created as the global object. - auto* global_object = static_cast(interpreter->heap().allocate_without_global_object(forward(args)...)); + auto* global_object = static_cast(interpreter->heap().allocate_without_global_object(*realm, forward(args)...)); // 8. If the host requires that the this binding in realm's global scope return an object other than the global object, let thisValue be such an object created // in a host-defined manner. Otherwise, let thisValue be undefined, indicating that realm's global this binding should be the global object. @@ -73,7 +73,7 @@ public: this_value = global_object; } else { // FIXME: Should we pass args in here? Let's er on the side of caution and say yes. - this_value = static_cast(interpreter->heap().allocate_without_global_object(forward(args)...)); + this_value = static_cast(interpreter->heap().allocate_without_global_object(*realm, forward(args)...)); } // 9. Perform SetRealmGlobalObject(realm, global, thisValue). diff --git a/Userland/Libraries/LibJS/Runtime/GlobalObject.cpp b/Userland/Libraries/LibJS/Runtime/GlobalObject.cpp index d287973d61..4f43d720dc 100644 --- a/Userland/Libraries/LibJS/Runtime/GlobalObject.cpp +++ b/Userland/Libraries/LibJS/Runtime/GlobalObject.cpp @@ -139,8 +139,8 @@ namespace JS { -GlobalObject::GlobalObject() - : Object(GlobalObjectTag::Tag) +GlobalObject::GlobalObject(Realm& realm) + : Object(GlobalObjectTag::Tag, realm) , m_console(make(*this)) { } @@ -152,14 +152,16 @@ void GlobalObject::initialize_global_object() ensure_shape_is_unique(); // These are done first since other prototypes depend on their presence. - m_empty_object_shape = heap().allocate_without_global_object(*this); + VERIFY(associated_realm()); + auto& realm = *associated_realm(); + m_empty_object_shape = heap().allocate_without_global_object(realm); m_object_prototype = heap().allocate_without_global_object(*this); m_function_prototype = heap().allocate_without_global_object(*this); - m_new_object_shape = vm.heap().allocate_without_global_object(*this); + m_new_object_shape = vm.heap().allocate_without_global_object(realm); m_new_object_shape->set_prototype_without_transition(m_object_prototype); - m_new_ordinary_function_prototype_object_shape = vm.heap().allocate_without_global_object(*this); + m_new_ordinary_function_prototype_object_shape = vm.heap().allocate_without_global_object(realm); m_new_ordinary_function_prototype_object_shape->set_prototype_without_transition(m_object_prototype); m_new_ordinary_function_prototype_object_shape->add_property_without_transition(vm.names.constructor, Attribute::Writable | Attribute::Configurable); @@ -359,8 +361,9 @@ Realm* GlobalObject::associated_realm() return m_associated_realm; } -void GlobalObject::set_associated_realm(Badge, Realm& realm) +void GlobalObject::set_associated_realm(Realm& realm) { + VERIFY(&realm == &shape().realm()); m_associated_realm = &realm; } diff --git a/Userland/Libraries/LibJS/Runtime/GlobalObject.h b/Userland/Libraries/LibJS/Runtime/GlobalObject.h index fa3a20a365..e07c608985 100644 --- a/Userland/Libraries/LibJS/Runtime/GlobalObject.h +++ b/Userland/Libraries/LibJS/Runtime/GlobalObject.h @@ -17,7 +17,7 @@ class GlobalObject : public Object { JS_OBJECT(GlobalObject, Object); public: - explicit GlobalObject(); + explicit GlobalObject(Realm&); virtual void initialize_global_object(); virtual ~GlobalObject() override; @@ -25,7 +25,7 @@ public: Console& console() { return *m_console; } Realm* associated_realm(); - void set_associated_realm(Badge, Realm&); + void set_associated_realm(Realm&); Shape* empty_object_shape() { return m_empty_object_shape; } @@ -56,25 +56,46 @@ public: FunctionObject* throw_type_error_function() const { return m_throw_type_error_function; } #define __JS_ENUMERATE(ClassName, snake_name, PrototypeName, ConstructorName, ArrayType) \ - ConstructorName* snake_name##_constructor() { return m_##snake_name##_constructor; } \ - Object* snake_name##_prototype() { return m_##snake_name##_prototype; } + ConstructorName* snake_name##_constructor() \ + { \ + return m_##snake_name##_constructor; \ + } \ + Object* snake_name##_prototype() \ + { \ + return m_##snake_name##_prototype; \ + } JS_ENUMERATE_BUILTIN_TYPES #undef __JS_ENUMERATE -#define __JS_ENUMERATE(ClassName, snake_name, PrototypeName, ConstructorName) \ - Intl::ConstructorName* intl_##snake_name##_constructor() { return m_intl_##snake_name##_constructor; } \ - Object* intl_##snake_name##_prototype() { return m_intl_##snake_name##_prototype; } +#define __JS_ENUMERATE(ClassName, snake_name, PrototypeName, ConstructorName) \ + Intl::ConstructorName* intl_##snake_name##_constructor() \ + { \ + return m_intl_##snake_name##_constructor; \ + } \ + Object* intl_##snake_name##_prototype() \ + { \ + return m_intl_##snake_name##_prototype; \ + } JS_ENUMERATE_INTL_OBJECTS #undef __JS_ENUMERATE -#define __JS_ENUMERATE(ClassName, snake_name, PrototypeName, ConstructorName) \ - Temporal::ConstructorName* temporal_##snake_name##_constructor() { return m_temporal_##snake_name##_constructor; } \ - Object* temporal_##snake_name##_prototype() { return m_temporal_##snake_name##_prototype; } +#define __JS_ENUMERATE(ClassName, snake_name, PrototypeName, ConstructorName) \ + Temporal::ConstructorName* temporal_##snake_name##_constructor() \ + { \ + return m_temporal_##snake_name##_constructor; \ + } \ + Object* temporal_##snake_name##_prototype() \ + { \ + return m_temporal_##snake_name##_prototype; \ + } JS_ENUMERATE_TEMPORAL_OBJECTS #undef __JS_ENUMERATE #define __JS_ENUMERATE(ClassName, snake_name) \ - Object* snake_name##_prototype() { return m_##snake_name##_prototype; } + Object* snake_name##_prototype() \ + { \ + return m_##snake_name##_prototype; \ + } JS_ENUMERATE_ITERATOR_PROTOTYPES #undef __JS_ENUMERATE @@ -173,7 +194,7 @@ inline void GlobalObject::add_constructor(PropertyKey const& property_key, Const inline GlobalObject* Shape::global_object() const { - return static_cast(m_global_object); + return &static_cast(m_realm.global_object()); } template<> diff --git a/Userland/Libraries/LibJS/Runtime/Object.cpp b/Userland/Libraries/LibJS/Runtime/Object.cpp index 2efaa9b8d4..1d31293670 100644 --- a/Userland/Libraries/LibJS/Runtime/Object.cpp +++ b/Userland/Libraries/LibJS/Runtime/Object.cpp @@ -34,15 +34,21 @@ Object* Object::create(GlobalObject& global_object, Object* prototype) return global_object.heap().allocate(global_object, *prototype); } -Object::Object(GlobalObjectTag) +GlobalObject& Object::global_object() const +{ + return *shape().global_object(); +} + +Object::Object(GlobalObjectTag, Realm& realm) { // This is the global object - m_shape = heap().allocate_without_global_object(*this); + m_shape = heap().allocate_without_global_object(realm); } Object::Object(ConstructWithoutPrototypeTag, GlobalObject& global_object) { - m_shape = heap().allocate_without_global_object(global_object); + VERIFY(global_object.associated_realm()); + m_shape = heap().allocate_without_global_object(*global_object.associated_realm()); } Object::Object(GlobalObject& global_object, Object* prototype) diff --git a/Userland/Libraries/LibJS/Runtime/Object.h b/Userland/Libraries/LibJS/Runtime/Object.h index e77fda9c17..d3ed79b51a 100644 --- a/Userland/Libraries/LibJS/Runtime/Object.h +++ b/Userland/Libraries/LibJS/Runtime/Object.h @@ -186,7 +186,7 @@ public: Shape& shape() { return *m_shape; } Shape const& shape() const { return *m_shape; } - GlobalObject& global_object() const { return *shape().global_object(); } + GlobalObject& global_object() const; void ensure_shape_is_unique(); @@ -196,7 +196,7 @@ public: protected: enum class GlobalObjectTag { Tag }; enum class ConstructWithoutPrototypeTag { Tag }; - explicit Object(GlobalObjectTag); + explicit Object(GlobalObjectTag, Realm&); Object(ConstructWithoutPrototypeTag, GlobalObject&); void set_prototype(Object*); diff --git a/Userland/Libraries/LibJS/Runtime/Realm.cpp b/Userland/Libraries/LibJS/Runtime/Realm.cpp index 35c8faa3e6..87516cb883 100644 --- a/Userland/Libraries/LibJS/Runtime/Realm.cpp +++ b/Userland/Libraries/LibJS/Runtime/Realm.cpp @@ -24,7 +24,7 @@ void Realm::set_global_object(GlobalObject& global_object, Object* this_value) // 2. Assert: Type(globalObj) is Object. // Non-standard - global_object.set_associated_realm({}, *this); + global_object.set_associated_realm(*this); // 3. If thisValue is undefined, set thisValue to globalObj. if (!this_value) diff --git a/Userland/Libraries/LibJS/Runtime/ShadowRealmConstructor.cpp b/Userland/Libraries/LibJS/Runtime/ShadowRealmConstructor.cpp index ecfbe393f9..f70b78c581 100644 --- a/Userland/Libraries/LibJS/Runtime/ShadowRealmConstructor.cpp +++ b/Userland/Libraries/LibJS/Runtime/ShadowRealmConstructor.cpp @@ -63,9 +63,9 @@ ThrowCompletionOr ShadowRealmConstructor::construct(FunctionObject& new auto* object = TRY(ordinary_create_from_constructor(global_object, new_target, &GlobalObject::shadow_realm_prototype, *realm, move(context))); // 10. Perform ? SetRealmGlobalObject(realmRec, undefined, undefined). - auto* new_global_object = vm.heap().allocate_without_global_object(); - new_global_object->initialize_global_object(); + auto* new_global_object = vm.heap().allocate_without_global_object(*realm); realm->set_global_object(*new_global_object, nullptr); + new_global_object->initialize_global_object(); // TODO: I don't think we should have these exactly like this, that doesn't work well with how // we create global objects. Still, it should be possible to make a ShadowRealm with a diff --git a/Userland/Libraries/LibJS/Runtime/Shape.cpp b/Userland/Libraries/LibJS/Runtime/Shape.cpp index d4090418c9..5f4397656a 100644 --- a/Userland/Libraries/LibJS/Runtime/Shape.cpp +++ b/Userland/Libraries/LibJS/Runtime/Shape.cpp @@ -12,8 +12,7 @@ namespace JS { Shape* Shape::create_unique_clone() const { - VERIFY(m_global_object); - auto* new_shape = heap().allocate_without_global_object(*m_global_object); + auto* new_shape = heap().allocate_without_global_object(m_realm); new_shape->m_unique = true; new_shape->m_prototype = m_prototype; ensure_property_table(); @@ -88,13 +87,13 @@ Shape* Shape::create_prototype_transition(Object* new_prototype) return new_shape; } -Shape::Shape(Object& global_object) - : m_global_object(&global_object) +Shape::Shape(Realm& realm) + : m_realm(realm) { } Shape::Shape(Shape& previous_shape, StringOrSymbol const& property_key, PropertyAttributes attributes, TransitionType transition_type) - : m_global_object(previous_shape.m_global_object) + : m_realm(previous_shape.m_realm) , m_previous(&previous_shape) , m_property_key(property_key) , m_prototype(previous_shape.m_prototype) @@ -105,7 +104,7 @@ Shape::Shape(Shape& previous_shape, StringOrSymbol const& property_key, Property } Shape::Shape(Shape& previous_shape, Object* new_prototype) - : m_global_object(previous_shape.m_global_object) + : m_realm(previous_shape.m_realm) , m_previous(&previous_shape) , m_prototype(new_prototype) , m_property_count(previous_shape.m_property_count) @@ -116,7 +115,7 @@ Shape::Shape(Shape& previous_shape, Object* new_prototype) void Shape::visit_edges(Cell::Visitor& visitor) { Cell::visit_edges(visitor); - visitor.visit(m_global_object); + visitor.visit(&m_realm); visitor.visit(m_prototype); visitor.visit(m_previous); m_property_key.visit_edges(visitor); diff --git a/Userland/Libraries/LibJS/Runtime/Shape.h b/Userland/Libraries/LibJS/Runtime/Shape.h index 58f60c67c8..9f380788fd 100644 --- a/Userland/Libraries/LibJS/Runtime/Shape.h +++ b/Userland/Libraries/LibJS/Runtime/Shape.h @@ -47,7 +47,7 @@ public: Prototype, }; - explicit Shape(Object& global_object); + explicit Shape(Realm&); Shape(Shape& previous_shape, StringOrSymbol const& property_key, PropertyAttributes attributes, TransitionType); Shape(Shape& previous_shape, Object* new_prototype); @@ -61,6 +61,7 @@ public: bool is_unique() const { return m_unique; } Shape* create_unique_clone() const; + Realm& realm() const { return m_realm; } GlobalObject* global_object() const; Object* prototype() { return m_prototype; } @@ -92,7 +93,7 @@ private: void ensure_property_table() const; - Object* m_global_object { nullptr }; + Realm& m_realm; mutable OwnPtr> m_property_table; diff --git a/Userland/Libraries/LibTest/JavaScriptTestRunner.h b/Userland/Libraries/LibTest/JavaScriptTestRunner.h index 8c8672b990..5752075213 100644 --- a/Userland/Libraries/LibTest/JavaScriptTestRunner.h +++ b/Userland/Libraries/LibTest/JavaScriptTestRunner.h @@ -190,7 +190,11 @@ class TestRunnerGlobalObject final : public JS::GlobalObject { JS_OBJECT(TestRunnerGlobalObject, JS::GlobalObject); public: - TestRunnerGlobalObject() = default; + TestRunnerGlobalObject(JS::Realm& realm) + : JS::GlobalObject(realm) + { + } + virtual ~TestRunnerGlobalObject() override = default; virtual void initialize_global_object() override; diff --git a/Userland/Libraries/LibWeb/Bindings/WindowObject.cpp b/Userland/Libraries/LibWeb/Bindings/WindowObject.cpp index 89ea8ed2df..97197a2698 100644 --- a/Userland/Libraries/LibWeb/Bindings/WindowObject.cpp +++ b/Userland/Libraries/LibWeb/Bindings/WindowObject.cpp @@ -50,8 +50,9 @@ namespace Web::Bindings { -WindowObject::WindowObject(HTML::Window& impl) - : m_impl(impl) +WindowObject::WindowObject(JS::Realm& realm, HTML::Window& impl) + : GlobalObject(realm) + , m_impl(impl) { impl.set_wrapper({}, *this); } diff --git a/Userland/Libraries/LibWeb/Bindings/WindowObject.h b/Userland/Libraries/LibWeb/Bindings/WindowObject.h index 2af38ae551..383280ae86 100644 --- a/Userland/Libraries/LibWeb/Bindings/WindowObject.h +++ b/Userland/Libraries/LibWeb/Bindings/WindowObject.h @@ -32,7 +32,7 @@ class WindowObject JS_OBJECT(WindowObject, JS::GlobalObject); public: - explicit WindowObject(HTML::Window&); + explicit WindowObject(JS::Realm&, HTML::Window&); virtual void initialize_global_object() override; virtual ~WindowObject() override = default; diff --git a/Userland/Libraries/LibWeb/HTML/Worker.cpp b/Userland/Libraries/LibWeb/HTML/Worker.cpp index 3fef01f121..55cebc5afd 100644 --- a/Userland/Libraries/LibWeb/HTML/Worker.cpp +++ b/Userland/Libraries/LibWeb/HTML/Worker.cpp @@ -113,7 +113,7 @@ void Worker::run_a_worker(AK::URL& url, EnvironmentSettingsObject& outside_setti // FIXME: Make and use subclasses of WorkerGlobalScope, however this requires JS::GlobalObject to // play nicely with the IDL interpreter, to make spec-compliant extensions, which it currently does not. - m_worker_scope = m_worker_vm->heap().allocate_without_global_object(); + m_worker_scope = m_worker_vm->heap().allocate_without_global_object(*m_worker_realm); m_worker_scope->initialize_global_object(); m_console = adopt_ref(*new WorkerDebugConsoleClient(m_worker_scope->console())); diff --git a/Userland/Services/WebContent/ConsoleGlobalObject.cpp b/Userland/Services/WebContent/ConsoleGlobalObject.cpp index 411d5e56e0..478c5305db 100644 --- a/Userland/Services/WebContent/ConsoleGlobalObject.cpp +++ b/Userland/Services/WebContent/ConsoleGlobalObject.cpp @@ -14,8 +14,9 @@ namespace WebContent { -ConsoleGlobalObject::ConsoleGlobalObject(Web::Bindings::WindowObject& parent_object) - : m_window_object(&parent_object) +ConsoleGlobalObject::ConsoleGlobalObject(JS::Realm& realm, Web::Bindings::WindowObject& parent_object) + : GlobalObject(realm) + , m_window_object(&parent_object) { } diff --git a/Userland/Services/WebContent/ConsoleGlobalObject.h b/Userland/Services/WebContent/ConsoleGlobalObject.h index ca2ef828b6..9f024c1859 100644 --- a/Userland/Services/WebContent/ConsoleGlobalObject.h +++ b/Userland/Services/WebContent/ConsoleGlobalObject.h @@ -20,7 +20,7 @@ class ConsoleGlobalObject final : public JS::GlobalObject { JS_OBJECT(ConsoleGlobalObject, JS::GlobalObject); public: - ConsoleGlobalObject(Web::Bindings::WindowObject&); + ConsoleGlobalObject(JS::Realm&, Web::Bindings::WindowObject&); virtual ~ConsoleGlobalObject() override = default; virtual JS::ThrowCompletionOr internal_get_prototype_of() const override; diff --git a/Userland/Services/WebContent/WebContentConsoleClient.cpp b/Userland/Services/WebContent/WebContentConsoleClient.cpp index 1cd97fec50..dd59dbae53 100644 --- a/Userland/Services/WebContent/WebContentConsoleClient.cpp +++ b/Userland/Services/WebContent/WebContentConsoleClient.cpp @@ -26,12 +26,13 @@ WebContentConsoleClient::WebContentConsoleClient(JS::Console& console, WeakPtrvm(); auto& global_object = m_interpreter->global_object(); - auto console_global_object = m_interpreter->heap().allocate_without_global_object(static_cast(global_object)); + auto console_global_object = m_interpreter->heap().allocate_without_global_object(m_interpreter->realm(), static_cast(global_object)); // NOTE: We need to push an execution context here for NativeFunction::create() to succeed during global object initialization. // It gets removed immediately after creating the interpreter in Document::interpreter(). auto& eso = verify_cast(*m_interpreter->realm().host_defined()); vm.push_execution_context(eso.realm_execution_context()); + console_global_object->set_associated_realm(m_interpreter->realm()); console_global_object->initialize_global_object(); vm.pop_execution_context(); diff --git a/Userland/Utilities/js.cpp b/Userland/Utilities/js.cpp index 375efd69ce..06c0a96e67 100644 --- a/Userland/Utilities/js.cpp +++ b/Userland/Utilities/js.cpp @@ -92,7 +92,10 @@ class ReplObject final : public JS::GlobalObject { JS_OBJECT(ReplObject, JS::GlobalObject); public: - ReplObject() = default; + ReplObject(JS::Realm& realm) + : GlobalObject(realm) + { + } virtual void initialize_global_object() override; virtual ~ReplObject() override = default; @@ -110,7 +113,10 @@ class ScriptObject final : public JS::GlobalObject { JS_OBJECT(ScriptObject, JS::GlobalObject); public: - ScriptObject() = default; + ScriptObject(JS::Realm& realm) + : JS::GlobalObject(realm) + { + } virtual void initialize_global_object() override; virtual ~ScriptObject() override = default;