Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 55b6903

Browse files
perf: improve hot interpreter loop
Signed-off-by: Henry Gressmann <[email protected]>
1 parent 893e72e commit 55b6903

File tree

2 files changed

+15
-15
lines changed

2 files changed

+15
-15
lines changed

benches/selfhosted.rs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -9,7 +9,7 @@ fn run_tinywasm(module: TinyWasmModule) {
99
let mut store = Store::default();
1010
let mut imports = Imports::default();
1111
imports.define("env", "printi32", Extern::typed_func(|_: FuncContext<'_>, _: i32| Ok(()))).expect("define");
12-
let instance = module.instantiate(&mut store, Some(imports)).expect("instantiate");
12+
let instance = ModuleInstance::instantiate(&mut store, module, Some(imports)).expect("instantiate");
1313
let hello = instance.exported_func::<(), ()>(&mut store, "hello").expect("exported_func");
1414
hello.call(&mut store, ()).expect("call");
1515
}

crates/tinywasm/src/runtime/interpreter/mod.rs

Lines changed: 14 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -4,6 +4,7 @@ use crate::{
44
runtime::{BlockType, CallFrame, LabelArgs, LabelFrame},
55
Error, FuncContext, ModuleInstance, Result, Store, Trap,
66
};
7+
use alloc::format;
78
use alloc::{string::ToString, vec::Vec};
89
use core::ops::{BitAnd, BitOr, BitXor, Neg};
910
use tinywasm_types::{ElementKind, Instruction, ValType};
@@ -32,28 +33,33 @@ impl InterpreterRuntime {
3233

3334
// The function to execute, gets updated from ExecResult::Call
3435
let mut instrs = &wasm_func.instructions;
36+
let mut instr_count = instrs.len();
3537

3638
let mut current_module = store.get_module_instance(func_inst.owner).unwrap().clone();
3739

38-
while let Some(instr) = instrs.get(cf.instr_ptr) {
40+
loop {
41+
if unlikely(cf.instr_ptr >= instr_count) {
42+
cold();
43+
log::error!("instr_ptr out of bounds: {} >= {}", cf.instr_ptr, instr_count);
44+
return Err(Error::Other(format!("instr_ptr out of bounds: {} >= {}", cf.instr_ptr, instr_count)));
45+
}
46+
let instr = &instrs[cf.instr_ptr];
47+
3948
match exec_one(&mut cf, instr, instrs, stack, store, &current_module)? {
4049
// Continue execution at the new top of the call stack
4150
ExecResult::Call => {
4251
cf = stack.call_stack.pop()?;
4352
func_inst = cf.func_instance.clone();
44-
wasm_func = func_inst.assert_wasm().expect("exec expected wasm function");
53+
wasm_func =
54+
func_inst.assert_wasm().map_err(|_| Error::Other("call expected wasm function".to_string()))?;
4555
instrs = &wasm_func.instructions;
56+
instr_count = instrs.len();
4657

4758
if cf.func_instance.owner != current_module.id() {
4859
current_module.swap(
4960
store
5061
.get_module_instance(cf.func_instance.owner)
51-
.unwrap_or_else(|| {
52-
panic!(
53-
"exec expected module instance {} to exist for function",
54-
cf.func_instance.owner
55-
)
56-
})
62+
.ok_or_else(|| Error::Other("call expected module instance".to_string()))?
5763
.clone(),
5864
);
5965
}
@@ -79,12 +85,6 @@ impl InterpreterRuntime {
7985
}
8086
}
8187
}
82-
83-
log::debug!("end of exec");
84-
log::debug!("stack: {:?}", stack.values);
85-
log::debug!("insts: {:?}", instrs);
86-
log::debug!("instr_ptr: {}", cf.instr_ptr);
87-
Err(Error::FuncDidNotReturn)
8888
}
8989
}
9090

0 commit comments

Comments
 (0)