summaryrefslogtreecommitdiff
path: root/ops/op2/dispatch_slow.rs
diff options
context:
space:
mode:
Diffstat (limited to 'ops/op2/dispatch_slow.rs')
-rw-r--r--ops/op2/dispatch_slow.rs119
1 files changed, 100 insertions, 19 deletions
diff --git a/ops/op2/dispatch_slow.rs b/ops/op2/dispatch_slow.rs
index dd47b2017..f54a28f1c 100644
--- a/ops/op2/dispatch_slow.rs
+++ b/ops/op2/dispatch_slow.rs
@@ -18,37 +18,34 @@ pub fn generate_dispatch_slow(
output.extend(extract_arg(generator_state, index)?);
output.extend(from_arg(generator_state, index, arg)?);
}
- output.extend(call(generator_state));
- output.extend(return_value(generator_state, &signature.ret_val));
-
- let GeneratorState {
- deno_core,
- scope,
- fn_args,
- retval,
- info,
- slow_function,
- ..
- } = &generator_state;
+ output.extend(call(generator_state)?);
+ output.extend(return_value(generator_state, &signature.ret_val)?);
let with_scope = if generator_state.needs_scope {
- quote!(let #scope = &mut unsafe { #deno_core::v8::CallbackScope::new(&*#info) };)
+ with_scope(generator_state)
} else {
quote!()
};
let with_retval = if generator_state.needs_retval {
- quote!(let mut #retval = #deno_core::v8::ReturnValue::from_function_callback_info(unsafe { &*#info });)
+ with_retval(generator_state)
} else {
quote!()
};
let with_args = if generator_state.needs_args {
- quote!(let #fn_args = #deno_core::v8::FunctionCallbackArguments::from_function_callback_info(unsafe { &*#info });)
+ with_fn_args(generator_state)
} else {
quote!()
};
+ let GeneratorState {
+ deno_core,
+ info,
+ slow_function,
+ ..
+ } = &generator_state;
+
Ok(quote! {
pub extern "C" fn #slow_function(#info: *const #deno_core::v8::FunctionCallbackInfo) {
#with_scope
@@ -59,6 +56,53 @@ pub fn generate_dispatch_slow(
}})
}
+fn with_scope(generator_state: &mut GeneratorState) -> TokenStream {
+ let GeneratorState {
+ deno_core,
+ scope,
+ info,
+ ..
+ } = &generator_state;
+
+ quote!(let #scope = &mut unsafe { #deno_core::v8::CallbackScope::new(&*#info) };)
+}
+
+fn with_retval(generator_state: &mut GeneratorState) -> TokenStream {
+ let GeneratorState {
+ deno_core,
+ retval,
+ info,
+ ..
+ } = &generator_state;
+
+ quote!(let mut #retval = #deno_core::v8::ReturnValue::from_function_callback_info(unsafe { &*#info });)
+}
+
+fn with_fn_args(generator_state: &mut GeneratorState) -> TokenStream {
+ let GeneratorState {
+ deno_core,
+ fn_args,
+ info,
+ ..
+ } = &generator_state;
+
+ quote!(let #fn_args = #deno_core::v8::FunctionCallbackArguments::from_function_callback_info(unsafe { &*#info });)
+}
+
+fn with_opctx(generator_state: &mut GeneratorState) -> TokenStream {
+ let GeneratorState {
+ deno_core,
+ opctx,
+ fn_args,
+ ..
+ } = &generator_state;
+
+ quote!(let #opctx = unsafe {
+ &*(#deno_core::v8::Local::<#deno_core::v8::External>::cast(#fn_args.data()).value()
+ as *const #deno_core::_ops::OpCtx)
+ };)
+}
+
pub fn extract_arg(
generator_state: &mut GeneratorState,
index: usize,
@@ -176,6 +220,9 @@ pub fn return_value_infallible(
} = generator_state;
let res = match ret_type {
+ Arg::Void => {
+ quote! {/* void */}
+ }
Arg::Numeric(NumericArg::u8)
| Arg::Numeric(NumericArg::u16)
| Arg::Numeric(NumericArg::u32) => {
@@ -204,17 +251,51 @@ pub fn return_value_result(
ret_type: &Arg,
) -> Result<TokenStream, V8MappingError> {
let infallible = return_value_infallible(generator_state, ret_type)?;
- let GeneratorState { result, .. } = &generator_state;
+ let maybe_scope = if generator_state.needs_scope {
+ quote!()
+ } else {
+ with_scope(generator_state)
+ };
+
+ let maybe_args = if generator_state.needs_args {
+ quote!()
+ } else {
+ with_fn_args(generator_state)
+ };
+
+ let maybe_opctx = if generator_state.needs_opctx {
+ quote!()
+ } else {
+ with_opctx(generator_state)
+ };
+
+ let GeneratorState {
+ deno_core,
+ result,
+ scope,
+ opctx,
+ ..
+ } = &generator_state;
let tokens = quote!(
- let result = match ret_type {
+ match #result {
Ok(#result) => {
- #infallible,
+ #infallible
}
Err(err) => {
+ #maybe_scope
+ #maybe_args
+ #maybe_opctx
+ let opstate = ::std::cell::RefCell::borrow(&*#opctx.state);
+ let exception = #deno_core::error::to_v8_error(
+ #scope,
+ opstate.get_error_class_fn,
+ &err,
+ );
+ scope.throw_exception(exception);
return;
}
- }
+ };
);
Ok(tokens)
}