mirror of
https://github.com/fluencelabs/wasmer
synced 2025-05-12 02:27:11 +00:00
feat(runtime-core) Introduce vm::FuncCtx
.
`vm::FuncCtx` replaces `vm::Ctx` as first argument passed to host functions (aka imported functions).
This commit is contained in:
parent
656491a337
commit
177c507a4e
@ -15,7 +15,7 @@ use crate::{
|
|||||||
},
|
},
|
||||||
vm,
|
vm,
|
||||||
};
|
};
|
||||||
use std::{fmt::Debug, slice};
|
use std::{fmt::Debug, ptr, slice};
|
||||||
|
|
||||||
pub const INTERNALS_SIZE: usize = 256;
|
pub const INTERNALS_SIZE: usize = 256;
|
||||||
|
|
||||||
@ -384,7 +384,7 @@ impl LocalBacking {
|
|||||||
LocalOrImport::Import(imported_func_index) => {
|
LocalOrImport::Import(imported_func_index) => {
|
||||||
let vm::ImportedFunc { func, vmctx } =
|
let vm::ImportedFunc { func, vmctx } =
|
||||||
imports.vm_functions[imported_func_index];
|
imports.vm_functions[imported_func_index];
|
||||||
(func, vmctx)
|
(func, vmctx as _)
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -417,7 +417,7 @@ impl LocalBacking {
|
|||||||
LocalOrImport::Import(imported_func_index) => {
|
LocalOrImport::Import(imported_func_index) => {
|
||||||
let vm::ImportedFunc { func, vmctx } =
|
let vm::ImportedFunc { func, vmctx } =
|
||||||
imports.vm_functions[imported_func_index];
|
imports.vm_functions[imported_func_index];
|
||||||
(func, vmctx)
|
(func, vmctx as _)
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -541,6 +541,15 @@ impl ImportBacking {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
impl Drop for ImportBacking {
|
||||||
|
fn drop(&mut self) {
|
||||||
|
for (_imported_func_index, imported_func) in (*self.vm_functions).iter_mut() {
|
||||||
|
let _: Box<vm::FuncCtx> = unsafe { Box::from_raw(imported_func.vmctx) };
|
||||||
|
imported_func.vmctx = ptr::null_mut();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
fn import_functions(
|
fn import_functions(
|
||||||
module: &ModuleInner,
|
module: &ModuleInner,
|
||||||
imports: &ImportObject,
|
imports: &ImportObject,
|
||||||
@ -564,6 +573,7 @@ fn import_functions(
|
|||||||
|
|
||||||
let import =
|
let import =
|
||||||
imports.maybe_with_namespace(namespace, |namespace| namespace.get_export(name));
|
imports.maybe_with_namespace(namespace, |namespace| namespace.get_export(name));
|
||||||
|
dbg!(vmctx);
|
||||||
match import {
|
match import {
|
||||||
Some(Export::Function {
|
Some(Export::Function {
|
||||||
func,
|
func,
|
||||||
@ -573,9 +583,16 @@ fn import_functions(
|
|||||||
if *expected_sig == *signature {
|
if *expected_sig == *signature {
|
||||||
functions.push(vm::ImportedFunc {
|
functions.push(vm::ImportedFunc {
|
||||||
func: func.inner(),
|
func: func.inner(),
|
||||||
vmctx: match ctx {
|
vmctx: {
|
||||||
|
let _ = match ctx {
|
||||||
Context::External(ctx) => ctx,
|
Context::External(ctx) => ctx,
|
||||||
Context::Internal => vmctx,
|
Context::Internal => vmctx,
|
||||||
|
};
|
||||||
|
|
||||||
|
Box::into_raw(Box::new(vm::FuncCtx {
|
||||||
|
vmctx,
|
||||||
|
func_env: ptr::null_mut(),
|
||||||
|
}))
|
||||||
},
|
},
|
||||||
});
|
});
|
||||||
} else {
|
} else {
|
||||||
|
@ -111,7 +111,7 @@ impl Instance {
|
|||||||
let ctx_ptr = match start_index.local_or_import(&instance.module.info) {
|
let ctx_ptr = match start_index.local_or_import(&instance.module.info) {
|
||||||
LocalOrImport::Local(_) => instance.inner.vmctx,
|
LocalOrImport::Local(_) => instance.inner.vmctx,
|
||||||
LocalOrImport::Import(imported_func_index) => {
|
LocalOrImport::Import(imported_func_index) => {
|
||||||
instance.inner.import_backing.vm_functions[imported_func_index].vmctx
|
instance.inner.import_backing.vm_functions[imported_func_index].vmctx as _
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -196,7 +196,7 @@ impl Instance {
|
|||||||
let ctx = match func_index.local_or_import(&self.module.info) {
|
let ctx = match func_index.local_or_import(&self.module.info) {
|
||||||
LocalOrImport::Local(_) => self.inner.vmctx,
|
LocalOrImport::Local(_) => self.inner.vmctx,
|
||||||
LocalOrImport::Import(imported_func_index) => {
|
LocalOrImport::Import(imported_func_index) => {
|
||||||
self.inner.import_backing.vm_functions[imported_func_index].vmctx
|
self.inner.import_backing.vm_functions[imported_func_index].vmctx as _
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -449,7 +449,7 @@ impl InstanceInner {
|
|||||||
let imported_func = &self.import_backing.vm_functions[imported_func_index];
|
let imported_func = &self.import_backing.vm_functions[imported_func_index];
|
||||||
(
|
(
|
||||||
imported_func.func as *const _,
|
imported_func.func as *const _,
|
||||||
Context::External(imported_func.vmctx),
|
Context::External(imported_func.vmctx as _),
|
||||||
)
|
)
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
@ -575,7 +575,7 @@ fn call_func_with_index(
|
|||||||
let ctx_ptr = match func_index.local_or_import(info) {
|
let ctx_ptr = match func_index.local_or_import(info) {
|
||||||
LocalOrImport::Local(_) => local_ctx,
|
LocalOrImport::Local(_) => local_ctx,
|
||||||
LocalOrImport::Import(imported_func_index) => {
|
LocalOrImport::Import(imported_func_index) => {
|
||||||
import_backing.vm_functions[imported_func_index].vmctx
|
import_backing.vm_functions[imported_func_index].vmctx as _
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -490,7 +490,7 @@ macro_rules! impl_traits {
|
|||||||
/// This is required for the llvm backend to be able to unwind through this function.
|
/// This is required for the llvm backend to be able to unwind through this function.
|
||||||
#[cfg_attr(nightly, unwind(allowed))]
|
#[cfg_attr(nightly, unwind(allowed))]
|
||||||
extern fn wrap<$( $x, )* Rets, Trap, FN>(
|
extern fn wrap<$( $x, )* Rets, Trap, FN>(
|
||||||
vmctx: &mut vm::Ctx $( , $x: <$x as WasmExternType>::Native )*
|
func_ctx: &mut vm::FuncCtx $( , $x: <$x as WasmExternType>::Native )*
|
||||||
) -> Rets::CStruct
|
) -> Rets::CStruct
|
||||||
where
|
where
|
||||||
$( $x: WasmExternType, )*
|
$( $x: WasmExternType, )*
|
||||||
@ -498,6 +498,7 @@ macro_rules! impl_traits {
|
|||||||
Trap: TrapEarly<Rets>,
|
Trap: TrapEarly<Rets>,
|
||||||
FN: Fn(&mut vm::Ctx, $( $x, )*) -> Trap,
|
FN: Fn(&mut vm::Ctx, $( $x, )*) -> Trap,
|
||||||
{
|
{
|
||||||
|
let vmctx = unsafe { &mut *func_ctx.vmctx };
|
||||||
let f: FN = unsafe { mem::transmute_copy(&()) };
|
let f: FN = unsafe { mem::transmute_copy(&()) };
|
||||||
|
|
||||||
let err = match panic::catch_unwind(
|
let err = match panic::catch_unwind(
|
||||||
@ -548,7 +549,7 @@ macro_rules! impl_traits {
|
|||||||
/// This is required for the llvm backend to be able to unwind through this function.
|
/// This is required for the llvm backend to be able to unwind through this function.
|
||||||
#[cfg_attr(nightly, unwind(allowed))]
|
#[cfg_attr(nightly, unwind(allowed))]
|
||||||
extern fn wrap<$( $x, )* Rets, Trap, FN>(
|
extern fn wrap<$( $x, )* Rets, Trap, FN>(
|
||||||
vmctx: &mut vm::Ctx $( , $x: <$x as WasmExternType>::Native )*
|
func_ctx: &mut vm::FuncCtx $( , $x: <$x as WasmExternType>::Native )*
|
||||||
) -> Rets::CStruct
|
) -> Rets::CStruct
|
||||||
where
|
where
|
||||||
$( $x: WasmExternType, )*
|
$( $x: WasmExternType, )*
|
||||||
@ -556,6 +557,7 @@ macro_rules! impl_traits {
|
|||||||
Trap: TrapEarly<Rets>,
|
Trap: TrapEarly<Rets>,
|
||||||
FN: Fn($( $x, )*) -> Trap,
|
FN: Fn($( $x, )*) -> Trap,
|
||||||
{
|
{
|
||||||
|
let vmctx = unsafe { &mut *func_ctx.vmctx };
|
||||||
let f: FN = unsafe { mem::transmute_copy(&()) };
|
let f: FN = unsafe { mem::transmute_copy(&()) };
|
||||||
|
|
||||||
let err = match panic::catch_unwind(
|
let err = match panic::catch_unwind(
|
||||||
|
@ -498,19 +498,30 @@ impl Ctx {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
enum InnerFunc {}
|
|
||||||
/// Used to provide type safety (ish) for passing around function pointers.
|
/// Used to provide type safety (ish) for passing around function pointers.
|
||||||
/// The typesystem ensures this cannot be dereferenced since an
|
|
||||||
/// empty enum cannot actually exist.
|
|
||||||
#[repr(C)]
|
#[repr(C)]
|
||||||
pub struct Func(InnerFunc);
|
pub struct Func {
|
||||||
|
_private: [u8; 0],
|
||||||
|
}
|
||||||
|
|
||||||
|
#[repr(C)]
|
||||||
|
pub struct FuncEnv {
|
||||||
|
_private: [u8; 0],
|
||||||
|
}
|
||||||
|
|
||||||
|
#[derive(Debug)]
|
||||||
|
#[repr(C)]
|
||||||
|
pub struct FuncCtx {
|
||||||
|
pub vmctx: *mut Ctx,
|
||||||
|
pub func_env: *mut FuncEnv,
|
||||||
|
}
|
||||||
|
|
||||||
/// An imported function, which contains the vmctx that owns this function.
|
/// An imported function, which contains the vmctx that owns this function.
|
||||||
#[derive(Debug, Clone)]
|
#[derive(Debug, Clone)]
|
||||||
#[repr(C)]
|
#[repr(C)]
|
||||||
pub struct ImportedFunc {
|
pub struct ImportedFunc {
|
||||||
pub func: *const Func,
|
pub func: *const Func,
|
||||||
pub vmctx: *mut Ctx,
|
pub vmctx: *mut FuncCtx,
|
||||||
}
|
}
|
||||||
|
|
||||||
// manually implemented because ImportedFunc contains raw pointers directly; `Func` is marked Send (But `Ctx` actually isn't! (TODO: review this, shouldn't `Ctx` be Send?))
|
// manually implemented because ImportedFunc contains raw pointers directly; `Func` is marked Send (But `Ctx` actually isn't! (TODO: review this, shouldn't `Ctx` be Send?))
|
||||||
|
Loading…
x
Reference in New Issue
Block a user