diff --git a/.github/workflows/clippy.yml b/.github/workflows/clippy.yml index ffcfea31e0c..bd4d9f672f6 100644 --- a/.github/workflows/clippy.yml +++ b/.github/workflows/clippy.yml @@ -28,7 +28,7 @@ env: # Pin the toolchain explicitly so rustup ignores rust-toolchain.toml's # `targets` list (11 cross triples ≈ 450 MB of prebuilt std we don't need # to lint the host). Keep in sync with `channel` in rust-toolchain.toml. - RUSTUP_TOOLCHAIN: nightly-2026-05-06 + RUSTUP_TOOLCHAIN: nightly-2026-07-20 jobs: clippy: diff --git a/.github/workflows/format.yml b/.github/workflows/format.yml index 5e96c0d3c9a..9dfbb49cb8f 100644 --- a/.github/workflows/format.yml +++ b/.github/workflows/format.yml @@ -40,7 +40,7 @@ jobs: # Pin the toolchain explicitly so rustup ignores rust-toolchain.toml's # `targets` list (11 cross triples ≈ 450 MB of prebuilt std we don't # need just to run rustfmt). Keep this in sync with `channel` there. - RUSTUP_TOOLCHAIN: nightly-2026-05-06 + RUSTUP_TOOLCHAIN: nightly-2026-07-20 run: | # Without pipefail, `cmd | sed` always reports sed's exit status, so a # failing formatter is invisible to the `wait $PID` checks below. diff --git a/.github/workflows/miri.yml b/.github/workflows/miri.yml index 76bf543731f..6a71a0e306e 100644 --- a/.github/workflows/miri.yml +++ b/.github/workflows/miri.yml @@ -37,7 +37,7 @@ env: LLVM_VERSION_MAJOR: "21" # Pin so rustup ignores rust-toolchain.toml's `targets` list (11 cross # triples ≈ 450 MB we don't need). Keep in sync with `channel` there. - RUSTUP_TOOLCHAIN: nightly-2026-05-06 + RUSTUP_TOOLCHAIN: nightly-2026-07-20 jobs: miri: diff --git a/rust-toolchain.toml b/rust-toolchain.toml index 187dac114b2..e48bb2731da 100644 --- a/rust-toolchain.toml +++ b/rust-toolchain.toml @@ -1,5 +1,5 @@ [toolchain] -channel = "nightly-2026-05-06" +channel = "nightly-2026-07-20" # rust-src is needed for -Zbuild-std (Tier 3 targets like # aarch64-unknown-freebsd have no prebuilt std). miri is for # `bun run rust:miri`. targets ensures the diff --git a/scripts/build/rust.ts b/scripts/build/rust.ts index 73ef1993238..ca3b88346fb 100644 --- a/scripts/build/rust.ts +++ b/scripts/build/rust.ts @@ -297,8 +297,10 @@ export function registerRustRules(n: Ninja, cfg: Config): void { const rustup = findRustup(cfg); if (rustup !== undefined && cfg.rustToolchain !== undefined) { + // `-q` + `--no-self-update` silence the five `info:` lines rustup prints + // on every no-op reinstall; warnings/errors still show. const chain = - `${stream} --console $env ${q(rustup)} toolchain install ${cfg.rustToolchain} --force --component rust-src $rust_target_arg && ` + + `${stream} --console $env ${q(rustup)} -q toolchain install ${cfg.rustToolchain} --force --no-self-update --component rust-src $rust_target_arg && ` + `${stream} --console --cwd=$cwd $env ${q(cfg.cargo)} build $args`; n.rule("rust_build_cross", { command: hostWin ? `cmd /c "${chain}"` : chain, diff --git a/scripts/build/source.ts b/scripts/build/source.ts index 92fc48cfac7..7c34cecdbd0 100644 --- a/scripts/build/source.ts +++ b/scripts/build/source.ts @@ -601,8 +601,8 @@ export function registerDepRules(n: Ninja, cfg: Config): void { const rustup = q(join(dirname(cfg.cargo), `rustup${cfg.host.exeSuffix}`)); const cargoCrossEnsure = cfg.rustToolchain !== undefined - ? `${stream} $env ${rustup} toolchain install ${cfg.rustToolchain} --force --component rust-src --target $rust_target` - : `${stream} $env ${rustup} target add $rust_target`; + ? `${stream} $env ${rustup} -q toolchain install ${cfg.rustToolchain} --force --no-self-update --component rust-src --target $rust_target` + : `${stream} $env ${rustup} -q target add $rust_target`; // Windows: ninja runs commands via CreateProcess (no shell) — wrap in // `cmd /c "..."` so `&&` is interpreted as a chain operator instead of // being passed as a literal arg. See rust.ts `rust_build_cross`. diff --git a/scripts/build/tools.ts b/scripts/build/tools.ts index ff216313129..dde0b6f4503 100644 --- a/scripts/build/tools.ts +++ b/scripts/build/tools.ts @@ -664,11 +664,26 @@ export function findRustLld(os: OS): { const rustup = findTool({ names: ["rustup"], paths: [join(cargoHome, "bin")], required: false })?.path; const channel = readRustToolchainChannel(); if (rustup !== undefined && channel !== undefined) { - spawnSync(rustup, ["toolchain", "install", channel, "--force", "--profile", "minimal", "--component", "rust-src"], { - encoding: "utf8", - timeout: 300_000, - stdio: ["ignore", "ignore", "inherit"], // surface download/error output - }); + spawnSync( + rustup, + [ + "-q", + "toolchain", + "install", + channel, + "--force", + "--no-self-update", + "--profile", + "minimal", + "--component", + "rust-src", + ], + { + encoding: "utf8", + timeout: 300_000, + stdio: ["ignore", "ignore", "inherit"], // surface download/error output; `-q` hides `info:` noise + }, + ); } // One spawn for both sysroot and host triple / LLVM version. `-vV` prints diff --git a/src/ast/char_freq.rs b/src/ast/char_freq.rs index dca51831233..78e28bd8c88 100644 --- a/src/ast/char_freq.rs +++ b/src/ast/char_freq.rs @@ -117,7 +117,7 @@ fn scan_big(out: &mut Buffer, text: &[u8], delta: i32) { let unrolled = text.len() - (text.len() % SCAN_BIG_CHUNK_SIZE); let (chunks, remain) = text.split_at(unrolled); - for chunk in chunks.chunks_exact(SCAN_BIG_CHUNK_SIZE) { + for chunk in chunks.as_chunks::().0 { // PERF: candidate for unrolling — profile for i in 0..SCAN_BIG_CHUNK_SIZE { deltas[chunk[i] as usize] += delta; diff --git a/src/boringssl/lib.rs b/src/boringssl/lib.rs index a7f6f01126a..1dbc14ef5b5 100644 --- a/src/boringssl/lib.rs +++ b/src/boringssl/lib.rs @@ -392,8 +392,8 @@ impl core::fmt::Display for AltNameIp<'_> { match self.0 { [a, b, c, d] => write!(f, "{a}.{b}.{c}.{d}"), octets if octets.len() == 16 => { - for (i, pair) in octets.chunks_exact(2).enumerate() { - let group = u16::from_be_bytes([pair[0], pair[1]]); + for (i, pair) in octets.as_chunks::<2>().0.iter().enumerate() { + let group = u16::from_be_bytes(*pair); if i > 0 { f.write_str(":")?; } diff --git a/src/bun_alloc/lib.rs b/src/bun_alloc/lib.rs index bc3f4981e2d..88e17bf8c87 100644 --- a/src/bun_alloc/lib.rs +++ b/src/bun_alloc/lib.rs @@ -3375,12 +3375,10 @@ impl< ) -> core::result::Result<(), AllocError> { let _guard = self.map().mutex.lock(); - let slice: &'static [u8]; - // Is this actually a slice into the map? Don't free it. - if self.is_key_statically_allocated(key) { + let slice: &'static [u8] = if self.is_key_statically_allocated(key) { // SAFETY: key points into self.key_list_buffer which lives for the singleton's life. - slice = unsafe { core::slice::from_raw_parts(key.as_ptr(), key.len()) }; + unsafe { core::slice::from_raw_parts(key.as_ptr(), key.len()) } } else if self.key_list_buffer_used + key.len() < self.key_list_buffer.len() { let start = self.key_list_buffer_used; self.key_list_buffer_used += key.len(); @@ -3396,7 +3394,7 @@ impl< }; dst.copy_from_slice(key); // SAFETY: points into self.key_list_buffer (singleton-static lifetime). - slice = unsafe { core::slice::from_raw_parts(dst.as_ptr(), dst.len()) }; + unsafe { core::slice::from_raw_parts(dst.as_ptr(), dst.len()) } } else { // Propagate OOM. Route // through mimalloc directly (PORTING.md forbids `Box::leak`) so the @@ -3410,8 +3408,8 @@ impl< unsafe { core::ptr::copy_nonoverlapping(key.as_ptr(), ptr, key.len()) }; // SAFETY: allocation is owned by this singleton for process lifetime (or until // freed below on overwrite). - slice = unsafe { core::slice::from_raw_parts(ptr, key.len()) }; - } + unsafe { core::slice::from_raw_parts(ptr, key.len()) } + }; let slice = if REMOVE_TRAILING_SLASHES { trim_right(slice, b"/") diff --git a/src/bun_core/Global.rs b/src/bun_core/Global.rs index dd59d7770ba..798c22dbe0d 100644 --- a/src/bun_core/Global.rs +++ b/src/bun_core/Global.rs @@ -624,6 +624,8 @@ pub(crate) fn is_exiting() -> bool { // args and are `noreturn`/kernel-validated — no memory-safety preconditions, // so `safe fn` discharges the link-time proof and the call sites are plain // calls. `#[link_name]` avoids colliding with this module's own `pub fn exit`. +// The lint fires on the `safe` annotation only; the ABI matches std's. +#[allow(suspicious_runtime_symbol_definitions)] unsafe extern "C" { #[link_name = "abort"] safe fn libc_abort() -> !; diff --git a/src/bun_core/lib.rs b/src/bun_core/lib.rs index 85aed1f307c..50fbdc9ec8a 100644 --- a/src/bun_core/lib.rs +++ b/src/bun_core/lib.rs @@ -1846,15 +1846,17 @@ pub(crate) mod strings_impl { const HIGH_BITS: u64 = 0x8080_8080_8080_8080; let mut copied = 0usize; - for (d, s) in dst.chunks_exact_mut(8).zip(src.chunks_exact(8)) { - let word = u64::from_ne_bytes(s.try_into().expect("infallible: size matches")); + let (dst_chunks, _) = dst.as_chunks_mut::<8>(); + let (src_chunks, _) = src.as_chunks::<8>(); + for (d, s) in dst_chunks.iter_mut().zip(src_chunks) { + let word = u64::from_ne_bytes(*s); let mask = word & HIGH_BITS; if mask != 0 { let ascii = (mask.trailing_zeros() / 8) as usize; d[..ascii].copy_from_slice(&s[..ascii]); return copied + ascii; } - d.copy_from_slice(&word.to_ne_bytes()); + *d = word.to_ne_bytes(); copied += 8; } for (d, &s) in dst[copied..].iter_mut().zip(&src[copied..]) { diff --git a/src/collections/bit_set.rs b/src/collections/bit_set.rs index c1b843e5139..a72d0a584a2 100644 --- a/src/collections/bit_set.rs +++ b/src/collections/bit_set.rs @@ -83,15 +83,14 @@ fn set_range_value_masks(masks: &mut [usize], range: Range, value: bool) { mask2 = bool_mask_usize(value) >> ((MASK_LEN - 1) - (end_bit - 1)); masks[start_mask_index] |= mask1 & mask2; } else { - let bulk_mask_index: usize; - if start_bit > 0 { + let bulk_mask_index: usize = if start_bit > 0 { masks[start_mask_index] = (masks[start_mask_index] & !(bool_mask_usize(true) << start_bit)) | (bool_mask_usize(value) << start_bit); - bulk_mask_index = start_mask_index + 1; + start_mask_index + 1 } else { - bulk_mask_index = start_mask_index; - } + start_mask_index + }; for mask in &mut masks[bulk_mask_index..end_mask_index] { *mask = bool_mask_usize(value); diff --git a/src/collections/multi_array_list.rs b/src/collections/multi_array_list.rs index 883f3d72888..8cd3e767879 100644 --- a/src/collections/multi_array_list.rs +++ b/src/collections/multi_array_list.rs @@ -255,7 +255,7 @@ use crate::const_str_eq; /// callers routinely use lifetime-carrying field types (`&'a [u8]`, `Ref<'a>`). #[inline(always)] const fn type_id_of() -> TypeId { - core::intrinsics::type_id::() + const { core::intrinsics::type_id::() } } /// Reflected fields of `T` (struct only). Panics at const-eval for non-structs. @@ -295,7 +295,7 @@ const fn align_sort_key(size: usize, struct_align: usize) -> usize { return 1; } // Largest power of two dividing `size`. - let pow2 = size & size.wrapping_neg(); + let pow2 = size.isolate_lowest_one(); if pow2 < struct_align { pow2 } else { @@ -344,7 +344,7 @@ impl Reflected { let mut i = 0; while i < n { let f = &fields[i]; - let size = match f.ty.info().size { + let size = match f.ty.size() { Some(s) => s, None => panic!("MultiArrayList: field type must be Sized"), }; diff --git a/src/css/values/color.rs b/src/css/values/color.rs index c714d993f54..80336dbc272 100644 --- a/src/css/values/color.rs +++ b/src/css/values/color.rs @@ -954,7 +954,7 @@ bitflags::bitflags! { impl ColorFallbackKind { pub fn lowest(self) -> ColorFallbackKind { - ColorFallbackKind::from_bits_truncate(self.bits() & self.bits().wrapping_neg()) + ColorFallbackKind::from_bits_truncate(self.bits().isolate_lowest_one()) } pub fn highest(self) -> ColorFallbackKind { diff --git a/src/http_jsc/websocket_client/WebSocketUpgradeClient.rs b/src/http_jsc/websocket_client/WebSocketUpgradeClient.rs index e7c63e78ba6..55e522b8e2c 100644 --- a/src/http_jsc/websocket_client/WebSocketUpgradeClient.rs +++ b/src/http_jsc/websocket_client/WebSocketUpgradeClient.rs @@ -1843,7 +1843,9 @@ impl<'a> Headers8Bit<'a> { fn iter(&self) -> impl Iterator + '_ { self.slices - .chunks_exact(2) + .as_chunks::<2>() + .0 + .iter() .map(|pair| (pair[0].slice(), pair[1].slice())) } diff --git a/src/install/PackageManager/CommandLineArguments.rs b/src/install/PackageManager/CommandLineArguments.rs index 498787b95e2..a430696dfd5 100644 --- a/src/install/PackageManager/CommandLineArguments.rs +++ b/src/install/PackageManager/CommandLineArguments.rs @@ -1320,8 +1320,8 @@ Full documentation is available at https://bun.com/docs/cli/pm#scan. if let Some(cwd_) = args.option(b"--cwd") { let mut buf = PathBuffer::uninit(); let mut buf2 = PathBuffer::uninit(); - let final_path: &mut bun_core::ZStr; - if !cwd_.is_empty() && cwd_[0] == b'.' { + + let final_path: &mut bun_core::ZStr = if !cwd_.is_empty() && cwd_[0] == b'.' { let cwd_len = bun_sys::getcwd(&mut buf[..])?; let cwd = &buf[..cwd_len]; let parts: [&[u8]; 1] = [cwd_]; @@ -1332,12 +1332,12 @@ Full documentation is available at https://bun.com/docs/cli/pm#scan. ) .len(); buf2[len] = 0; - final_path = bun_core::ZStr::from_buf_mut(&mut buf2[..], len); + bun_core::ZStr::from_buf_mut(&mut buf2[..], len) } else { buf[..cwd_.len()].copy_from_slice(cwd_); buf[cwd_.len()] = 0; - final_path = bun_core::ZStr::from_buf_mut(&mut buf[..], cwd_.len()); - } + bun_core::ZStr::from_buf_mut(&mut buf[..], cwd_.len()) + }; if let Err(err) = bun_sys::chdir(final_path) { Output::err_generic( "failed to change directory to \"{}\": {}\n", diff --git a/src/install/resolvers/folder_resolver.rs b/src/install/resolvers/folder_resolver.rs index f967e3a93b6..14f8b834f92 100644 --- a/src/install/resolvers/folder_resolver.rs +++ b/src/install/resolvers/folder_resolver.rs @@ -186,7 +186,7 @@ fn normalize_package_json_path<'a>( non_normalized_path: &[u8], ) -> Paths<'a> { let abs: &[u8]; - let rel: &[u8]; + // We consider it valid if there is a package.json in the folder let normalized: &[u8] = if non_normalized_path.len() == 1 && non_normalized_path[0] == b'.' { non_normalized_path @@ -198,7 +198,7 @@ fn normalize_package_json_path<'a>( const PACKAGE_JSON_LEN: usize = "/package.json".len(); - if strings::starts_with_char(normalized, b'.') { + let rel: &[u8] = if strings::starts_with_char(normalized, b'.') { let mut tempcat = PathBuffer::uninit(); tempcat[..normalized.len()].copy_from_slice(normalized); @@ -210,10 +210,10 @@ fn normalize_package_json_path<'a>( &tempcat[0..normalized.len() + PACKAGE_JSON_LEN], ]; abs = FileSystem::instance().abs_buf(&parts, joined); - rel = FileSystem::instance().relative( + FileSystem::instance().relative( FileSystem::instance().top_level_dir(), &abs[0..abs.len() - PACKAGE_JSON_LEN], - ); + ) } else { let joined_len = joined.len(); let mut remain: &mut [u8] = &mut joined[..]; @@ -246,11 +246,11 @@ fn normalize_package_json_path<'a>( let abs_len = joined_len - remain_after; abs = &joined[0..abs_len]; // We store the folder name without package.json - rel = FileSystem::instance().relative( + FileSystem::instance().relative( FileSystem::instance().top_level_dir(), &abs[0..abs.len() - PACKAGE_JSON_LEN], - ); - } + ) + }; let abs_len = abs.len(); joined[abs_len] = 0; diff --git a/src/js_parser/parse/parse_typescript.rs b/src/js_parser/parse/parse_typescript.rs index 194d5dd1326..7fa12bd316f 100644 --- a/src/js_parser/parse/parse_typescript.rs +++ b/src/js_parser/parse/parse_typescript.rs @@ -632,25 +632,22 @@ impl<'a, const TYPESCRIPT: bool, const SCAN_ONLY: bool> P<'a, TYPESCRIPT, SCAN_O name: js_ast::StoreStr::new(b"" as &[u8]), value: None, }; - // Assigned in both live arms below; the third arm returns. - let needs_symbol: bool; - // Parse the name - if p.lexer.token == T::TStringLiteral { + let needs_symbol: bool = if p.lexer.token == T::TStringLiteral { // `slice8()` is currently duplicated in E.rs (two impl blocks); // read `.data` directly — `to_utf8_e_string` guarantees `is_utf16 == false`. let estr = p.lexer.to_utf8_e_string()?; debug_assert!(!estr.is_utf16); value.name = estr.data; - needs_symbol = js_lexer::is_identifier(value.name.slice()); + js_lexer::is_identifier(value.name.slice()) } else if p.lexer.is_identifier_or_keyword() { value.name = js_ast::StoreStr::new(p.lexer.identifier); - needs_symbol = true; + true } else { p.lexer.expect(T::TIdentifier)?; // error early, name is still `undefined` return Err(crate::Error::SyntaxError); - } + }; p.lexer.next()?; // Identifiers can be referenced by other values diff --git a/src/js_printer/lib.rs b/src/js_printer/lib.rs index 2125118f209..e8a3691d53b 100644 --- a/src/js_printer/lib.rs +++ b/src/js_printer/lib.rs @@ -7923,14 +7923,13 @@ pub fn print_ast<'a, W: WriterTrait, const ASCII_ONLY: bool, const GENERATE_SOUR // hoisted out of the `minify_identifiers` arm so the // `&'r mut MinifyRenamer` borrow stored in `renamer` outlives the branch. let mut minify_renamer; - let renamer: rename::Renamer<'_, '_>; // `Scope` isn't `Copy` here and the only // consumer (`compute_reserved_names_for_scope`) walks `members`/`generated`/ // `children` — never `parent` — so we re-point at the in-place // `tree.module_scope` instead (lives for `'a`). let module_scope = &tree.module_scope; let stable_source_indices = [source.index.0]; - if opts.minify_identifiers { + let renamer: rename::Renamer<'_, '_> = if opts.minify_identifiers { let mut reserved_names = rename::compute_initial_reserved_names(opts.module_type)?; for child in module_scope.children.slice() { // `StoreRef` has safe `DerefMut`; copy the handle to a mut @@ -8008,11 +8007,11 @@ pub fn print_ast<'a, W: WriterTrait, const ASCII_ONLY: bool, const GENERATE_SOUR let minifier = tree.char_freq.as_ref().unwrap().compile(); minify_renamer.assign_names_by_frequency(&minifier)?; - renamer = rename::Renamer::MinifyRenamer(&mut *minify_renamer); + rename::Renamer::MinifyRenamer(&mut *minify_renamer) } else { no_op_renamer = rename::NoOpRenamer::init(symbols, source); - renamer = no_op_renamer.to_renamer(); - } + no_op_renamer.to_renamer() + }; // defer: if minify_identifiers { renamer.deinit() } — Drop handles. diff --git a/src/react_compiler/ssa/enter_ssa.rs b/src/react_compiler/ssa/enter_ssa.rs index 79eba68e0b3..7104e4716e3 100644 --- a/src/react_compiler/ssa/enter_ssa.rs +++ b/src/react_compiler/ssa/enter_ssa.rs @@ -240,12 +240,12 @@ impl SSABuilder { } fn fix_incomplete_phis(&mut self, block_id: BlockId, env: &mut Environment) { - let incomplete_phis: Vec = self.states[block_id.0 as usize] - .as_mut() - .unwrap() - .incomplete_phis - .drain(..) - .collect(); + let incomplete_phis: Vec = core::mem::take( + &mut self.states[block_id.0 as usize] + .as_mut() + .unwrap() + .incomplete_phis, + ); for phi in &incomplete_phis { self.add_phi(block_id, &phi.old_place, &phi.new_place, env); } diff --git a/src/router/lib.rs b/src/router/lib.rs index 79736534802..af0d175782c 100644 --- a/src/router/lib.rs +++ b/src/router/lib.rs @@ -1570,7 +1570,7 @@ pub mod pattern { let segment = &path_[0..path_.iter().position(|&b| b == b'/').unwrap_or(path_.len())]; if !str_.eql_bytes(segment) { - params.truncate(0); // shrinkRetainingCapacity(0) + params.clear(); // shrinkRetainingCapacity(0) return false; } @@ -1593,7 +1593,7 @@ pub mod pattern { path_ = &path_[i + 1..]; if pattern.is_end(name) { - params.truncate(0); // shrinkRetainingCapacity(0) + params.clear(); // shrinkRetainingCapacity(0) return false; } @@ -2395,7 +2395,7 @@ mod tests { let mut parameters = route_param::List::default(); let mut failures: usize = 0; for (pattern, pathname, entries) in list.iter() { - parameters.truncate(0); + parameters.clear(); 'fail: { if !Pattern::match_::(pathname, pattern, pattern, &mut parameters) { diff --git a/src/runtime/cli/upgrade_command.rs b/src/runtime/cli/upgrade_command.rs index ebab8377c38..4bf5f2bf20c 100644 --- a/src/runtime/cli/upgrade_command.rs +++ b/src/runtime/cli/upgrade_command.rs @@ -161,7 +161,7 @@ impl Version { tag: IntegrityTag::SHA256, ..Default::default() }; - for (i, pair) in buf[PREFIX.len()..].chunks_exact(2).enumerate() { + for (i, pair) in buf[PREFIX.len()..].as_chunks::<2>().0.iter().enumerate() { match bun_fmt::hex_pair_value(pair[0], pair[1]) { Some(byte) => digest.value[i] = byte, None => return Integrity::default(), diff --git a/src/runtime/image/codecs.rs b/src/runtime/image/codecs.rs index e6388b129cb..347fb2eec6a 100644 --- a/src/runtime/image/codecs.rs +++ b/src/runtime/image/codecs.rs @@ -301,7 +301,7 @@ pub fn decode(bytes: &[u8], max_pixels: u64, hint: DecodeHint) -> Result().0 { if px[3] == 0 { px[0] = 0; px[1] = 0; diff --git a/src/runtime/node/path.rs b/src/runtime/node/path.rs index 39f3b0d3197..705d0980c89 100644 --- a/src/runtime/node/path.rs +++ b/src/runtime/node/path.rs @@ -1085,10 +1085,10 @@ fn _format_t<'a, T: PathCharCwd>( // `${pathObject.name || ''}${formatExt(pathObject.ext)}`; let mut base_len = base.len(); // Borrowck: track range into buf instead of slice. - let base_or_name_ext_range: (usize, usize); - if base_len > 0 { + + let base_or_name_ext_range: (usize, usize) = if base_len > 0 { memmove(&mut buf[0..base_len], base); - base_or_name_ext_range = (0, base_len); + (0, base_len) } else { let formatted_ext_len = { // Borrowck: inline format_ext_t to avoid overlapping &mut. @@ -1116,12 +1116,12 @@ fn _format_t<'a, T: PathCharCwd>( if name_len > 0 { memmove(&mut buf[0..name_len], _name); } - base_or_name_ext_range = if buf_size > 0 { + if buf_size > 0 { (0, buf_size) } else { (0, base_len) - }; - } + } + }; // Translated from the following JS code: // if (!dir) { diff --git a/src/runtime/socket/udp_socket.rs b/src/runtime/socket/udp_socket.rs index c0a45d8341d..25da46e3411 100644 --- a/src/runtime/socket/udp_socket.rs +++ b/src/runtime/socket/udp_socket.rs @@ -2289,7 +2289,7 @@ pub fn js_dgram_bind_fd(global: &JSGlobalObject, frame: &CallFrame) -> JsResult< // Numeric literals only — the JS layer resolves names before calling. let mut storage: sockaddr_storage = bun_core::ffi::zeroed(); - let socklen: libc::socklen_t; + // SAFETY: storage is large enough for sockaddr_in; src is NUL-terminated. let addr4 = unsafe { &mut *std::ptr::from_mut(&mut storage).cast::() }; // SAFETY: libc addr-format fn; src is NUL-terminated, dst points to in_addr-sized storage. @@ -2300,10 +2300,10 @@ pub fn js_dgram_bind_fd(global: &JSGlobalObject, frame: &CallFrame) -> JsResult< (&raw mut addr4.addr).cast::(), ) }; - if parsed_v4 == 1 { + let socklen: libc::socklen_t = if parsed_v4 == 1 { addr4.family = inet::AF_INET as inet::sa_family_t; addr4.port = htons(port); - socklen = size_of::() as libc::socklen_t; + size_of::() as libc::socklen_t } else { // SAFETY: storage is large enough for sockaddr_in6. let addr6 = unsafe { &mut *std::ptr::from_mut(&mut storage).cast::() }; @@ -2326,8 +2326,8 @@ pub fn js_dgram_bind_fd(global: &JSGlobalObject, frame: &CallFrame) -> JsResult< } addr6.family = inet::AF_INET6 as inet::sa_family_t; addr6.port = htons(port); - socklen = size_of::() as libc::socklen_t; - } + size_of::() as libc::socklen_t + }; // IPV6_V6ONLY, SO_REUSEADDR/SO_REUSEPORT and bind(2) go through bsd.c // so this doesn't fork its platform gate. diff --git a/src/runtime/valkey_jsc/valkey.rs b/src/runtime/valkey_jsc/valkey.rs index 8af08821c23..b2a61080693 100644 --- a/src/runtime/valkey_jsc/valkey.rs +++ b/src/runtime/valkey_jsc/valkey.rs @@ -1214,9 +1214,8 @@ impl ValkeyClient { // `self.write_buffer` directly (disjoint field) via `WriteBufWriter`. let hello_write_result = { let mut hello_args_buf: [&[u8]; 4] = [b"3", b"AUTH", b"", b""]; - let hello_args: &[&[u8]]; - if !self.username.is_empty() || !self.password.is_empty() { + let hello_args: &[&[u8]] = if !self.username.is_empty() || !self.password.is_empty() { hello_args_buf[0] = b"3"; hello_args_buf[1] = b"AUTH"; @@ -1228,10 +1227,10 @@ impl ValkeyClient { hello_args_buf[3] = &self.password; } - hello_args = &hello_args_buf[0..4]; + &hello_args_buf[0..4] } else { - hello_args = &hello_args_buf[0..1]; - } + &hello_args_buf[0..1] + }; // Format and send the HELLO command without adding to command queue // We'll handle this response specially in handleResponse diff --git a/src/runtime/webcore/encoding.rs b/src/runtime/webcore/encoding.rs index 1af04d964c7..344d8a57b14 100644 --- a/src/runtime/webcore/encoding.rs +++ b/src/runtime/webcore/encoding.rs @@ -811,8 +811,8 @@ pub(crate) unsafe fn construct_from_u8( // directly into a `Vec` so we never depend on an allocator- // layout-dependent `Vec → Vec` header reinterpret. let mut to = vec![0u8; len * 2]; - for (out, &b) in to.chunks_exact_mut(2).zip(input_slice) { - out.copy_from_slice(&u16::from(b).to_ne_bytes()); + for (out, &b) in to.as_chunks_mut::<2>().0.iter_mut().zip(input_slice) { + *out = u16::from(b).to_ne_bytes(); } to } diff --git a/src/sql_jsc/mysql/MySQLValue.rs b/src/sql_jsc/mysql/MySQLValue.rs index d6e4c49424e..7d2f4e999b9 100644 --- a/src/sql_jsc/mysql/MySQLValue.rs +++ b/src/sql_jsc/mysql/MySQLValue.rs @@ -217,51 +217,47 @@ fn validate_bigint( impl Value { pub fn to_data(&self, field_type: FieldType) -> Result { let mut buffer = [0u8; 15]; // Large enough for all fixed-size types - let pos: usize; - match self { + + let pos: usize = match self { Value::Null => return Ok(Data::Empty), Value::Bool(b) => { buffer[0] = if *b { 1 } else { 0 }; - pos = 1; + 1 } Value::Short(s) => { buffer[0..2].copy_from_slice(&s.to_le_bytes()); - pos = 2; + 2 } Value::Ushort(s) => { buffer[0..2].copy_from_slice(&s.to_le_bytes()); - pos = 2; + 2 } Value::Int(i) => { buffer[0..4].copy_from_slice(&i.to_le_bytes()); - pos = 4; + 4 } Value::Uint(i) => { buffer[0..4].copy_from_slice(&i.to_le_bytes()); - pos = 4; + 4 } Value::Long(l) => { buffer[0..8].copy_from_slice(&l.to_le_bytes()); - pos = 8; + 8 } Value::Ulong(l) => { buffer[0..8].copy_from_slice(&l.to_le_bytes()); - pos = 8; + 8 } Value::Float(f) => { buffer[0..4].copy_from_slice(&f.to_bits().to_le_bytes()); - pos = 4; + 4 } Value::Double(d) => { buffer[0..8].copy_from_slice(&d.to_bits().to_le_bytes()); - pos = 8; - } - Value::Date(d) => { - pos = d.to_binary(field_type, &mut buffer) as usize; - } - Value::Time(d) => { - pos = d.to_binary(field_type, &mut buffer) as usize; + 8 } + Value::Date(d) => d.to_binary(field_type, &mut buffer) as usize, + Value::Time(d) => d.to_binary(field_type, &mut buffer) as usize, Value::StringData(data) | Value::BytesData(data) => { // `bun_sql::shared::Data` is not // `Clone`, so return a `Temporary` aliasing the @@ -290,7 +286,7 @@ impl Value { Data::Temporary(bun_ptr::RawSlice::new(s)) }); } - } + }; Data::create(&buffer[0..pos]).map_err(|_| any_mysql_error::Error::OutOfMemory) }