summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorHenry Gressmann <mail@henrygressmann.de>2024-01-27 00:43:32 +0100
committerHenry Gressmann <mail@henrygressmann.de>2024-01-27 00:43:32 +0100
commita89f75ce42f83de09bad72c1baf697a007751b1b (patch)
tree40541a89de89df89b36eb4586d821267a466b362
parent55b69039c954b49cb98f90c30d58187b9741f545 (diff)
pref: use Rc's for Module Instances
Signed-off-by: Henry Gressmann <mail@henrygressmann.de>
-rw-r--r--crates/tinywasm/src/func.rs16
-rw-r--r--crates/tinywasm/src/imports.rs22
-rw-r--r--crates/tinywasm/src/instance.rs10
-rw-r--r--crates/tinywasm/src/store.rs2
-rw-r--r--crates/tinywasm/tests/testsuite/run.rs2
-rw-r--r--crates/tinywasm/tests/testsuite/util.rs4
-rw-r--r--crates/types/src/lib.rs2
7 files changed, 27 insertions, 31 deletions
diff --git a/crates/tinywasm/src/func.rs b/crates/tinywasm/src/func.rs
index 8433236..9c9938b 100644
--- a/crates/tinywasm/src/func.rs
+++ b/crates/tinywasm/src/func.rs
@@ -100,7 +100,7 @@ pub trait IntoWasmValueTuple {
}
pub trait FromWasmValueTuple {
- fn from_wasm_value_tuple(values: Vec<WasmValue>) -> Result<Self>
+ fn from_wasm_value_tuple(values: &[WasmValue]) -> Result<Self>
where
Self: Sized;
}
@@ -115,7 +115,7 @@ impl<P: IntoWasmValueTuple, R: FromWasmValueTuple> FuncHandleTyped<P, R> {
let result = self.func.call(store, &wasm_values)?;
// Convert the Vec<WasmValue> back to R
- R::from_wasm_value_tuple(result)
+ R::from_wasm_value_tuple(&result)
}
}
macro_rules! impl_into_wasm_value_tuple {
@@ -164,14 +164,14 @@ macro_rules! impl_from_wasm_value_tuple {
where
$($T: TryFrom<WasmValue, Error = ()>),*
{
- fn from_wasm_value_tuple(values: Vec<WasmValue>) -> Result<Self> {
+ fn from_wasm_value_tuple(values: &[WasmValue]) -> Result<Self> {
#[allow(unused_variables, unused_mut)]
- let mut iter = values.into_iter();
+ let mut iter = values.iter();
Ok((
$(
$T::try_from(
- iter.next()
+ *iter.next()
.ok_or(Error::Other("Not enough values in WasmValue vector".to_string()))?
)
.map_err(|e| Error::Other(format!("FromWasmValueTuple: Could not convert WasmValue to expected type: {:?}", e,
@@ -186,10 +186,10 @@ macro_rules! impl_from_wasm_value_tuple {
macro_rules! impl_from_wasm_value_tuple_single {
($T:ident) => {
impl FromWasmValueTuple for $T {
- fn from_wasm_value_tuple(values: Vec<WasmValue>) -> Result<Self> {
+ fn from_wasm_value_tuple(values: &[WasmValue]) -> Result<Self> {
#[allow(unused_variables, unused_mut)]
- let mut iter = values.into_iter();
- $T::try_from(iter.next().ok_or(Error::Other("Not enough values in WasmValue vector".to_string()))?)
+ let mut iter = values.iter();
+ $T::try_from(*iter.next().ok_or(Error::Other("Not enough values in WasmValue vector".to_string()))?)
.map_err(|e| {
Error::Other(format!(
"FromWasmValueTupleSingle: Could not convert WasmValue to expected type: {:?}",
diff --git a/crates/tinywasm/src/imports.rs b/crates/tinywasm/src/imports.rs
index 294e547..28ea0ec 100644
--- a/crates/tinywasm/src/imports.rs
+++ b/crates/tinywasm/src/imports.rs
@@ -8,8 +8,8 @@ use crate::{
};
use alloc::{
collections::BTreeMap,
+ rc::Rc,
string::{String, ToString},
- sync::Arc,
vec::Vec,
};
use tinywasm_types::*;
@@ -52,8 +52,7 @@ impl HostFunction {
}
}
-pub(crate) type HostFuncInner =
- Arc<dyn Fn(FuncContext<'_>, &[WasmValue]) -> Result<Vec<WasmValue>> + 'static + Send + Sync>;
+pub(crate) type HostFuncInner = Rc<dyn Fn(FuncContext<'_>, &[WasmValue]) -> Result<Vec<WasmValue>>>;
/// The context of a host-function call
#[derive(Debug)]
@@ -139,31 +138,28 @@ impl Extern {
/// Create a new function import
pub fn func(
ty: &tinywasm_types::FuncType,
- func: impl Fn(FuncContext<'_>, &[WasmValue]) -> Result<Vec<WasmValue>> + 'static + Send + Sync,
+ func: impl Fn(FuncContext<'_>, &[WasmValue]) -> Result<Vec<WasmValue>> + 'static,
) -> Self {
- let inner_func = move |ctx: FuncContext<'_>, args: &[WasmValue]| {
- let args = args.to_vec();
- func(ctx, &args)
- };
-
- Self::Function(Function::Host(HostFunction { func: Arc::new(inner_func), ty: ty.clone() }))
+ Self::Function(Function::Host(HostFunction { func: Rc::new(func), ty: ty.clone() }))
}
/// Create a new typed function import
- pub fn typed_func<P, R>(func: impl Fn(FuncContext<'_>, P) -> Result<R> + 'static + Send + Sync) -> Self
+ // TODO: currently, this is slower than `Extern::func` because of the type conversions.
+ // we should be able to optimize this and make it even faster than `Extern::func`.
+ pub fn typed_func<P, R>(func: impl Fn(FuncContext<'_>, P) -> Result<R> + 'static) -> Self
where
P: FromWasmValueTuple + ValTypesFromTuple,
R: IntoWasmValueTuple + ValTypesFromTuple + Debug,
{
let inner_func = move |ctx: FuncContext<'_>, args: &[WasmValue]| -> Result<Vec<WasmValue>> {
- let args = P::from_wasm_value_tuple(args.to_vec())?;
+ let args = P::from_wasm_value_tuple(args)?;
let result = func(ctx, args)?;
Ok(result.into_wasm_value_tuple())
};
let ty = tinywasm_types::FuncType { params: P::val_types(), results: R::val_types() };
- Self::Function(Function::Host(HostFunction { func: Arc::new(inner_func), ty }))
+ Self::Function(Function::Host(HostFunction { func: Rc::new(inner_func), ty }))
}
pub(crate) fn kind(&self) -> ExternalKind {
diff --git a/crates/tinywasm/src/instance.rs b/crates/tinywasm/src/instance.rs
index 35b54d6..b79f551 100644
--- a/crates/tinywasm/src/instance.rs
+++ b/crates/tinywasm/src/instance.rs
@@ -1,4 +1,4 @@
-use alloc::{boxed::Box, format, string::ToString, sync::Arc};
+use alloc::{boxed::Box, format, rc::Rc, string::ToString};
use tinywasm_types::*;
use crate::{
@@ -8,11 +8,11 @@ use crate::{
/// An instanciated WebAssembly module
///
-/// Backed by an Arc, so cloning is cheap
+/// Backed by an Rc, so cloning is cheap
///
/// See <https://webassembly.github.io/spec/core/exec/runtime.html#module-instances>
#[derive(Debug, Clone)]
-pub struct ModuleInstance(Arc<ModuleInstanceInner>);
+pub struct ModuleInstance(Rc<ModuleInstanceInner>);
#[allow(dead_code)]
#[derive(Debug)]
@@ -69,7 +69,7 @@ impl ModuleInstance {
let global_addrs = store.init_globals(addrs.globals, data.globals.into(), &addrs.funcs, idx)?;
let (elem_addrs, elem_trapped) =
- store.init_elements(&addrs.tables, &addrs.funcs, &global_addrs, data.elements.into(), idx)?;
+ store.init_elements(&addrs.tables, &addrs.funcs, &global_addrs, &data.elements, idx)?;
let (data_addrs, data_trapped) = store.init_datas(&addrs.memories, data.data.into(), idx)?;
let instance = ModuleInstanceInner {
@@ -126,7 +126,7 @@ impl ModuleInstance {
}
pub(crate) fn new(inner: ModuleInstanceInner) -> Self {
- Self(Arc::new(inner))
+ Self(Rc::new(inner))
}
pub(crate) fn func_ty(&self, addr: FuncAddr) -> &FuncType {
diff --git a/crates/tinywasm/src/store.rs b/crates/tinywasm/src/store.rs
index 1c0d260..ff40b33 100644
--- a/crates/tinywasm/src/store.rs
+++ b/crates/tinywasm/src/store.rs
@@ -217,7 +217,7 @@ impl Store {
table_addrs: &[TableAddr],
func_addrs: &[FuncAddr],
global_addrs: &[Addr],
- elements: Vec<Element>,
+ elements: &[Element],
idx: ModuleInstanceAddr,
) -> Result<(Box<[Addr]>, Option<Trap>)> {
let elem_count = self.data.elements.len();
diff --git a/crates/tinywasm/tests/testsuite/run.rs b/crates/tinywasm/tests/testsuite/run.rs
index c44c3fb..de5d5ab 100644
--- a/crates/tinywasm/tests/testsuite/run.rs
+++ b/crates/tinywasm/tests/testsuite/run.rs
@@ -413,7 +413,7 @@ impl TestSuite {
AssertReturn { span, exec, results } => {
info!("AssertReturn: {:?}", exec);
- let expected = convert_wastret(results)?;
+ let expected = convert_wastret(results.into_iter())?;
let invoke = match match exec {
wast::WastExecute::Wat(_) => Err(eyre!("wat not supported")),
diff --git a/crates/tinywasm/tests/testsuite/util.rs b/crates/tinywasm/tests/testsuite/util.rs
index 09a4769..1b91e1e 100644
--- a/crates/tinywasm/tests/testsuite/util.rs
+++ b/crates/tinywasm/tests/testsuite/util.rs
@@ -62,8 +62,8 @@ pub fn convert_wastargs(args: Vec<wast::WastArg>) -> Result<Vec<tinywasm_types::
args.into_iter().map(|a| wastarg2tinywasmvalue(a)).collect()
}
-pub fn convert_wastret(args: Vec<wast::WastRet>) -> Result<Vec<tinywasm_types::WasmValue>> {
- args.into_iter().map(|a| wastret2tinywasmvalue(a)).collect()
+pub fn convert_wastret<'a>(args: impl Iterator<Item = wast::WastRet<'a>>) -> Result<Vec<tinywasm_types::WasmValue>> {
+ args.map(|a| wastret2tinywasmvalue(a)).collect()
}
fn wastarg2tinywasmvalue(arg: wast::WastArg) -> Result<tinywasm_types::WasmValue> {
diff --git a/crates/types/src/lib.rs b/crates/types/src/lib.rs
index 365ead7..3729e1a 100644
--- a/crates/types/src/lib.rs
+++ b/crates/types/src/lib.rs
@@ -480,7 +480,7 @@ pub struct Element {
pub ty: ValType,
}
-#[derive(Debug, Clone, PartialEq)]
+#[derive(Debug, Clone, Copy, PartialEq)]
pub enum ElementKind {
Passive,
Active { table: TableAddr, offset: ConstInstruction },