Problem
All node:* / bun:* builtins are broken on main: require("node:path"), node:fs, node:os, etc. return empty objects or infinitely recurse in the C++ InternalModuleRegistry (createInternalModuleById → createInternalModuleById, ~10k frames → crash). This blocks the entire native test-loop — no Bun test that imports a node builtin can run.
Root cause
ResolvedSource.Tag is ABI with the C++ InternalModuleRegistry: the loader masks off InternalModuleRegistryFlag (512) and calls internalModuleRegistry()->requireId(tag & 511). So the Zig enum ids must match the InternalModuleRegistryConstants of the Bun C++ objects Home actually links.
Home links the pinned Bun build (~/Code/bun @ fd0b6f1a27 / 1.3.14, objects built Jul 7), whose codegen ResolvedSourceTag.zig has 161 builtin entries. The enum had been regenerated from a newer Bun HEAD (4982b91e3) with 182 entries — ~21 extra internal modules inserted mid-range (internal:async_context_frame, internal:async_hooks, internal:fs/binding, internal:streams/iter/*, node:stream/iter, node:zlib/iter, …). Every id past the first insertion is shifted:
| module | linked (pin) | enum was (HEAD) |
|---|---|---|
node:fs | 610 | 628 |
node:path | 619 | 637 |
node:test | 631 | 650 |
bun:test | 650 | 670 |
bun | 661 | 681 |
→ require("node:path") selected the wrong registry module → recursion.
Fix
Restore the enum verbatim from the linked codegen (~/Code/bun/build/release/codegen/ResolvedSourceTag.zig) and add a test pinning the ids so drift fails loudly at build time instead of recursing at runtime.
This undoes the id shift introduced in 496160c05.
If you're bumping the linked Bun objects to a newer HEAD: regenerate this enum from the new
build/*/codegen/ResolvedSourceTag.zigin the same change. The added test will catch a mismatch — that's the intended guardrail.
Verification (home-debug)
require("node:path").join("a","b")→a/brequire("node:fs").openSync/mkdirSync→functionrequire("node:os").platform()→darwin- decorators (bun:wrap synthetic path, unaffected) →
@log m(41)→42