wr64-decomp
Wave Race 64 turned back into C that compiles, with Nintendo’s own compiler, to the exact same ROM.
make toolchain && make init # with your own US Rev 1 ROM as baserom.us.rev1.z64- status
- live 1,302 of 1,348 functions matched (96.6%)
- stack
- C / IDO 5.3 / splat / MIPS binutils / Python
- source
- github.com/nickallevato/wr64-decomp ↗
- links
- build steps ↗ · FORK.md, the milestones ↗ · upstream: LLONSIT/Wave-Race-64 ↗
- since
What it is
Wave Race 64 shipped in 1996 as a compiled MIPS binary. This turns the binary back into C source, and that source, compiled with the same compiler Nintendo used (IDO 5.3), produces the same ROM down to the last byte. Every build ends with a SHA-1 check against the cartridge, so one wrong instruction fails it.
It’s a fork of LLONSIT/Wave-Race-64, which did the groundwork: the ROM split, the build system and the first nine hundred or so functions. This fork is written with Claude, and upstream doesn’t take AI-generated code, so it runs independently and nothing goes back.
Where it stands
| Area | What’s in it | Matched |
|---|---|---|
libultra | Nintendo’s N64 OS library | 157 / 157 |
| other | handwritten assembly, loose segments | 55 / 55 |
audio | sequence and sound playback | 227 / 228 |
overlays | courses and menu screens | 148 / 151 |
codeseg | HUD, menus, text, popups, fades | 210 / 219 |
sys | boot, threads, memory | 35 / 37 |
game | race logic, riders, camera, water | 470 / 501 |
| total | 1,302 / 1,348 |
The functions that don’t match yet keep a readable C attempt beside the assembly, with a note on what still differs. make NON_MATCHING=1 builds with those, so most of the game can already be read and changed as C. The ROM differs then, which is expected.
What it’s for
A matching tree is the floor everything else stands on: how the water simulation really works, bug fixes, a native port, and mods well past what patching a binary allows. The one I want is in 64 riders in Wave Race 64, which stopped short of growing the game’s four-rider arrays from the inside because the decomp wasn’t far enough along.
After the bytes comes the half of the job the hash can’t judge: names, structs, documentation. The hash will say when the bytes are right. Nothing will say when the names are. That argument is the bytes don’t remember the names.
You need your own copy of the game, US Rev 1, .z64. It isn’t in the repo and never will be.
writing about it
2the bytes don't remember the names
Here is a line from the Wave Race 64 source: if (1) {} // FAKE: gives the original's i * 19 (shifts, not a multu by a hoisted 19) It does nothing. …
64 riders in Wave Race 64
Wave Race 64 puts four jet skis on the water: you and three computer riders. I want to turn it into a 64-rider elimination race, where everyone starts …