summaryrefslogtreecommitdiff
path: root/crates
diff options
context:
space:
mode:
Diffstat (limited to 'crates')
-rw-r--r--crates/tinywasm/src/imports.rs3
-rw-r--r--crates/tinywasm/src/runtime/executor/mod.rs42
-rw-r--r--crates/tinywasm/src/runtime/stack/blocks.rs3
-rw-r--r--crates/tinywasm/src/runtime/stack/call_stack.rs7
-rw-r--r--crates/tinywasm/tests/generated/progress-mvp.svg6
5 files changed, 26 insertions, 35 deletions
diff --git a/crates/tinywasm/src/imports.rs b/crates/tinywasm/src/imports.rs
index a13e488..1b3a9cf 100644
--- a/crates/tinywasm/src/imports.rs
+++ b/crates/tinywasm/src/imports.rs
@@ -84,7 +84,8 @@ impl Imports {
Ok(self)
}
- pub(crate) fn link(self, store: &mut crate::Store, module: &crate::Module) -> Result<LinkedImports> {
+ pub(crate) fn link(self, _store: &mut crate::Store, _module: &crate::Module) -> Result<LinkedImports> {
+ // TODO: link to other modules (currently only direct imports are supported)
let values = self.values;
Ok(LinkedImports { values })
}
diff --git a/crates/tinywasm/src/runtime/executor/mod.rs b/crates/tinywasm/src/runtime/executor/mod.rs
index fae095f..e3d8a93 100644
--- a/crates/tinywasm/src/runtime/executor/mod.rs
+++ b/crates/tinywasm/src/runtime/executor/mod.rs
@@ -35,6 +35,7 @@ impl DefaultRuntime {
match exec_one(&mut cf, instr, instrs, stack, store, &module)? {
// Continue execution at the new top of the call stack
ExecResult::Call => {
+ cf = stack.call_stack.pop()?;
func = store.get_func(cf.func_ptr)?.clone();
instrs = func.instructions();
continue;
@@ -76,18 +77,17 @@ enum ExecResult {
// Break to a block at the given index (relative to the current frame)
// If there is no block at the given index, return or call the parent function
+//
+// This is a bit hard to see from the spec, but it's vaild to use breaks to return
+// from a function, so we need to check if the label stack is empty
macro_rules! break_to {
($cf:ident, $stack:ident, $break_to_relative:ident) => {{
- let res = $cf.break_to(*$break_to_relative, &mut $stack.values);
- match res {
- Some(()) => {}
- None => match $stack.call_stack.is_empty() {
- true => return Ok(ExecResult::Return),
- false => {
- *$cf = $stack.call_stack.pop()?;
- return Ok(ExecResult::Call);
- }
- },
+ if $cf.break_to(*$break_to_relative, &mut $stack.values).is_none() {
+ if $stack.call_stack.is_empty() {
+ return Ok(ExecResult::Return);
+ } else {
+ return Ok(ExecResult::Call);
+ }
}
}};
}
@@ -143,8 +143,6 @@ fn exec_one(
stack.call_stack.push(call_frame);
// call the function
- *cf = stack.call_stack.pop()?;
- debug!("calling: {:?}", func);
return Ok(ExecResult::Call);
}
@@ -221,6 +219,7 @@ fn exec_one(
if instr.len() != *len {
panic!("Expected {} BrLabel instructions, got {}", len, instr.len());
}
+ cf.instr_ptr += *len;
todo!("br_table");
}
@@ -234,27 +233,22 @@ fn exec_one(
Return => match stack.call_stack.is_empty() {
true => return Ok(ExecResult::Return),
- false => {
- *cf = stack.call_stack.pop()?;
- return Ok(ExecResult::Call);
- }
+ false => return Ok(ExecResult::Call),
},
EndFunc => {
- if cf.labels.len() > 0 {
- panic!("endfunc: block frames not empty, this should have been validated by the parser");
- }
+ debug_assert!(
+ cf.labels.len() > 0,
+ "endfunc: block frames not empty, this should have been validated by the parser"
+ );
match stack.call_stack.is_empty() {
true => return Ok(ExecResult::Return),
- false => {
- *cf = stack.call_stack.pop()?;
- return Ok(ExecResult::Call);
- }
+ false => return Ok(ExecResult::Call),
}
}
- // We're essentially using else as a EndBlockFrame instruction
+ // We're essentially using else as a EndBlockFrame instruction for if blocks
Else(end_offset) => {
let Some(block) = cf.labels.pop() else {
panic!("else: no label to end, this should have been validated by the parser");
diff --git a/crates/tinywasm/src/runtime/stack/blocks.rs b/crates/tinywasm/src/runtime/stack/blocks.rs
index 46c341d..f5a0d8d 100644
--- a/crates/tinywasm/src/runtime/stack/blocks.rs
+++ b/crates/tinywasm/src/runtime/stack/blocks.rs
@@ -1,5 +1,4 @@
-use alloc::{vec, vec::Vec};
-use log::info;
+use alloc::vec::Vec;
use tinywasm_types::BlockArgs;
use crate::{ModuleInstance, Result};
diff --git a/crates/tinywasm/src/runtime/stack/call_stack.rs b/crates/tinywasm/src/runtime/stack/call_stack.rs
index c5193c3..239659c 100644
--- a/crates/tinywasm/src/runtime/stack/call_stack.rs
+++ b/crates/tinywasm/src/runtime/stack/call_stack.rs
@@ -89,13 +89,10 @@ impl CallFrame {
}
/// Break to a block at the given index (relative to the current frame)
- /// Returns `None` if there is no block at the given index (e.g. if we need to return, this is validated by the parser)
+ /// Returns `None` if there is no block at the given index (e.g. if we need to return, this is handled by the caller)
#[inline]
pub(crate) fn break_to(&mut self, break_to_relative: u32, value_stack: &mut super::ValueStack) -> Option<()> {
- let Some(break_to) = self.labels.get_relative_to_top(break_to_relative as usize) else {
- return None;
- };
-
+ let break_to = self.labels.get_relative_to_top(break_to_relative as usize)?;
value_stack.break_to(break_to.stack_ptr, break_to.args.results);
// instr_ptr points to the label instruction, but the next step
diff --git a/crates/tinywasm/tests/generated/progress-mvp.svg b/crates/tinywasm/tests/generated/progress-mvp.svg
index caad2bb..7829bdc 100644
--- a/crates/tinywasm/tests/generated/progress-mvp.svg
+++ b/crates/tinywasm/tests/generated/progress-mvp.svg
@@ -53,12 +53,12 @@ v0.1.0 (17630)
</text>
<polyline fill="none" opacity="1" stroke="#000000" stroke-width="1" points="716,345 716,350 "/>
<text x="898" y="355" dy="0.76em" text-anchor="middle" font-family="Victor Mono" font-size="12.096774193548388" opacity="1" fill="#000000">
-v0.2.0-alpha.0 (18657)
+v0.2.0-alpha.0 (18674)
</text>
<polyline fill="none" opacity="1" stroke="#000000" stroke-width="1" points="898,345 898,350 "/>
-<rect x="266" y="212" width="172" height="132" opacity="0.5" fill="#0000FF" stroke="none"/>
<rect x="85" y="212" width="171" height="132" opacity="0.5" fill="#0000FF" stroke="none"/>
+<rect x="266" y="212" width="172" height="132" opacity="0.5" fill="#0000FF" stroke="none"/>
+<rect x="812" y="77" width="172" height="267" opacity="0.5" fill="#0000FF" stroke="none"/>
<rect x="630" y="92" width="172" height="252" opacity="0.5" fill="#0000FF" stroke="none"/>
<rect x="448" y="185" width="172" height="159" opacity="0.5" fill="#0000FF" stroke="none"/>
-<rect x="812" y="77" width="172" height="267" opacity="0.5" fill="#0000FF" stroke="none"/>
</svg>