mirror of
https://github.com/fergalmoran/ladybird.git
synced 2026-01-03 15:16:14 +00:00
LibJS: Add BytecodeGenerator helpers for reference get/put
This allows code sharing between all AST nodes that want to get and/or put through a reference.
This commit is contained in:
@@ -93,4 +93,65 @@ void Generator::end_breakable_scope()
|
||||
{
|
||||
m_breakable_scopes.take_last();
|
||||
}
|
||||
|
||||
void Generator::emit_load_from_reference(JS::ASTNode const& node)
|
||||
{
|
||||
if (is<Identifier>(node)) {
|
||||
auto& identifier = static_cast<Identifier const&>(node);
|
||||
emit<Bytecode::Op::GetVariable>(intern_identifier(identifier.string()));
|
||||
return;
|
||||
}
|
||||
if (is<MemberExpression>(node)) {
|
||||
auto& expression = static_cast<MemberExpression const&>(node);
|
||||
expression.object().generate_bytecode(*this);
|
||||
|
||||
auto object_reg = allocate_register();
|
||||
emit<Bytecode::Op::Store>(object_reg);
|
||||
|
||||
if (expression.is_computed()) {
|
||||
expression.property().generate_bytecode(*this);
|
||||
emit<Bytecode::Op::GetByValue>(object_reg);
|
||||
} else {
|
||||
auto identifier_table_ref = intern_identifier(verify_cast<Identifier>(expression.property()).string());
|
||||
emit<Bytecode::Op::GetById>(identifier_table_ref);
|
||||
}
|
||||
return;
|
||||
}
|
||||
VERIFY_NOT_REACHED();
|
||||
}
|
||||
|
||||
void Generator::emit_store_to_reference(JS::ASTNode const& node)
|
||||
{
|
||||
if (is<Identifier>(node)) {
|
||||
auto& identifier = static_cast<Identifier const&>(node);
|
||||
emit<Bytecode::Op::SetVariable>(intern_identifier(identifier.string()));
|
||||
return;
|
||||
}
|
||||
if (is<MemberExpression>(node)) {
|
||||
// NOTE: The value is in the accumulator, so we have to store that away first.
|
||||
auto value_reg = allocate_register();
|
||||
emit<Bytecode::Op::Store>(value_reg);
|
||||
|
||||
auto& expression = static_cast<MemberExpression const&>(node);
|
||||
expression.object().generate_bytecode(*this);
|
||||
|
||||
auto object_reg = allocate_register();
|
||||
emit<Bytecode::Op::Store>(object_reg);
|
||||
|
||||
if (expression.is_computed()) {
|
||||
expression.property().generate_bytecode(*this);
|
||||
auto property_reg = allocate_register();
|
||||
emit<Bytecode::Op::Store>(property_reg);
|
||||
emit<Bytecode::Op::Load>(value_reg);
|
||||
emit<Bytecode::Op::PutByValue>(object_reg, property_reg);
|
||||
} else {
|
||||
emit<Bytecode::Op::Load>(value_reg);
|
||||
auto identifier_table_ref = intern_identifier(verify_cast<Identifier>(expression.property()).string());
|
||||
emit<Bytecode::Op::PutById>(object_reg, identifier_table_ref);
|
||||
}
|
||||
return;
|
||||
}
|
||||
VERIFY_NOT_REACHED();
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user