Remove dead code from platform/darwin, webcrypto, sqlite, NodeVM, ast

Merged
RO
3mo ago
+71-351

Net -285 LOC (349 deletions, 64 insertions including the source-lint test).

Each symbol was verified with rg -w <symbol> src/ build/debug/codegen/ to have zero references outside its own definition, then confirmed by a full bun bd build and bun run rust:check-all across all 10 targets.

src/platform/darwin.rs (whole file, 210 LOC)

The entire file duplicates bun_sys::darwin: the OSLog/Signpost/Interval API and the nocancel extern block have zero callers. bun_perf (the only signpost consumer) imports bun_sys::darwin::OSLog and bun_sys::darwin::os_log::signpost::*. bun_platform is force-linked only for linux.rs's #[no_mangle] export. Also drops the now-unused bun_opaque/strum deps from bun_platform/Cargo.toml and the stale doc comment in src/sys/lib.rs that pointed here.

webcrypto C++

  • CryptoKeyHMAC::create + const-ref ctor, CryptoKeyAES::create + const-ref ctor: never called; generate/importRaw/importJwk all construct via the rvalue ctor directly.
  • JSCryptoKey::fromJS: declared, never defined, never called.
  • JSSubtleCrypto::toWrapped: only reachable via convert<IDLInterface<SubtleCrypto>>; no such call exists.
  • OpenSSLCryptoUniquePtr.h: X509Ptr/BIOPtr aliases (zero refs) and the OPENSSL_VERSION_NUMBER >= 0x30000000L block (BoringSSL defines 0x1010107f, so it never compiles, and no code references OsslParamBldPtr/OsslParamPtr/EVPKDFCtxPtr/EVPKDFPtr).
  • CommonCryptoDERUtilities.h: extraBytesNeededForEncodedLength is only called from the same TU; header decl removed, made static in the .cpp.
  • ScriptExecutionContext.h: wrapCryptoKey/unwrapCryptoKey stubs plus the commented-out virtual decls; leftover from the earlier SerializedCryptoKeyWrap removal.

sqlite / NodeVM C++

  • lazy_sqlite3.h: sqlite3_column_int / sqlite3_memory_used / sqlite3_prepare16_v3 typedef+var+define+dlsym lines (code uses sqlite3_column_int64, tracks memory via sqlite_malloc_amount, uses sqlite3_prepare_v3).
  • SQLiteSingleton::schema_versions: never read, never appended to.
  • JSStatementSync::allowBareNamedParams/allowUnknownNamedParams/rowStructure getters: members are accessed directly.
  • DOMIsoSubspaces/DOMClientIsoSubspaces::m_*subspaceForJSSQLStatementConstructor: JSSQLStatementConstructor lives in JSFunction's subspace per the static_assert in JSSQLStatement.h.
  • NodeVMGlobalObject::sigintReceived: not virtual, never called; SigintWatcher::signalAll invokes vm().notifyNeedTermination() directly.
  • NodeVMModuleRequest::specifier/importAttributes getters: toJS reads m_specifier/m_importAttributes directly.

Rust

  • bun_ast::PartTag::{JsxImport, CjsImports, ReactFastRefresh}: never assigned or compared.
  • bun_ast::flags::JSXElement::HasAnyDynamic: never inserted or tested.
  • bun_ast::import_record::Tag::Tailwind: last variant, never constructed or matched.
  • bun_ast::BindingNodeList type alias + its unused re-export in bun_js_parser::parser.
  • bun_ast::StoreAstAllocHeap::reset: callers invoke the free fn store_ast_alloc_heap::reset() directly.
  • bun_jsc::JSPromise::reject_task: sibling resolve_task has 4 callers, reject_task has zero.
  • bun_jsc::JSRuntimeType::UNDEFINED: only NOTHING is referenced.

src/js

  • readline.js: unused ObjectSetPrototypeOf primordial destructure.
  • repl.js: unused ArrayPrototypeSlice primordial destructure.
  • zlib.ts: collapse redundant ArrayBufferIsView intermediate alias.

Verification

  • bun bd builds clean
  • bun run rust:check-all passes all 10 targets (incl. aarch64-apple-darwin for the bun_platform change)
  • Smoke tests pass: web-crypto.test.ts, sqlite.test.js, node-sqlite.test.ts, zlib.test.js, transpiler.test.js
  • test/internal/source-lints/dead-symbols-platform-webcrypto-sqlite-vm.test.ts fails on main, passes on this branch

