mirror of
https://github.com/LadybirdBrowser/ladybird.git
synced 2025-12-08 06:09:58 +00:00
LibJS: Generate bytecode for the BlockDeclarationInstantiation AO
This necessitated adding some new instructions for creating mutable and immutable bindings.
This commit is contained in:
parent
892c7d980e
commit
44fa9566a8
Notes:
github-actions[bot]
2025-10-27 20:15:37 +00:00
Author: https://github.com/awesomekling
Commit: 44fa9566a8
Pull-request: https://github.com/LadybirdBrowser/ladybird/pull/6604
6 changed files with 131 additions and 117 deletions
|
|
@ -1,5 +1,5 @@
|
|||
/*
|
||||
* Copyright (c) 2021-2024, Andreas Kling <andreas@ladybird.org>
|
||||
* Copyright (c) 2021-2025, Andreas Kling <andreas@ladybird.org>
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
|
@ -179,7 +179,7 @@ CodeGenerationErrorOr<void> Generator::emit_function_declaration_instantiation(E
|
|||
if (!function.is_strict_mode()) {
|
||||
bool can_elide_lexical_environment = !scope_body || !scope_body->has_non_local_lexical_declarations();
|
||||
if (!can_elide_lexical_environment) {
|
||||
emit<Op::CreateLexicalEnvironment>(function.shared_data().m_lex_environment_bindings_count);
|
||||
emit<Op::CreateLexicalEnvironment>(OptionalNone {}, function.shared_data().m_lex_environment_bindings_count);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -570,10 +570,58 @@ bool Generator::emit_block_declaration_instantiation(ScopeNode const& scope_node
|
|||
if (!needs_block_declaration_instantiation)
|
||||
return false;
|
||||
|
||||
// FIXME: Generate the actual bytecode for block declaration instantiation
|
||||
// and get rid of the BlockDeclarationInstantiation instruction.
|
||||
auto environment = allocate_register();
|
||||
emit<Bytecode::Op::CreateLexicalEnvironment>(environment);
|
||||
start_boundary(BlockBoundaryType::LeaveLexicalEnvironment);
|
||||
emit<Bytecode::Op::BlockDeclarationInstantiation>(scope_node);
|
||||
|
||||
MUST(scope_node.for_each_lexically_scoped_declaration([&](Declaration const& declaration) {
|
||||
auto is_constant_declaration = declaration.is_constant_declaration();
|
||||
// NOTE: Due to the use of MUST with `create_immutable_binding` and `create_mutable_binding` below,
|
||||
// an exception should not result from `for_each_bound_name`.
|
||||
// a. For each element dn of the BoundNames of d, do
|
||||
MUST(declaration.for_each_bound_identifier([&](Identifier const& identifier) {
|
||||
if (identifier.is_local()) {
|
||||
// NOTE: No need to create bindings for local variables as their values are not stored in an environment.
|
||||
return;
|
||||
}
|
||||
|
||||
auto const& name = identifier.string();
|
||||
|
||||
// i. If IsConstantDeclaration of d is true, then
|
||||
if (is_constant_declaration) {
|
||||
// 1. Perform ! env.CreateImmutableBinding(dn, true).
|
||||
emit<Bytecode::Op::CreateImmutableBinding>(environment, intern_identifier(name), true);
|
||||
}
|
||||
// ii. Else,
|
||||
else {
|
||||
// 1. Perform ! env.CreateMutableBinding(dn, false). NOTE: This step is replaced in section B.3.2.6.
|
||||
emit<Bytecode::Op::CreateMutableBinding>(environment, intern_identifier(name), false);
|
||||
}
|
||||
}));
|
||||
|
||||
// b. If d is either a FunctionDeclaration, a GeneratorDeclaration, an AsyncFunctionDeclaration, or an AsyncGeneratorDeclaration, then
|
||||
if (is<FunctionDeclaration>(declaration)) {
|
||||
// i. Let fn be the sole element of the BoundNames of d.
|
||||
auto& function_declaration = static_cast<FunctionDeclaration const&>(declaration);
|
||||
|
||||
// ii. Let fo be InstantiateFunctionObject of d with arguments env and privateEnv.
|
||||
auto fo = allocate_register();
|
||||
emit<Bytecode::Op::NewFunction>(fo, function_declaration, OptionalNone {});
|
||||
|
||||
// iii. Perform ! env.InitializeBinding(fn, fo). NOTE: This step is replaced in section B.3.2.6.
|
||||
if (function_declaration.name_identifier()->is_local()) {
|
||||
auto local_index = function_declaration.name_identifier()->local_index();
|
||||
if (local_index.is_variable()) {
|
||||
emit<Bytecode::Op::Mov>(local(local_index), fo);
|
||||
} else {
|
||||
VERIFY_NOT_REACHED();
|
||||
}
|
||||
} else {
|
||||
emit<Bytecode::Op::InitializeLexicalBinding>(intern_identifier(function_declaration.name()), fo);
|
||||
}
|
||||
}
|
||||
}));
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue