use frunk::{hlist, hlist_pat, HList};
use wasmer::FromToNativeWasmType;
use crate::{memory_layout::FlatLayout, primitive_types::FlatType};
pub trait WasmerParameters: FlatLayout {
type ImportParameters;
type ExportParameters;
fn into_wasmer(self) -> Self::ImportParameters;
fn from_wasmer(parameters: Self::ExportParameters) -> Self;
}
impl WasmerParameters for HList![] {
type ImportParameters = ();
type ExportParameters = ();
fn into_wasmer(self) -> Self::ImportParameters {}
fn from_wasmer((): Self::ExportParameters) -> Self {
hlist![]
}
}
impl<Parameter> WasmerParameters for HList![Parameter]
where
Parameter: FlatType + FromToNativeWasmType,
{
type ImportParameters = Parameter;
type ExportParameters = (Parameter,);
fn into_wasmer(self) -> Self::ImportParameters {
let hlist_pat![parameter] = self;
parameter
}
fn from_wasmer((parameter,): Self::ExportParameters) -> Self {
hlist![parameter]
}
}
macro_rules! parameters {
($( $names:ident : $types:ident ),*) => {
impl<$( $types ),*> WasmerParameters for HList![$( $types ),*]
where
$( $types: FlatType + FromToNativeWasmType, )*
{
type ImportParameters = ($( $types, )*);
type ExportParameters = ($( $types, )*);
#[allow(clippy::unused_unit)]
fn into_wasmer(self) -> Self::ImportParameters {
let hlist_pat![$( $names ),*] = self;
($( $names, )*)
}
fn from_wasmer(($( $names, )*): Self::ExportParameters) -> Self {
hlist![$( $names ),*]
}
}
};
}
repeat_macro!(parameters =>
a: A,
b: B |
c: C,
d: D,
e: E,
f: F,
g: G,
h: H,
i: I,
j: J,
k: K,
l: L,
m: M,
n: N,
o: O,
p: P,
q: Q
);