mod guest_interface;
mod result_storage;
use self::{guest_interface::GuestInterface, result_storage::ResultStorage};
use crate::{
InstanceWithMemory, Layout, Memory, Runtime, RuntimeError, RuntimeMemory, WitLoad, WitStore,
WitType,
};
pub trait ExportTo<Instance> {
fn export_to(instance: &mut Instance) -> Result<(), RuntimeError>;
}
pub trait ExportFunction<Handler, Parameters, Results> {
fn export(
&mut self,
module_name: &str,
function_name: &str,
handler: Handler,
) -> Result<(), RuntimeError>;
}
pub trait ExportedFunctionInterface {
type HostParameters: WitType;
type HostResults: WitStore;
type GuestInterface: GuestInterface<
FlatHostParameters = <<Self::HostParameters as WitType>::Layout as Layout>::Flat,
ResultStorage = Self::ResultStorage,
>;
type GuestParameters;
type GuestResults;
type ResultStorage: ResultStorage<OutputFor<Self::HostResults> = Self::GuestResults>;
fn lift_parameters<Instance>(
guest_parameters: Self::GuestParameters,
memory: &Memory<'_, Instance>,
) -> Result<(Self::HostParameters, Self::ResultStorage), RuntimeError>
where
Instance: InstanceWithMemory,
<Instance::Runtime as Runtime>::Memory: RuntimeMemory<Instance>;
fn lower_results<Instance>(
results: Self::HostResults,
result_storage: Self::ResultStorage,
memory: &mut Memory<'_, Instance>,
) -> Result<Self::GuestResults, RuntimeError>
where
Instance: InstanceWithMemory,
<Instance::Runtime as Runtime>::Memory: RuntimeMemory<Instance>;
}
impl<Parameters, Results> ExportedFunctionInterface for (Parameters, Results)
where
Parameters: WitLoad,
Results: WitStore,
(
<Parameters::Layout as Layout>::Flat,
<Results::Layout as Layout>::Flat,
): GuestInterface<FlatHostParameters = <Parameters::Layout as Layout>::Flat>,
<() as WitType>::Layout: Layout<Flat = frunk::HNil>,
{
type HostParameters = Parameters;
type HostResults = Results;
type GuestInterface = (
<Parameters::Layout as Layout>::Flat,
<Results::Layout as Layout>::Flat,
);
type GuestParameters = <Self::GuestInterface as GuestInterface>::FlatGuestParameters;
type GuestResults =
<<Self::GuestInterface as GuestInterface>::ResultStorage as ResultStorage>::OutputFor<
Self::HostResults,
>;
type ResultStorage = <Self::GuestInterface as GuestInterface>::ResultStorage;
fn lift_parameters<Instance>(
guest_parameters: Self::GuestParameters,
memory: &Memory<'_, Instance>,
) -> Result<(Self::HostParameters, Self::ResultStorage), RuntimeError>
where
Instance: InstanceWithMemory,
<Instance::Runtime as Runtime>::Memory: RuntimeMemory<Instance>,
{
Self::GuestInterface::lift_parameters(guest_parameters, memory)
}
fn lower_results<Instance>(
results: Self::HostResults,
result_storage: Self::ResultStorage,
memory: &mut Memory<'_, Instance>,
) -> Result<Self::GuestResults, RuntimeError>
where
Instance: InstanceWithMemory,
<Instance::Runtime as Runtime>::Memory: RuntimeMemory<Instance>,
{
result_storage.lower_result(results, memory)
}
}