Skip to content
This repository was archived by the owner on Oct 3, 2025. It is now read-only.

Commit af3caca

Browse files
feat: improve func_addr resolution
Signed-off-by: Henry Gressmann <mail@henrygressmann.de>
1 parent ca1837b commit af3caca

File tree

7 files changed

+40
-23
lines changed

7 files changed

+40
-23
lines changed

crates/tinywasm/src/instance.rs

Lines changed: 13 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,14 @@ impl ModuleInstance {
3636
&self.0.exports
3737
}
3838

39+
pub(crate) fn func_addrs(&self) -> &[FuncAddr] {
40+
&self.0.func_addrs
41+
}
42+
43+
pub(crate) fn func_ty_addrs(&self) -> &[FuncType] {
44+
&self.0.types
45+
}
46+
3947
pub(crate) fn new(
4048
types: Box<[FuncType]>,
4149
func_start: Option<FuncAddr>,
@@ -58,32 +66,21 @@ impl ModuleInstance {
5866
&self.0.types[addr as usize]
5967
}
6068

61-
// resolve a function address to the index of the function in the store
62-
pub(crate) fn func_addr(&self, addr: FuncAddr) -> FuncAddr {
69+
// resolve a function address to the global store address
70+
pub(crate) fn resolve_func_addr(&self, addr: FuncAddr) -> FuncAddr {
6371
self.0.func_addrs[addr as usize]
6472
}
6573

66-
pub(crate) fn func_addrs(&self) -> &[FuncAddr] {
67-
&self.0.func_addrs
68-
}
69-
7074
/// Get an exported function by name
7175
pub fn exported_func_by_name(&self, store: &Store, name: &str) -> Result<FuncHandle> {
7276
if self.0.store_id != store.id() {
7377
return Err(Error::InvalidStore);
7478
}
7579

7680
let export = self.0.exports.get(name, ExternalKind::Func)?;
77-
log::debug!("get_func: export: {:?}", export);
78-
79-
log::debug!("{:?}", self.0.func_addrs);
8081
let func_addr = self.0.func_addrs[export.index as usize];
81-
log::debug!("get_func: func index: {}", export.index);
8282
let func = store.get_func(func_addr as usize)?;
83-
log::debug!("get_func: func_addr: {}, func: {:?}", func_addr, func);
8483
let ty = self.0.types[func.ty_addr() as usize].clone();
85-
log::debug!("get_func: ty: {:?}", ty);
86-
log::debug!("types: {:?}", self.0.types);
8784

8885
Ok(FuncHandle {
8986
addr: export.index,
@@ -94,7 +91,7 @@ impl ModuleInstance {
9491
}
9592

9693
/// Get a typed exported function by name
97-
pub fn get_typed_func<P, R>(&self, store: &Store, name: &str) -> Result<TypedFuncHandle<P, R>>
94+
pub fn typed_func<P, R>(&self, store: &Store, name: &str) -> Result<TypedFuncHandle<P, R>>
9895
where
9996
P: IntoWasmValueTuple,
10097
R: FromWasmValueTuple,
@@ -113,7 +110,7 @@ impl ModuleInstance {
113110
/// (which is not part of the spec, but used by llvm)
114111
///
115112
/// See <https://webassembly.github.io/spec/core/syntax/modules.html#start-function>
116-
pub fn get_start_func(&mut self, store: &Store) -> Result<Option<FuncHandle>> {
113+
pub fn start_func(&mut self, store: &Store) -> Result<Option<FuncHandle>> {
117114
if self.0.store_id != store.id() {
118115
return Err(Error::InvalidStore);
119116
}
@@ -148,7 +145,7 @@ impl ModuleInstance {
148145
///
149146
/// See <https://webassembly.github.io/spec/core/syntax/modules.html#syntax-start>
150147
pub fn start(&mut self, store: &mut Store) -> Result<Option<()>> {
151-
let Some(func) = self.get_start_func(store)? else {
148+
let Some(func) = self.start_func(store)? else {
152149
return Ok(None);
153150
};
154151

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

Lines changed: 3 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ impl DefaultRuntime {
2020
pub(crate) fn exec(&self, store: &mut Store, stack: &mut Stack, module: ModuleInstance) -> Result<()> {
2121
log::info!("exports: {:?}", module.exports());
2222
log::info!("func_addrs: {:?}", module.func_addrs());
23+
log::info!("func_ty_addrs: {:?}", module.func_ty_addrs().len());
2324
log::info!("store funcs: {:?}", store.data.funcs.len());
2425

2526
// The current call frame, gets updated inside of exec_one
@@ -110,9 +111,9 @@ fn exec_one(
110111
Call(v) => {
111112
debug!("start call");
112113
// prepare the call frame
113-
let func_idx = module.func_addr(*v);
114+
let func_idx = module.resolve_func_addr(*v);
114115
let func = store.get_func(func_idx as usize)?;
115-
let func_ty = module.func_ty(func_idx);
116+
let func_ty = module.func_ty(func.ty_addr());
116117

117118
debug!("params: {:?}", func_ty.params);
118119
debug!("stack: {:?}", stack.values);

crates/tinywasm/tests/generated/mvp.csv

Lines changed: 1 addition & 1 deletion
Large diffs are not rendered by default.

crates/tinywasm/tests/test-mvp.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -9,8 +9,13 @@ fn main() -> Result<()> {
99

1010
fn test_mvp() -> Result<()> {
1111
let mut test_suite = TestSuite::new();
12+
13+
// currently hangs, so skip it for now
14+
test_suite.skip(&["fac.wast"]);
15+
1216
TestSuite::set_log_level(log::LevelFilter::Off);
1317
test_suite.run_spec_group(wasm_testsuite::MVP_TESTS)?;
18+
1419
test_suite.save_csv("./tests/generated/mvp.csv", env!("CARGO_PKG_VERSION"))?;
1520

1621
if test_suite.failed() {

crates/tinywasm/tests/test-wast.rs

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,11 @@ fn test_wast(wast_file: &str) -> Result<()> {
4444
println!();
4545
test_suite.print_errors();
4646
println!();
47-
Err(eyre!(format!("{}", "failed one or more tests".red().bold())))
47+
Err(eyre!(format!(
48+
"{}:\n{:#?}",
49+
"failed one or more tests".red().bold(),
50+
test_suite,
51+
)))
4852
} else {
4953
println!("\n\npassed all tests:\n{:#?}", test_suite);
5054
Ok(())

crates/tinywasm/tests/testsuite/mod.rs

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -25,9 +25,13 @@ fn format_linecol(linecol: (usize, usize)) -> String {
2525
format!("{}:{}", linecol.0 + 1, linecol.1 + 1)
2626
}
2727

28-
pub struct TestSuite(BTreeMap<String, TestGroup>);
28+
pub struct TestSuite(BTreeMap<String, TestGroup>, Vec<String>);
2929

3030
impl TestSuite {
31+
pub fn skip(&mut self, groups: &[&str]) {
32+
self.1.extend(groups.iter().map(|s| s.to_string()));
33+
}
34+
3135
pub fn set_log_level(level: log::LevelFilter) {
3236
pretty_env_logger::formatted_builder().filter_level(level).init();
3337
}
@@ -51,7 +55,7 @@ impl TestSuite {
5155
}
5256

5357
pub fn new() -> Self {
54-
Self(BTreeMap::new())
58+
Self(BTreeMap::new(), Vec::new())
5559
}
5660

5761
pub fn failed(&self) -> bool {

crates/tinywasm/tests/testsuite/run.rs

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,12 @@ impl TestSuite {
2121
pub fn run_spec_group(&mut self, tests: &[&str]) -> Result<()> {
2222
tests.iter().for_each(|group| {
2323
let group_wast = wasm_testsuite::get_test_wast(group).expect("failed to get test wast");
24+
if self.1.contains(&group.to_string()) {
25+
info!("skipping group: {}", group);
26+
self.test_group(&format!("{} (skipped)", group), group);
27+
return;
28+
}
29+
2430
self.run_group(group, group_wast).expect("failed to run group");
2531
});
2632

@@ -40,7 +46,7 @@ impl TestSuite {
4046
let wast_data = wast::parser::parse::<Wast>(&buf).expect("failed to parse wat");
4147

4248
let mut last_module: Option<TinyWasmModule> = None;
43-
debug!("running {} tests for group: {}", wast_data.directives.len(), group_name);
49+
println!("running {} tests for group: {}", wast_data.directives.len(), group_name);
4450
for (i, directive) in wast_data.directives.into_iter().enumerate() {
4551
let span = directive.span();
4652
use wast::WastDirective::*;

0 commit comments

Comments
 (0)