diff options
| author | Henry Gressmann <mail@henrygressmann.de> | 2023-12-14 21:03:57 +0100 |
|---|---|---|
| committer | Henry Gressmann <mail@henrygressmann.de> | 2023-12-14 21:03:57 +0100 |
| commit | 4697f7c63c0e985029e7f0683b518b1dadf17ccb (patch) | |
| tree | 5f9726f0afee3d7df6aedfbaf8dd363f80c4ceb9 | |
| parent | b4cb5f9b93387922255acdb49863182372c708db (diff) | |
test(tinywasm): compare test results - we actually pass the majority now
Signed-off-by: Henry Gressmann <mail@henrygressmann.de>
| -rw-r--r-- | crates/tinywasm/src/runtime/executor/mod.rs | 3 | ||||
| -rw-r--r-- | crates/tinywasm/src/runtime/stack/value_stack.rs | 5 | ||||
| -rw-r--r-- | crates/tinywasm/tests/mvp.rs | 82 |
3 files changed, 75 insertions, 15 deletions
diff --git a/crates/tinywasm/src/runtime/executor/mod.rs b/crates/tinywasm/src/runtime/executor/mod.rs index 3577325..7d8ead4 100644 --- a/crates/tinywasm/src/runtime/executor/mod.rs +++ b/crates/tinywasm/src/runtime/executor/mod.rs @@ -91,7 +91,8 @@ fn exec_one( // if cond != 0, we already have the right value on the stack if cond == 0 { - stack.values.last_mut().map(|v| *v = val2); + let _ = stack.values.pop()?; + stack.values.push(val2); } } Call(v) => { diff --git a/crates/tinywasm/src/runtime/stack/value_stack.rs b/crates/tinywasm/src/runtime/stack/value_stack.rs index 717d251..59be3d2 100644 --- a/crates/tinywasm/src/runtime/stack/value_stack.rs +++ b/crates/tinywasm/src/runtime/stack/value_stack.rs @@ -24,11 +24,6 @@ impl Default for ValueStack { impl ValueStack { #[inline] - pub(crate) fn last_mut(&mut self) -> Option<&mut RawWasmValue> { - self.stack.last_mut() - } - - #[inline] pub(crate) fn len(&self) -> usize { assert!(self.top <= self.stack.len()); self.top diff --git a/crates/tinywasm/tests/mvp.rs b/crates/tinywasm/tests/mvp.rs index c6fe43d..9331c02 100644 --- a/crates/tinywasm/tests/mvp.rs +++ b/crates/tinywasm/tests/mvp.rs @@ -72,7 +72,7 @@ fn test_mvp() -> Result<()> { }, ); } - AssertReturn { span, exec, results: _ } => { + AssertReturn { span, exec, results } => { let Some(module) = last_module.as_ref() else { // println!("no module found for assert_return: {:?}", exec); continue; @@ -84,15 +84,30 @@ fn test_mvp() -> Result<()> { let instance = module.instantiate(&mut store)?; use wast::WastExecute::*; - match exec { + let invoke = match exec { Wat(_) => return Result::Ok(()), // not used by the testsuite Get { module: _, global: _ } => return Result::Ok(()), - Invoke(invoke) => { - for arg in invoke.args { - let arg = get_tinywasm_wasm_value(arg)?; - let _res = instance.get_func(&store, invoke.name)?.call(&mut store, &[arg])?; - // TODO: check the result - } + Invoke(invoke) => invoke, + }; + + let args = invoke + .args + .into_iter() + .map(wastarg2tinywasmvalue) + .collect::<Result<Vec<_>>>()?; + let res = instance.get_func(&store, invoke.name)?.call(&mut store, &args)?; + let expected = results + .into_iter() + .map(wastret2tinywasmvalue) + .collect::<Result<Vec<_>>>()?; + + if res.len() != expected.len() { + return Result::Err(eyre!("expected {} results, got {}", expected.len(), res.len())); + } + + for (i, (res, expected)) in res.iter().zip(expected).enumerate() { + if res != &expected { + return Result::Err(eyre!("result {} did not match: {:?} != {:?}", i, res, expected)); } } @@ -130,7 +145,7 @@ fn test_mvp() -> Result<()> { } } -fn get_tinywasm_wasm_value(arg: wast::WastArg) -> Result<tinywasm_types::WasmValue> { +fn wastarg2tinywasmvalue(arg: wast::WastArg) -> Result<tinywasm_types::WasmValue> { let wast::WastArg::Core(arg) = arg else { return Err(eyre!("unsupported arg type")); }; @@ -146,6 +161,55 @@ fn get_tinywasm_wasm_value(arg: wast::WastArg) -> Result<tinywasm_types::WasmVal }) } +fn wastret2tinywasmvalue(arg: wast::WastRet) -> Result<tinywasm_types::WasmValue> { + let wast::WastRet::Core(arg) = arg else { + return Err(eyre!("unsupported arg type")); + }; + + use tinywasm_types::WasmValue; + use wast::core::WastRetCore::*; + Ok(match arg { + F32(f) => nanpattern2tinywasmvalue(f)?, + F64(f) => nanpattern2tinywasmvalue(f)?, + I32(i) => WasmValue::I32(i), + I64(i) => WasmValue::I64(i), + _ => return Err(eyre!("unsupported arg type")), + }) +} + +enum Bits { + U32(u32), + U64(u64), +} +trait FloatToken { + fn bits(&self) -> Bits; +} +impl FloatToken for wast::token::Float32 { + fn bits(&self) -> Bits { + Bits::U32(self.bits) + } +} +impl FloatToken for wast::token::Float64 { + fn bits(&self) -> Bits { + Bits::U64(self.bits) + } +} + +fn nanpattern2tinywasmvalue<T>(arg: wast::core::NanPattern<T>) -> Result<tinywasm_types::WasmValue> +where + T: FloatToken, +{ + use wast::core::NanPattern::*; + Ok(match arg { + CanonicalNan => tinywasm_types::WasmValue::F32(f32::NAN), + ArithmeticNan => tinywasm_types::WasmValue::F32(f32::NAN), + Value(v) => match v.bits() { + Bits::U32(v) => tinywasm_types::WasmValue::F32(f32::from_bits(v)), + Bits::U64(v) => tinywasm_types::WasmValue::F64(f64::from_bits(v)), + }, + }) +} + struct TestSuite(BTreeMap<String, TestGroup>); impl TestSuite { |
