summaryrefslogtreecommitdiff
path: root/ext/ffi/lib.rs
diff options
context:
space:
mode:
Diffstat (limited to 'ext/ffi/lib.rs')
-rw-r--r--ext/ffi/lib.rs39
1 files changed, 32 insertions, 7 deletions
diff --git a/ext/ffi/lib.rs b/ext/ffi/lib.rs
index a5a156727..feb879aba 100644
--- a/ext/ffi/lib.rs
+++ b/ext/ffi/lib.rs
@@ -39,6 +39,11 @@ use std::path::PathBuf;
use std::ptr;
use std::rc::Rc;
+#[cfg(not(target_os = "windows"))]
+mod jit_trampoline;
+#[cfg(not(target_os = "windows"))]
+mod tcc;
+
thread_local! {
static LOCAL_ISOLATE_POINTER: RefCell<*const v8::Isolate> = RefCell::new(ptr::null());
}
@@ -72,6 +77,8 @@ struct Symbol {
ptr: libffi::middle::CodePtr,
parameter_types: Vec<NativeType>,
result_type: NativeType,
+ // This is dead code only on Windows
+ #[allow(dead_code)]
can_callback: bool,
}
@@ -678,6 +685,7 @@ impl From<&NativeType> for fast_api::Type {
}
}
+#[cfg(not(target_os = "windows"))]
fn is_fast_api(rv: NativeType) -> bool {
!matches!(
rv,
@@ -696,25 +704,36 @@ fn make_sync_fn<'s>(
scope: &mut v8::HandleScope<'s>,
sym: Box<Symbol>,
) -> v8::Local<'s, v8::Function> {
- let mut fast_ffi_templ = None;
+ #[cfg(not(target_os = "windows"))]
+ let mut fast_ffi_templ: Option<FfiFastCallTemplate> = None;
+
+ #[cfg(target_os = "windows")]
+ let fast_ffi_templ: Option<FfiFastCallTemplate> = None;
+ #[cfg(not(target_os = "windows"))]
+ let mut fast_allocations: Option<*mut ()> = None;
+ #[cfg(not(target_os = "windows"))]
if !sym.can_callback
&& !sym.parameter_types.iter().any(|t| !is_fast_api(*t))
&& is_fast_api(sym.result_type)
{
+ let ret = fast_api::Type::from(&sym.result_type);
+
let mut args = sym
.parameter_types
.iter()
.map(|t| t.into())
.collect::<Vec<_>>();
- if args.is_empty() {
- args.push(fast_api::Type::V8Value);
- }
+ // recv
+ args.insert(0, fast_api::Type::V8Value);
+ let symbol_trampoline =
+ jit_trampoline::gen_trampoline(sym.clone()).expect("gen_trampoline");
fast_ffi_templ = Some(FfiFastCallTemplate {
args: args.into_boxed_slice(),
- ret: (&fast_api::Type::from(&sym.result_type)).into(),
- symbol_ptr: sym.ptr.as_ptr() as *const c_void,
+ ret: (&ret).into(),
+ symbol_ptr: symbol_trampoline.addr,
});
+ fast_allocations = Some(Box::into_raw(symbol_trampoline) as *mut ());
}
let sym = Box::leak(sym);
@@ -754,7 +773,13 @@ fn make_sync_fn<'s>(
Box::new(move |_| {
// SAFETY: This is never called twice. pointer obtained
// from Box::into_raw, hence, satisfies memory layout requirements.
- unsafe { Box::from_raw(sym) };
+ unsafe {
+ Box::from_raw(sym);
+ #[cfg(not(target_os = "windows"))]
+ if let Some(fast_allocations) = fast_allocations {
+ Box::from_raw(fast_allocations as *mut jit_trampoline::Allocation);
+ }
+ }
}),
);