LibJS: Call AsmInt directly from run_executable
Remove the empty AsmInterpreter wrapper and the VM::run_bytecode() trampoline now that the bytecode interpreter only enters AsmInt. Move the stack-limit check and generated assembly entry call into run_executable(), then drop the stale wrapper source file and includes.
This commit is contained in:
parent
060ba41a84
commit
8fee268851
7 changed files with 29 additions and 93 deletions
|
|
@ -1,29 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2026, the Ladybird developers.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#include <LibJS/Bytecode/AsmInterpreter/AsmInterpreter.h>
|
||||
#include <LibJS/Runtime/ExecutionContext.h>
|
||||
#include <LibJS/Runtime/VM.h>
|
||||
#include <LibJS/Runtime/Value.h>
|
||||
|
||||
extern "C" void asm_register_slow_path_stats();
|
||||
namespace JS::Bytecode {
|
||||
|
||||
// Defined in generated assembly (asmint_x86_64.S or asmint_aarch64.S)
|
||||
extern "C" void asm_interpreter_entry(u8 const* bytecode, u32 entry_point, Value* values, VM* vm);
|
||||
|
||||
void AsmInterpreter::run(VM& vm, size_t entry_point)
|
||||
{
|
||||
asm_register_slow_path_stats();
|
||||
|
||||
auto& context = vm.running_execution_context();
|
||||
auto* bytecode = context.executable->bytecode.data();
|
||||
auto* values = context.registers_and_constants_and_locals_and_arguments_span().data();
|
||||
|
||||
asm_interpreter_entry(bytecode, static_cast<u32>(entry_point), values, &vm);
|
||||
}
|
||||
|
||||
}
|
||||
|
|
@ -1,22 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2026, the Ladybird developers.
|
||||
*
|
||||
* SPDX-License-Identifier: BSD-2-Clause
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <AK/Types.h>
|
||||
|
||||
namespace JS {
|
||||
|
||||
class VM;
|
||||
namespace Bytecode {
|
||||
|
||||
class AsmInterpreter {
|
||||
public:
|
||||
static void run(VM&, size_t entry_point);
|
||||
};
|
||||
|
||||
}
|
||||
}
|
||||
|
|
@ -5,7 +5,7 @@
|
|||
*/
|
||||
|
||||
#include <AK/ScopeGuard.h>
|
||||
#include <LibJS/Bytecode/AsmInterpreter/AsmInterpreter.h>
|
||||
#include <AK/Types.h>
|
||||
#include <LibJS/Bytecode/Builtins.h>
|
||||
#include <LibJS/Bytecode/Instruction.h>
|
||||
#include <LibJS/Bytecode/Op.h>
|
||||
|
|
@ -1534,7 +1534,10 @@ NEVER_INLINE static ThrowCompletionOr<void> execute_asm_call(
|
|||
auto* callee_context = stack.allocate(registers_and_locals_count, constants, max(arguments.size(), argument_count));
|
||||
if (!callee_context) [[unlikely]]
|
||||
return vm.throw_completion<InternalError>(ErrorType::CallStackSizeExceeded);
|
||||
ScopeGuard deallocate_guard = [&stack, stack_mark] { stack.deallocate(stack_mark); };
|
||||
ScopeGuard deallocate_guard = [&stack, stack_mark] {
|
||||
if (stack.top() > stack_mark)
|
||||
stack.deallocate(stack_mark);
|
||||
};
|
||||
|
||||
auto* callee_context_argument_values = callee_context->arguments_data();
|
||||
auto const callee_context_argument_count = callee_context->argument_count;
|
||||
|
|
@ -1652,7 +1655,10 @@ static ThrowCompletionOr<void> call_with_argument_array(
|
|||
auto* callee_context = stack.allocate(registers_and_locals_count, constants, max(argument_array_length, argument_count));
|
||||
if (!callee_context) [[unlikely]]
|
||||
return vm.throw_completion<InternalError>(ErrorType::CallStackSizeExceeded);
|
||||
ScopeGuard deallocate_guard = [&stack, stack_mark] { stack.deallocate(stack_mark); };
|
||||
ScopeGuard deallocate_guard = [&stack, stack_mark] {
|
||||
if (stack.top() > stack_mark)
|
||||
stack.deallocate(stack_mark);
|
||||
};
|
||||
|
||||
auto* callee_context_argument_values = callee_context->arguments_data();
|
||||
auto const callee_context_argument_count = callee_context->argument_count;
|
||||
|
|
@ -1977,7 +1983,10 @@ i64 asm_slow_path_super_call_with_argument_array(VM* vm, u32 pc)
|
|||
auto completion = vm->throw_completion<InternalError>(ErrorType::CallStackSizeExceeded);
|
||||
return handle_asm_exception(*vm, pc, completion.value());
|
||||
}
|
||||
ScopeGuard deallocate_guard = [&stack, stack_mark] { stack.deallocate(stack_mark); };
|
||||
ScopeGuard deallocate_guard = [&stack, stack_mark] {
|
||||
if (stack.top() > stack_mark)
|
||||
stack.deallocate(stack_mark);
|
||||
};
|
||||
|
||||
auto* callee_context_argument_values = callee_context->arguments_data();
|
||||
auto const callee_context_argument_count = callee_context->argument_count;
|
||||
|
|
|
|||
|
|
@ -2738,7 +2738,7 @@ handler Call
|
|||
# The native threw. Hand the thrown Value off to a C++ helper, which
|
||||
# unwinds the callee frame off the interpreter stack and calls through
|
||||
# to VM::handle_exception. Return value follows the standard asm
|
||||
# slow-path convention (see AsmInterpreter.cpp:127):
|
||||
# slow-path convention:
|
||||
# >= 0 : an enclosing handler was found; the result is the new
|
||||
# program counter to resume at inside the (post-unwind)
|
||||
# running execution context.
|
||||
|
|
|
|||
|
|
@ -6,54 +6,35 @@
|
|||
*/
|
||||
|
||||
#include <AK/Debug.h>
|
||||
#include <AK/HashTable.h>
|
||||
#include <AK/NumericLimits.h>
|
||||
#include <AK/TemporaryChange.h>
|
||||
#include <LibGC/ConservativeHashTable.h>
|
||||
#include <LibGC/RootHashMap.h>
|
||||
#include <LibGC/RootHashTable.h>
|
||||
#include <LibJS/Bytecode/AsmInterpreter/AsmInterpreter.h>
|
||||
#include <LibJS/Bytecode/BasicBlock.h>
|
||||
#include <LibJS/Bytecode/Builtins.h>
|
||||
#include <LibJS/Bytecode/Debug.h>
|
||||
#include <LibJS/Bytecode/FormatOperand.h>
|
||||
#include <LibJS/Bytecode/Instruction.h>
|
||||
#include <LibJS/Bytecode/Label.h>
|
||||
#include <LibJS/Bytecode/Op.h>
|
||||
#include <LibJS/Bytecode/PropertyAccess.h>
|
||||
#include <LibJS/Export.h>
|
||||
#include <LibJS/Runtime/AbstractOperations.h>
|
||||
#include <LibJS/Runtime/Accessor.h>
|
||||
#include <LibJS/Runtime/Array.h>
|
||||
#include <LibJS/Runtime/AsyncFromSyncIterator.h>
|
||||
#include <LibJS/Runtime/AsyncFromSyncIteratorPrototype.h>
|
||||
#include <LibJS/Runtime/AsyncGenerator.h>
|
||||
#include <LibJS/Runtime/BigInt.h>
|
||||
#include <LibJS/Runtime/ClassConstruction.h>
|
||||
#include <LibJS/Runtime/DeclarativeEnvironment.h>
|
||||
#include <LibJS/Runtime/ECMAScriptFunctionObject.h>
|
||||
#include <LibJS/Runtime/Environment.h>
|
||||
#include <LibJS/Runtime/FunctionEnvironment.h>
|
||||
#include <LibJS/Runtime/GeneratorObject.h>
|
||||
#include <LibJS/Runtime/GlobalEnvironment.h>
|
||||
#include <LibJS/Runtime/GlobalObject.h>
|
||||
#include <LibJS/Runtime/Iterator.h>
|
||||
#include <LibJS/Runtime/ModuleEnvironment.h>
|
||||
#include <LibJS/Runtime/NativeFunction.h>
|
||||
#include <LibJS/Runtime/Realm.h>
|
||||
#include <LibJS/Runtime/Reference.h>
|
||||
#include <LibJS/Runtime/RegExpObject.h>
|
||||
#include <LibJS/Runtime/TypedArray.h>
|
||||
#include <LibJS/Runtime/VM.h>
|
||||
#include <LibJS/Runtime/Value.h>
|
||||
#include <LibJS/Runtime/ValueInlines.h>
|
||||
#include <LibJS/SourceTextModule.h>
|
||||
#include <math.h>
|
||||
|
||||
namespace JS {
|
||||
|
||||
using namespace Bytecode;
|
||||
|
||||
extern "C" void asm_register_slow_path_stats();
|
||||
|
||||
// Defined in generated assembly (asmint_x86_64.S or asmint_aarch64.S)
|
||||
extern "C" void asm_interpreter_entry(u8 const* bytecode, u32 entry_point, Value* values, VM* vm);
|
||||
|
||||
bool Bytecode::g_dump_bytecode = false;
|
||||
|
||||
// 16.1.6 ScriptEvaluation ( scriptRecord ), https://tc39.es/ecma262/#sec-runtime-semantics-scriptevaluation
|
||||
|
|
@ -279,16 +260,6 @@ NEVER_INLINE void VM::unwind_inline_frame_for_exception()
|
|||
m_running_execution_context = caller_frame;
|
||||
}
|
||||
|
||||
void VM::run_bytecode(size_t entry_point)
|
||||
{
|
||||
if (vm().interpreter_stack().is_exhausted() || vm().did_reach_stack_space_limit()) [[unlikely]] {
|
||||
reg(Register::exception()) = vm().throw_completion<InternalError>(ErrorType::CallStackSizeExceeded).value();
|
||||
return;
|
||||
}
|
||||
|
||||
AsmInterpreter::run(*this, entry_point);
|
||||
}
|
||||
|
||||
Utf16FlyString const& VM::get_identifier(IdentifierTableIndex index) const
|
||||
{
|
||||
return m_running_execution_context->executable->get_identifier(index);
|
||||
|
|
@ -327,7 +298,16 @@ ThrowCompletionOr<Value> VM::run_executable(ExecutionContext& context, Executabl
|
|||
if (reg(Register::this_value()).is_special_empty_value())
|
||||
reg(Register::this_value()) = context.this_value.value_or(js_special_empty_value());
|
||||
|
||||
run_bytecode(entry_point);
|
||||
if (vm().interpreter_stack().is_exhausted() || vm().did_reach_stack_space_limit()) [[unlikely]] {
|
||||
reg(Register::exception()) = vm().throw_completion<InternalError>(ErrorType::CallStackSizeExceeded).value();
|
||||
} else {
|
||||
asm_register_slow_path_stats();
|
||||
|
||||
auto* bytecode = executable.bytecode.data();
|
||||
auto* values = context.registers_and_constants_and_locals_and_arguments_span().data();
|
||||
|
||||
asm_interpreter_entry(bytecode, entry_point, values, this);
|
||||
}
|
||||
|
||||
dbgln_if(JS_BYTECODE_DEBUG, "VM did run bytecode unit {}", context.executable);
|
||||
|
||||
|
|
|
|||
|
|
@ -1,7 +1,6 @@
|
|||
include(libjs_generators)
|
||||
|
||||
set(SOURCES
|
||||
Bytecode/AsmInterpreter/AsmInterpreter.cpp
|
||||
Bytecode/AsmInterpreter/AsmSlowPaths.cpp
|
||||
Bytecode/BasicBlock.cpp
|
||||
Bytecode/Executable.cpp
|
||||
|
|
|
|||
|
|
@ -513,7 +513,6 @@ private:
|
|||
void set_well_known_symbols(WellKnownSymbols well_known_symbols) { m_well_known_symbols = move(well_known_symbols); }
|
||||
|
||||
void run_queued_promise_jobs_impl();
|
||||
void run_bytecode(size_t entry_point);
|
||||
|
||||
static VM* s_the;
|
||||
|
||||
|
|
|
|||
Loading…
Reference in a new issue