mirror of
https://github.com/RGBCube/serenity
synced 2025-07-24 21:47:43 +00:00
LibJS: Move the GlobalEnvironment from GlobalObject to Realm
This is where the spec wants to have it. Requires a couple of hacks as currently everything that needs a Realm actually has a GlobalObject, so we need to go via the Interpreter.
This commit is contained in:
parent
1e79934acf
commit
f29a82dd84
6 changed files with 13 additions and 16 deletions
|
@ -12,6 +12,7 @@
|
||||||
#include <LibJS/Bytecode/Op.h>
|
#include <LibJS/Bytecode/Op.h>
|
||||||
#include <LibJS/Runtime/GlobalEnvironment.h>
|
#include <LibJS/Runtime/GlobalEnvironment.h>
|
||||||
#include <LibJS/Runtime/GlobalObject.h>
|
#include <LibJS/Runtime/GlobalObject.h>
|
||||||
|
#include <LibJS/Runtime/Realm.h>
|
||||||
|
|
||||||
namespace JS::Bytecode {
|
namespace JS::Bytecode {
|
||||||
|
|
||||||
|
@ -50,8 +51,8 @@ Value Interpreter::run(Executable const& executable, BasicBlock const* entry_poi
|
||||||
execution_context.this_value = &global_object();
|
execution_context.this_value = &global_object();
|
||||||
static FlyString global_execution_context_name = "(*BC* global execution context)";
|
static FlyString global_execution_context_name = "(*BC* global execution context)";
|
||||||
execution_context.function_name = global_execution_context_name;
|
execution_context.function_name = global_execution_context_name;
|
||||||
execution_context.lexical_environment = &global_object().environment();
|
execution_context.lexical_environment = &m_realm.global_environment();
|
||||||
execution_context.variable_environment = &global_object().environment();
|
execution_context.variable_environment = &m_realm.global_environment();
|
||||||
VERIFY(!vm().exception());
|
VERIFY(!vm().exception());
|
||||||
// FIXME: How do we know if we're in strict mode? Maybe the Bytecode::Block should know this?
|
// FIXME: How do we know if we're in strict mode? Maybe the Bytecode::Block should know this?
|
||||||
// execution_context.is_strict_mode = ???;
|
// execution_context.is_strict_mode = ???;
|
||||||
|
|
|
@ -37,6 +37,8 @@ Interpreter::~Interpreter()
|
||||||
|
|
||||||
void Interpreter::run(GlobalObject& global_object, const Program& program)
|
void Interpreter::run(GlobalObject& global_object, const Program& program)
|
||||||
{
|
{
|
||||||
|
// FIXME: Why does this receive a GlobalObject? Interpreter has one already, and this might not be in sync with the Realm's GlobalObject.
|
||||||
|
|
||||||
auto& vm = this->vm();
|
auto& vm = this->vm();
|
||||||
VERIFY(!vm.exception());
|
VERIFY(!vm.exception());
|
||||||
|
|
||||||
|
@ -49,8 +51,8 @@ void Interpreter::run(GlobalObject& global_object, const Program& program)
|
||||||
execution_context.this_value = &global_object;
|
execution_context.this_value = &global_object;
|
||||||
static FlyString global_execution_context_name = "(global execution context)";
|
static FlyString global_execution_context_name = "(global execution context)";
|
||||||
execution_context.function_name = global_execution_context_name;
|
execution_context.function_name = global_execution_context_name;
|
||||||
execution_context.lexical_environment = &global_object.environment();
|
execution_context.lexical_environment = &realm().global_environment();
|
||||||
execution_context.variable_environment = &global_object.environment();
|
execution_context.variable_environment = &realm().global_environment();
|
||||||
VERIFY(!vm.exception());
|
VERIFY(!vm.exception());
|
||||||
execution_context.is_strict_mode = program.is_strict_mode();
|
execution_context.is_strict_mode = program.is_strict_mode();
|
||||||
vm.push_execution_context(execution_context, global_object);
|
vm.push_execution_context(execution_context, global_object);
|
||||||
|
|
|
@ -399,7 +399,7 @@ Value perform_eval(Value x, GlobalObject& caller_realm, CallerMode strict_caller
|
||||||
if (direct == EvalMode::Direct)
|
if (direct == EvalMode::Direct)
|
||||||
return interpreter.execute_statement(caller_realm, program).value_or(js_undefined());
|
return interpreter.execute_statement(caller_realm, program).value_or(js_undefined());
|
||||||
|
|
||||||
TemporaryChange scope_change(vm.running_execution_context().lexical_environment, static_cast<Environment*>(&caller_realm.environment()));
|
TemporaryChange scope_change(vm.running_execution_context().lexical_environment, static_cast<Environment*>(&interpreter.realm().global_environment()));
|
||||||
TemporaryChange scope_change_strict(vm.running_execution_context().is_strict_mode, strict_caller == CallerMode::Strict);
|
TemporaryChange scope_change_strict(vm.running_execution_context().is_strict_mode, strict_caller == CallerMode::Strict);
|
||||||
return interpreter.execute_statement(caller_realm, program).value_or(js_undefined());
|
return interpreter.execute_statement(caller_realm, program).value_or(js_undefined());
|
||||||
}
|
}
|
||||||
|
|
|
@ -129,8 +129,6 @@ void GlobalObject::initialize_global_object()
|
||||||
m_object_prototype = heap().allocate_without_global_object<ObjectPrototype>(*this);
|
m_object_prototype = heap().allocate_without_global_object<ObjectPrototype>(*this);
|
||||||
m_function_prototype = heap().allocate_without_global_object<FunctionPrototype>(*this);
|
m_function_prototype = heap().allocate_without_global_object<FunctionPrototype>(*this);
|
||||||
|
|
||||||
m_environment = heap().allocate<GlobalEnvironment>(*this, *this, *this);
|
|
||||||
|
|
||||||
m_new_object_shape = vm.heap().allocate_without_global_object<Shape>(*this);
|
m_new_object_shape = vm.heap().allocate_without_global_object<Shape>(*this);
|
||||||
m_new_object_shape->set_prototype_without_transition(m_object_prototype);
|
m_new_object_shape->set_prototype_without_transition(m_object_prototype);
|
||||||
|
|
||||||
|
@ -293,7 +291,6 @@ void GlobalObject::visit_edges(Visitor& visitor)
|
||||||
visitor.visit(m_new_ordinary_function_prototype_object_shape);
|
visitor.visit(m_new_ordinary_function_prototype_object_shape);
|
||||||
visitor.visit(m_proxy_constructor);
|
visitor.visit(m_proxy_constructor);
|
||||||
visitor.visit(m_generator_object_prototype);
|
visitor.visit(m_generator_object_prototype);
|
||||||
visitor.visit(m_environment);
|
|
||||||
visitor.visit(m_array_prototype_values_function);
|
visitor.visit(m_array_prototype_values_function);
|
||||||
visitor.visit(m_eval_function);
|
visitor.visit(m_eval_function);
|
||||||
visitor.visit(m_temporal_time_zone_prototype_get_offset_nanoseconds_for_function);
|
visitor.visit(m_temporal_time_zone_prototype_get_offset_nanoseconds_for_function);
|
||||||
|
|
|
@ -21,8 +21,6 @@ public:
|
||||||
|
|
||||||
virtual ~GlobalObject() override;
|
virtual ~GlobalObject() override;
|
||||||
|
|
||||||
GlobalEnvironment& environment() { return *m_environment; }
|
|
||||||
|
|
||||||
Console& console() { return *m_console; }
|
Console& console() { return *m_console; }
|
||||||
|
|
||||||
Shape* empty_object_shape() { return m_empty_object_shape; }
|
Shape* empty_object_shape() { return m_empty_object_shape; }
|
||||||
|
@ -100,8 +98,6 @@ private:
|
||||||
// Not included in JS_ENUMERATE_NATIVE_OBJECTS due to missing distinct constructor
|
// Not included in JS_ENUMERATE_NATIVE_OBJECTS due to missing distinct constructor
|
||||||
GeneratorObjectPrototype* m_generator_object_prototype { nullptr };
|
GeneratorObjectPrototype* m_generator_object_prototype { nullptr };
|
||||||
|
|
||||||
GlobalEnvironment* m_environment { nullptr };
|
|
||||||
|
|
||||||
FunctionObject* m_array_prototype_values_function { nullptr };
|
FunctionObject* m_array_prototype_values_function { nullptr };
|
||||||
FunctionObject* m_eval_function { nullptr };
|
FunctionObject* m_eval_function { nullptr };
|
||||||
FunctionObject* m_temporal_time_zone_prototype_get_offset_nanoseconds_for_function { nullptr };
|
FunctionObject* m_temporal_time_zone_prototype_get_offset_nanoseconds_for_function { nullptr };
|
||||||
|
|
|
@ -413,15 +413,15 @@ Reference VM::get_identifier_reference(Environment* environment, FlyString name,
|
||||||
|
|
||||||
// FIXME: The remainder of this function is non-conforming.
|
// FIXME: The remainder of this function is non-conforming.
|
||||||
|
|
||||||
auto& global_object = environment->global_object();
|
|
||||||
for (; environment && environment->outer_environment(); environment = environment->outer_environment()) {
|
for (; environment && environment->outer_environment(); environment = environment->outer_environment()) {
|
||||||
auto possible_match = environment->get_from_environment(name);
|
auto possible_match = environment->get_from_environment(name);
|
||||||
if (possible_match.has_value())
|
if (possible_match.has_value())
|
||||||
return Reference { *environment, move(name), strict };
|
return Reference { *environment, move(name), strict };
|
||||||
}
|
}
|
||||||
|
|
||||||
if (global_object.environment().has_binding(name) || !in_strict_mode()) {
|
auto& global_environment = interpreter().realm().global_environment();
|
||||||
return Reference { global_object.environment(), move(name), strict };
|
if (global_environment.has_binding(name) || !in_strict_mode()) {
|
||||||
|
return Reference { global_environment, move(name), strict };
|
||||||
}
|
}
|
||||||
|
|
||||||
return Reference { Reference::BaseType::Unresolvable, move(name), strict };
|
return Reference { Reference::BaseType::Unresolvable, move(name), strict };
|
||||||
|
@ -646,7 +646,8 @@ void VM::ordinary_call_bind_this(FunctionObject& function, ExecutionContext& cal
|
||||||
if (function.is_strict_mode()) {
|
if (function.is_strict_mode()) {
|
||||||
this_value = this_argument;
|
this_value = this_argument;
|
||||||
} else if (this_argument.is_nullish()) {
|
} else if (this_argument.is_nullish()) {
|
||||||
auto& global_environment = callee_realm->environment();
|
// FIXME: Make function.realm() an actual Realm, then this will become less horrendous.
|
||||||
|
auto& global_environment = interpreter().realm().global_environment();
|
||||||
this_value = &global_environment.global_this_value();
|
this_value = &global_environment.global_this_value();
|
||||||
} else {
|
} else {
|
||||||
this_value = this_argument.to_object(function.global_object());
|
this_value = this_argument.to_object(function.global_object());
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue