diff --git a/src/css_jsc/css_internals.rs b/src/css_jsc/css_internals.rs index 2cf9edafb1b7..75ee97221310 100644 --- a/src/css_jsc/css_internals.rs +++ b/src/css_jsc/css_internals.rs @@ -106,10 +106,9 @@ pub(crate) fn testing_impl( // out of it below. let alloc: &'static Arena = unsafe { bun_ptr::detach_lifetime_ref(&arena) }; - let arguments_ = frame.arguments_old::<3>(); // SAFETY: bunVM() never returns null for a Bun-owned global; reborrow the // raw `*mut VirtualMachine` as a shared ref for the slice's lifetime. - let mut arguments = bun_jsc::ArgumentsSlice::init(global.bun_vm(), arguments_.slice()); + let mut arguments = bun_jsc::ArgumentsSlice::init(global.bun_vm(), frame.arguments()); let source_bunstr = eat_string_arg( &mut arguments, global, @@ -316,9 +315,8 @@ pub fn attr_test(global: &JSGlobalObject, frame: &CallFrame) -> JsResult(); // SAFETY: bunVM() never returns null for a Bun-owned global. - let mut arguments = bun_jsc::ArgumentsSlice::init(global.bun_vm(), arguments_.slice()); + let mut arguments = bun_jsc::ArgumentsSlice::init(global.bun_vm(), frame.arguments()); let source_bunstr = eat_string_arg(&mut arguments, global, "attrTest", 3, 0, "source")?; let source = source_bunstr.to_utf8(); diff --git a/src/install_jsc/dependency_jsc.rs b/src/install_jsc/dependency_jsc.rs index 0f0839f53a54..96ec23bcb1c8 100644 --- a/src/install_jsc/dependency_jsc.rs +++ b/src/install_jsc/dependency_jsc.rs @@ -104,8 +104,7 @@ pub fn tag_infer_from_js(global: &JSGlobalObject, frame: &CallFrame) -> JsResult use bun_core::String as BunString; use bun_install::dependency::{TagExt, version::Tag}; - let arguments = frame.arguments_old::<1>(); - let arguments = arguments.slice(); + let arguments = frame.arguments(); if arguments.is_empty() || !arguments[0].is_string() { return Ok(JSValue::UNDEFINED); } @@ -133,8 +132,7 @@ pub fn dependency_from_js(global: &JSGlobalObject, frame: &CallFrame) -> JsResul use bun_install::dependency; use bun_semver::SlicedString; - let arguments = frame.arguments_old::<2>(); - let arguments = arguments.slice(); + let arguments = frame.arguments(); if arguments.len() == 1 { return crate::update_request_jsc::from_js(global, arguments[0]); } diff --git a/src/install_jsc/ini_jsc.rs b/src/install_jsc/ini_jsc.rs index cab4f79650af..0a56aa776d0d 100644 --- a/src/install_jsc/ini_jsc.rs +++ b/src/install_jsc/ini_jsc.rs @@ -193,8 +193,7 @@ impl IniTestingAPIs { use bun_ini::Parser; use bun_jsc::JsError; - let arguments_ = frame.arguments_old::<1>(); - let arguments = arguments_.slice(); + let arguments = frame.arguments(); let jsstr = arguments[0]; let bunstr = bun_core::OwnedString::new(jsstr.to_bun_string(global)?); diff --git a/src/install_jsc/install_binding.rs b/src/install_jsc/install_binding.rs index d184803c2552..074e3479760f 100644 --- a/src/install_jsc/install_binding.rs +++ b/src/install_jsc/install_binding.rs @@ -43,8 +43,7 @@ pub mod bun_install_js_bindings { let mut log = bun_ast::Log::init(); - let args = frame.arguments_old::<1>(); - let args = args.slice(); + let args = frame.arguments(); let cwd = args[0].to_slice_or_null(global)?; let dir = match bun_sys::open_dir_absolute_not_for_deleting_or_renaming(cwd.slice()) { diff --git a/src/install_jsc/npm_jsc.rs b/src/install_jsc/npm_jsc.rs index bfe6efbe1c4a..b705dc48952d 100644 --- a/src/install_jsc/npm_jsc.rs +++ b/src/install_jsc/npm_jsc.rs @@ -5,9 +5,9 @@ use bun_jsc::{CallFrame, JSGlobalObject, JSValue, JsResult}; pub fn operating_system_is_match(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { use bun_install::npm; - let args = frame.arguments_old::<1>(); + let [arg] = frame.arguments_as_array::<1>(); let mut operating_system = npm::OperatingSystem::NONE.negatable(); - let mut iter = args.ptr[0].array_iterator(global)?; + let mut iter = arg.array_iterator(global)?; while let Some(item) = iter.next()? { let slice = item.to_slice(global)?; operating_system.apply(slice.slice()); @@ -27,9 +27,9 @@ pub fn operating_system_is_match(global: &JSGlobalObject, frame: &CallFrame) -> pub fn architecture_is_match(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { use bun_install::npm; - let args = frame.arguments_old::<1>(); + let [arg] = frame.arguments_as_array::<1>(); let mut architecture = npm::Architecture::NONE.negatable(); - let mut iter = args.ptr[0].array_iterator(global)?; + let mut iter = arg.array_iterator(global)?; while let Some(item) = iter.next()? { let slice = item.to_slice(global)?; architecture.apply(slice.slice()); @@ -87,8 +87,7 @@ pub(crate) fn js_parse_manifest(global: &JSGlobalObject, frame: &CallFrame) -> J use bun_jsc::JsError; use std::io::Write as _; - let args = frame.arguments_old::<2>(); - let args = args.slice(); + let args = frame.arguments(); if args.len() < 2 || !args[0].is_string() || !args[1].is_string() { return Err(global.throw(format_args!( "expected manifest filename and registry string arguments" diff --git a/src/jsc/BuildMessage.rs b/src/jsc/BuildMessage.rs index 2ce713da3b77..df779e857c3c 100644 --- a/src/jsc/BuildMessage.rs +++ b/src/jsc/BuildMessage.rs @@ -106,8 +106,7 @@ impl BuildMessage { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_ = callframe.arguments_old::<1>(); - let args = &args_.ptr[0..args_.len]; + let args = callframe.arguments(); if !args.is_empty() { if !args[0].is_string() { return Ok(JSValue::NULL); diff --git a/src/jsc/CallFrame.rs b/src/jsc/CallFrame.rs index 29f8131f9a77..0694082c9f10 100644 --- a/src/jsc/CallFrame.rs +++ b/src/jsc/CallFrame.rs @@ -35,7 +35,7 @@ impl CallFrame { pub fn arguments_as_array(&self) -> [JSValue; COUNT] { let slice = self.arguments(); let mut value: [JSValue; COUNT] = [JSValue::UNDEFINED; COUNT]; - let n = (self.arguments_count() as usize).min(COUNT); + let n = slice.len().min(COUNT); value[0..n].copy_from_slice(&slice[0..n]); value } @@ -128,24 +128,6 @@ impl CallFrame { } } - /// Do not use this function. Migration path: - /// arguments(n).ptr[k] -> arguments_as_array::()[k] - /// arguments(n).slice() -> arguments() - /// arguments(n).mut() -> `let mut args = arguments_as_array::(); &mut args` - pub fn arguments_old(&self) -> Arguments { - let slice = self.arguments(); - debug_assert!(MAX <= 15); - let count = slice.len().min(MAX); - if count == 0 { - Arguments { - ptr: [JSValue::ZERO; MAX], - len: 0, - } - } else { - Arguments::::init(count.min(MAX), slice) - } - } - /// Do not use this function. Migration path: /// arguments_as_array::() pub fn arguments_undef(&self) -> Arguments { @@ -220,13 +202,6 @@ pub struct Arguments { } impl Arguments { - #[inline] - pub fn init(i: usize, src: &[JSValue]) -> Self { - let mut args: [JSValue; MAX] = [JSValue::ZERO; MAX]; - args[0..i].copy_from_slice(&src[0..i]); - Self { ptr: args, len: i } - } - #[inline] pub fn init_undef(i: usize, src: &[JSValue]) -> Self { let mut args: [JSValue; MAX] = [JSValue::UNDEFINED; MAX]; diff --git a/src/jsc/ResolveMessage.rs b/src/jsc/ResolveMessage.rs index c67605a5117d..d2f9eef4bbb2 100644 --- a/src/jsc/ResolveMessage.rs +++ b/src/jsc/ResolveMessage.rs @@ -267,8 +267,7 @@ impl ResolveMessage { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_ = callframe.arguments_old::<1>(); - let args = &args_.ptr[0..args_.len]; + let args = callframe.arguments(); if !args.is_empty() { if !args[0].is_string() { return Ok(JSValue::NULL); diff --git a/src/jsc/virtual_machine_exports.rs b/src/jsc/virtual_machine_exports.rs index 89258ef3d574..749067bd49ce 100644 --- a/src/jsc/virtual_machine_exports.rs +++ b/src/jsc/virtual_machine_exports.rs @@ -323,23 +323,23 @@ pub fn Bun__setSyntheticAllocationLimitForTesting( global: &JSGlobalObject, frame: &CallFrame, ) -> JsResult { - let args = frame.arguments_old::<1>(); - if args.len < 1 { + let [arg] = frame.arguments_as_array::<1>(); + if frame.arguments_count() < 1 { return Err(global.throw_not_enough_arguments( "setSyntheticAllocationLimitForTesting", 1, - args.len, + frame.arguments_count() as usize, )); } - if !args.ptr[0].is_number() { + if !arg.is_number() { return Err(global.throw_invalid_arguments(format_args!( "setSyntheticAllocationLimitForTesting expects a number" ))); } let limit: usize = - usize::try_from(args.ptr[0].coerce_to_int64(global)?.max(1024 * 1024)).expect("int cast"); + usize::try_from(arg.coerce_to_int64(global)?.max(1024 * 1024)).expect("int cast"); let prev = crate::virtual_machine::SYNTHETIC_ALLOCATION_LIMIT .swap(limit, core::sync::atomic::Ordering::Relaxed); crate::virtual_machine::STRING_ALLOCATION_LIMIT diff --git a/src/patch_jsc/testing.rs b/src/patch_jsc/testing.rs index 8c4680faa1dd..b47c62e35389 100644 --- a/src/patch_jsc/testing.rs +++ b/src/patch_jsc/testing.rs @@ -14,10 +14,9 @@ impl TestingAPIs { // `fn_name(g, f)` call, so it cannot wrap an associated fn. The C-ABI // shim is emitted at module scope below (`__jsc_host_*`). pub fn make_diff(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { - let arguments_ = frame.arguments_old::<2>(); // SAFETY: `bun_vm()` never returns null for a Bun-owned global; the VM // outlives this call frame. - let mut arguments = ArgumentsSlice::init(global.bun_vm(), arguments_.slice()); + let mut arguments = ArgumentsSlice::init(global.bun_vm(), frame.arguments()); let Some(old_folder_jsval) = arguments.next_eat() else { return Err(global.throw(format_args!("expected 2 strings"))); @@ -74,10 +73,9 @@ impl TestingAPIs { /// Used in JS tests, see `internal-for-testing.ts` and patch tests. pub fn parse(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { - let arguments_ = frame.arguments_old::<2>(); // SAFETY: `bun_vm()` never returns null for a Bun-owned global; the VM // outlives this call frame. - let mut arguments = ArgumentsSlice::init(global.bun_vm(), arguments_.slice()); + let mut arguments = ArgumentsSlice::init(global.bun_vm(), frame.arguments()); let Some(patchfile_src_js) = arguments.next_eat() else { return Err(global.throw(format_args!( @@ -112,10 +110,9 @@ impl TestingAPIs { } pub fn parse_apply_args(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { - let arguments_ = frame.arguments_old::<2>(); // SAFETY: `bun_vm()` never returns null for a Bun-owned global; the VM // outlives this call frame. - let mut arguments = ArgumentsSlice::init(global.bun_vm(), arguments_.slice()); + let mut arguments = ArgumentsSlice::init(global.bun_vm(), frame.arguments()); let Some(patchfile_js) = arguments.next_eat() else { return Err(global.throw(format_args!("apply: expected at least 1 argument, got 0"))); diff --git a/src/runtime/api/BunObject.rs b/src/runtime/api/BunObject.rs index 77180e3042cb..b79832168a7d 100644 --- a/src/runtime/api/BunObject.rs +++ b/src/runtime/api/BunObject.rs @@ -114,62 +114,29 @@ mod static_adapters { use super::*; pub(super) fn listener_connect(g: &JSGlobalObject, cf: &CallFrame) -> JsResult { - let args = cf.arguments_old::<1>(); - let opts = if args.len >= 1 { - args.ptr[0] - } else { - JSValue::UNDEFINED - }; + let [opts] = cf.arguments_as_array::<1>(); crate::socket::Listener::connect(g, opts) } pub(super) fn listener_listen(g: &JSGlobalObject, cf: &CallFrame) -> JsResult { - let args = cf.arguments_old::<1>(); - let opts = if args.len >= 1 { - args.ptr[0] - } else { - JSValue::UNDEFINED - }; + let [opts] = cf.arguments_as_array::<1>(); crate::socket::Listener::listen(g, opts) } pub(super) fn udp_socket(g: &JSGlobalObject, cf: &CallFrame) -> JsResult { - let args = cf.arguments_old::<1>(); - let opts = if args.len >= 1 { - args.ptr[0] - } else { - JSValue::UNDEFINED - }; + let [opts] = cf.arguments_as_array::<1>(); crate::socket::udp_socket_draft::UDPSocket::udp_socket(g, opts) } pub(super) fn subprocess_spawn(g: &JSGlobalObject, cf: &CallFrame) -> JsResult { - let args = cf.arguments_old::<2>(); - let a0 = if args.len >= 1 { - args.ptr[0] - } else { - JSValue::UNDEFINED - }; - let a1 = if args.len >= 2 { - Some(args.ptr[1]) - } else { - None - }; + let [a0] = cf.arguments_as_array::<1>(); + let a1 = cf.arguments().get(1).copied(); crate::api::js_bun_spawn_bindings::spawn(g, a0, a1) } pub(super) fn subprocess_spawn_sync(g: &JSGlobalObject, cf: &CallFrame) -> JsResult { - let args = cf.arguments_old::<2>(); - let a0 = if args.len >= 1 { - args.ptr[0] - } else { - JSValue::UNDEFINED - }; - let a1 = if args.len >= 2 { - Some(args.ptr[1]) - } else { - None - }; + let [a0] = cf.arguments_as_array::<1>(); + let a1 = cf.arguments().get(1).copied(); crate::api::js_bun_spawn_bindings::spawn_sync(g, a0, a1) } @@ -198,17 +165,7 @@ mod static_adapters { /// `wrapStaticMethod` would emit, with auto-protect on each argument. pub(super) fn sha(g: &JSGlobalObject, cf: &CallFrame) -> JsResult { use crate::node::types::{BlobOrStringOrBuffer, StringOrBuffer}; - let args = cf.arguments_old::<2>(); - let a0 = if args.len >= 1 { - args.ptr[0] - } else { - JSValue::UNDEFINED - }; - let a1 = if args.len >= 2 { - args.ptr[1] - } else { - JSValue::UNDEFINED - }; + let [a0, a1] = cf.arguments_as_array::<2>(); // Protect each arg across the call (Blob materialization // re-enters the VM). let _a0_guard = a0.protected(); @@ -439,12 +396,11 @@ pub(crate) fn shell_escape( callframe: &CallFrame, ) -> JsResult { use bun_jsc::StringJsc as _; - let arguments = callframe.arguments_old::<1>(); - if arguments.len < 1 { + let [jsval] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global_this.throw(format_args!("shell escape expected at least 1 argument"))); } - let jsval = arguments.ptr[0]; let bunstr = jsval.to_bun_string(global_this)?; if global_this.has_exception() { return Ok(JSValue::ZERO); @@ -571,11 +527,10 @@ pub(crate) fn braces( #[bun_jsc::host_fn] pub(crate) fn which(global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments_ = callframe.arguments_old::<2>(); let mut path_buf = bun_paths::path_buffer_pool::get(); // SAFETY: bun_vm() returns the live per-thread singleton VM for a Bun-owned global. let vm = global_this.bun_vm(); - let mut arguments = ArgumentsSlice::init(vm, arguments_.slice()); + let mut arguments = ArgumentsSlice::init(vm, callframe.arguments()); let Some(path_arg) = arguments.next_eat() else { return Err(global_this.throw(format_args!("which: expected 1 argument, got 0"))); }; @@ -702,17 +657,17 @@ pub(crate) fn inspect_table( #[bun_jsc::host_fn] pub(crate) fn inspect(global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let args_buf = callframe.arguments_old::<4>(); - if args_buf.len == 0 { + let arguments = callframe.arguments(); + if arguments.is_empty() { return BunString::empty().to_js(global_this); } - for arg in args_buf.slice() { + for arg in arguments { arg.protect(); } // Each arg is unprotected on scope exit. - // `arguments_old::<4>` is a stack `[JSValue; 4]`; move it into the guard - // and re-slice instead of heap-allocating a `Vec` per call. + // `arguments()` borrows the call-frame slot array; wrap the borrowed slice + // in the guard instead of heap-allocating a `Vec` per call. // // NOTE: this is *not* the fix for error-gc-test.test.js timing out under // debug+ASAN — that test does 100k `Bun.inspect(new Error)` and the cost @@ -720,12 +675,12 @@ pub(crate) fn inspect(global_this: &JSGlobalObject, callframe: &CallFrame) -> Js // and the source-file re-read in `remap_zig_exception`, none of which a // 32-byte alloc elision can recover. The test is classified `[TIMEOUT]` // for ASAN in test/expectations.txt instead. - let args_buf = scopeguard::guard(args_buf, |buf| { - for arg in buf.slice() { + let args_buf = scopeguard::guard(arguments, |buf| { + for arg in buf { arg.unprotect(); } }); - let arguments = args_buf.slice(); + let arguments = *args_buf; let mut format_options = ConsoleObject::FormatOptions { enable_colors: false, @@ -838,9 +793,8 @@ pub(crate) fn register_macro( global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments_ = callframe.arguments_old::<2>(); - let arguments = arguments_.slice(); - if arguments.len() != 2 || !arguments[0].is_number() { + let arguments = callframe.arguments(); + if arguments.len() < 2 || !arguments[0].is_number() { return Err(global_object.throw_invalid_arguments(format_args!( "Internal error registering macros: invalid args" ))); @@ -1009,10 +963,9 @@ pub(crate) fn open_in_editor( global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<4>(); // SAFETY: bun_vm() returns the live per-thread singleton. let vm = global_this.bun_vm(); - let mut arguments = ArgumentsSlice::init(vm, args.slice()); + let mut arguments = ArgumentsSlice::init(vm, callframe.arguments()); let mut path = ZigStringSlice::EMPTY; let mut editor_choice: Option = None; let mut line: Option = None; @@ -1114,14 +1067,13 @@ pub(crate) fn sleep_sync( global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<1>(); + let [arg] = callframe.arguments_as_array::<1>(); // Expect at least one argument. We allow more than one but ignore them; this // is useful for supporting things like `[1, 2].map(sleepSync)` - if arguments.len < 1 { + if callframe.arguments_count() < 1 { return Err(global_object.throw_not_enough_arguments("sleepSync", 1, 0)); } - let arg = arguments.slice()[0]; // The argument must be a number if !arg.is_number() { @@ -1283,8 +1235,7 @@ pub(crate) fn resolve_sync( #[bun_jsc::host_fn] pub(crate) fn resolve(global_object: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<3>(); - let value = match do_resolve(global_object, arguments.slice()) { + let value = match do_resolve(global_object, callframe.arguments()) { Ok(v) => v, Err(e) => { let err = global_object.take_error(e); @@ -1494,8 +1445,7 @@ pub(crate) fn index_of_line( global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments_ = callframe.arguments_old::<2>(); - let arguments = arguments_.slice(); + let arguments = callframe.arguments(); if arguments.is_empty() { return Ok(JSValue::js_number_from_int32(-1)); } @@ -1550,8 +1500,7 @@ pub(crate) fn nanoseconds(global_this: &JSGlobalObject, _: &CallFrame) -> JsResu #[bun_jsc::host_fn] pub(crate) fn serve(global_object: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<2>(); - let arguments = arguments.slice(); + let arguments = callframe.arguments(); // SAFETY: bun_vm() returns the live thread-local VM for a Bun-owned global. let vm = global_object.bun_vm().as_mut(); let mut config: crate::server::ServerConfig = 'brk: { @@ -1749,8 +1698,7 @@ pub(crate) fn alloc_unsafe( global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<1>(); - let size = arguments.ptr[0]; + let [size] = callframe.arguments_as_array::<1>(); if !size.is_uint32_as_any_int() { return Err(global_this.throw_invalid_arguments(format_args!("Expected a positive number"))); } @@ -1767,10 +1715,9 @@ pub(crate) fn mmap_file(global_this: &JSGlobalObject, callframe: &CallFrame) -> #[cfg(not(windows))] { - let arguments_ = callframe.arguments_old::<2>(); // SAFETY: bun_vm() returns the live thread-local VM for a Bun-owned global. let vm = global_this.bun_vm(); - let mut args = ArgumentsSlice::init(vm, arguments_.slice()); + let mut args = ArgumentsSlice::init(vm, callframe.arguments()); let mut buf = PathBuffer::uninit(); let path = 'brk: { diff --git a/src/runtime/api/HashObject.rs b/src/runtime/api/HashObject.rs index 1f91c1ec0b29..83983675368f 100644 --- a/src/runtime/api/HashObject.rs +++ b/src/runtime/api/HashObject.rs @@ -245,10 +245,9 @@ pub(crate) fn create(global: &JSGlobalObject) -> JSValue { } fn hash_wrap(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { - let arguments = frame.arguments_old::<2>(); // SAFETY: `bun_vm()` never returns null for a Bun-owned global; // ArgumentsSlice borrows it for the call. - let mut args = jsc::ArgumentsSlice::init(global.bun_vm(), arguments.slice()); + let mut args = jsc::ArgumentsSlice::init(global.bun_vm(), frame.arguments()); let mut input: &[u8] = b""; let input_slice: ZigStringSlice; diff --git a/src/runtime/api/JSBundler.rs b/src/runtime/api/JSBundler.rs index abf14975491d..cfbd22382da3 100644 --- a/src/runtime/api/JSBundler.rs +++ b/src/runtime/api/JSBundler.rs @@ -1367,8 +1367,7 @@ pub mod js_bundler { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<1>(); - build(global_this, arguments.slice()) + build(global_this, callframe.arguments()) } // NOTE: `Resolve`/`Load`/`MiniImportRecord`/etc. are owned by diff --git a/src/runtime/api/JSTranspiler.rs b/src/runtime/api/JSTranspiler.rs index b2ab29e4b03c..cdde6429ea73 100644 --- a/src/runtime/api/JSTranspiler.rs +++ b/src/runtime/api/JSTranspiler.rs @@ -963,7 +963,7 @@ impl JSTranspiler { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult<*mut JSTranspiler> { - let arguments = callframe.arguments_old::<3>(); + let [config_arg] = callframe.arguments_as_array::<1>(); // NOTE: a non-POD field cannot be left uninitialized in a live Box // (zeroed()/assume_init() on Transpiler is UB), so build `config` + `transpiler` on the @@ -990,11 +990,6 @@ impl JSTranspiler { // covers config.log, config.tsconfig, arena. ref_count.clearWithoutDestructor is a // no-op when we never handed out refs. `bun.destroy(this)` → Box not yet created. - let config_arg = if arguments.len > 0 { - arguments.ptr[0] - } else { - JSValue::UNDEFINED - }; config.from_js(global, config_arg, arena_ref)?; if global.has_exception() { @@ -1308,10 +1303,9 @@ impl JSTranspiler { #[bun_jsc::host_fn(method)] pub fn scan(&self, global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { jsc::mark_binding(); - let arguments = callframe.arguments_old::<3>(); // SAFETY: bun_vm() returns the live VM singleton on this thread. let vm = global.bun_vm(); - let mut args = ArgumentsSlice::init(vm, arguments.slice()); + let mut args = ArgumentsSlice::init(vm, callframe.arguments()); // defer args.deinit() → Drop let Some(code_arg) = args.next() else { return Err(global.throw_invalid_argument_type("scan", "code", "string or Uint8Array")); @@ -1395,10 +1389,9 @@ impl JSTranspiler { #[bun_jsc::host_fn(method)] pub fn transform(&self, global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { jsc::mark_binding(); - let arguments = callframe.arguments_old::<3>(); // SAFETY: bun_vm() returns the live VM singleton on this thread. let vm = global.bun_vm(); - let mut args = ArgumentsSlice::init(vm, arguments.slice()); + let mut args = ArgumentsSlice::init(vm, callframe.arguments()); // defer args.arena.deinit() → Drop let Some(code_arg) = args.next() else { return Err(global.throw_invalid_argument_type( @@ -1461,11 +1454,11 @@ impl JSTranspiler { callframe: &CallFrame, ) -> JsResult { jsc::mark_binding(); - let arguments = callframe.arguments_old::<3>(); + let arguments = callframe.arguments(); // SAFETY: bun_vm() returns the live VM singleton on this thread. let vm = global.bun_vm(); - let mut args = ArgumentsSlice::init(vm, arguments.slice()); + let mut args = ArgumentsSlice::init(vm, arguments); // defer args.arena.deinit() → Drop let Some(code_arg) = args.next() else { return Err(global.throw_invalid_argument_type( @@ -1485,8 +1478,8 @@ impl JSTranspiler { }; // defer code_holder.deinit() → Drop let code = code_holder.slice(); - arguments.ptr[0].ensure_still_alive(); - let _keep0 = bun_jsc::EnsureStillAlive(arguments.ptr[0]); + arguments[0].ensure_still_alive(); + let _keep0 = bun_jsc::EnsureStillAlive(arguments[0]); args.eat(); let mut js_ctx_value: JSValue = JSValue::ZERO; @@ -1674,10 +1667,9 @@ impl JSTranspiler { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<2>(); // SAFETY: bun_vm() returns the live VM singleton on this thread. let vm = global.bun_vm(); - let mut args = ArgumentsSlice::init(vm, arguments.slice()); + let mut args = ArgumentsSlice::init(vm, callframe.arguments()); // defer args.deinit() → Drop let Some(code_arg) = args.next() else { diff --git a/src/runtime/api/UnsafeObject.rs b/src/runtime/api/UnsafeObject.rs index 5c92dc9a83ac..fc2206f04266 100644 --- a/src/runtime/api/UnsafeObject.rs +++ b/src/runtime/api/UnsafeObject.rs @@ -23,7 +23,7 @@ pub(crate) fn gc_aggression_level(global: &JSGlobalObject, frame: &CallFrame) -> // we hold no other Rust borrow of the VM across these accesses. let vm = global.bun_vm().as_mut(); let ret = JSValue::js_number(vm.aggressive_garbage_collection as i32 as f64); - let value = frame.arguments_old::<1>().ptr[0]; + let [value] = frame.arguments_as_array::<1>(); if !value.is_empty_or_undefined_or_null() { match value.coerce::(global)? { @@ -41,8 +41,7 @@ pub(crate) fn array_buffer_to_string( global: &JSGlobalObject, frame: &CallFrame, ) -> JsResult { - let args_buf = frame.arguments_old::<2>(); - let args = args_buf.slice(); + let args = frame.arguments(); if args.len() < 1 || !args[0].is_cell() || !args[0].js_type().is_typed_array_or_array_buffer() { return Err(global.throw_invalid_arguments(format_args!("Expected an ArrayBuffer"))); } diff --git a/src/runtime/api/bun/h2_frame_parser.rs b/src/runtime/api/bun/h2_frame_parser.rs index c56342c93895..7f77c86bebdd 100644 --- a/src/runtime/api/bun/h2_frame_parser.rs +++ b/src/runtime/api/bun/h2_frame_parser.rs @@ -756,13 +756,12 @@ pub fn js_assert_settings( global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<1>(); - if args_list.len < 1 { + let [options] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global_object.throw(format_args!("Expected settings to be a object"))); } - if args_list.len > 0 && !args_list.ptr[0].is_empty_or_undefined_or_null() { - let options = args_list.ptr[0]; + if callframe.arguments_count() > 0 && !options.is_empty_or_undefined_or_null() { if !options.is_object() { return Err(global_object.throw(format_args!("Expected settings to be a object"))); } @@ -6434,13 +6433,11 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<1>(); - if args_list.len < 1 { + let [options] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global_object.throw(format_args!("Expected settings argument"))); } - let options = args_list.ptr[0]; - this.load_settings_from_js_value(global_object, options)?; Ok(JSValue::from(this.set_settings(this.local_settings.get()))) @@ -6452,13 +6449,12 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<1>(); - if args_list.len < 1 { + let [window_size] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err( global_object.throw_invalid_arguments(format_args!("Expected windowSize argument")) ); } - let window_size = args_list.ptr[0]; if !window_size.is_number() { return Err(global_object .throw_invalid_arguments(format_args!("Expected windowSize to be a number"))); @@ -6579,21 +6575,19 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<3>(); - if args_list.len < 1 { + let [error_code_arg, last_stream_arg, opaque_data_arg] = + callframe.arguments_as_array::<3>(); + if callframe.arguments_count() < 1 { return Err(global_object.throw(format_args!("Expected errorCode argument"))); } - let error_code_arg = args_list.ptr[0]; - if !error_code_arg.is_number() { return Err(global_object.throw(format_args!("Expected errorCode to be a number"))); } let error_code = error_code_arg.to_int32(); let mut last_stream_id = this.last_peer_stream_id.get(); - if args_list.len >= 2 { - let last_stream_arg = args_list.ptr[1]; + if callframe.arguments_count() >= 2 { if !last_stream_arg.is_empty_or_undefined_or_null() { if !last_stream_arg.is_number() { return Err( @@ -6610,8 +6604,7 @@ impl H2FrameParser { last_stream_id = u32::try_from(id).expect("int cast"); } } - if args_list.len >= 3 { - let opaque_data_arg = args_list.ptr[2]; + if callframe.arguments_count() >= 3 { if !opaque_data_arg.is_empty_or_undefined_or_null() { if let Some(array_buffer) = opaque_data_arg.as_array_buffer(global_object) { let slice = array_buffer.byte_slice(); @@ -6638,8 +6631,8 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<1>(); - if args_list.len < 1 { + let [payload_arg] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global_object.throw(format_args!("Expected payload argument"))); } @@ -6650,7 +6643,7 @@ impl H2FrameParser { return Ok(JSValue::FALSE); } - if let Some(array_buffer) = args_list.ptr[0].as_array_buffer(global_object) { + if let Some(array_buffer) = payload_arg.as_array_buffer(global_object) { let slice = array_buffer.slice(); this.send_ping(false, slice); return Ok(JSValue::TRUE); @@ -6820,11 +6813,10 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<1>(); - if args_list.len < 1 { + let [stream_arg] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global_object.throw(format_args!("Expected stream argument"))); } - let stream_arg = args_list.ptr[0]; if !stream_arg.is_number() { return Err(global_object.throw(format_args!("Invalid stream id"))); @@ -6849,11 +6841,10 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<1>(); - if args_list.len < 1 { + let [stream_arg] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global_object.throw(format_args!("Expected stream argument"))); } - let stream_arg = args_list.ptr[0]; if !stream_arg.is_number() { return Err(global_object.throw(format_args!("Invalid stream id"))); @@ -6885,11 +6876,10 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<1>(); - if args_list.len < 1 { + let [stream_arg] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global_object.throw(format_args!("Expected stream argument"))); } - let stream_arg = args_list.ptr[0]; if !stream_arg.is_number() { return Err(global_object.throw(format_args!("Invalid stream id"))); @@ -6948,12 +6938,10 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<2>(); - if args_list.len < 2 { + let [stream_arg, options] = callframe.arguments_as_array::<2>(); + if callframe.arguments_count() < 2 { return Err(global_object.throw(format_args!("Expected stream and options arguments"))); } - let stream_arg = args_list.ptr[0]; - let options = args_list.ptr[1]; if !stream_arg.is_number() { return Err(global_object.throw(format_args!("Invalid stream id"))); @@ -7061,12 +7049,10 @@ impl H2FrameParser { callframe: &CallFrame, ) -> JsResult { bun_output::scoped_log!(H2FrameParser, "rstStream"); - let args_list = callframe.arguments_old::<2>(); - if args_list.len < 2 { + let [stream_arg, error_arg] = callframe.arguments_as_array::<2>(); + if callframe.arguments_count() < 2 { return Err(global_object.throw(format_args!("Expected stream and code arguments"))); } - let stream_arg = args_list.ptr[0]; - let error_arg = args_list.ptr[1]; if !stream_arg.is_number() { return Err(global_object.throw(format_args!("Invalid stream id"))); @@ -7434,15 +7420,13 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<1>(); - if args_list.len < 1 { + let [stream_arg] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global_object.throw(format_args!( "Expected stream, headers and sensitiveHeaders arguments" ))); } - let stream_arg = args_list.ptr[0]; - if !stream_arg.is_number() { return Err(global_object.throw(format_args!("Expected stream to be a number"))); } @@ -7482,18 +7466,17 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<2>(); - if args_list.len < 2 { + let [stream_arg, reading_arg] = callframe.arguments_as_array::<2>(); + if callframe.arguments_count() < 2 { return Err( global_object.throw(format_args!("Expected streamId and reading arguments")) ); } - let stream_arg = args_list.ptr[0]; if !stream_arg.is_number() { return Ok(JSValue::UNDEFINED); } let stream_id = stream_arg.to_u32(); - let reading = args_list.ptr[1].to_boolean(); + let reading = reading_arg.to_boolean(); let Some(stream) = this.streams.get().get(&stream_id).copied() else { // The stream already finished (or never reached the wire); nothing to backpressure. return Ok(JSValue::UNDEFINED); @@ -7595,17 +7578,13 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<3>(); - if args_list.len < 3 { + let [stream_arg, headers_arg, sensitive_arg] = callframe.arguments_as_array::<3>(); + if callframe.arguments_count() < 3 { return Err(global_object.throw(format_args!( "Expected stream, headers and sensitiveHeaders arguments" ))); } - let stream_arg = args_list.ptr[0]; - let headers_arg = args_list.ptr[1]; - let sensitive_arg = args_list.ptr[2]; - if !stream_arg.is_number() { return Err(global_object.throw(format_args!("Expected stream to be a number"))); } @@ -8106,16 +8085,15 @@ impl H2FrameParser { global_object.throw(format_args!("Push streams can only be created by servers")) ); } - let args_list = callframe.arguments_old::<4>(); - if args_list.len < 4 { + let [parent_id_arg, promised_id_arg, headers_arg, sensitive_arg] = + callframe.arguments_as_array::<4>(); + if callframe.arguments_count() < 4 { return Err(global_object.throw(format_args!( "Expected parentId, promisedId, headers and sensitiveHeaders arguments" ))); } - let parent_id = args_list.ptr[0].to_u32(); - let promised_id = args_list.ptr[1].to_u32(); - let headers_arg = args_list.ptr[2]; - let sensitive_arg = args_list.ptr[3]; + let parent_id = parent_id_arg.to_u32(); + let promised_id = promised_id_arg.to_u32(); if promised_id > MAX_STREAM_ID { return Ok(JSValue::js_number(-1.0)); } @@ -8281,12 +8259,11 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<1>(); - if args_list.len < 1 { + let [stream_id_arg] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global_object.throw(format_args!("Expected stream_id argument"))); } - let stream_id_arg = args_list.ptr[0]; if !stream_id_arg.is_number() { return Err(global_object.throw(format_args!("Expected stream_id to be a number"))); } @@ -8305,18 +8282,16 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<2>(); - if args_list.len < 2 { + let [stream_id_arg, context_arg] = callframe.arguments_as_array::<2>(); + if callframe.arguments_count() < 2 { return Err( global_object.throw(format_args!("Expected stream_id and context arguments")) ); } - let stream_id_arg = args_list.ptr[0]; if !stream_id_arg.is_number() { return Err(global_object.throw(format_args!("Expected stream_id to be a number"))); } - let context_arg = args_list.ptr[1]; let stream_id = stream_id_arg.to_u32(); if context_arg.is_empty_or_undefined_or_null() { // Release: a pushed stream torn down before its PUSH_PROMISE left has no reset @@ -8426,14 +8401,13 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<1>(); - if args_list.len < 1 { + let [error_arg] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global_object.throw(format_args!("Expected error argument"))); } // Like `goaway`: only numbers reach `to_u32` (it requires one), and the code is read // once before any `&mut Stream` exists instead of once per stream inside the loop. - let error_arg = args_list.ptr[0]; if !error_arg.is_number() { return Err(global_object.throw(format_args!("Expected errorCode to be a number"))); } @@ -8475,18 +8449,19 @@ impl H2FrameParser { ) -> JsResult { bun_output::scoped_log!(H2FrameParser, "request"); - let args_list = callframe.arguments_old::<5>(); - if args_list.len < 4 { + let [ + stream_id_arg, + stream_ctx_arg, + headers_arg, + sensitive_arg, + options_arg, + ] = callframe.arguments_as_array::<5>(); + if callframe.arguments_count() < 4 { return Err(global_object.throw(format_args!( "Expected stream_id, stream_ctx, headers and sensitiveHeaders arguments" ))); } - let stream_id_arg = args_list.ptr[0]; - let stream_ctx_arg = args_list.ptr[1]; - let headers_arg = args_list.ptr[2]; - let sensitive_arg = args_list.ptr[3]; - let Some(headers_obj) = headers_arg.get_object() else { return Err(global_object.throw(format_args!("Expected headers to be an object"))); }; @@ -8917,8 +8892,8 @@ impl H2FrameParser { let mut silent: bool = false; let mut wait_for_trailers: bool = false; let mut end_stream: bool = false; - if args_list.len > 4 && !args_list.ptr[4].is_empty_or_undefined_or_null() { - let options = args_list.ptr[4]; + if callframe.arguments_count() > 4 && !options_arg.is_empty_or_undefined_or_null() { + let options = options_arg; if !options.is_object() { stream.state = StreamState::CLOSED; stream.rst_code = ErrorCode::INTERNAL_ERROR.0; @@ -9326,11 +9301,10 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<1>(); - if args_list.len < 1 { + let [buffer] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global_object.throw(format_args!("Expected 1 argument"))); } - let buffer = args_list.ptr[0]; buffer.ensure_still_alive(); // Same engine-driven inbound path as on_native_read (JS-fed sockets / proxied streams). // The engine dispatches into JS between frames, and a handler can detach/transfer this @@ -9385,12 +9359,11 @@ impl H2FrameParser { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<1>(); - if args_list.len < 1 { + let [socket_js] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global_object.throw(format_args!("Expected socket argument"))); } - let socket_js = args_list.ptr[0]; this.detach_native_socket(); if let Some(socket) = TLSSocket::from_js(socket_js) { bun_output::scoped_log!(H2FrameParser, "TLSSocket attached"); @@ -9468,12 +9441,11 @@ impl H2FrameParser { callframe: &CallFrame, this_value: JSValue, ) -> JsResult<*mut H2FrameParser> { - let args_list = callframe.arguments_old::<1>(); - if args_list.len < 1 { + let [options] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global_object.throw(format_args!("Expected 1 argument"))); } - let options = args_list.ptr[0]; if options.is_empty_or_undefined_or_null() || options.is_boolean() || !options.is_object() { return Err( global_object.throw_invalid_arguments(format_args!("expected options as argument")) diff --git a/src/runtime/api/bun/subprocess.rs b/src/runtime/api/bun/subprocess.rs index 052899cb0e50..a2dc30c9eecc 100644 --- a/src/runtime/api/bun/subprocess.rs +++ b/src/runtime/api/bun/subprocess.rs @@ -731,10 +731,10 @@ impl Subprocess<'_> { this.this_value .with_mut(|v| v.update(global_this, callframe.this())); - let arguments = callframe.arguments_old::<1>(); + let [signal_arg] = callframe.arguments_as_array::<1>(); // If signal is 0, then no actual signal is sent, but error checking // is still performed. - let sig: SignalCode = bun_sys_jsc::signal_code_jsc::from_js(arguments.ptr[0], global_this)?; + let sig: SignalCode = bun_sys_jsc::signal_code_jsc::from_js(signal_arg, global_this)?; if global_this.has_exception() { return Ok(JSValue::ZERO); diff --git a/src/runtime/api/filesystem_router.rs b/src/runtime/api/filesystem_router.rs index 194d056f6df4..3557270fa979 100644 --- a/src/runtime/api/filesystem_router.rs +++ b/src/runtime/api/filesystem_router.rs @@ -121,12 +121,11 @@ impl FileSystemRouter { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult> { - let argument_ = callframe.arguments_old::<1>(); - if argument_.len == 0 { + let [argument] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() == 0 { return Err(global_this.throw_invalid_arguments(format_args!("Expected object"))); } - let argument = argument_.ptr[0]; if argument.is_empty_or_undefined_or_null() || !argument.is_object() { return Err(global_this.throw_invalid_arguments(format_args!("Expected object"))); } @@ -544,13 +543,12 @@ impl FileSystemRouter { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let argument_ = callframe.arguments_old::<2>(); - if argument_.len == 0 { + let [argument] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() == 0 { return Err(global_this .throw_invalid_arguments(format_args!("Expected string, Request or Response"))); } - let argument = argument_.ptr[0]; if argument.is_empty_or_undefined_or_null() || !argument.is_cell() { return Err(global_this .throw_invalid_arguments(format_args!("Expected string, Request or Response"))); diff --git a/src/runtime/api/glob.rs b/src/runtime/api/glob.rs index 03ea9e8ca8eb..03bb50e2dfda 100644 --- a/src/runtime/api/glob.rs +++ b/src/runtime/api/glob.rs @@ -358,9 +358,8 @@ impl Glob { // `::constructor(..)`. The free-fn `host_fn` expansion can't name an // associated fn without a receiver. pub fn constructor(global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult> { - let arguments_ = callframe.arguments_old::<1>(); // SAFETY: bun_vm() returns a non-null *mut to the live VirtualMachine for this global. - let mut arguments = ArgumentsSlice::init(global_this.bun_vm(), arguments_.slice()); + let mut arguments = ArgumentsSlice::init(global_this.bun_vm(), callframe.arguments()); // `arguments` drops at scope exit. let Some(pat_arg) = arguments.next_eat() else { return Err(global_this.throw(format_args!( @@ -410,9 +409,8 @@ impl Glob { // `this: &mut Glob`; `&mut T` auto-derefs to `&T`. #[bun_jsc::host_fn(method)] pub fn __scan(&self, global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments_ = callframe.arguments_old::<1>(); // SAFETY: bun_vm() returns a non-null *mut to the live VirtualMachine for this global. - let mut arguments = ArgumentsSlice::init(global_this.bun_vm(), arguments_.slice()); + let mut arguments = ArgumentsSlice::init(global_this.bun_vm(), callframe.arguments()); // `arguments` drops at scope exit. let mut arena = Arena::new(); @@ -451,9 +449,8 @@ impl Glob { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments_ = callframe.arguments_old::<1>(); // SAFETY: bun_vm() returns a non-null *mut to the live VirtualMachine for this global. - let mut arguments = ArgumentsSlice::init(global_this.bun_vm(), arguments_.slice()); + let mut arguments = ArgumentsSlice::init(global_this.bun_vm(), callframe.arguments()); let mut arena = Arena::new(); let mut glob_walker = @@ -486,9 +483,8 @@ impl Glob { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments_ = callframe.arguments_old::<1>(); // SAFETY: bun_vm() returns a non-null *mut to the live VirtualMachine for this global. - let mut arguments = ArgumentsSlice::init(global_this.bun_vm(), arguments_.slice()); + let mut arguments = ArgumentsSlice::init(global_this.bun_vm(), callframe.arguments()); let Some(str_arg) = arguments.next_eat() else { return Err(global_this.throw(format_args!( "Glob.matchString: expected 1 arguments, got 0" diff --git a/src/runtime/api/html_rewriter.rs b/src/runtime/api/html_rewriter.rs index 67c55d538a20..0be913da95c0 100644 --- a/src/runtime/api/html_rewriter.rs +++ b/src/runtime/api/html_rewriter.rs @@ -117,8 +117,7 @@ fn eat_content_args( global: &JSGlobalObject, call_frame: &CallFrame, ) -> JsResult<(ZigString, Option)> { - let args = call_frame.arguments_old::<2>(); - let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), args.slice()); + let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), call_frame.arguments()); let content = eat_zig_string(&mut iter, global)?; let opts = eat_content_options(&mut iter, global)?; Ok((content, opts)) @@ -514,8 +513,7 @@ impl HTMLRewriter { // See arg-decode helpers at top of file. pub fn on(&self, global: &JSGlobalObject, call_frame: &CallFrame) -> JsResult { - let args = call_frame.arguments_old::<2>(); - let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), args.slice()); + let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), call_frame.arguments()); let selector_name = eat_zig_string(&mut iter, global)?; let listener = eat_js_value(&mut iter, global)?; self.on_(global, selector_name, call_frame, listener) @@ -526,15 +524,13 @@ impl HTMLRewriter { global: &JSGlobalObject, call_frame: &CallFrame, ) -> JsResult { - let args = call_frame.arguments_old::<1>(); - let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), args.slice()); + let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), call_frame.arguments()); let listener = eat_js_value(&mut iter, global)?; self.on_document_(global, listener, call_frame) } pub fn transform(&self, global: &JSGlobalObject, call_frame: &CallFrame) -> JsResult { - let args = call_frame.arguments_old::<1>(); - let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), args.slice()); + let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), call_frame.arguments()); let response_value = eat_js_value(&mut iter, global)?; self.transform_(global, response_value) } @@ -2102,8 +2098,7 @@ impl Element { // ── instance-method arg-decode wrappers (attribute ops) ────────────── pub fn on_end_tag(&self, global: &JSGlobalObject, call_frame: &CallFrame) -> JsResult { - let args = call_frame.arguments_old::<1>(); - let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), args.slice()); + let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), call_frame.arguments()); let function = eat_js_value(&mut iter, global)?; self.on_end_tag_(global, function, call_frame) } @@ -2113,8 +2108,7 @@ impl Element { global: &JSGlobalObject, call_frame: &CallFrame, ) -> JsResult { - let args = call_frame.arguments_old::<1>(); - let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), args.slice()); + let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), call_frame.arguments()); let name = eat_zig_string(&mut iter, global)?; self.get_attribute_(global, name) } @@ -2124,8 +2118,7 @@ impl Element { global: &JSGlobalObject, call_frame: &CallFrame, ) -> JsResult { - let args = call_frame.arguments_old::<1>(); - let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), args.slice()); + let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), call_frame.arguments()); let name = eat_zig_string(&mut iter, global)?; self.has_attribute_(global, name) } @@ -2135,8 +2128,7 @@ impl Element { global: &JSGlobalObject, call_frame: &CallFrame, ) -> JsResult { - let args = call_frame.arguments_old::<2>(); - let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), args.slice()); + let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), call_frame.arguments()); let name = eat_zig_string(&mut iter, global)?; let value = eat_zig_string(&mut iter, global)?; self.set_attribute_(call_frame, global, name, value) @@ -2147,8 +2139,7 @@ impl Element { global: &JSGlobalObject, call_frame: &CallFrame, ) -> JsResult { - let args = call_frame.arguments_old::<1>(); - let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), args.slice()); + let mut iter = ArgumentsSlice::init(global.bun_vm_ref(), call_frame.arguments()); let name = eat_zig_string(&mut iter, global)?; self.remove_attribute_(call_frame, global, name) } diff --git a/src/runtime/cli/pack_command.rs b/src/runtime/cli/pack_command.rs index cd88fd4a72c3..4e4d75f5ae31 100644 --- a/src/runtime/cli/pack_command.rs +++ b/src/runtime/cli/pack_command.rs @@ -4033,8 +4033,7 @@ pub mod bindings { global: &JSGlobalObject, call_frame: &CallFrame, ) -> JsResult { - let arguments = call_frame.arguments_old::<1>(); - let args = arguments.slice(); + let args = call_frame.arguments(); if args.len() < 1 || !args[0].is_string() { return Err(global.throw(format_args!("expected tarball path string argument"))); } diff --git a/src/runtime/crypto/CryptoHasher.rs b/src/runtime/crypto/CryptoHasher.rs index a5cc8cd87126..469d943b4ebe 100644 --- a/src/runtime/crypto/CryptoHasher.rs +++ b/src/runtime/crypto/CryptoHasher.rs @@ -218,10 +218,9 @@ impl CryptoHasher { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<1>(); + let [arg] = callframe.arguments_as_array::<1>(); // ?Node.StringOrBuffer (instance-method arm: empty/undefined/null → None) - let output: Option = if arguments.len > 0 { - let arg = arguments.ptr[0]; + let output: Option = if callframe.arguments_count() > 0 { if !arg.is_empty_or_undefined_or_null() { match StringOrBuffer::from_js(global, arg)? { Some(v) => Some(v), @@ -242,11 +241,11 @@ impl CryptoHasher { /// Hand-expanded static-method argument decode for the parameter list /// `(algorithm string, input, optional output buffer/encoding)`. pub fn hash(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<3>(); + let arguments = callframe.arguments(); let mut i = 0usize; let mut next_eat = || { - if i < arguments.len { - let v = arguments.ptr[i]; + if i < arguments.len() { + let v = arguments[i]; i += 1; Some(v) } else { @@ -470,14 +469,13 @@ impl CryptoHasher { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult> { - let arguments = callframe.arguments_old::<2>(); - if arguments.len == 0 { + let [algorithm_name, hmac_value] = callframe.arguments_as_array::<2>(); + if callframe.arguments_count() == 0 { return Err(global.throw_invalid_arguments(format_args!( "Expected an algorithm name as an argument" ))); } - let algorithm_name = arguments.ptr[0]; if algorithm_name.is_empty_or_undefined_or_null() || !algorithm_name.is_string() { return Err(global.throw_invalid_arguments(format_args!("algorithm must be a string"))); } @@ -488,7 +486,6 @@ impl CryptoHasher { return Err(global.throw_invalid_arguments(format_args!("Invalid algorithm name"))); } - let hmac_value = arguments.ptr[1]; let mut hmac_key: Option = None; // `defer { if (hmac_key) |*key| key.deinit(); }` — handled by Drop on `hmac_key`. @@ -571,14 +568,12 @@ impl CryptoHasher { callframe: &CallFrame, ) -> JsResult { let this_value = callframe.this(); - let arguments = callframe.arguments_old::<2>(); - let input = arguments.ptr[0]; + let [input, encoding_value] = callframe.arguments_as_array::<2>(); if input.is_empty_or_undefined_or_null() { return Err( global.throw_invalid_arguments(format_args!("expected blob, string or buffer")) ); } - let encoding_value = arguments.ptr[1]; // Encoding only affects string inputs (same gate as JSHash.cpp); don't // coerce it for Blob/Buffer inputs where it is ignored. let encoding = if input.is_string() && encoding_value.is_cell() { @@ -1217,10 +1212,9 @@ impl StaticCryptoHasher { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<1>(); + let [arg] = callframe.arguments_as_array::<1>(); // ?Node.StringOrBuffer (instance-method arm: empty/undefined/null → None) - let output: Option = if arguments.len > 0 { - let arg = arguments.ptr[0]; + let output: Option = if callframe.arguments_count() > 0 { if !arg.is_empty_or_undefined_or_null() { match StringOrBuffer::from_js(global, arg)? { Some(v) => Some(v), @@ -1243,11 +1237,11 @@ impl StaticCryptoHasher { /// Hand-expanded `wrapStaticMethod` decode for the parameter list /// `(*JSGlobalObject, Node.BlobOrStringOrBuffer, ?Node.StringOrBuffer)`. pub fn hash(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<2>(); + let arguments = callframe.arguments(); let mut i = 0usize; let mut next_eat = || { - if i < arguments.len { - let v = arguments.ptr[i]; + if i < arguments.len() { + let v = arguments[i]; i += 1; Some(v) } else { diff --git a/src/runtime/crypto/PasswordObject.rs b/src/runtime/crypto/PasswordObject.rs index a40a2294107d..9fe555e60420 100644 --- a/src/runtime/crypto/PasswordObject.rs +++ b/src/runtime/crypto/PasswordObject.rs @@ -715,8 +715,7 @@ pub(crate) fn js_password_object_hash( global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments_ = callframe.arguments_old::<2>(); - let arguments = &arguments_.ptr[..arguments_.len]; + let arguments = callframe.arguments(); if arguments.len() < 1 { return Err(global_object.throw_not_enough_arguments("hash", 1, 0)); @@ -755,8 +754,7 @@ pub(crate) fn js_password_object_hash_sync( global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments_ = callframe.arguments_old::<2>(); - let arguments = &arguments_.ptr[..arguments_.len]; + let arguments = callframe.arguments(); if arguments.len() < 1 { return Err(global_object.throw_not_enough_arguments("hash", 1, 0)); @@ -800,8 +798,7 @@ pub(crate) fn js_password_object_verify( global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments_ = callframe.arguments_old::<3>(); - let arguments = &arguments_.ptr[..arguments_.len]; + let arguments = callframe.arguments(); if arguments.len() < 2 { return Err(global_object.throw_not_enough_arguments("verify", 2, 0)); @@ -881,8 +878,7 @@ pub(crate) fn js_password_object_verify_sync( global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments_ = callframe.arguments_old::<3>(); - let arguments = &arguments_.ptr[..arguments_.len]; + let arguments = callframe.arguments(); if arguments.len() < 2 { return Err(global_object.throw_not_enough_arguments("verify", 2, 0)); diff --git a/src/runtime/dns_jsc/dns.rs b/src/runtime/dns_jsc/dns.rs index 88533da4b7ed..7d0dc6d20daf 100644 --- a/src/runtime/dns_jsc/dns.rs +++ b/src/runtime/dns_jsc/dns.rs @@ -4991,16 +4991,17 @@ impl Resolver { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<3>(); - if arguments.len < 1 { - return Err(global_this.throw_not_enough_arguments("resolve", 3, arguments.len)); + let arguments = callframe.arguments_as_array::<3>(); + let arguments_len = callframe.arguments_count() as usize; + if arguments_len < 1 { + return Err(global_this.throw_not_enough_arguments("resolve", 3, arguments_len)); } - let record_type: RecordType = if arguments.len <= 1 { + let record_type: RecordType = if arguments_len <= 1 { RecordType::DEFAULT } else { 'brk: { - let record_type_value = arguments.ptr[1]; + let record_type_value = arguments[1]; if record_type_value.is_empty_or_undefined_or_null() || !record_type_value.is_string() { @@ -5024,7 +5025,7 @@ impl Resolver { } }; - let name_value = arguments.ptr[0]; + let name_value = arguments[0]; if name_value.is_empty_or_undefined_or_null() || !name_value.is_string() { return Err(global_this.throw_invalid_argument_type("resolve", "name", "string")); } @@ -5082,12 +5083,13 @@ impl Resolver { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<2>(); - if arguments.len < 1 { - return Err(global_this.throw_not_enough_arguments("reverse", 1, arguments.len)); + let arguments = callframe.arguments_as_array::<2>(); + let arguments_len = callframe.arguments_count() as usize; + if arguments_len < 1 { + return Err(global_this.throw_not_enough_arguments("reverse", 1, arguments_len)); } - let ip_value = arguments.ptr[0]; + let ip_value = arguments[0]; if ip_value.is_empty_or_undefined_or_null() || !ip_value.is_string() { return Err(global_this.throw_invalid_argument_type("reverse", "ip", "string")); } @@ -5148,12 +5150,13 @@ impl Resolver { // JSC-ABI shim emitted by `export_host_fn!` at module scope (see `global_resolve`). pub fn global_lookup(global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<2>(); - if arguments.len < 1 { - return Err(global_this.throw_not_enough_arguments("lookup", 2, arguments.len)); + let arguments = callframe.arguments_as_array::<2>(); + let arguments_len = callframe.arguments_count() as usize; + if arguments_len < 1 { + return Err(global_this.throw_not_enough_arguments("lookup", 2, arguments_len)); } - let name_value = arguments.ptr[0]; + let name_value = arguments[0]; if name_value.is_empty_or_undefined_or_null() || !name_value.is_string() { return Err(global_this.throw_invalid_argument_type("lookup", "hostname", "string")); } @@ -5170,8 +5173,8 @@ impl Resolver { let mut options = GetAddrInfoOptions::default(); let mut port: u16 = 0; - if arguments.len > 1 && arguments.ptr[1].is_object() { - let options_object = arguments.ptr[1]; + if arguments_len > 1 && arguments[1].is_object() { + let options_object = arguments[1]; if let Some(port_value) = options_object.get_truthy(global_this, "port")? { port = port_value.to_port_number(global_this)?; @@ -5287,11 +5290,12 @@ macro_rules! resolve_record_fn { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<2>(); - if arguments.len < 1 { - return Err(global_this.throw_not_enough_arguments($jsname, 1, arguments.len)); + let arguments = callframe.arguments_as_array::<2>(); + let arguments_len = callframe.arguments_count() as usize; + if arguments_len < 1 { + return Err(global_this.throw_not_enough_arguments($jsname, 1, arguments_len)); } - let name_value = arguments.ptr[0]; + let name_value = arguments[0]; if name_value.is_empty_or_undefined_or_null() || !name_value.is_string() { return Err(global_this.throw_invalid_argument_type($jsname, "hostname", "string")); } @@ -5937,12 +5941,13 @@ impl Resolver { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<2>(); - if arguments.len < 2 { - return Err(global_this.throw_not_enough_arguments("lookupService", 2, arguments.len)); + let arguments = callframe.arguments_as_array::<2>(); + let arguments_len = callframe.arguments_count() as usize; + if arguments_len < 2 { + return Err(global_this.throw_not_enough_arguments("lookupService", 2, arguments_len)); } - let addr_value = arguments.ptr[0]; + let addr_value = arguments[0]; if addr_value.is_empty_or_undefined_or_null() || !addr_value.is_string() { return Err(global_this.throw_invalid_argument_type( "lookupService", @@ -5961,7 +5966,7 @@ impl Resolver { let addr_slice = addr_str.to_slice(global_this); let addr_s = addr_slice.slice(); - let port_value = arguments.ptr[1]; + let port_value = arguments[1]; let port: u16 = port_value.to_port_number(global_this)?; let mut sa: SockaddrStorage = bun_core::ffi::zeroed(); diff --git a/src/runtime/ffi/FFIObject.rs b/src/runtime/ffi/FFIObject.rs index c557d4e8eaa6..079cf4bd01e7 100644 --- a/src/runtime/ffi/FFIObject.rs +++ b/src/runtime/ffi/FFIObject.rs @@ -742,7 +742,7 @@ pub(crate) fn getter(global_object: &JSGlobalObject, _: &JSObject) -> JSValue { /// Minimal `ArgumentsSlice::nextEat` — pops the next non-consumed argument. /// `wrapStaticMethod`'s arena/protect machinery is unused for the FFI fields /// (no `StringOrBuffer` params, `auto_protect=false`), so a bare cursor over -/// `arguments_old(N).slice()` is semantically identical. +/// `callframe.arguments()` is semantically identical. #[inline] fn next_eat<'a>(iter: &mut core::slice::Iter<'a, JSValue>) -> Option { iter.next().copied() @@ -803,8 +803,7 @@ mod fields { // viewSource → FFI::print(global, JSValue, ?JSValue) -> JsResult pub(super) fn view_source(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let args = callframe.arguments_old::<2>(); - let mut iter = args.slice().iter(); + let mut iter = callframe.arguments().iter(); let object = eat_required(global, &mut iter)?; let is_callback = next_eat(&mut iter); FfiImpl::print(global, object, is_callback) @@ -812,8 +811,7 @@ mod fields { // dlopen → FFI::open(global, ZigString, JSValue) -> JSValue pub(super) fn dlopen(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let args = callframe.arguments_old::<2>(); - let mut iter = args.slice().iter(); + let mut iter = callframe.arguments().iter(); let name = eat_zig_string(global, &mut iter)?; let object = eat_required(global, &mut iter)?; Ok(FfiImpl::open(global, name, object)) @@ -821,8 +819,7 @@ mod fields { // callback → FFI::callback(global, JSValue, JSValue) -> JsResult pub(super) fn callback(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let args = callframe.arguments_old::<2>(); - let mut iter = args.slice().iter(); + let mut iter = callframe.arguments().iter(); let interface = eat_required(global, &mut iter)?; let js_callback = eat_required(global, &mut iter)?; FfiImpl::callback(global, interface, js_callback) @@ -833,16 +830,14 @@ mod fields { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<1>(); - let mut iter = args.slice().iter(); + let mut iter = callframe.arguments().iter(); let object = eat_required(global, &mut iter)?; Ok(FfiImpl::link_symbols(global, object)) } // toBuffer → to_buffer(global, JSValue, ?JSValue×4) -> JsResult pub(super) fn to_buffer(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let args = callframe.arguments_old::<5>(); - let mut iter = args.slice().iter(); + let mut iter = callframe.arguments().iter(); let value = eat_required(global, &mut iter)?; let byte_offset = next_eat(&mut iter); let length = next_eat(&mut iter); @@ -856,8 +851,7 @@ mod fields { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<5>(); - let mut iter = args.slice().iter(); + let mut iter = callframe.arguments().iter(); let value = eat_required(global, &mut iter)?; let byte_offset = next_eat(&mut iter); let length = next_eat(&mut iter); @@ -871,16 +865,14 @@ mod fields { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<1>(); - let mut iter = args.slice().iter(); + let mut iter = callframe.arguments().iter(); let ctx = eat_required(global, &mut iter)?; Ok(FfiImpl::close_callback(global, ctx)) } // CString → new_cstring(global, JSValue, ?JSValue, ?JSValue) -> JsResult pub(super) fn cstring(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let args = callframe.arguments_old::<3>(); - let mut iter = args.slice().iter(); + let mut iter = callframe.arguments().iter(); let value = eat_required(global, &mut iter)?; let byte_offset = next_eat(&mut iter); let length = next_eat(&mut iter); diff --git a/src/runtime/ffi/ffi_body.rs b/src/runtime/ffi/ffi_body.rs index fc033bf7ad2f..b52d75af720b 100644 --- a/src/runtime/ffi/ffi_body.rs +++ b/src/runtime/ffi/ffi_body.rs @@ -976,8 +976,7 @@ impl FFI { "bun:ffi cc() is not available in this build (TinyCC is disabled)" ))); } - let arguments = callframe.arguments_old::<1>(); - let arguments = arguments.slice(); + let arguments = callframe.arguments(); if arguments.is_empty() || !arguments[0].is_object() { return Err(global_this.throw_invalid_arguments(format_args!("Expected object"))); } diff --git a/src/runtime/node/node_cluster_binding.rs b/src/runtime/node/node_cluster_binding.rs index 680d5aff2821..64d147e25773 100644 --- a/src/runtime/node/node_cluster_binding.rs +++ b/src/runtime/node/node_cluster_binding.rs @@ -53,10 +53,7 @@ fn child_singleton<'a>() -> &'a mut InternalMsgHolder { pub(crate) fn send_helper_child(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { bun_output::scoped_log!(IPC, "sendHelperChild"); - let arguments = frame.arguments_old::<3>().ptr; - let message = arguments[0]; - let handle = arguments[1]; - let callback = arguments[2]; + let [message, handle, callback] = frame.arguments_as_array::<3>(); let vm = global.bun_vm().as_mut(); // SAFETY: `bun_vm()` never returns null for a Bun-owned global; sole &mut on JS thread. @@ -103,8 +100,7 @@ pub(crate) fn send_helper_child(global: &JSGlobalObject, frame: &CallFrame) -> J #[bun_jsc::host_fn] fn impl_(global_: &JSGlobalObject, frame_: &CallFrame) -> JsResult { - let arguments_ = frame_.arguments_old::<1>(); - let arguments_ = arguments_.slice(); + let arguments_ = frame_.arguments(); let ex = arguments_[0]; Process__emitErrorEvent(global_, ex.to_error().unwrap_or(ex)); Ok(JSValue::UNDEFINED) @@ -144,7 +140,7 @@ pub(crate) fn on_internal_message_child( frame: &CallFrame, ) -> JsResult { bun_output::scoped_log!(IPC, "onInternalMessageChild"); - let arguments = frame.arguments_old::<2>().ptr; + let arguments = frame.arguments_as_array::<2>(); let singleton = child_singleton(); // TODO: we should not create two jsc.Strong.Optional here. If absolutely necessary, a single Array. should be all we use. singleton.worker = StrongOptional::create(arguments[0], global); @@ -167,7 +163,7 @@ pub(crate) fn handle_internal_message_child( pub(crate) fn send_helper_primary(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { bun_output::scoped_log!(IPC, "sendHelperPrimary"); - let arguments = frame.arguments_old::<4>().ptr; + let arguments = frame.arguments_as_array::<4>(); // `as_class_ref` is the safe shared-borrow downcast (centralised deref // proof in `JSValue`); `Subprocess::ipc(&self)` projects the `JsCell`. // `cluster.Worker({ process })` accepts any object, so `process[kHandle]` @@ -272,7 +268,7 @@ pub(crate) fn on_internal_message_primary( global: &JSGlobalObject, frame: &CallFrame, ) -> JsResult { - let arguments = frame.arguments_old::<3>().ptr; + let arguments = frame.arguments_as_array::<3>(); // `as_class_ref` is the safe shared-borrow downcast; `ipc()` takes `&self`. // Same guard as `send_helper_primary`: nothing to subscribe to when the // worker's process has no native child handle. @@ -349,7 +345,7 @@ pub(crate) fn handle_internal_message_primary( #[bun_jsc::host_fn] pub(crate) fn set_ref(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { - let arguments = frame.arguments_old::<1>().ptr; + let arguments = frame.arguments_as_array::<1>(); if arguments.len() == 0 { return Err(global.throw_missing_arguments_value(&["enabled"])); diff --git a/src/runtime/node/node_fs_binding.rs b/src/runtime/node/node_fs_binding.rs index 269f3204e9a4..0e0349891e41 100644 --- a/src/runtime/node/node_fs_binding.rs +++ b/src/runtime/node/node_fs_binding.rs @@ -460,12 +460,7 @@ pub(crate) fn string_to_flags_for_testing( frame: &CallFrame, ) -> JsResult { use crate::node::types::FileSystemFlags; - let arguments = frame.arguments_old::<1>(); - let val = if arguments.len < 1 { - JSValue::UNDEFINED - } else { - arguments.ptr[0] - }; + let [val] = frame.arguments_as_array::<1>(); let flags = FileSystemFlags::from_js(global, val)?.unwrap_or(FileSystemFlags::R); // On Windows the internal bun.O bits are POSIX-shaped and translated to the // MSVCRT `_O_*` values at the open boundary; node's stringToFlags and @@ -482,15 +477,15 @@ pub(crate) fn create_memfd_for_testing( global: &JSGlobalObject, frame: &CallFrame, ) -> JsResult { - let arguments = frame.arguments_old::<1>(); + let [size_arg] = frame.arguments_as_array::<1>(); - if arguments.len < 1 { + if frame.arguments_count() < 1 { return Ok(JSValue::UNDEFINED); } #[cfg(not(any(target_os = "linux", target_os = "android")))] { - let _ = arguments; + let _ = size_arg; return Err(global.throw(format_args!( "memfd_create is not implemented on this platform" ))); @@ -498,7 +493,7 @@ pub(crate) fn create_memfd_for_testing( #[cfg(any(target_os = "linux", target_os = "android"))] { - let size = arguments.ptr[0].to_int64(); + let size = size_arg.to_int64(); match bun_sys::memfd_create(c"my_memfd", bun_sys::MemfdFlags::NonExecutable) { Ok(fd) => { let _ = bun_sys::ftruncate(fd, size); diff --git a/src/runtime/node/node_http_binding.rs b/src/runtime/node/node_http_binding.rs index 26dbeb13a947..c44247f8704f 100644 --- a/src/runtime/node/node_http_binding.rs +++ b/src/runtime/node/node_http_binding.rs @@ -9,8 +9,7 @@ pub(crate) fn get_bun_server_all_closed_promise( global: &JSGlobalObject, frame: &CallFrame, ) -> JsResult { - let arguments = frame.arguments_old::<1>(); - let arguments = arguments.slice(); + let arguments = frame.arguments(); if arguments.is_empty() { return Err(global.throw_not_enough_arguments( "getBunServerAllClosePromise", @@ -51,8 +50,7 @@ pub(crate) fn set_max_http_header_size( global: &JSGlobalObject, frame: &CallFrame, ) -> JsResult { - let arguments = frame.arguments_old::<1>(); - let arguments = arguments.slice(); + let arguments = frame.arguments(); if arguments.is_empty() { return Err(global.throw_not_enough_arguments("setMaxHTTPHeaderSize", 1, arguments.len())); } diff --git a/src/runtime/node/node_net_binding.rs b/src/runtime/node/node_net_binding.rs index 5f8f34eac4c5..f766a5a992cb 100644 --- a/src/runtime/node/node_net_binding.rs +++ b/src/runtime/node/node_net_binding.rs @@ -47,11 +47,10 @@ pub(crate) fn get_default_auto_select_family(global: &JSGlobalObject) -> JSValue pub(crate) fn set_default_auto_select_family(global: &JSGlobalObject) -> JSValue { #[bun_jsc::host_fn(export = "Bun__NodeNet__setDefaultAutoSelectFamily")] fn setter(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { - let arguments = frame.arguments_old::<1>(); - if arguments.len < 1 { + let [arg] = frame.arguments_as_array::<1>(); + if frame.arguments_count() < 1 { return Err(global.throw(format_args!("missing argument"))); } - let arg = arguments.slice()[0]; if !arg.is_boolean() { return Err(global.throw_invalid_arguments(format_args!("autoSelectFamilyDefault"))); } @@ -87,11 +86,10 @@ pub(crate) fn get_default_auto_select_family_attempt_timeout(global: &JSGlobalOb pub(crate) fn set_default_auto_select_family_attempt_timeout(global: &JSGlobalObject) -> JSValue { #[bun_jsc::host_fn(export = "Bun__NodeNet__setDefaultAutoSelectFamilyAttemptTimeout")] fn setter(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { - let arguments = frame.arguments_old::<1>(); - if arguments.len < 1 { + let [arg] = frame.arguments_as_array::<1>(); + if frame.arguments_count() < 1 { return Err(global.throw(format_args!("missing argument"))); } - let arg = arguments.slice()[0]; let mut value = validators::validate_int32(global, arg, format_args!("value"), Some(1), None)?; if value < 10 { diff --git a/src/runtime/node/node_util_binding.rs b/src/runtime/node/node_util_binding.rs index ac1ea3fd1c2e..0f1e5867e965 100644 --- a/src/runtime/node/node_util_binding.rs +++ b/src/runtime/node/node_util_binding.rs @@ -9,8 +9,7 @@ use bun_dotenv::env_loader as envloader; #[bun_jsc::host_fn] pub(crate) fn internal_error_name(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { - let arguments = frame.arguments_old::<1>(); - let arguments = arguments.slice(); + let arguments = frame.arguments(); if arguments.is_empty() { return Err(global.throw_not_enough_arguments("internalErrorName", 1, arguments.len())); } diff --git a/src/runtime/node/node_zlib_binding.rs b/src/runtime/node/node_zlib_binding.rs index 80019620ddd0..773615da2ecb 100644 --- a/src/runtime/node/node_zlib_binding.rs +++ b/src/runtime/node/node_zlib_binding.rs @@ -107,12 +107,12 @@ impl CountedKeepAlive { #[bun_jsc::host_fn] pub(crate) fn crc32(global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<2>().ptr; + let arguments = callframe.arguments_as_array::<2>(); let data: ZigStringSlice = 'blk: { let data: JSValue = arguments[0]; - if data.is_empty() { + if callframe.arguments_count() < 1 { return Err(global_this.throw_invalid_argument_type_value( b"data", b"string or an instance of Buffer, TypedArray, or DataView", @@ -144,7 +144,7 @@ pub(crate) fn crc32(global_this: &JSGlobalObject, callframe: &CallFrame) -> JsRe let value: u32 = 'blk: { let value: JSValue = arguments[1]; - if value.is_empty() { + if callframe.arguments_count() < 2 { break 'blk 0; } if !value.is_number() { diff --git a/src/runtime/server/NodeHTTPResponse.rs b/src/runtime/server/NodeHTTPResponse.rs index 4a6f35d04efb..3945a7331475 100644 --- a/src/runtime/server/NodeHTTPResponse.rs +++ b/src/runtime/server/NodeHTTPResponse.rs @@ -1462,10 +1462,10 @@ pub(crate) fn node_http_request_on_resolve( callframe: &CallFrame, ) -> JSValue { scoped_log!(NodeHTTPResponse, "onResolve"); - let arguments = callframe.arguments_old::<2>(); + let arguments = callframe.arguments_as_array::<2>(); // arguments[1] is the JSNodeHTTPResponse cell from the resolve callback. // R-2: deref shared — `maybe_stop_reading_body`/`on_request_complete` re-enter. - let this: &NodeHTTPResponse = arguments.ptr[1].as_class_ref::().unwrap(); + let this: &NodeHTTPResponse = arguments[1].as_class_ref::().unwrap(); // `promise` non-empty is the ownership token for the server-handler ref; // `mark_request_as_done` may have already released it on abort. let had_promise = this.promise.with_mut(|p| { @@ -1474,7 +1474,7 @@ pub(crate) fn node_http_request_on_resolve( had }); // defer this.deref(); — moved to tail. - this.maybe_stop_reading_body(bun_vm_mut(global_object), arguments.ptr[1]); + this.maybe_stop_reading_body(bun_vm_mut(global_object), arguments[1]); let flags = this.flags.get(); if !flags.contains(Flags::REQUEST_HAS_COMPLETED) && !flags.contains(Flags::SOCKET_CLOSED) { @@ -1508,11 +1508,11 @@ pub(crate) fn node_http_request_on_reject( global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JSValue { - let arguments = callframe.arguments_old::<2>(); - let err = arguments.ptr[0]; + let arguments = callframe.arguments_as_array::<2>(); + let err = arguments[0]; // arguments[1] is the JSNodeHTTPResponse cell from the reject callback. // R-2: deref shared — `maybe_stop_reading_body`/`on_request_complete` re-enter. - let this: &NodeHTTPResponse = arguments.ptr[1].as_class_ref::().unwrap(); + let this: &NodeHTTPResponse = arguments[1].as_class_ref::().unwrap(); // `promise` non-empty is the ownership token for the server-handler ref; // `mark_request_as_done` may have already released it on abort. let had_promise = this.promise.with_mut(|p| { @@ -1520,7 +1520,7 @@ pub(crate) fn node_http_request_on_reject( p.deinit(); had }); - this.maybe_stop_reading_body(bun_vm_mut(global_object), arguments.ptr[1]); + this.maybe_stop_reading_body(bun_vm_mut(global_object), arguments[1]); // defer this.deref(); — moved to tail. diff --git a/src/runtime/server/RequestContext.rs b/src/runtime/server/RequestContext.rs index d44f8b4afa0f..0159365b1a43 100644 --- a/src/runtime/server/RequestContext.rs +++ b/src/runtime/server/RequestContext.rs @@ -637,15 +637,15 @@ where pub fn on_resolve(_global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { ctx_log!("onResolve"); - let arguments = callframe.arguments_old::<2>(); - let Some(ctx) = NativePromiseContext::take::(arguments.ptr[1]) else { + let arguments = callframe.arguments_as_array::<2>(); + let Some(ctx) = NativePromiseContext::take::(arguments[1]) else { // The cell's destructor already released the ref (the Promise // was collected before a prior microtask turn reached us). return Ok(JSValue::UNDEFINED); }; let _ref = RequestContextRef(std::ptr::from_mut::(ctx)); - let result = arguments.ptr[0]; + let result = arguments[0]; result.ensure_still_alive(); Self::handle_resolve(ctx, result); @@ -885,15 +885,15 @@ where pub fn on_reject(_global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { ctx_log!("onReject"); - let arguments = callframe.arguments_old::<2>(); - let Some(ctx) = NativePromiseContext::take::(arguments.ptr[1]) else { + let arguments = callframe.arguments_as_array::<2>(); + let Some(ctx) = NativePromiseContext::take::(arguments[1]) else { // The cell's destructor already released the ref (the Promise // was collected before a prior microtask turn reached us). return Ok(JSValue::UNDEFINED); }; let _ref = RequestContextRef(std::ptr::from_mut::(ctx)); - let err = arguments.ptr[0]; + let err = arguments[0]; // Pass the rejection reason through verbatim (including `null` and // `undefined`) so `error()` sees the same value the already-settled // path delivers. Only an empty JSValue is normalized. @@ -2906,8 +2906,8 @@ where pub fn on_resolve_stream(_global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { stream_log!("onResolveStream"); - let args = callframe.arguments_old::<2>(); - let Some(req) = NativePromiseContext::take::(args.ptr[args.len - 1]) else { + let args = callframe.arguments(); + let Some(req) = NativePromiseContext::take::(args[args.len() - 1]) else { return Ok(JSValue::UNDEFINED); }; let _ref = RequestContextRef(std::ptr::from_mut::(req)); @@ -2920,11 +2920,11 @@ where callframe: &CallFrame, ) -> JsResult { stream_log!("onRejectStream"); - let args = callframe.arguments_old::<2>(); - let Some(req) = NativePromiseContext::take::(args.ptr[args.len - 1]) else { + let args = callframe.arguments(); + let Some(req) = NativePromiseContext::take::(args[args.len() - 1]) else { return Ok(JSValue::UNDEFINED); }; - let err = args.ptr[0]; + let err = args[0]; let _ref = RequestContextRef(std::ptr::from_mut::(req)); Self::handle_reject_stream(req, global_this, err); diff --git a/src/runtime/server/ServerWebSocket.rs b/src/runtime/server/ServerWebSocket.rs index 5d8d1331cdd5..9cbc24a33b91 100644 --- a/src/runtime/server/ServerWebSocket.rs +++ b/src/runtime/server/ServerWebSocket.rs @@ -305,8 +305,8 @@ impl ServerWebSocket { fn_name: &'static str, op: impl FnOnce(AnyWebSocket, &[u8]) -> bool, ) -> JsResult { - let args = callframe.arguments_old::<1>(); - if args.len < 1 { + let args = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global_this.throw(format_args!("{fn_name} requires at least 1 argument"))); } @@ -314,15 +314,11 @@ impl ServerWebSocket { return Ok(JSValue::FALSE); } - if !args.ptr[0].is_string() { - return Err(global_this.throw_invalid_argument_type_value( - b"topic", - b"string", - args.ptr[0], - )); + if !args[0].is_string() { + return Err(global_this.throw_invalid_argument_type_value(b"topic", b"string", args[0])); } - let topic = args.ptr[0].to_slice(global_this)?; + let topic = args[0].to_slice(global_this)?; if topic.slice().is_empty() { return Err( @@ -813,8 +809,8 @@ impl ServerWebSocket { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<4>(); - if args.len < 1 { + let [topic_value, message_value, compress_value] = callframe.arguments_as_array::<3>(); + if callframe.arguments_count() < 1 { bun_output::scoped_log!(WebSocketServer, "publish()"); return Err(global_this.throw(format_args!("publish requires at least 1 argument"))); } @@ -824,10 +820,6 @@ impl ServerWebSocket { return Ok(JSValue::js_number(0.0)); }; - let topic_value = args.ptr[0]; - let message_value = args.ptr[1]; - let compress_value = args.ptr[2]; - if topic_value.is_empty_or_undefined_or_null() || !topic_value.is_string() { bun_output::scoped_log!(WebSocketServer, "publish() topic invalid"); return Err(global_this.throw(format_args!("publish requires a topic string"))); @@ -838,7 +830,12 @@ impl ServerWebSocket { return Err(global_this.throw(format_args!("publish requires a non-empty topic"))); } - let compress = Self::parse_compress_arg(global_this, "publish", compress_value, args.len)?; + let compress = Self::parse_compress_arg( + global_this, + "publish", + compress_value, + callframe.arguments_count() as usize, + )?; if message_value.is_empty_or_undefined_or_null() { return Err(global_this.throw(format_args!("publish requires a non-empty message"))); @@ -882,9 +879,9 @@ impl ServerWebSocket { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<4>(); + let [topic_value, message_value, compress_value] = callframe.arguments_as_array::<3>(); - if args.len < 1 { + if callframe.arguments_count() < 1 { bun_output::scoped_log!(WebSocketServer, "publish()"); return Err(global_this.throw(format_args!("publish requires at least 1 argument"))); } @@ -894,10 +891,6 @@ impl ServerWebSocket { return Ok(JSValue::js_number(0.0)); }; - let topic_value = args.ptr[0]; - let message_value = args.ptr[1]; - let compress_value = args.ptr[2]; - if topic_value.is_empty_or_undefined_or_null() || !topic_value.is_string() { bun_output::scoped_log!(WebSocketServer, "publish() topic invalid"); return Err(global_this.throw(format_args!("publishText requires a topic string"))); @@ -905,8 +898,12 @@ impl ServerWebSocket { let topic_slice = topic_value.to_slice(global_this)?; - let compress = - Self::parse_compress_arg(global_this, "publishText", compress_value, args.len)?; + let compress = Self::parse_compress_arg( + global_this, + "publishText", + compress_value, + callframe.arguments_count() as usize, + )?; if message_value.is_empty_or_undefined_or_null() || !message_value.is_string() { return Err(global_this.throw(format_args!("publishText requires a non-empty message"))); @@ -935,9 +932,9 @@ impl ServerWebSocket { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<4>(); + let [topic_value, message_value, compress_value] = callframe.arguments_as_array::<3>(); - if args.len < 1 { + if callframe.arguments_count() < 1 { bun_output::scoped_log!(WebSocketServer, "publishBinary()"); return Err( global_this.throw(format_args!("publishBinary requires at least 1 argument")) @@ -948,9 +945,6 @@ impl ServerWebSocket { bun_output::scoped_log!(WebSocketServer, "publish() closed"); return Ok(JSValue::js_number(0.0)); }; - let topic_value = args.ptr[0]; - let message_value = args.ptr[1]; - let compress_value = args.ptr[2]; if topic_value.is_empty_or_undefined_or_null() || !topic_value.is_string() { bun_output::scoped_log!(WebSocketServer, "publishBinary() topic invalid"); @@ -962,8 +956,12 @@ impl ServerWebSocket { return Err(global_this.throw(format_args!("publishBinary requires a non-empty topic"))); } - let compress = - Self::parse_compress_arg(global_this, "publishBinary", compress_value, args.len)?; + let compress = Self::parse_compress_arg( + global_this, + "publishBinary", + compress_value, + callframe.arguments_count() as usize, + )?; if message_value.is_empty_or_undefined_or_null() { return Err( @@ -995,13 +993,12 @@ impl ServerWebSocket { callframe: &CallFrame, this_value: JSValue, ) -> JsResult { - let args = callframe.arguments_old::<1>(); + let [callback] = callframe.arguments_as_array::<1>(); - if args.len < 1 { + if callframe.arguments_count() < 1 { return Err(global_this.throw_not_enough_arguments("cork", 1, 0)); } - let callback = args.ptr[0]; if callback.is_empty_or_undefined_or_null() || !callback.is_callable() { return Err(global_this.throw_invalid_argument_type_value( b"cork", @@ -1034,9 +1031,9 @@ impl ServerWebSocket { #[bun_jsc::host_fn(method)] pub fn send(&self, global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let args = callframe.arguments_old::<2>(); + let [message_value, compress_value] = callframe.arguments_as_array::<2>(); - if args.len < 1 { + if callframe.arguments_count() < 1 { bun_output::scoped_log!(WebSocketServer, "send()"); return Err(global_this.throw(format_args!("send requires at least 1 argument"))); } @@ -1046,10 +1043,12 @@ impl ServerWebSocket { return Ok(JSValue::js_number(0.0)); } - let message_value = args.ptr[0]; - let compress_value = args.ptr[1]; - - let compress = Self::parse_compress_arg(global_this, "send", compress_value, args.len)?; + let compress = Self::parse_compress_arg( + global_this, + "send", + compress_value, + callframe.arguments_count() as usize, + )?; if message_value.is_empty_or_undefined_or_null() { return Err(global_this.throw(format_args!("send requires a non-empty message"))); @@ -1088,9 +1087,9 @@ impl ServerWebSocket { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<2>(); + let [message_value, compress_value] = callframe.arguments_as_array::<2>(); - if args.len < 1 { + if callframe.arguments_count() < 1 { bun_output::scoped_log!(WebSocketServer, "sendText()"); return Err(global_this.throw(format_args!("sendText requires at least 1 argument"))); } @@ -1100,10 +1099,12 @@ impl ServerWebSocket { return Ok(JSValue::js_number(0.0)); } - let message_value = args.ptr[0]; - let compress_value = args.ptr[1]; - - let compress = Self::parse_compress_arg(global_this, "sendText", compress_value, args.len)?; + let compress = Self::parse_compress_arg( + global_this, + "sendText", + compress_value, + callframe.arguments_count() as usize, + )?; if message_value.is_empty_or_undefined_or_null() || !message_value.is_string() { return Err(global_this.throw(format_args!("sendText expects a string"))); @@ -1130,9 +1131,9 @@ impl ServerWebSocket { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<2>(); + let [message_value, compress_value] = callframe.arguments_as_array::<2>(); - if args.len < 1 { + if callframe.arguments_count() < 1 { bun_output::scoped_log!(WebSocketServer, "sendBinary()"); return Err(global_this.throw(format_args!("sendBinary requires at least 1 argument"))); } @@ -1142,11 +1143,12 @@ impl ServerWebSocket { return Ok(JSValue::js_number(0.0)); } - let message_value = args.ptr[0]; - let compress_value = args.ptr[1]; - - let compress = - Self::parse_compress_arg(global_this, "sendBinary", compress_value, args.len)?; + let compress = Self::parse_compress_arg( + global_this, + "sendBinary", + compress_value, + callframe.arguments_count() as usize, + )?; let Some(buffer) = message_value.as_array_buffer(global_this) else { return Err(global_this.throw(format_args!("sendBinary requires an ArrayBufferView"))); @@ -1179,14 +1181,12 @@ impl ServerWebSocket { name: &'static str, opcode: Opcode, ) -> JsResult { - let args = callframe.arguments_old::<2>(); - if self.is_closed() { return Ok(JSValue::js_number(0.0)); } - if args.len > 0 { - let value = args.ptr[0]; + if callframe.arguments_count() > 0 { + let value = callframe.argument(0); if !value.is_empty_or_undefined_or_null() { if let Some(data) = value.as_array_buffer(global_this) { let buffer = data.slice(); @@ -1266,7 +1266,7 @@ impl ServerWebSocket { // Since close() can lead to the close() callback being called, let's always ensure the `this` value is up to date. _this_value: JSValue, ) -> JsResult { - let args = callframe.arguments_old::<2>(); + let args = callframe.arguments_as_array::<2>(); bun_output::scoped_log!(WebSocketServer, "close()"); if self.is_closed() { @@ -1274,25 +1274,25 @@ impl ServerWebSocket { } let code: i32 = 'brk: { - if args.ptr[0].is_empty() || args.ptr[0].is_undefined() { + if args[0].is_undefined() { // default exception code break 'brk 1000; } - if !args.ptr[0].is_number() { + if !args[0].is_number() { return Err(global_this.throw_invalid_arguments(format_args!( "close requires a numeric code or undefined" ))); } - break 'brk args.ptr[0].coerce_to_i32(global_this)?; + break 'brk args[0].coerce_to_i32(global_this)?; }; let message_value: ZigStringSlice = 'brk: { - if args.ptr[1].is_empty() || args.ptr[1].is_undefined() { + if args[1].is_undefined() { break 'brk ZigStringSlice::empty(); } - break 'brk args.ptr[1].to_slice_or_null(global_this)?; + break 'brk args[1].to_slice_or_null(global_this)?; }; // `to_slice_or_null` can run user `toString()`, which may re-entrantly diff --git a/src/runtime/server/server_body.rs b/src/runtime/server/server_body.rs index 3111061e1be4..87505e9240f6 100644 --- a/src/runtime/server/server_body.rs +++ b/src/runtime/server/server_body.rs @@ -1417,18 +1417,18 @@ where global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<1>(); - if arguments.len < 1 { + let [topic_value] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global.throw_not_enough_arguments("subscriberCount", 1, 0)); } - if arguments.ptr[0].is_empty_or_undefined_or_null() { + if topic_value.is_empty_or_undefined_or_null() { return Err(global.throw_invalid_arguments(format_args!( "subscriberCount requires a topic name as a string" ))); } - let topic = arguments.ptr[0].to_slice(global)?; + let topic = topic_value.to_slice(global)?; if topic.slice().is_empty() { return Ok(JSValue::js_number(0.0)); @@ -1449,8 +1449,7 @@ where /// `pub const doStop = host_fn.wrapInstanceMethod(ThisServer, "stopFromJS", false)` #[bun_jsc::host_fn(method)] pub fn do_stop(&mut self, global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let args = callframe.arguments_old::<2>(); - let mut iter = jsc::ArgumentsSlice::init(global.bun_vm_ref(), args.slice()); + let mut iter = jsc::ArgumentsSlice::init(global.bun_vm_ref(), callframe.arguments()); // ?jsc.JSValue let abruptly = iter.next_eat(); Ok(self.stop_from_js(abruptly)) @@ -1473,8 +1472,7 @@ where global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<4>(); - let mut iter = jsc::ArgumentsSlice::init(global.bun_vm_ref(), args.slice()); + let mut iter = jsc::ArgumentsSlice::init(global.bun_vm_ref(), callframe.arguments()); // jsc.JSValue let object = iter .next_eat() @@ -1491,8 +1489,7 @@ where global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<5>(); - let mut iter = jsc::ArgumentsSlice::init(global.bun_vm_ref(), args.slice()); + let mut iter = jsc::ArgumentsSlice::init(global.bun_vm_ref(), callframe.arguments()); let topic_value = iter .next_eat() .ok_or_else(|| global.throw_invalid_arguments(format_args!("Missing argument")))?; @@ -1516,8 +1513,7 @@ where global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<2>(); - let mut iter = jsc::ArgumentsSlice::init(global.bun_vm_ref(), args.slice()); + let mut iter = jsc::ArgumentsSlice::init(global.bun_vm_ref(), callframe.arguments()); // *jsc.WebCore.Request let arg = iter.next_eat().ok_or_else(|| { global.throw_invalid_arguments(format_args!("Missing Request object")) @@ -1575,8 +1571,7 @@ where #[bun_jsc::host_fn(method)] pub fn timeout(&mut self, global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments_buf = callframe.arguments_old::<2>(); - let arguments = arguments_buf.slice(); + let arguments = callframe.arguments(); if arguments.len() < 2 || arguments[0].is_empty_or_undefined_or_null() { return Err(global.throw_not_enough_arguments("timeout", 2, arguments.len())); } @@ -2308,8 +2303,7 @@ where ); } - let arguments_buf = callframe.arguments_old::<2>(); - let arguments = arguments_buf.slice(); + let arguments = callframe.arguments(); if arguments.is_empty() { let fetch_error = Fetch::FETCH_ERROR_NO_ARGS; return Ok( diff --git a/src/runtime/shell/ParsedShellScript.rs b/src/runtime/shell/ParsedShellScript.rs index cc8f347d898e..35237d2b0003 100644 --- a/src/runtime/shell/ParsedShellScript.rs +++ b/src/runtime/shell/ParsedShellScript.rs @@ -113,10 +113,9 @@ impl ParsedShellScript { #[bun_jsc::host_fn(method)] pub fn set_cwd(&self, global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<2>(); // SAFETY: `bun_vm()` is non-null for a Bun-owned global. let vm = global.bun_vm(); - let mut arguments = bun_jsc::ArgumentsSlice::init(vm, arguments.slice()); + let mut arguments = bun_jsc::ArgumentsSlice::init(vm, callframe.arguments()); let Some(str_js) = arguments.next_eat() else { return Err(global.throw(format_args!("$`...`.cwd(): expected a string argument"))); }; @@ -223,8 +222,7 @@ fn create_parsed_shell_script_impl( // so no scopeguard is needed. let mut shargs: Box = ShellArgs::init(); - let arguments_ = callframe.arguments_old::<2>(); - let arguments = arguments_.slice(); + let arguments = callframe.arguments(); if arguments.len() < 2 { return Err(global.throw_not_enough_arguments("Bun.$", 2, arguments.len())); } diff --git a/src/runtime/shell/interpreter.rs b/src/runtime/shell/interpreter.rs index c5e1180025cf..c911d7c63c85 100644 --- a/src/runtime/shell/interpreter.rs +++ b/src/runtime/shell/interpreter.rs @@ -2764,10 +2764,9 @@ pub fn create_shell_interpreter( use crate::jsc::{ArgumentsSlice, JsClass as _}; use crate::shell::parsed_shell_script::ParsedShellScript; - let arguments_ = callframe.arguments_old::<3>(); // SAFETY: bun_vm() returns the live thread-local VM for a Bun-owned global. let vm = global.bun_vm(); - let mut arguments = ArgumentsSlice::init(vm, arguments_.slice()); + let mut arguments = ArgumentsSlice::init(vm, callframe.arguments()); let resolve = arguments .next_eat() diff --git a/src/runtime/shell/shell_body.rs b/src/runtime/shell/shell_body.rs index b9f286f80f72..8e2709adbc7c 100644 --- a/src/runtime/shell/shell_body.rs +++ b/src/runtime/shell/shell_body.rs @@ -720,10 +720,9 @@ pub mod testing_apis { } #[cfg(not(windows))] { - let arguments_ = callframe.arguments_old::<1>(); // SAFETY: bun_vm() is non-null for a Bun-owned global. let vm = global.bun_vm(); - let mut arguments = jsc::ArgumentsSlice::init(vm, arguments_.slice()); + let mut arguments = jsc::ArgumentsSlice::init(vm, callframe.arguments()); let string: JSValue = match arguments.next_eat() { Some(s) => s, None => { @@ -758,10 +757,9 @@ pub mod testing_apis { callframe: &CallFrame, marked_argument_buffer: &mut MarkedArgumentBuffer, ) -> JsResult { - let arguments_ = callframe.arguments_old::<2>(); // SAFETY: bun_vm() is non-null for a Bun-owned global. let vm = global.bun_vm(); - let mut arguments = jsc::ArgumentsSlice::init(vm, arguments_.slice()); + let mut arguments = jsc::ArgumentsSlice::init(vm, callframe.arguments()); let string_args: JSValue = match arguments.next_eat() { Some(s) => s, None => { @@ -838,10 +836,9 @@ pub mod testing_apis { callframe: &CallFrame, marked_argument_buffer: &mut MarkedArgumentBuffer, ) -> JsResult { - let arguments_ = callframe.arguments_old::<2>(); // SAFETY: bun_vm() is non-null for a Bun-owned global. let vm = global.bun_vm(); - let mut arguments = jsc::ArgumentsSlice::init(vm, arguments_.slice()); + let mut arguments = jsc::ArgumentsSlice::init(vm, callframe.arguments()); let string_args: JSValue = match arguments.next_eat() { Some(s) => s, None => { diff --git a/src/runtime/socket/Listener.rs b/src/runtime/socket/Listener.rs index b0e6c3e160c2..b8b7ce2a932d 100644 --- a/src/runtime/socket/Listener.rs +++ b/src/runtime/socket/Listener.rs @@ -134,16 +134,15 @@ pub enum UnixOrHost { impl Listener { #[bun_jsc::host_fn(method)] pub fn reload(this: &Self, global: &JSGlobalObject, frame: &CallFrame) -> JsResult { - let args = frame.arguments_old::<1>(); + let [opts] = frame.arguments_as_array::<1>(); - if args.len < 1 + if frame.arguments_count() < 1 || (matches!(this.listener.get(), ListenerType::None) && this.handlers.active_connections.get() == 0) { return Err(global.throw(format_args!("Expected 1 argument"))); } - let opts = args.ptr[0]; if opts.is_empty_or_undefined_or_null() || opts.is_boolean() || !opts.is_object() { return Err(global.throw_invalid_arguments(format_args!("Expected options object"))); } @@ -786,13 +785,13 @@ impl Listener { #[bun_jsc::host_fn(method)] pub fn stop(this: &Self, _global: &JSGlobalObject, frame: &CallFrame) -> JsResult { - let arguments = frame.arguments_old::<1>(); + let [arg0] = frame.arguments_as_array::<1>(); log!("close"); Self::do_stop( this, - if arguments.len > 0 && arguments.ptr[0].is_boolean() { - arguments.ptr[0].to_boolean() + if frame.arguments_count() > 0 && arg0.is_boolean() { + arg0.to_boolean() } else { false }, @@ -1601,13 +1600,16 @@ fn connect_finish( pub(crate) fn js_add_server_name(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { jsc::mark_binding!(); - let arguments = frame.arguments_old::<3>(); - if arguments.len < 3 { - return Err(global.throw_not_enough_arguments("addServerName", 3, arguments.len)); + let [listener, hostname, tls] = frame.arguments_as_array::<3>(); + if frame.arguments_count() < 3 { + return Err(global.throw_not_enough_arguments( + "addServerName", + 3, + frame.arguments_count() as usize, + )); } - let listener = arguments.ptr[0]; if let Some(this) = listener.as_class_ref::() { - return Listener::add_server_name(this, global, arguments.ptr[1], arguments.ptr[2]); + return Listener::add_server_name(this, global, hostname, tls); } Err(global.throw(format_args!("Expected a Listener instance"))) } diff --git a/src/runtime/socket/UpgradedDuplex.rs b/src/runtime/socket/UpgradedDuplex.rs index d4d76ba4a8b6..a7e6f55099fb 100644 --- a/src/runtime/socket/UpgradedDuplex.rs +++ b/src/runtime/socket/UpgradedDuplex.rs @@ -576,13 +576,12 @@ fn on_received_data(global: &JSGlobalObject, frame: &CallFrame) -> JsResult(); + let [data_arg] = frame.arguments_as_array::<1>(); if let Some(self_ptr) = host_fn::get_function_data(function) { // SAFETY: function data was set to *mut UpgradedDuplex in get_js_handlers. let this = unsafe { bun_ptr::callback_ctx::(self_ptr) }; - if args.len >= 1 { - let data_arg = args.ptr[0]; + if frame.arguments_count() >= 1 { if !this.origin.is_empty() { if data_arg.is_empty_or_undefined_or_null() { return Ok(JSValue::UNDEFINED); diff --git a/src/runtime/socket/socket_body.rs b/src/runtime/socket/socket_body.rs index 2ba157a48cd2..b2edbe15a79a 100644 --- a/src/runtime/socket/socket_body.rs +++ b/src/runtime/socket/socket_body.rs @@ -724,18 +724,18 @@ impl NewSocket { callframe: &CallFrame, ) -> JsResult { jsc::mark_binding!(); - let args = callframe.arguments_old::<2>(); + let [enabled_arg, initial_delay_arg] = callframe.arguments_as_array::<2>(); - let enabled: bool = if args.len >= 1 { - args.ptr[0].to_boolean() + let enabled: bool = if callframe.arguments_count() >= 1 { + enabled_arg.to_boolean() } else { false }; // `initialDelay` is documented in milliseconds; TCP_KEEPIDLE is seconds. - let initial_delay_ms: u32 = if args.len > 1 { + let initial_delay_ms: u32 = if callframe.arguments_count() > 1 { u32::try_from(global.validate_integer_range( - args.ptr[1], + initial_delay_arg, 0i32, bun_sql_jsc::jsc::IntegerRange { min: 0, @@ -762,9 +762,9 @@ impl NewSocket { callframe: &CallFrame, ) -> JsResult { jsc::mark_binding!(); - let args = callframe.arguments_old::<1>(); - let enabled: bool = if args.len >= 1 { - args.ptr[0].to_boolean() + let [enabled_arg] = callframe.arguments_as_array::<1>(); + let enabled: bool = if callframe.arguments_count() >= 1 { + enabled_arg.to_boolean() } else { true }; @@ -783,9 +783,8 @@ impl NewSocket { callframe: &CallFrame, ) -> JsResult { jsc::mark_binding!(); - let args = callframe.arguments_old::<1>(); - let tos: i32 = if args.len >= 1 { - let arg = args.ptr[0]; + let [arg] = callframe.arguments_as_array::<1>(); + let tos: i32 = if callframe.arguments_count() >= 1 { // validate_integer_range maps NaN to the default; node:net rejects // it with ERR_INVALID_ARG_TYPE, so do that explicitly here. if arg.is_number() && arg.as_number().is_nan() { @@ -831,19 +830,19 @@ impl NewSocket { callframe: &CallFrame, ) -> JsResult { jsc::mark_binding!(); - let args = callframe.arguments_old::<2>(); + let [ctx_arg, is_error_arg] = callframe.arguments_as_array::<2>(); log!("resumeSNI"); let socket = this.socket.get(); if socket.is_detached() { return Ok(JSValue::UNDEFINED); } - let is_error = args.len > 1 && args.ptr[1].to_boolean(); + let is_error = callframe.arguments_count() > 1 && is_error_arg.to_boolean(); // The selected context: a native SecureContext (borrow() hands back an // owned SSL_CTX reference that us_socket_sni_resolve consumes) or null // to fall through to the listener's default context. - let ctx_ptr = if args.len >= 1 && !is_error { + let ctx_ptr = if callframe.arguments_count() >= 1 && !is_error { if let Some(sc) = - args.ptr[0].as_class_ref::() + ctx_arg.as_class_ref::() { sc.borrow() } else { @@ -2190,14 +2189,14 @@ impl NewSocket { callframe: &CallFrame, ) -> JsResult { jsc::mark_binding!(); - let args = callframe.arguments_old::<1>(); + let [t_arg] = callframe.arguments_as_array::<1>(); if this.socket.get().is_detached() { return Ok(JSValue::UNDEFINED); } - if args.len == 0 { + if callframe.arguments_count() == 0 { return Err(global.throw(format_args!("Expected 1 argument, got 0"))); } - let t = args.ptr[0].coerce::(global)?; + let t = t_arg.coerce::(global)?; if t < 0 { return Err(global.throw(format_args!("Timeout must be a positive integer"))); } @@ -3050,8 +3049,8 @@ impl NewSocket { callframe: &CallFrame, ) -> JsResult { jsc::mark_binding!(); - let args = callframe.arguments_old::<1>(); - if args.len > 0 && args.ptr[0].to_boolean() { + let [arg] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() > 0 && arg.to_boolean() { this.socket.get().shutdown_read(); } else { this.socket.get().shutdown(); @@ -3235,9 +3234,9 @@ impl NewSocket { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<1>(); + let [opts] = callframe.arguments_as_array::<1>(); - if args.len < 1 { + if callframe.arguments_count() < 1 { return Err(global.throw(format_args!("Expected 1 argument"))); } @@ -3245,7 +3244,6 @@ impl NewSocket { return Ok(JSValue::UNDEFINED); } - let opts = args.ptr[0]; if opts.is_empty_or_undefined_or_null() || opts.is_boolean() || !opts.is_object() { return Err(global.throw(format_args!("Expected options object"))); } @@ -3299,11 +3297,11 @@ impl NewSocket { callframe: &CallFrame, ) -> JsResult { jsc::mark_binding!(); - let args = callframe.arguments_old::<1>(); - if args.len < 1 { + let [opts] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { return Err(global.throw(format_args!("Expected 1 arguments"))); } - Self::upgrade_tls_impl(this, global, args.ptr[0], false) + Self::upgrade_tls_impl(this, global, opts, false) } /// `defers_server_identity`: node:tls owns hostname policy in its JS layer @@ -4421,17 +4419,15 @@ pub fn js_upgrade_duplex_to_tls( ) -> JsResult { jsc::mark_binding!(); - let args = callframe.arguments_old::<2>(); - if args.len < 2 { + let [duplex, opts] = callframe.arguments_as_array::<2>(); + if callframe.arguments_count() < 2 { return Err(global.throw(format_args!("Expected 2 arguments"))); } - let duplex = args.ptr[0]; // TODO: do better type checking if duplex.is_empty_or_undefined_or_null() { return Err(global.throw(format_args!("Expected a Duplex instance"))); } - let opts = args.ptr[1]; if opts.is_empty_or_undefined_or_null() || opts.is_boolean() || !opts.is_object() { return Err(global.throw(format_args!("Expected options object"))); } @@ -4694,11 +4690,14 @@ pub fn js_is_named_pipe_socket( ) -> JsResult { jsc::mark_binding!(); - let arguments = callframe.arguments_old::<3>(); - if arguments.len < 1 { - return Err(global.throw_not_enough_arguments("isNamedPipeSocket", 1, arguments.len)); + let [socket, _, _] = callframe.arguments_as_array::<3>(); + if callframe.arguments_count() < 1 { + return Err(global.throw_not_enough_arguments( + "isNamedPipeSocket", + 1, + callframe.arguments_count() as usize, + )); } - let socket = arguments.ptr[0]; if let Some(this) = socket.as_class_ref::() { return Ok(JSValue::from(this.socket.get().is_named_pipe())); } else if let Some(this) = socket.as_class_ref::() { @@ -4711,11 +4710,14 @@ pub fn js_is_named_pipe_socket( pub fn js_get_buffered_amount(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { jsc::mark_binding!(); - let arguments = callframe.arguments_old::<3>(); - if arguments.len < 1 { - return Err(global.throw_not_enough_arguments("getBufferedAmount", 1, arguments.len)); + let [socket, _, _] = callframe.arguments_as_array::<3>(); + if callframe.arguments_count() < 1 { + return Err(global.throw_not_enough_arguments( + "getBufferedAmount", + 1, + callframe.arguments_count() as usize, + )); } - let socket = arguments.ptr[0]; if let Some(this) = socket.as_class_ref::() { return Ok(JSValue::js_number( this.buffered_data_for_node_net.get().len() as f64, diff --git a/src/runtime/socket/tls_socket_functions.rs b/src/runtime/socket/tls_socket_functions.rs index a1875d1e7cbf..40f94ee65055 100644 --- a/src/runtime/socket/tls_socket_functions.rs +++ b/src/runtime/socket/tls_socket_functions.rs @@ -312,12 +312,11 @@ pub(super) fn set_servername( ))); } - let args = frame.arguments_old::<1>(); - if args.len < 1 { + let [server_name] = frame.arguments_as_array::<1>(); + if frame.arguments_count() < 1 { return Err(global.throw(format_args!("Expected 1 argument"))); } - let server_name = args.ptr[0]; if !server_name.is_string() { return Err(global.throw(format_args!("Expected \"serverName\" to be a string"))); } @@ -408,17 +407,16 @@ pub(super) fn set_max_send_fragment( ) -> JsResult { jsc::mark_binding(); - let args = frame.arguments_old::<1>(); + let [arg] = frame.arguments_as_array::<1>(); - if args.len < 1 { + if frame.arguments_count() < 1 { return Err(global.throw(format_args!("Expected size to be a number"))); } - let arg = args.ptr[0]; if !arg.is_number() { return Err(global.throw(format_args!("Expected size to be a number"))); } - let size = args.ptr[0].coerce_to_int64(global)?; + let size = arg.coerce_to_int64(global)?; if !(512..=16384).contains(&size) { return Ok(JSValue::FALSE); } @@ -441,10 +439,9 @@ pub(super) fn get_peer_certificate( ) -> JsResult { jsc::mark_binding(); - let args = frame.arguments_old::<1>(); + let [arg] = frame.arguments_as_array::<1>(); let mut abbreviated: bool = true; - if args.len > 0 { - let arg = args.ptr[0]; + if frame.arguments_count() > 0 { if !arg.is_boolean() { return Err(global.throw(format_args!("Expected abbreviated to be a boolean"))); } @@ -872,11 +869,11 @@ pub(crate) fn set_key_cert( if this.socket.get().is_detached() { return Ok(JSValue::UNDEFINED); } - let args = frame.arguments_old::<1>(); - if args.len < 1 { + let [arg] = frame.arguments_as_array::<1>(); + if frame.arguments_count() < 1 { return Err(global.throw(format_args!("setKeyCert requires a SecureContext"))); } - let Some(sc) = SecureContext::from_js(args.ptr[0]) else { + let Some(sc) = SecureContext::from_js(arg) else { return Err(global.throw(format_args!("setKeyCert requires a SecureContext"))); }; let Some(ssl_ptr) = this.socket.get().ssl() else { @@ -919,11 +916,10 @@ pub(crate) fn export_keying_material( return Ok(JSValue::UNDEFINED); } - let args = frame.arguments_old::<3>(); - if args.len < 2 { + let [length_arg, label_arg, context_arg] = frame.arguments_as_array::<3>(); + if frame.arguments_count() < 2 { return Err(global.throw(format_args!("Expected length and label to be provided"))); } - let length_arg = args.ptr[0]; if !length_arg.is_number() { return Err(global.throw(format_args!("Expected length to be a number"))); } @@ -933,7 +929,6 @@ pub(crate) fn export_keying_material( return Err(global.throw(format_args!("Expected length to be a positive number"))); } - let label_arg = args.ptr[1]; if !label_arg.is_string() { return Err(global.throw(format_args!("Expected label to be a string"))); } @@ -944,9 +939,7 @@ pub(crate) fn export_keying_material( return Ok(JSValue::UNDEFINED); }; - if args.len > 2 { - let context_arg = args.ptr[2]; - + if frame.arguments_count() > 2 { if let Some(sb) = StringOrBuffer::from_js(global, context_arg)? { let context_slice = sb.slice(); @@ -1144,16 +1137,14 @@ pub(super) fn set_session( return Ok(JSValue::UNDEFINED); } - let args = frame.arguments_old::<1>(); + let [session_arg] = frame.arguments_as_array::<1>(); - if args.len < 1 { + if frame.arguments_count() < 1 { return Err(global.throw(format_args!( "Expected session to be a string, Buffer or TypedArray" ))); } - let session_arg = args.ptr[0]; - if let Some(sb) = StringOrBuffer::from_js(global, session_arg)? { let session_slice = sb.slice(); let Some(ssl_ptr) = this.socket.get().ssl() else { @@ -1272,15 +1263,13 @@ pub(super) fn set_verify_mode( return Ok(JSValue::UNDEFINED); } - let args = frame.arguments_old::<2>(); + let [request_cert_js, reject_unauthorized_js] = frame.arguments_as_array::<2>(); - if args.len < 2 { + if frame.arguments_count() < 2 { return Err(global.throw(format_args!( "Expected requestCert and rejectUnauthorized arguments" ))); } - let request_cert_js = args.ptr[0]; - let reject_unauthorized_js = args.ptr[1]; if !request_cert_js.is_boolean() || !reject_unauthorized_js.is_boolean() { return Err(global.throw(format_args!( "Expected requestCert and rejectUnauthorized arguments to be boolean" diff --git a/src/runtime/socket/udp_socket.rs b/src/runtime/socket/udp_socket.rs index 7ece3bee1568..69c8b709fc58 100644 --- a/src/runtime/socket/udp_socket.rs +++ b/src/runtime/socket/udp_socket.rs @@ -1295,15 +1295,14 @@ impl UDPSocket { if this.closed.get() { return Err(global_this.throw(format_args!("Socket is closed"))); } - let arguments = callframe.arguments_old::<1>(); - if arguments.len != 1 { + if callframe.arguments_count() < 1 { return Err(global_this.throw_invalid_arguments(format_args!( "Expected 1 argument, got {}", - arguments.len + callframe.arguments_count() ))); } - let arg = arguments.ptr[0]; + let [arg] = callframe.arguments_as_array::<1>(); if !arg.js_type().is_array() { return Err(global_this.throw_invalid_argument_type( "sendMany", @@ -1465,31 +1464,32 @@ impl UDPSocket { if this.closed.get() { return Err(global_this.throw(format_args!("Socket is closed"))); } - let arguments = callframe.arguments_old::<3>(); + let arguments = callframe.arguments_as_array::<3>(); + let args_len = callframe.arguments_count(); let dst: Option = 'brk: { if this.connect_info.get().is_some() { - if arguments.len == 1 { + if args_len == 1 { break 'brk None; } - if arguments.len == 3 { + if args_len >= 3 { return Err(global_this.throw_invalid_arguments(format_args!( "Cannot specify destination on connected socket" ))); } return Err(global_this.throw_invalid_arguments(format_args!( "Expected 1 argument, got {}", - arguments.len + args_len ))); } else { - if arguments.len != 3 { + if args_len < 3 { return Err(global_this.throw_invalid_arguments(format_args!( "Expected 3 arguments, got {}", - arguments.len + args_len ))); } break 'brk Some(Destination { - port: arguments.ptr[1], - address: arguments.ptr[2], + port: arguments[1], + address: arguments[2], }); } }; @@ -1515,7 +1515,7 @@ impl UDPSocket { } }; - let payload_arg = arguments.ptr[0]; + let payload_arg = arguments[0]; let mut payload_str = ZigStringSlice::empty(); // Hoisted so the `slice()` borrow outlives the `'brk` block; the // backing store is kept alive by `payload_arg` on the JS stack. @@ -1735,13 +1735,11 @@ impl UDPSocket { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<1>(); - - if args.len < 1 { + if callframe.arguments_count() < 1 { return Err(global_this.throw_invalid_arguments(format_args!("Expected 1 argument"))); } - let options = args.ptr[0]; + let [options] = callframe.arguments_as_array::<1>(); let Some(this_value) = this.this_value.get().try_get() else { return Ok(JSValue::UNDEFINED); }; @@ -1874,7 +1872,7 @@ impl UDPSocket { // bare `js_connect(..)` call which doesn't resolve inside an `impl` block. // The codegen `JsClass` derive owns the link name, so the shim isn't needed. pub fn js_connect(global_this: &JSGlobalObject, call_frame: &CallFrame) -> JsResult { - let args = call_frame.arguments_old::<2>(); + let args = call_frame.arguments_as_array::<2>(); // `as_class_ref` is the safe `&T` downcast (encapsulates `&*from_js`); // mutation goes through `Cell`, so a shared borrow suffices (R-2). @@ -1892,14 +1890,14 @@ impl UDPSocket { return Err(global_this.throw(format_args!("Socket is closed"))); } - if args.len < 2 { + if call_frame.arguments_count() < 2 { return Err(global_this.throw_invalid_arguments(format_args!("Expected 2 arguments"))); } - let str = bun_core::OwnedString::new(args.ptr[0].to_bun_string(global_this)?); + let str = bun_core::OwnedString::new(args[0].to_bun_string(global_this)?); let connect_host = str.to_owned_slice_z(); - let connect_port_js = args.ptr[1]; + let connect_port_js = args[1]; if !connect_port_js.is_number() { return Err(global_this @@ -1974,13 +1972,13 @@ impl UDPSocket { ); }; - let args = call_frame.arguments_old::<2>(); - if args.len < 2 { + let args = call_frame.arguments_as_array::<2>(); + if call_frame.arguments_count() < 2 { return Err(global_this.throw_invalid_arguments(format_args!("Expected 2 arguments"))); } - let size = args.ptr[0].coerce_to_i32(global_this)?; - let is_recv = args.ptr[1].to_boolean(); + let size = args[0].coerce_to_i32(global_this)?; + let is_recv = args[1].to_boolean(); let bad_fd = || bun_sys::Error::from_code_int(SystemErrno::EBADF as c_int, bun_sys::Tag::setsockopt); diff --git a/src/runtime/test_runner/expect.rs b/src/runtime/test_runner/expect.rs index f10d5c7f42cb..96f1e67a4335 100644 --- a/src/runtime/test_runner/expect.rs +++ b/src/runtime/test_runner/expect.rs @@ -689,8 +689,7 @@ impl Expect { // extern shim emitted by `#[bun_jsc::JsClass]` codegen (TypeClass__construct/__call); bare `#[host_fn]` cannot target an associated fn without a receiver. pub fn call(global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments_ = callframe.arguments_old::<2>(); - let arguments = arguments_.slice(); + let arguments = callframe.arguments(); let value = if arguments.len() < 1 { JSValue::UNDEFINED } else { arguments[0] }; let mut custom_label = bun_core::String::empty(); @@ -771,8 +770,7 @@ impl Expect { // post_match on drop so it runs on every exit path. let this = scopeguard::guard(self, |t| t.post_match(global_this)); - let arguments_ = call_frame.arguments_old::<1>(); - let arguments = arguments_.slice(); + let arguments = call_frame.arguments(); let mut _msg: ZigString = ZigString::EMPTY; @@ -818,8 +816,7 @@ impl Expect { // so `post_match` runs on every exit. let this = scopeguard::guard(self, |t| t.post_match(global_this)); - let arguments_ = call_frame.arguments_old::<1>(); - let arguments = arguments_.slice(); + let arguments = call_frame.arguments(); let mut _msg: ZigString = ZigString::EMPTY; @@ -1354,8 +1351,7 @@ impl Expect { /// Implements `expect.extend({ ... })` // extern shim emitted by `#[bun_jsc::JsClass]` codegen (TypeClass__construct/__call); bare `#[host_fn]` cannot target an associated fn without a receiver. pub fn extend(global_this: &JSGlobalObject, call_frame: &CallFrame) -> JsResult { - let args_ = call_frame.arguments_old::<1>(); - let args = args_.slice(); + let args = call_frame.arguments(); if args.is_empty() || !args[0].is_object() { return Err(crate::throw_pretty_static!( @@ -1679,8 +1675,7 @@ impl Expect { // SAFETY: bun_vm() returns the live VM pointer for this global. let _gc = global_this.bun_vm().as_mut().auto_gc_on_drop(); - let arguments_ = call_frame.arguments_old::<1>(); - let arguments = arguments_.slice(); + let arguments = call_frame.arguments(); if arguments.is_empty() { return Err(global_this.throw_invalid_arguments(format_args!("expect.assertions() takes 1 argument"))); @@ -1773,7 +1768,7 @@ impl Expect { // extern shim emitted by `#[bun_jsc::JsClass]` codegen (TypeClass__construct/__call); bare `#[host_fn]` cannot target an associated fn without a receiver. pub fn do_unreachable(global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arg = callframe.arguments_old::<1>().ptr[0]; + let [arg] = callframe.arguments_as_array::<1>(); if arg.is_empty_or_undefined_or_null() { let error_value = bun_core::String::init("reached unreachable code").to_error_instance(global_this); @@ -2076,8 +2071,7 @@ impl Expect { ) -> JsResult { let this = self.post_match_guard(global); - let arguments_ = frame.arguments_old::<1>(); - let arguments = arguments_.slice(); + let arguments = frame.arguments(); if arguments.len() < 1 { return Err(global.throw_invalid_arguments(format_args!("{matcher_name}() requires 1 argument"))); } @@ -2200,8 +2194,7 @@ impl Expect { let this = self.post_match_guard(global); let this_value = frame.this(); - let arguments_ = frame.arguments_old::<1>(); - let arguments = arguments_.slice(); + let arguments = frame.arguments(); if arguments.len() < 1 { return Err(global.throw_invalid_arguments(format_args!("{matcher_name}() takes 1 argument"))); } @@ -2394,8 +2387,7 @@ pub struct ExpectCloseTo { impl ExpectCloseTo { // extern shim emitted by `#[bun_jsc::JsClass]` codegen (TypeClass__construct/__call); bare `#[host_fn]` cannot target an associated fn without a receiver. pub fn call(global_this: &JSGlobalObject, call_frame: &CallFrame) -> JsResult { - let args_buf = call_frame.arguments_old::<2>(); - let args = args_buf.slice(); + let args = call_frame.arguments(); if args.is_empty() || !args[0].is_number() { return Err(crate::throw_pretty_static!( @@ -2435,8 +2427,7 @@ pub struct ExpectObjectContaining { impl ExpectObjectContaining { // extern shim emitted by `#[bun_jsc::JsClass]` codegen (TypeClass__construct/__call); bare `#[host_fn]` cannot target an associated fn without a receiver. pub fn call(global_this: &JSGlobalObject, call_frame: &CallFrame) -> JsResult { - let args_buf = call_frame.arguments_old::<1>(); - let args = args_buf.slice(); + let args = call_frame.arguments(); if args.is_empty() || !args[0].is_object() { return Err(crate::throw_pretty_static!( @@ -2463,8 +2454,7 @@ pub struct ExpectStringContaining { impl ExpectStringContaining { // extern shim emitted by `#[bun_jsc::JsClass]` codegen (TypeClass__construct/__call); bare `#[host_fn]` cannot target an associated fn without a receiver. pub fn call(global_this: &JSGlobalObject, call_frame: &CallFrame) -> JsResult { - let args_buf = call_frame.arguments_old::<1>(); - let args = args_buf.slice(); + let args = call_frame.arguments(); if args.is_empty() || !args[0].is_string() { return Err(crate::throw_pretty_static!( @@ -2491,8 +2481,7 @@ pub struct ExpectAny { impl ExpectAny { // extern shim emitted by `#[bun_jsc::JsClass]` codegen (TypeClass__construct/__call); bare `#[host_fn]` cannot target an associated fn without a receiver. pub fn call(global_this: &JSGlobalObject, call_frame: &CallFrame) -> JsResult { - let _arguments = call_frame.arguments_old::<1>(); - let arguments: &[JSValue] = &_arguments.ptr[.._arguments.len]; + let arguments = call_frame.arguments(); if arguments.is_empty() { return Err(global_this.throw2( @@ -2539,8 +2528,7 @@ pub struct ExpectArrayContaining { impl ExpectArrayContaining { // extern shim emitted by `#[bun_jsc::JsClass]` codegen (TypeClass__construct/__call); bare `#[host_fn]` cannot target an associated fn without a receiver. pub fn call(global_this: &JSGlobalObject, call_frame: &CallFrame) -> JsResult { - let args_buf = call_frame.arguments_old::<1>(); - let args = args_buf.slice(); + let args = call_frame.arguments(); if args.is_empty() || !args[0].js_type().is_array() { return Err(crate::throw_pretty_static!( @@ -2770,14 +2758,13 @@ impl ExpectMatcherContext { #[bun_jsc::host_fn(method)] pub fn equals(&self, global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<3>(); - if arguments.len < 2 { + let args = callframe.arguments(); + if args.len() < 2 { return Err(global_this.throw2( "expect.extends matcher: this.util.equals expects at least 2 arguments", (), )); } - let args = arguments.slice(); Ok(JSValue::from(args[0].jest_deep_equals(args[1], global_this)?)) } } @@ -2837,32 +2824,28 @@ impl ExpectMatcherUtils { #[bun_jsc::host_fn(method)] pub fn stringify(&self, global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<1>(); - let arguments = arguments.slice(); + let arguments = callframe.arguments(); let value = if arguments.is_empty() { JSValue::UNDEFINED } else { arguments[0] }; Ok(Self::print_value_catched(global_this, value, None)) } #[bun_jsc::host_fn(method)] pub fn print_expected(&self, global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<1>(); - let arguments = arguments.slice(); + let arguments = callframe.arguments(); let value = if arguments.is_empty() { JSValue::UNDEFINED } else { arguments[0] }; Ok(Self::print_value_catched(global_this, value, Some(""))) } #[bun_jsc::host_fn(method)] pub fn print_received(&self, global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<1>(); - let arguments = arguments.slice(); + let arguments = callframe.arguments(); let value = if arguments.is_empty() { JSValue::UNDEFINED } else { arguments[0] }; Ok(Self::print_value_catched(global_this, value, Some(""))) } #[bun_jsc::host_fn(method)] pub fn matcher_hint(&self, global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<4>(); - let arguments = arguments.slice(); + let arguments = callframe.arguments(); if arguments.is_empty() || !arguments[0].is_string() { return Err(global_this.throw2( diff --git a/src/runtime/test_runner/expect/toBe.rs b/src/runtime/test_runner/expect/toBe.rs index f13194db63e5..32a349310de0 100644 --- a/src/runtime/test_runner/expect/toBe.rs +++ b/src/runtime/test_runner/expect/toBe.rs @@ -15,8 +15,7 @@ impl Expect { let (this, left, not) = self.matcher_prelude(global_this, callframe.this(), "toBe", "expected")?; - let arguments_ = callframe.arguments_old::<2>(); - let arguments = arguments_.slice(); + let arguments = callframe.arguments(); if arguments.len() < 1 { return Err(global_this.throw_invalid_arguments(format_args!("toBe() takes 1 argument"))); diff --git a/src/runtime/test_runner/expect/toBeArrayOfSize.rs b/src/runtime/test_runner/expect/toBeArrayOfSize.rs index 6d0fac1852f8..56f3ddb9ae2d 100644 --- a/src/runtime/test_runner/expect/toBeArrayOfSize.rs +++ b/src/runtime/test_runner/expect/toBeArrayOfSize.rs @@ -15,8 +15,7 @@ pub(crate) fn to_be_array_of_size( let this = this.post_match_guard(global); let this_value = frame.this(); - let _arguments = frame.arguments_old::<1>(); - let arguments = &_arguments.ptr[0.._arguments.len]; + let arguments = frame.arguments(); if arguments.len() < 1 { return Err(global.throw_invalid_arguments(format_args!("toBeArrayOfSize() requires 1 argument"))); diff --git a/src/runtime/test_runner/expect/toBeCloseTo.rs b/src/runtime/test_runner/expect/toBeCloseTo.rs index 091e9fb6711e..a15320996c53 100644 --- a/src/runtime/test_runner/expect/toBeCloseTo.rs +++ b/src/runtime/test_runner/expect/toBeCloseTo.rs @@ -14,8 +14,7 @@ impl Expect { let this = self.post_match_guard(global); let this_value = call_frame.this(); - let this_arguments = call_frame.arguments_old::<2>(); - let arguments = this_arguments.slice(); + let arguments = call_frame.arguments(); this.increment_expect_call_counter(); diff --git a/src/runtime/test_runner/expect/toBeInstanceOf.rs b/src/runtime/test_runner/expect/toBeInstanceOf.rs index 57be5c41138c..5a997fb9b56f 100644 --- a/src/runtime/test_runner/expect/toBeInstanceOf.rs +++ b/src/runtime/test_runner/expect/toBeInstanceOf.rs @@ -16,8 +16,7 @@ pub(crate) fn to_be_instance_of( // then call `post_match` exactly once on every exit path (success or throw). let res = (|| -> JsResult { let this_value = frame.this(); - // Collapsed `arguments_old(1)` + ptr/len slice into a single &[JSValue]. - let arguments_ = frame.arguments_old::<1>(); let arguments: &[JSValue] = arguments_.slice(); + let arguments: &[JSValue] = frame.arguments(); if arguments.len() < 1 { return Err(global.throw_invalid_arguments(format_args!( diff --git a/src/runtime/test_runner/expect/toBeOneOf.rs b/src/runtime/test_runner/expect/toBeOneOf.rs index 1048aa72935f..bb5267ca536f 100644 --- a/src/runtime/test_runner/expect/toBeOneOf.rs +++ b/src/runtime/test_runner/expect/toBeOneOf.rs @@ -40,8 +40,7 @@ pub(crate) fn to_be_one_of( let (this, expected, not) = this.matcher_prelude(global_this, call_frame.this(), "toBeOneOf", "expected")?; - let arguments_ = call_frame.arguments_old::<1>(); - let arguments = arguments_.slice(); + let arguments = call_frame.arguments(); if arguments.len() < 1 { return Err(global_this.throw_invalid_arguments(format_args!("toBeOneOf() takes 1 argument"))); diff --git a/src/runtime/test_runner/expect/toBeTypeOf.rs b/src/runtime/test_runner/expect/toBeTypeOf.rs index bb7f578f942a..36477742e9a3 100644 --- a/src/runtime/test_runner/expect/toBeTypeOf.rs +++ b/src/runtime/test_runner/expect/toBeTypeOf.rs @@ -24,8 +24,7 @@ pub(crate) fn to_be_type_of( frame: &CallFrame, ) -> JsResult { let (this, value, not) = this.matcher_prelude(global, frame.this(), "toBeTypeOf", "")?; - let _arguments = frame.arguments_old::<1>(); - let arguments = _arguments.slice(); + let arguments = frame.arguments(); if arguments.len() < 1 { return Err(global.throw_invalid_arguments(format_args!("toBeTypeOf() requires 1 argument"))); diff --git a/src/runtime/test_runner/expect/toBeWithin.rs b/src/runtime/test_runner/expect/toBeWithin.rs index de53187cc18b..18409d0f1cc3 100644 --- a/src/runtime/test_runner/expect/toBeWithin.rs +++ b/src/runtime/test_runner/expect/toBeWithin.rs @@ -16,8 +16,7 @@ impl Expect { "start, end", )?; - let _arguments = frame.arguments_old::<2>(); - let arguments = _arguments.slice(); + let arguments = frame.arguments(); if arguments.len() < 1 { return Err(global.throw_invalid_arguments(format_args!( diff --git a/src/runtime/test_runner/expect/toContain.rs b/src/runtime/test_runner/expect/toContain.rs index b6f73486d01a..3640940e616f 100644 --- a/src/runtime/test_runner/expect/toContain.rs +++ b/src/runtime/test_runner/expect/toContain.rs @@ -17,8 +17,7 @@ impl Expect { let (this, value, not) = self.matcher_prelude(global, frame.this(), "toContain", "expected")?; - let arguments_ = frame.arguments_old::<1>(); - let arguments = arguments_.slice(); + let arguments = frame.arguments(); if arguments.len() < 1 { return Err(global.throw_invalid_arguments(format_args!("toContain() takes 1 argument"))); diff --git a/src/runtime/test_runner/expect/toContainEqual.rs b/src/runtime/test_runner/expect/toContainEqual.rs index f1b09e169631..319bb60443e5 100644 --- a/src/runtime/test_runner/expect/toContainEqual.rs +++ b/src/runtime/test_runner/expect/toContainEqual.rs @@ -38,8 +38,7 @@ pub(crate) fn to_contain_equal( let this_value = frame.this(); let (this, value, not) = this.matcher_prelude(global, this_value, "toContainEqual", "expected")?; - let arguments_ = frame.arguments_old::<1>(); - let arguments = arguments_.slice(); + let arguments = frame.arguments(); if arguments.len() < 1 { return Err(global.throw_invalid_arguments(format_args!("toContainEqual() takes 1 argument"))); diff --git a/src/runtime/test_runner/expect/toEqual.rs b/src/runtime/test_runner/expect/toEqual.rs index bdeca002dc30..4be4f5fede85 100644 --- a/src/runtime/test_runner/expect/toEqual.rs +++ b/src/runtime/test_runner/expect/toEqual.rs @@ -14,8 +14,7 @@ impl Expect { let (this, value, not) = self.matcher_prelude(global, frame.this(), "toEqual", "expected")?; - let _arguments = frame.arguments_old::<1>(); - let arguments: &[JSValue] = _arguments.slice(); + let arguments = frame.arguments(); if arguments.len() < 1 { return Err(global.throw_invalid_arguments(format_args!("toEqual() requires 1 argument"))); diff --git a/src/runtime/test_runner/expect/toEqualIgnoringWhitespace.rs b/src/runtime/test_runner/expect/toEqualIgnoringWhitespace.rs index f747ed44e3ff..dc27e3238f89 100644 --- a/src/runtime/test_runner/expect/toEqualIgnoringWhitespace.rs +++ b/src/runtime/test_runner/expect/toEqualIgnoringWhitespace.rs @@ -19,7 +19,7 @@ pub(crate) fn to_equal_ignoring_whitespace( let (this, value, not) = this.matcher_prelude(global, frame.this(), "toEqualIgnoringWhitespace", "expected")?; - let arguments_ = frame.arguments_old::<1>(); let arguments: &[JSValue] = arguments_.slice(); + let arguments: &[JSValue] = frame.arguments(); if arguments.len() < 1 { return Err(global.throw_invalid_arguments(format_args!( diff --git a/src/runtime/test_runner/expect/toHaveBeenCalledTimes.rs b/src/runtime/test_runner/expect/toHaveBeenCalledTimes.rs index 17bd03c297ba..aaf1fc509dbd 100644 --- a/src/runtime/test_runner/expect/toHaveBeenCalledTimes.rs +++ b/src/runtime/test_runner/expect/toHaveBeenCalledTimes.rs @@ -8,8 +8,7 @@ pub(crate) fn to_have_been_called_times( global: &JSGlobalObject, frame: &CallFrame, ) -> JsResult { - let arguments_ = frame.arguments_old::<1>(); - let arguments: &[JSValue] = arguments_.slice(); + let arguments: &[JSValue] = frame.arguments(); let (this, calls, _value) = this.mock_prologue( global, frame.this(), diff --git a/src/runtime/test_runner/expect/toHaveLength.rs b/src/runtime/test_runner/expect/toHaveLength.rs index 003229edfce1..816ec9a2d790 100644 --- a/src/runtime/test_runner/expect/toHaveLength.rs +++ b/src/runtime/test_runner/expect/toHaveLength.rs @@ -12,8 +12,7 @@ pub(crate) fn to_have_length( let (this, value, not) = this.matcher_prelude(global, frame.this(), "toHaveLength", "expected")?; - let arguments_ = frame.arguments_old::<1>(); - let arguments = arguments_.slice(); + let arguments = frame.arguments(); if arguments.len() < 1 { return Err(global.throw_invalid_arguments(format_args!("toHaveLength() takes 1 argument"))); diff --git a/src/runtime/test_runner/expect/toHaveProperty.rs b/src/runtime/test_runner/expect/toHaveProperty.rs index 5fedf6bbe7f6..5218e3b64c44 100644 --- a/src/runtime/test_runner/expect/toHaveProperty.rs +++ b/src/runtime/test_runner/expect/toHaveProperty.rs @@ -14,8 +14,7 @@ pub(crate) fn to_have_property( let this = scopeguard::guard(this, |this| this.post_match(global)); let this_value = frame.this(); - let _arguments = frame.arguments_old::<2>(); - let arguments: &[JSValue] = _arguments.slice(); + let arguments = frame.arguments(); if arguments.len() < 1 { return Err(global.throw_invalid_arguments(format_args!( diff --git a/src/runtime/test_runner/expect/toIncludeRepeated.rs b/src/runtime/test_runner/expect/toIncludeRepeated.rs index 97621b4626c0..d0be67b3c798 100644 --- a/src/runtime/test_runner/expect/toIncludeRepeated.rs +++ b/src/runtime/test_runner/expect/toIncludeRepeated.rs @@ -15,8 +15,7 @@ impl Expect { let this = self.post_match_guard(global); let this_value = frame.this(); - let arguments_ = frame.arguments_old::<2>(); - let arguments = arguments_.slice(); + let arguments = frame.arguments(); if arguments.len() < 2 { return Err(global.throw_invalid_arguments(format_args!( diff --git a/src/runtime/test_runner/expect/toMatchInlineSnapshot.rs b/src/runtime/test_runner/expect/toMatchInlineSnapshot.rs index e659db8d1a3a..5a96073c8bd5 100644 --- a/src/runtime/test_runner/expect/toMatchInlineSnapshot.rs +++ b/src/runtime/test_runner/expect/toMatchInlineSnapshot.rs @@ -15,7 +15,7 @@ pub(crate) fn to_match_inline_snapshot( let this = scopeguard::guard(this, |this| this.post_match(global)); let this_value = frame.this(); - let arguments_ = frame.arguments_old::<2>(); let arguments: &[JSValue] = arguments_.slice(); + let arguments: &[JSValue] = frame.arguments(); this.increment_expect_call_counter(); diff --git a/src/runtime/test_runner/expect/toMatchObject.rs b/src/runtime/test_runner/expect/toMatchObject.rs index 5f0d420862cc..7ca906f706cf 100644 --- a/src/runtime/test_runner/expect/toMatchObject.rs +++ b/src/runtime/test_runner/expect/toMatchObject.rs @@ -10,8 +10,7 @@ pub(crate) fn to_match_object( ) -> JsResult { let (this, received_object, not) = this.matcher_prelude(global, frame.this(), "toMatchObject", "expected")?; - let args_buf = frame.arguments_old::<1>(); - let args = args_buf.slice(); + let args = frame.arguments(); if !received_object.is_object() { let signature: &str = get_signature("toMatchObject", "expected", not); diff --git a/src/runtime/test_runner/expect/toMatchSnapshot.rs b/src/runtime/test_runner/expect/toMatchSnapshot.rs index bb05dedd4976..b3953555441a 100644 --- a/src/runtime/test_runner/expect/toMatchSnapshot.rs +++ b/src/runtime/test_runner/expect/toMatchSnapshot.rs @@ -16,8 +16,7 @@ pub(crate) fn to_match_snapshot( let this = scopeguard::guard(this, |this| this.post_match(global)); let this_value = frame.this(); - let _arguments = frame.arguments_old::<2>(); - let arguments: &[JSValue] = &_arguments.ptr[0.._arguments.len]; + let arguments: &[JSValue] = frame.arguments(); this.increment_expect_call_counter(); diff --git a/src/runtime/test_runner/expect/toSatisfy.rs b/src/runtime/test_runner/expect/toSatisfy.rs index 41adfc956ee0..d8dc3170b6fb 100644 --- a/src/runtime/test_runner/expect/toSatisfy.rs +++ b/src/runtime/test_runner/expect/toSatisfy.rs @@ -11,8 +11,7 @@ pub(crate) fn to_satisfy(this: &Expect, global: &JSGlobalObject, frame: &CallFra let _guard = this.post_match_guard(global); let this_value = frame.this(); - let arguments_ = frame.arguments_old::<1>(); - let arguments = arguments_.slice(); + let arguments = frame.arguments(); if arguments.len() < 1 { return Err(global.throw_invalid_arguments(format_args!("toSatisfy() requires 1 argument"))); diff --git a/src/runtime/test_runner/expect/toStrictEqual.rs b/src/runtime/test_runner/expect/toStrictEqual.rs index dcda5dd90ad8..657b347f013f 100644 --- a/src/runtime/test_runner/expect/toStrictEqual.rs +++ b/src/runtime/test_runner/expect/toStrictEqual.rs @@ -14,8 +14,7 @@ impl Expect { let (this, value, not) = self.matcher_prelude(global, frame.this(), "toStrictEqual", "expected")?; - let _arguments = frame.arguments_old::<1>(); - let arguments: &[JSValue] = _arguments.slice(); + let arguments = frame.arguments(); if arguments.len() < 1 { return Err(global.throw_invalid_arguments( diff --git a/src/runtime/test_runner/expect/toThrowErrorMatchingInlineSnapshot.rs b/src/runtime/test_runner/expect/toThrowErrorMatchingInlineSnapshot.rs index 441825e735b2..6a5cc0a30e44 100644 --- a/src/runtime/test_runner/expect/toThrowErrorMatchingInlineSnapshot.rs +++ b/src/runtime/test_runner/expect/toThrowErrorMatchingInlineSnapshot.rs @@ -13,8 +13,7 @@ pub(crate) fn to_throw_error_matching_inline_snapshot( let this = scopeguard::guard(this, |t| t.post_match(global)); let this_value = frame.this(); - let _arguments = frame.arguments_old::<2>(); - let arguments: &[JSValue] = _arguments.slice(); + let arguments: &[JSValue] = frame.arguments(); this.increment_expect_call_counter(); diff --git a/src/runtime/test_runner/expect/toThrowErrorMatchingSnapshot.rs b/src/runtime/test_runner/expect/toThrowErrorMatchingSnapshot.rs index e1cd34758342..7c26e8e2c9b0 100644 --- a/src/runtime/test_runner/expect/toThrowErrorMatchingSnapshot.rs +++ b/src/runtime/test_runner/expect/toThrowErrorMatchingSnapshot.rs @@ -15,8 +15,7 @@ pub(crate) fn to_throw_error_matching_snapshot( let this = this.post_match_guard(global); let this_value = frame.this(); - let _arguments = frame.arguments_old::<2>(); - let arguments: &[JSValue] = _arguments.slice(); + let arguments: &[JSValue] = frame.arguments(); this.increment_expect_call_counter(); diff --git a/src/runtime/test_runner/jest.rs b/src/runtime/test_runner/jest.rs index 71d076e7089f..4a9fa4b9e18c 100644 --- a/src/runtime/test_runner/jest.rs +++ b/src/runtime/test_runner/jest.rs @@ -477,8 +477,7 @@ pub mod Jest { if vm.is_in_preload || runner().is_none() { // in preload, no arguments needed } else { - let arguments = callframe.arguments_old::<2>(); - let arguments = arguments.slice(); + let arguments = callframe.arguments(); if arguments.len() < 1 || !arguments[0].is_string() { return Err(global_object.throw(format_args!("Bun.jest() expects a string filename"))); @@ -502,8 +501,7 @@ pub mod Jest { global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<1>(); - let arguments = arguments.slice(); + let arguments = callframe.arguments(); if arguments.len() < 1 || !arguments[0].is_number() { return Err(global_object.throw(format_args!("setTimeout() expects a number (milliseconds)"))); } diff --git a/src/runtime/test_runner/mod.rs b/src/runtime/test_runner/mod.rs index c597d1b4a522..b356786cb631 100644 --- a/src/runtime/test_runner/mod.rs +++ b/src/runtime/test_runner/mod.rs @@ -468,8 +468,7 @@ pub mod expect { let this = scopeguard::guard(self, |this| this.post_match(global)); let this_value = frame.this(); - let args_buf = frame.arguments_old::<1>(); - let arguments: &[JSValue] = args_buf.slice(); + let arguments: &[JSValue] = frame.arguments(); if arguments.is_empty() { return Err(global.throw_invalid_arguments(format_args!( diff --git a/src/runtime/webcore/Blob.rs b/src/runtime/webcore/Blob.rs index e2176cd642f7..b9528197966a 100644 --- a/src/runtime/webcore/Blob.rs +++ b/src/runtime/webcore/Blob.rs @@ -1286,9 +1286,8 @@ impl BlobExt for Blob { JSValue::from(bun_sys::S::ISREG(file.mode) || bun_sys::S::ISFIFO(file.mode)) } fn do_write(&self, global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<3>(); // SAFETY: bun_vm() never returns null for a Bun-owned global. - let mut args = jsc::ArgumentsSlice::init(global_this.bun_vm(), arguments.slice()); + let mut args = jsc::ArgumentsSlice::init(global_this.bun_vm(), callframe.arguments()); validate_writable_blob(global_this, self)?; @@ -1359,9 +1358,8 @@ impl BlobExt for Blob { } fn do_unlink(&self, global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<1>(); // SAFETY: bun_vm() never returns null for a Bun-owned global. - let mut args = jsc::ArgumentsSlice::init(global_this.bun_vm(), arguments.slice()); + let mut args = jsc::ArgumentsSlice::init(global_this.bun_vm(), callframe.arguments()); validate_writable_blob(global_this, self)?; @@ -1704,12 +1702,8 @@ impl BlobExt for Blob { } fn get_writer(&self, global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments_ = callframe.arguments_old::<1>(); - // Index the fixed-size buffer (`arguments.ptr[0]`), not the - // len-bounded view, so the slot reads `.zero` when no arg was passed - // instead of panicking on `arguments[0]`. - let arg0 = arguments_.ptr[0]; - let has_args = arguments_.len > 0; + let [arg0] = callframe.arguments_as_array::<1>(); + let has_args = callframe.arguments_count() > 0; if !arg0.is_empty_or_undefined_or_null() && !arg0.is_object() { return Err(global_this @@ -1998,9 +1992,9 @@ impl BlobExt for Blob { /// https://w3c.github.io/FileAPI/#slice-method-algo fn get_slice(&self, global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let mut arguments_ = callframe.arguments_old::<3>(); + let mut arguments_ = callframe.arguments_as_array::<3>(); // index the full fixed-3 array (args[2] is written below regardless of len). - let args = &mut arguments_.ptr[..]; + let args = &mut arguments_[..]; if self.size.get() == 0 { let ptr = Blob::new(Blob::init_empty(global_this)); @@ -2024,7 +2018,7 @@ impl BlobExt for Blob { args[1] = JSValue::ZERO; } - let mut args_iter = jsc::ArgumentsSlice::init(global_this.bun_vm(), &arguments_.ptr[..3]); + let mut args_iter = jsc::ArgumentsSlice::init(global_this.bun_vm(), &arguments_[..3]); if let Some(start_) = args_iter.next_eat() { if start_.is_number() { let start = start_.to_int64(); @@ -2380,8 +2374,7 @@ impl BlobExt for Blob { } fn constructor(global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult<*mut Blob> { let blob: Blob; - let arguments = callframe.arguments_old::<2>(); - let args = arguments.slice(); + let args = callframe.arguments(); match args.len() { 0 => { @@ -5582,8 +5575,7 @@ pub fn jsdom_file_construct_( ) -> JsResult<*mut Blob> { jsc::mark_binding(); let blob: Blob; - let arguments = callframe.arguments_old::<3>(); - let args = arguments.slice(); + let args = callframe.arguments(); if args.len() < 2 { return Err(global_this.throw_invalid_arguments(format_args!( @@ -5691,8 +5683,7 @@ pub fn construct_bun_file( ) -> JsResult { // SAFETY: bun_vm() never returns null for a Bun-owned global. let vm = global_object.bun_vm(); - let arguments = callframe.arguments_old::<2>(); - let arguments_slice = arguments.slice(); + let arguments_slice = callframe.arguments(); let mut args = jsc::ArgumentsSlice::init(vm, arguments_slice); let Some(mut path) = PathOrFileDescriptor::from_js(global_object, &mut args)? else { @@ -5958,10 +5949,10 @@ pub fn on_file_stream_resolve_request_stream( global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<2>(); + let args = callframe.arguments(); // SAFETY: last arg is a promise-ptr created by FileStreamWrapper::new in pipe_readable_stream_to_blob. let mut this: Box = unsafe { - bun_core::heap::take(args.ptr[args.len - 1].as_number() as usize as *mut FileStreamWrapper) + bun_core::heap::take(args[args.len() - 1].as_number() as usize as *mut FileStreamWrapper) }; let strong = core::mem::take(&mut this.readable_stream_ref); if let Some(stream) = strong.get(global_this) { @@ -5975,15 +5966,15 @@ pub fn on_file_stream_reject_request_stream( global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<2>(); + let args = callframe.arguments(); // Take ownership via Box so Drop runs `sink.deref()` // and frees the wrapper. // SAFETY: the trailing argument is the `FileStreamWrapper*` boxed and passed // through `then()` from the resolve path; we are the sole consumer here. let mut this: Box = unsafe { - bun_core::heap::take(args.ptr[args.len - 1].as_number() as usize as *mut FileStreamWrapper) + bun_core::heap::take(args[args.len() - 1].as_number() as usize as *mut FileStreamWrapper) }; - let err = args.ptr[0]; + let err = args[0]; let strong = core::mem::take(&mut this.readable_stream_ref); diff --git a/src/runtime/webcore/Body.rs b/src/runtime/webcore/Body.rs index 5499f293894f..4f24aa306071 100644 --- a/src/runtime/webcore/Body.rs +++ b/src/runtime/webcore/Body.rs @@ -2339,8 +2339,8 @@ impl<'a> ValueBufferer<'a> { _global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<2>(); - let Some(sink) = Self::take_ctx(args.ptr[args.len - 1]) else { + let args = callframe.arguments(); + let Some(sink) = Self::take_ctx(args[args.len() - 1]) else { return Ok(JSValue::UNDEFINED); }; sink.handle_resolve_stream(true); @@ -2351,11 +2351,11 @@ impl<'a> ValueBufferer<'a> { _global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<2>(); - let Some(sink) = Self::take_ctx(args.ptr[args.len - 1]) else { + let args = callframe.arguments(); + let Some(sink) = Self::take_ctx(args[args.len() - 1]) else { return Ok(JSValue::UNDEFINED); }; - let err = args.ptr[0]; + let err = args[0]; sink.handle_reject_stream(err, true); Ok(JSValue::UNDEFINED) } diff --git a/src/runtime/webcore/FormData.rs b/src/runtime/webcore/FormData.rs index b43008313c31..f5264cd83f38 100644 --- a/src/runtime/webcore/FormData.rs +++ b/src/runtime/webcore/FormData.rs @@ -116,9 +116,7 @@ impl FormData { #[bun_jsc::host_fn(export = "FormData__jsFunctionFromMultipartData")] pub fn from_multipart_data(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { - let args = frame.arguments_old::<2>(); - let input_value = args.ptr[0]; - let boundary_value = args.ptr[1]; + let [input_value, boundary_value] = frame.arguments_as_array::<2>(); let boundary_slice: ZigStringSlice; let mut encoding = Encoding::URLEncoded; diff --git a/src/runtime/webcore/ObjectURLRegistry.rs b/src/runtime/webcore/ObjectURLRegistry.rs index c24d351528b8..33a11c042c6f 100644 --- a/src/runtime/webcore/ObjectURLRegistry.rs +++ b/src/runtime/webcore/ObjectURLRegistry.rs @@ -108,11 +108,15 @@ pub(crate) fn bun_create_object_url( global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<1>(); - if arguments.len < 1 { - return Err(global_object.throw_not_enough_arguments("createObjectURL", 1, arguments.len)); - } - let Some(blob) = arguments.ptr[0].as_class_ref::() else { + let [blob_arg] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { + return Err(global_object.throw_not_enough_arguments( + "createObjectURL", + 1, + callframe.arguments_count() as usize, + )); + } + let Some(blob) = blob_arg.as_class_ref::() else { return Err(global_object .throw_invalid_arguments(format_args!("createObjectURL expects a Blob object"))); }; @@ -128,22 +132,23 @@ pub(crate) fn bun_revoke_object_url( global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<1>(); - if arguments.len < 1 { - return Err(global_object.throw_not_enough_arguments("revokeObjectURL", 1, arguments.len)); - } - if !arguments.ptr[0].is_string() { + let [url_arg] = callframe.arguments_as_array::<1>(); + if callframe.arguments_count() < 1 { + return Err(global_object.throw_not_enough_arguments( + "revokeObjectURL", + 1, + callframe.arguments_count() as usize, + )); + } + if !url_arg.is_string() { return Err( global_object.throw_invalid_arguments(format_args!("revokeObjectURL expects a string")) ); } // `to_bun_string` returns a +1 ref; `bun_core::String` is `Copy` (no Drop), // so wrap in `OwnedString` for scope-exit `deref()`. - let str = bun_core::OwnedString::new( - arguments.ptr[0] - .to_bun_string(global_object) - .expect("unreachable"), - ); + let str = + bun_core::OwnedString::new(url_arg.to_bun_string(global_object).expect("unreachable")); if !str.has_prefix_comptime(b"blob:") { return Ok(JSValue::UNDEFINED); } @@ -164,17 +169,17 @@ pub(crate) fn js_function_resolve_object_url( global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<1>(); + let [url_arg] = callframe.arguments_as_array::<1>(); // Errors are ignored. // Not thrown. // https://github.com/nodejs/node/blob/2eff28fb7a93d3f672f80b582f664a7c701569fb/lib/internal/blob.js#L441 - if arguments.len < 1 { + if callframe.arguments_count() < 1 { return Ok(JSValue::UNDEFINED); } // `to_bun_string` returns a +1 ref; wrap in `OwnedString` so every exit // path (exception, non-blob prefix, success) releases it. - let str = bun_core::OwnedString::new(arguments.ptr[0].to_bun_string(global_object)?); + let str = bun_core::OwnedString::new(url_arg.to_bun_string(global_object)?); if global_object.has_exception() { return Ok(JSValue::ZERO); diff --git a/src/runtime/webcore/ReadableStream.rs b/src/runtime/webcore/ReadableStream.rs index 03e9b121f38e..f8ace5661b43 100644 --- a/src/runtime/webcore/ReadableStream.rs +++ b/src/runtime/webcore/ReadableStream.rs @@ -1026,14 +1026,13 @@ impl NewSource { call_frame: &CallFrame, ) -> JsResult { let this_jsvalue = call_frame.this(); - let arguments = call_frame.arguments_old::<2>(); - let view = arguments.ptr[0]; + let [view, flags] = call_frame.arguments_as_array::<2>(); view.ensure_still_alive(); let Some(mut buffer) = view.as_array_buffer(global_this) else { return Ok(JSValue::UNDEFINED); }; let result = self.on_pull_from_js(buffer.slice_mut(), view); - Self::process_result(this_jsvalue, global_this, arguments.ptr[1], result) + Self::process_result(this_jsvalue, global_this, flags, result) } pub fn start_from_js( diff --git a/src/runtime/webcore/Request.rs b/src/runtime/webcore/Request.rs index cc89b69d8ca3..a94fe5c79030 100644 --- a/src/runtime/webcore/Request.rs +++ b/src/runtime/webcore/Request.rs @@ -1517,8 +1517,7 @@ impl Request { callframe: &CallFrame, this_value: JSValue, ) -> JsResult> { - let arguments_ = callframe.arguments_old::<2>(); - let arguments = &arguments_.ptr[0..arguments_.len]; + let arguments = callframe.arguments(); let request = Self::construct_into(global_this, arguments, this_value)?; Ok(Request::new(request)) diff --git a/src/runtime/webcore/Response.rs b/src/runtime/webcore/Response.rs index 54fdeb59501f..f7d034360de1 100644 --- a/src/runtime/webcore/Response.rs +++ b/src/runtime/webcore/Response.rs @@ -469,8 +469,7 @@ mod _jsc_host_fns { _global: *mut JSGlobalObject, callframe: &CallFrame, ) -> JSValue { - let arguments = callframe.arguments_old::<1>(); - let this_value = arguments.ptr[0]; + let [this_value] = callframe.arguments_as_array::<1>(); if this_value.is_empty_or_undefined_or_null() { return JSValue::FALSE; } @@ -496,8 +495,7 @@ mod _jsc_host_fns { bun_opaque::opaque_deref(global_object), bun_opaque::opaque_deref(callframe), ); - let arguments = callframe.arguments_old::<1>(); - let this_value = arguments.ptr[0]; + let [this_value] = callframe.arguments_as_array::<1>(); if this_value.is_empty_or_undefined_or_null() { return JSValue::UNDEFINED; } @@ -909,12 +907,10 @@ impl Response { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<2>(); // https://github.com/remix-run/remix/blob/db2c31f64affb2095e4286b91306b96435967969/packages/remix-server-runtime/responses.ts#L4 // SAFETY: `bun_vm()` returns a raw `*mut VirtualMachine` (PORTING.md // §raw-ptr) — borrow it for the duration of args parsing. - let mut args = - bun_jsc::ArgumentsSlice::init(global_this.bun_vm(), &args_list.ptr[0..args_list.len]); + let mut args = bun_jsc::ArgumentsSlice::init(global_this.bun_vm(), callframe.arguments()); // `Init`'s field drop glue (HeadersRef + OwnedString) // releases its refs on `?`. `Body` has NO `Drop` and its @@ -1055,11 +1051,9 @@ impl Response { global_this: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args_list = callframe.arguments_old::<4>(); // https://github.com/remix-run/remix/blob/db2c31f64affb2095e4286b91306b96435967969/packages/remix-server-runtime/responses.ts#L4 // SAFETY: see `construct_json`. - let mut args = - bun_jsc::ArgumentsSlice::init(global_this.bun_vm(), &args_list.ptr[0..args_list.len]); + let mut args = bun_jsc::ArgumentsSlice::init(global_this.bun_vm(), callframe.arguments()); // url_string drops (derefs the WTF string) at scope exit let url_string: OwnedString; diff --git a/src/runtime/webcore/S3Client.rs b/src/runtime/webcore/S3Client.rs index 0e6cba37d083..02f6a6345b00 100644 --- a/src/runtime/webcore/S3Client.rs +++ b/src/runtime/webcore/S3Client.rs @@ -263,10 +263,9 @@ impl S3Client { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult> { - let arguments = callframe.arguments_old::<1>(); // SAFETY: `bun_vm()` returns the live VM pointer for `global`. let vm = global.bun_vm(); - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, arguments.slice()); + let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, callframe.arguments()); // `Transpiler::env_mut` is the safe accessor for the process-singleton // dotenv loader (set during init). `get_s3_credentials` takes `&mut self` // only to lazily memoize — single-threaded JS event-loop discipline applies. @@ -344,10 +343,9 @@ impl S3Client { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<2>(); // SAFETY: `bun_vm()` returns the live VM pointer for `global`. let vm = global.bun_vm(); - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, arguments.slice()); + let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, callframe.arguments()); let path: PathLike = match PathLike::from_js(global, &mut args)? { Some(p) => p, None => { @@ -389,10 +387,9 @@ impl S3Client { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<2>(); // SAFETY: `bun_vm()` returns the live VM pointer for `global`. let vm = global.bun_vm(); - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, arguments.slice()); + let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, callframe.arguments()); let path: PathLike = match PathLike::from_js(global, &mut args)? { Some(p) => p, None => { @@ -432,10 +429,9 @@ impl S3Client { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<2>(); // SAFETY: `bun_vm()` returns the live VM pointer for `global`. let vm = global.bun_vm(); - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, arguments.slice()); + let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, callframe.arguments()); let path: PathLike = match PathLike::from_js(global, &mut args)? { Some(p) => p, None => { @@ -473,10 +469,9 @@ impl S3Client { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<2>(); // SAFETY: `bun_vm()` returns the live VM pointer for `global`. let vm = global.bun_vm(); - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, arguments.slice()); + let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, callframe.arguments()); let path: PathLike = match PathLike::from_js(global, &mut args)? { Some(p) => p, None => { @@ -514,10 +509,9 @@ impl S3Client { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<2>(); // SAFETY: `bun_vm()` returns the live VM pointer for `global`. let vm = global.bun_vm(); - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, arguments.slice()); + let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, callframe.arguments()); let path: PathLike = match PathLike::from_js(global, &mut args)? { Some(p) => p, None => { @@ -555,10 +549,9 @@ impl S3Client { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<3>(); // SAFETY: `bun_vm()` returns the live VM pointer for `global`. let vm = global.bun_vm(); - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, arguments.slice()); + let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, callframe.arguments()); let path: PathLike = match PathLike::from_js(global, &mut args)? { Some(p) => p, None => { @@ -641,10 +634,9 @@ impl S3Client { global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<2>(); // SAFETY: `bun_vm()` returns the live VM pointer for `global`. let vm = global.bun_vm(); - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, arguments.slice()); + let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, callframe.arguments()); let path: PathLike = match PathLike::from_js(global, &mut args)? { Some(p) => p, None => { @@ -711,10 +703,9 @@ impl S3Client { } pub(crate) fn static_file(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<2>(); // SAFETY: `bun_vm()` returns the live VM pointer for `global`. let vm = global.bun_vm(); - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, arguments.slice()); + let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, callframe.arguments()); let Some(path) = PathLike::from_js(global, &mut args)? else { return Err(global.throw_invalid_arguments(format_args!("Expected file path string"))); diff --git a/src/runtime/webcore/S3File.rs b/src/runtime/webcore/S3File.rs index 5b8430631dfa..a43807cc3339 100644 --- a/src/runtime/webcore/S3File.rs +++ b/src/runtime/webcore/S3File.rs @@ -108,9 +108,9 @@ where #[bun_jsc::host_fn] pub(crate) fn presign(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<3>(); // SAFETY: bun_vm() returns the live VM raw ptr. - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(global.bun_vm(), arguments.slice()); + let mut args = + bun_jsc::call_frame::ArgumentsSlice::init(global.bun_vm(), callframe.arguments()); // accept a path or a blob let path_or_blob = PathOrBlob::from_js_no_copy(global, &mut args)?; @@ -145,9 +145,9 @@ pub(crate) fn presign(global: &JSGlobalObject, callframe: &CallFrame) -> JsResul #[bun_jsc::host_fn] pub(crate) fn unlink(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<3>(); // SAFETY: bun_vm() returns the live VM raw ptr. - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(global.bun_vm(), arguments.slice()); + let mut args = + bun_jsc::call_frame::ArgumentsSlice::init(global.bun_vm(), callframe.arguments()); // accept a path or a blob let path_or_blob = PathOrBlob::from_js_no_copy(global, &mut args)?; @@ -186,9 +186,9 @@ pub(crate) fn unlink(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult #[bun_jsc::host_fn] pub fn write(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<3>(); // SAFETY: bun_vm() returns the live VM raw ptr. - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(global.bun_vm(), arguments.slice()); + let mut args = + bun_jsc::call_frame::ArgumentsSlice::init(global.bun_vm(), callframe.arguments()); // accept a path or a blob let path_or_blob = PathOrBlob::from_js_no_copy(global, &mut args)?; @@ -256,9 +256,9 @@ pub fn write(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult JsResult { - let arguments = callframe.arguments_old::<3>(); // SAFETY: bun_vm() returns the live VM raw ptr. - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(global.bun_vm(), arguments.slice()); + let mut args = + bun_jsc::call_frame::ArgumentsSlice::init(global.bun_vm(), callframe.arguments()); // accept a path or a blob let mut path_or_blob = PathOrBlob::from_js_no_copy(global, &mut args)?; @@ -293,9 +293,9 @@ pub(crate) fn size(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult JsResult { - let arguments = callframe.arguments_old::<3>(); // SAFETY: bun_vm() returns the live VM raw ptr. - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(global.bun_vm(), arguments.slice()); + let mut args = + bun_jsc::call_frame::ArgumentsSlice::init(global.bun_vm(), callframe.arguments()); // accept a path or a blob let mut path_or_blob = PathOrBlob::from_js_no_copy(global, &mut args)?; @@ -792,16 +792,7 @@ pub(crate) fn get_presign_url( global: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let args = callframe.arguments_old::<1>(); - get_presign_url_from( - this, - global, - if args.len > 0 { - Some(args.ptr[0]) - } else { - None - }, - ) + get_presign_url_from(this, global, callframe.arguments().first().copied()) } pub(crate) fn get_stat( @@ -814,9 +805,9 @@ pub(crate) fn get_stat( #[bun_jsc::host_fn] pub(crate) fn stat(global: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments = callframe.arguments_old::<3>(); // SAFETY: bun_vm() returns the live VM raw ptr. - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(global.bun_vm(), arguments.slice()); + let mut args = + bun_jsc::call_frame::ArgumentsSlice::init(global.bun_vm(), callframe.arguments()); // accept a path or a blob let mut path_or_blob = PathOrBlob::from_js_no_copy(global, &mut args)?; @@ -874,8 +865,7 @@ pub(crate) fn construct_internal( ) -> JsResult<*mut Blob> { // SAFETY: bun_vm() returns the live VM raw ptr. let vm = global.bun_vm(); - let arguments = callframe.arguments_old::<2>(); - let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, arguments.slice()); + let mut args = bun_jsc::call_frame::ArgumentsSlice::init(vm, callframe.arguments()); let Some(path) = PathLike::from_js(global, &mut args)? else { return Err(global.throw_invalid_arguments(format_args!("Expected file path string"))); diff --git a/src/runtime/webcore/TextDecoder.rs b/src/runtime/webcore/TextDecoder.rs index a31c6671b8d2..b41bf80957ba 100644 --- a/src/runtime/webcore/TextDecoder.rs +++ b/src/runtime/webcore/TextDecoder.rs @@ -211,8 +211,7 @@ impl TextDecoder { #[bun_jsc::host_fn(method)] pub fn decode(&self, global_this: &JSGlobalObject, callframe: &CallFrame) -> JsResult { - let arguments_buf = callframe.arguments_old::<2>(); - let arguments = arguments_buf.slice(); + let arguments = callframe.arguments(); // Evaluate options.stream before reading the input bytes. Reading `stream` // can invoke a user-defined getter that detaches/transfers the input's diff --git a/src/runtime/webcore/TextEncoderStreamEncoder.rs b/src/runtime/webcore/TextEncoderStreamEncoder.rs index d5b56dc75954..8833bfd78b7b 100644 --- a/src/runtime/webcore/TextEncoderStreamEncoder.rs +++ b/src/runtime/webcore/TextEncoderStreamEncoder.rs @@ -28,8 +28,7 @@ impl TextEncoderStreamEncoder { #[bun_jsc::host_fn(method)] pub(crate) fn encode(&self, global: &JSGlobalObject, frame: &CallFrame) -> JsResult { - let arguments = frame.arguments_old::<1>(); - let arguments = arguments.slice(); + let arguments = frame.arguments(); if arguments.is_empty() { return Err(global.throw_not_enough_arguments( "TextEncoderStreamEncoder.encode", diff --git a/src/runtime/webcore/fetch.rs b/src/runtime/webcore/fetch.rs index c677adc0c5a1..526e44910f96 100644 --- a/src/runtime/webcore/fetch.rs +++ b/src/runtime/webcore/fetch.rs @@ -230,8 +230,7 @@ pub(crate) fn bun_fetch_preconnect( global_object: &JSGlobalObject, callframe: &CallFrame, ) -> JsResult { - let arguments = callframe.arguments_old::<1>(); - let arguments = arguments.slice(); + let arguments = callframe.arguments(); if arguments.len() < 1 { return Err(global_object.throw_not_enough_arguments( @@ -391,7 +390,6 @@ fn fetch_impl( ) -> JsResult { jsc::mark_binding(); let global_this = ctx; - let arguments = callframe.arguments_old::<2>(); bun_core::analytics::Features::FETCH.fetch_add(1, core::sync::atomic::Ordering::Relaxed); // SAFETY: `VirtualMachine::get()` returns the live thread-local VM pointer; it // outlives this call frame. @@ -402,7 +400,7 @@ fn fetch_impl( let mut force_http3 = false; let mut force_http1 = false; - if arguments.len == 0 { + if callframe.arguments_count() == 0 { let err = ctx.to_type_error( jsc::ErrorCode::MISSING_ARGS, format_args!("{FETCH_ERROR_NO_ARGS}"), @@ -421,7 +419,7 @@ fn fetch_impl( // immutable borrow of `vm` for the rest of the function. let vm_verbose_fetch = vm.get_verbose_fetch(); - let mut args = jsc::ArgumentsSlice::init(vm, arguments.slice()); + let mut args = jsc::ArgumentsSlice::init(vm, callframe.arguments()); let first_arg = args.next_eat().unwrap(); diff --git a/src/runtime/webcore/prompt.rs b/src/runtime/webcore/prompt.rs index e89629e1bed1..d847d58e9064 100644 --- a/src/runtime/webcore/prompt.rs +++ b/src/runtime/webcore/prompt.rs @@ -9,8 +9,7 @@ use bun_jsc::zig_string::ZigString; /// https://html.spec.whatwg.org/multipage/timers-and-user-prompts.html#dom-alert #[bun_jsc::host_fn(export = "WebCore__alert")] fn alert(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { - let arguments = frame.arguments_old::<1>(); - let arguments = arguments.slice(); + let arguments = frame.arguments(); let output = Output::writer(); let has_message = !arguments.is_empty(); @@ -66,8 +65,7 @@ fn alert(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { #[bun_jsc::host_fn(export = "WebCore__confirm")] fn confirm(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { - let arguments = frame.arguments_old::<1>(); - let arguments = arguments.slice(); + let arguments = frame.arguments(); let output = Output::writer(); let has_message = !arguments.is_empty(); @@ -232,8 +230,7 @@ pub mod prompt { /// https://html.spec.whatwg.org/multipage/timers-and-user-prompts.html#dom-prompt #[bun_jsc::host_fn(export = "WebCore__prompt")] pub(crate) fn call(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { - let arguments = frame.arguments_old::<3>(); - let arguments = arguments.slice(); + let arguments = frame.arguments(); let output = Output::writer(); let has_message = !arguments.is_empty(); let has_default = arguments.len() >= 2; diff --git a/src/semver_jsc/SemverObject.rs b/src/semver_jsc/SemverObject.rs index be524c0e2cf0..bd0e6b913abe 100644 --- a/src/semver_jsc/SemverObject.rs +++ b/src/semver_jsc/SemverObject.rs @@ -20,8 +20,7 @@ pub fn create(global: &JSGlobalObject) -> JSValue { pub(crate) fn order(global: &JSGlobalObject, frame: &CallFrame) -> JsResult { // `to_slice()` owns its buffer and frees it on Drop. - let arguments = frame.arguments_old::<2>(); - let arguments = arguments.slice(); + let arguments = frame.arguments(); if arguments.len() < 2 { return Err(global.throw(format_args!("Expected two arguments"))); } @@ -70,8 +69,7 @@ pub(crate) fn order(global: &JSGlobalObject, frame: &CallFrame) -> JsResult JsResult { - let arguments = frame.arguments_old::<2>(); - let arguments = arguments.slice(); + let arguments = frame.arguments(); if arguments.len() < 2 { return Err(global.throw(format_args!("Expected two arguments"))); } diff --git a/test/js/bun/websocket/websocket-server.test.ts b/test/js/bun/websocket/websocket-server.test.ts index 73a3fe3b23b4..72f8da73055a 100644 --- a/test/js/bun/websocket/websocket-server.test.ts +++ b/test/js/bun/websocket/websocket-server.test.ts @@ -1183,6 +1183,16 @@ describe("ServerWebSocket", () => { done(); }, })); + test("(undefined, undefined)", done => ({ + open(ws) { + ws.close(undefined, undefined); + }, + close(_, code, reason) { + expect(code).toBe(1000); + expect(reason).toBeEmpty(); + done(); + }, + })); test("(no reason)", done => ({ open(ws) { ws.close(1001); diff --git a/test/js/node/zlib/zlib.test.js b/test/js/node/zlib/zlib.test.js index f4e38a051c51..2c0e172128a5 100644 --- a/test/js/node/zlib/zlib.test.js +++ b/test/js/node/zlib/zlib.test.js @@ -765,4 +765,13 @@ describe("crc32", () => { expect(() => zlib.crc32(String.prototype)).toThrow(TypeError); expect(zlib.crc32("abc")).toBe(891568578); }); + + it("handles missing and undefined arguments", () => { + // No data argument: ERR_INVALID_ARG_TYPE (not a crash, not a different error). + expect(() => zlib.crc32()).toThrow(expect.objectContaining({ code: "ERR_INVALID_ARG_TYPE" })); + // Explicit undefined behaves the same as no argument. + expect(() => zlib.crc32(undefined)).toThrow(expect.objectContaining({ code: "ERR_INVALID_ARG_TYPE" })); + // Omitted second arg defaults to value=0. + expect(zlib.crc32("hello")).toBe(zlib.crc32("hello", 0)); + }); });