1
0
Fork 0
mirror of https://github.com/denoland/deno.git synced 2024-11-01 09:24:20 -04:00
denoland-deno/ext/napi/function.rs
Bartek Iwańczuk 869acee8fb
chore: upgrade rusty_v8 to 0.54.0 (#16368)
<!--
Before submitting a PR, please read http://deno.land/manual/contributing

1. Give the PR a descriptive title.

  Examples of good title:
    - fix(std/http): Fix race condition in server
    - docs(console): Update docstrings
    - feat(doc): Handle nested reexports

  Examples of bad title:
    - fix #7123
    - update docs
    - fix bugs

2. Ensure there is a related issue and it is referenced in the PR text.
3. Ensure there are tests that cover the changes.
4. Ensure `cargo test` passes.
5. Ensure `./tools/format.js` passes without changing files.
6. Ensure `./tools/lint.js` passes.
-->
2022-10-20 21:01:49 +02:00

102 lines
2.7 KiB
Rust

// Copyright 2018-2022 the Deno authors. All rights reserved. MIT license.
use crate::*;
#[repr(C)]
#[derive(Debug)]
pub struct CallbackInfo {
pub env: napi_env,
pub cb: napi_callback,
pub cb_info: napi_callback_info,
pub args: *const c_void,
}
impl CallbackInfo {
#[inline]
pub fn new_raw(
env: napi_env,
cb: napi_callback,
cb_info: napi_callback_info,
) -> *mut Self {
Box::into_raw(Box::new(Self {
env,
cb,
cb_info,
args: std::ptr::null(),
}))
}
}
extern "C" fn call_fn(info: *const v8::FunctionCallbackInfo) {
let info = unsafe { &*info };
let args = v8::FunctionCallbackArguments::from_function_callback_info(info);
let mut rv = v8::ReturnValue::from_function_callback_info(info);
// SAFETY: create_function guarantees that the data is a CallbackInfo external.
let info_ptr: *mut CallbackInfo = unsafe {
let external_value = v8::Local::<v8::External>::cast(args.data());
external_value.value() as _
};
// SAFETY: pointer from Box::into_raw.
let mut info = unsafe { &mut *info_ptr };
info.args = &args as *const _ as *const c_void;
if let Some(f) = info.cb {
// SAFETY: calling user provided function pointer.
let value = unsafe { f(info.env, info_ptr as *mut _) };
// SAFETY: napi_value is reprsented as v8::Local<v8::Value> internally.
rv.set(unsafe { transmute::<napi_value, v8::Local<v8::Value>>(value) });
}
}
#[allow(clippy::not_unsafe_ptr_arg_deref)]
pub fn create_function<'a>(
env_ptr: *mut Env,
name: Option<&str>,
cb: napi_callback,
cb_info: napi_callback_info,
) -> v8::Local<'a, v8::Function> {
let env: &mut Env = unsafe { &mut *env_ptr };
let scope = &mut env.scope();
let external = v8::External::new(
scope,
CallbackInfo::new_raw(env_ptr as _, cb, cb_info) as *mut _,
);
let function = v8::Function::builder_raw(call_fn)
.data(external.into())
.build(scope)
.unwrap();
if let Some(name) = name {
let v8str = v8::String::new(scope, name).unwrap();
function.set_name(v8str);
}
function
}
#[allow(clippy::not_unsafe_ptr_arg_deref)]
pub fn create_function_template<'a>(
env_ptr: *mut Env,
name: Option<&str>,
cb: napi_callback,
cb_info: napi_callback_info,
) -> v8::Local<'a, v8::FunctionTemplate> {
let env: &mut Env = unsafe { &mut *env_ptr };
let scope = &mut env.scope();
let external = v8::External::new(
scope,
CallbackInfo::new_raw(env_ptr as _, cb, cb_info) as *mut _,
);
let function = v8::FunctionTemplate::builder_raw(call_fn)
.data(external.into())
.build(scope);
if let Some(name) = name {
let v8str = v8::String::new(scope, name).unwrap();
function.set_class_name(v8str);
}
function
}