1
Fork 0
mirror of https://github.com/RGBCube/serenity synced 2025-07-25 03:07:43 +00:00

LibJS: Implement 'this' in the bytecode VM

ThisExpression now emits a "ResolveThisBinding" bytecode op, which
simply loads the VM's current 'this' binding into the accumulator.
This commit is contained in:
Andreas Kling 2021-10-24 14:43:00 +02:00
parent 7c7bc4f44a
commit 3117182c2e
5 changed files with 29 additions and 0 deletions

View file

@ -1214,6 +1214,7 @@ public:
}
virtual Value execute(Interpreter&, GlobalObject&) const override;
virtual void dump(int indent) const override;
virtual void generate_bytecode(Bytecode::Generator&) const override;
};
class CallExpression : public Expression {

View file

@ -1298,4 +1298,9 @@ void ClassDeclaration::generate_bytecode(Bytecode::Generator& generator) const
generator.emit<Bytecode::Op::SetVariable>(generator.intern_string(m_class_expression.ptr()->name()));
}
void ThisExpression::generate_bytecode(Bytecode::Generator& generator) const
{
generator.emit<Bytecode::Op::ResolveThisBinding>();
}
}

View file

@ -61,6 +61,7 @@
O(PushDeclarativeEnvironment) \
O(PutById) \
O(PutByValue) \
O(ResolveThisBinding) \
O(Return) \
O(RightShift) \
O(SetVariable) \

View file

@ -282,6 +282,11 @@ void Jump::execute_impl(Bytecode::Interpreter& interpreter) const
interpreter.jump(*m_true_target);
}
void ResolveThisBinding::execute_impl(Bytecode::Interpreter& interpreter) const
{
interpreter.accumulator() = interpreter.vm().resolve_this_binding(interpreter.global_object());
}
void Jump::replace_references_impl(BasicBlock const& from, BasicBlock const& to)
{
if (m_true_target.has_value() && &m_true_target->block() == &from)
@ -785,4 +790,9 @@ String IteratorResultValue::to_string_impl(Executable const&) const
return "IteratorResultValue";
}
String ResolveThisBinding::to_string_impl(Bytecode::Executable const&) const
{
return "ResolveThisBinding"sv;
}
}

View file

@ -715,6 +715,18 @@ public:
void replace_references_impl(BasicBlock const&, BasicBlock const&) { }
};
class ResolveThisBinding final : public Instruction {
public:
explicit ResolveThisBinding()
: Instruction(Type::ResolveThisBinding)
{
}
void execute_impl(Bytecode::Interpreter&) const;
String to_string_impl(Bytecode::Executable const&) const;
void replace_references_impl(BasicBlock const&, BasicBlock const&) { }
};
}
namespace JS::Bytecode {