Followups (not deleted; left for review)

  • src/runtime/api/bun/h2/connection.rs:1731-1941 outbound-stream API (begin_header_block/encode_header/send_header_block/send_data/send_push_promise + transitively SendWindow::{available,consume}, Coder::{take_pending_size_update,encode}, write_table_size_update, ~215 LOC): only called from #[cfg(test)]. File carries #![allow(dead_code)] and was authored in #31584; likely intentional WIP scaffolding for migrating h2_frame_parser's outbound path.
  • src/jsc/bindings/webcrypto/*.idl (29 files, ~1055 LOC): not processed by any build step (scripts/glob-sources.ts globs only *.cpp), but #34838 edited them recently so they may be maintained as documentation.
  • src/jsc/ErrorCode.rs: Zig_ErrorCodeJSErrorObject #[no_mangle] static with zero refs in any .cpp/.h (sibling Zig_ErrorCodeParserError is declared in headers-handwritten.h; this one is not).

[review] gate passed · iteration 0 · 34 files touched

fails on main (without fix)
ASAN without fix: 3 FAILED
$ BUN_DEBUG_QUIET_LOGS=1 bun scripts/build.ts --profile=debug --quiet test "--reporter=junit" "--reporter-outfile=/tmp/mechgate.xml" test/internal/source-lints/dead-symbols-platform-webcrypto-sqlite-vm.test.ts
bun test v1.4.0 (e2a9bd907)

test/internal/source-lints/dead-symbols-platform-webcrypto-sqlite-vm.test.ts:
19 | function src(p: string): string {
20 |   return readFileSync(path.join(repoRoot, p), "utf8");
21 | }
22 | 
23 | test("bun_platform no longer declares a darwin module (duplicated bun_sys::darwin)", () => {
24 |   expect(src("src/platform/lib.rs")).not.toMatch(/pub mod darwin;/);
                                              ^
error: expect(received).not.toMatch(expected)

Expected substring or pattern: not /pub mod darwin;/
Received: "#![allow(non_snake_case, non_camel_case_types, non_upper_case_globals)]\n#![warn(unused_must_use)]\n//! Per-OS APIs that don't fit in `bun_sys` (signposts, the `sys_epoll_pwait2` export).\n\n// Android is listed alongside Linux so the `#[no_mangle]` C exports\n// (`sys_epoll_pwait2`, …) reach the linker on the `*-linux-android` targets.\n#[cfg(target_os = \"macos\")]\npub mod darwin;\n#[cfg(any(target_os = \"linux\", t
... (truncated)

release without fix: 3 FAILED
bun test v1.4.0-canary.1 (1498d7b77)

test/internal/source-lints/dead-symbols-platform-webcrypto-sqlite-vm.test.ts:
19 | function src(p: string): string {
20 |   return readFileSync(path.join(repoRoot, p), "utf8");
21 | }
22 | 
23 | test("bun_platform no longer declares a darwin module (duplicated bun_sys::darwin)", () => {
24 |   expect(src("src/platform/lib.rs")).not.toMatch(/pub mod darwin;/);
                                              ^
error: expect(received).not.toMatch(expected)

Expected substring or pattern: not /pub mod darwin;/
Received: "#![allow(non_snake_case, non_camel_case_types, non_upper_case_globals)]\n#![warn(unused_must_use)]\n//! Per-OS APIs that don't fit in `bun_sys` (signposts, the `sys_epoll_pwait2` export).\n\n// Android is listed alongside Linux so the `#[no_mangle]` C exports\n// (`sys_epoll_pwait2`, …) reach the linker on the `*-linux-android` targets.\n#[cfg(target_os = \"macos\")]\npub mod darwin;\n#[cfg(any(target_os = \"linux\", target_os = \"android\"))]\npub(crate) mod linux;\n"

      at <anonymous> (/workspace/bun/test/internal/source-lints/dead-symbols-platform-webcrypto-sqlite-vm.test.ts:24:42)
(fail) bun_platform no long
... (truncated)
passes on PR (with fix)
ASAN with fix: all passed
$ BUN_DEBUG_QUIET_LOGS=1 bun scripts/build.ts --profile=debug --quiet test "--reporter=junit" "--reporter-outfile=/tmp/mechgate.xml" test/internal/source-lints/dead-symbols-platform-webcrypto-sqlite-vm.test.ts
bun test v1.4.0 (e2a9bd907)

test/internal/source-lints/dead-symbols-platform-webcrypto-sqlite-vm.test.ts:
(pass) bun_platform no longer declares a darwin module (duplicated bun_sys::darwin) [10.05ms]
(pass) dead C++ symbols in webcrypto/sqlite/NodeVM do not reappear [23.34ms]
(pass) dead Rust symbols in ast/jsc do not reappear [14.33ms]

 3 pass
 0 fail
 3 expect() calls
Ran 3 tests across 1 file. [2.09s]
__F:0:S:0

release with fix: all passed
$ bun scripts/build.ts --profile=release
[configured] bun-profile → bun (stripped) in 733ms (unchanged)
ninja: Entering directory `/workspace/bun/build/release'
[1/139] gen generated_host_exports.rs
generated_host_exports.rs: 94 exports (host=3, lazy=10, generic=81, rust=0); 238 extern-C blocks audited
[2/139] gen cpp.rs (cppbind)
[3/139] gen JS modules (bundle-modules)
Preprocess modules (9279ms)
Bundle modules (59ms)
Postprocesss modules (259ms)
Bundle Functions (943ms)
Generate Code (32ms)

[10.59s] Bundled "src/js" for production
  2558 kb
  193 internal modules
  13 native modules
  90 internal functions across 19 files
[3/138] cargo bun_bin → libbun_rust.a (--target x86_64-unknown-linux-gnu)

  nightly-2026-07-20-x86_64-unknown-linux-gnu unchanged - rustc 1.99.0-nightly (9f36de775 2026-07-19)

   Compiling bun_core v0.0.0 (/workspace/bun/src/bun_core)
   Compiling bun_errno v0.0.0 (/workspace/bun/src/errno)
   Compiling bun_ptr v0.0.0 (/workspace/bun/src/ptr)
   Compiling bun_boringssl_sys v0.0.0 (/workspace/bun/src/boringssl_sys)
   Compiling bun_safety v0.0.0 (/workspace/bun/src/safety)
[1
... (truncated)
diff hotspot
Cargo.lock                                         |   2 -
 src/ast/import_record.rs                           |   2 -
 src/ast/lib.rs                                     |   7 +-
 src/ast/nodes.rs                                   |   6 +-
 src/js/node/readline.js                            |   1 -
 src/js/node/repl.js                                |   1 -
 src/js/node/zlib.ts                                |   3 +-
 src/js_parser/parser.rs                            |   4 +-
 src/jsc/JSPromise.rs                               |  12 --
 src/jsc/JSRuntimeType.rs                           |   1 -
 src/jsc/bindings/NodeVM.cpp                        |   5 -
 src/jsc/bindings/NodeVM.h                          |   1 -
 src/jsc/bindings/NodeVMModule.h                    |   3 -
 src/jsc/bindings/ScriptExecutionContext.h          |  16 --
 src/jsc/bindings/sqlite/JSSQLStatement.cpp         |   2 -
 src/jsc/bindings/sqlite/NodeSqlite.h               |   3 -
 src/jsc/bindings/sqlite/lazy_sqlite3.h             |  18 --
 src/jsc/bindings/webcore/DOMClientIsoSubspaces.h   |   1 -
 src/jsc/bindings/webcore/DOMIsoSubspaces.h         |   1 -
 .../webcrypto/CommonCryptoDERUtilities.cpp         |   2 +-
 .../bindings/webcrypto/CommonCryptoDERUtilities.h  |   1 -
 src/jsc/bindings/webcrypto/CryptoKeyAES.cpp        |   7 -
 src/jsc/bindings/webcrypto/CryptoKeyAES.h          |   5 -
 src/jsc/bindings/webcrypto/CryptoKeyHMAC.cpp       |   7 -
 src/jsc/bindings/webcrypto/CryptoKeyHMAC.h         |   6 -
 src/jsc/bindings/webcrypto/JSCryptoKey.h           |   2 -
 src/jsc/bindings/webcrypto/JSSubtleCrypto.cpp      |   7 -
 src/jsc/bindings/webcrypto/JSSubtleCrypto.h        |   1 -
 .../bindings/webcrypto/OpenSSLCryptoUniquePtr.h    |  13 --
 src/platform/Cargo.toml                            |   2 -
 src/platform/darwin.rs                             | 210 ---------------------
 src/platform/lib.rs                                |   4 +-
 src/sys/lib.rs                    
... (truncated)

gate history · 1 passed · 0 rejected · iteration 0

evidence per changed file
file                                        reads  edits  tests
Cargo.lock                                      0      0      0
src/ast/import_record.rs                        1      1      0
src/ast/lib.rs                                  3      3      0
src/ast/nodes.rs                                2      2      0
src/js/node/readline.js                         1      1      0
src/js/node/repl.js                             1      1      0
src/js/node/zlib.ts                             1      1      0
src/js_parser/parser.rs                         1      1      0
src/jsc/JSPromise.rs                            1      1      0
src/jsc/JSRuntimeType.rs                        1      1      0
src/jsc/bindings/NodeVM.cpp                     1      1      0
src/jsc/bindings/NodeVM.h                       1      1      0
src/jsc/bindings/NodeVMModule.h                 1      1      0
src/jsc/bindings/ScriptExecutionContext.h       2      1      0
src/jsc/bindings/sqlite/JSSQLStatement.cpp      1      1      0
src/jsc/bindings/sqlite/NodeSqlite.h            2      2      0
(+ 18 more files)