From bd7c188b86b8a92025bd5a0166dd9e8e4fa8a0a8 Mon Sep 17 00:00:00 2001 From: Ali Mohammad Pur Date: Fri, 6 Jun 2025 14:07:22 +0200 Subject: [PATCH] LibWasm: Avoid memory copy in read_value() if possible If the address is already aligned properly, just read a T from it; otherwise copy it to a local aligned array. This was a bottleneck on memory-heavy benchmarks. --- .../AbstractMachine/BytecodeInterpreter.cpp | 26 ++++++------------- 1 file changed, 8 insertions(+), 18 deletions(-) diff --git a/Libraries/LibWasm/AbstractMachine/BytecodeInterpreter.cpp b/Libraries/LibWasm/AbstractMachine/BytecodeInterpreter.cpp index e163d7f37b2..fd6a3c7bd9b 100644 --- a/Libraries/LibWasm/AbstractMachine/BytecodeInterpreter.cpp +++ b/Libraries/LibWasm/AbstractMachine/BytecodeInterpreter.cpp @@ -370,35 +370,25 @@ void BytecodeInterpreter::store_to_memory(Configuration& configuration, Instruct template T BytecodeInterpreter::read_value(ReadonlyBytes data) { - FixedMemoryStream stream { data }; - auto value_or_error = stream.read_value>(); - if (value_or_error.is_error()) { - dbgln("Read from {} failed", data.data()); - m_trap = Trap::from_string("Read from memory failed"); + VERIFY(sizeof(T) <= data.size()); + if (bit_cast(data.data()) % alignof(T)) { + alignas(T) u8 buf[sizeof(T)]; + memcpy(buf, data.data(), sizeof(T)); + return bit_cast>(buf); } - return value_or_error.release_value(); + return *bit_cast const*>(data.data()); } template<> float BytecodeInterpreter::read_value(ReadonlyBytes data) { - FixedMemoryStream stream { data }; - auto raw_value_or_error = stream.read_value>(); - if (raw_value_or_error.is_error()) - m_trap = Trap::from_string("Read from memory failed"); - auto raw_value = raw_value_or_error.release_value(); - return bit_cast(static_cast(raw_value)); + return bit_cast(read_value(data)); } template<> double BytecodeInterpreter::read_value(ReadonlyBytes data) { - FixedMemoryStream stream { data }; - auto raw_value_or_error = stream.read_value>(); - if (raw_value_or_error.is_error()) - m_trap = Trap::from_string("Read from memory failed"); - auto raw_value = raw_value_or_error.release_value(); - return bit_cast(static_cast(raw_value)); + return bit_cast(read_value(data)); } ALWAYS_INLINE void BytecodeInterpreter::interpret_instruction(Configuration& configuration, InstructionPointer& ip, Instruction const& instruction)