Show HN: NES Contra (1987) port (ASM –> C and then C –> WebAssembly) (epoyraz.github.io)
Based on vermiceli's annotated disassembly of Contra: https://github.com/vermiceli/nes-contra-us. Thanks for the great work.
I ported it in two steps. First to C: the game logic is translated routine by routine from the 6502 assembly, and checked frame by frame against the original in the Mesen emulator. Then the C code to WebAssembly so it runs in the browser.
The cherry on top: online multiplayer, so two players can play co-op over the internet.
66 comments
[ 0.23 ms ] story [ 35.8 ms ] threadAre there any emulators out there that let you swap in higher resolution assets so a game can be freshened without a complete port?
Edit: For SNES, not NES, my bad.
The NES supports PCM audio. It was notably implemented wrong in the title screen of Double Dribble and fixed with a patch that produces clearer audio after bit reversal into the correct encoding for the hardware:
https://www.youtube.com/watch?v=Jli0RGpuZDg
The DMC is typically used for instruments that are hard to reproduce well with the other generators. Double Dribble is using the DMC for the speech, not some clever setup of the waveform generators.
https://store.steampowered.com/app/1147940/3dSen_PC
I used it to get games written in Lua running on SNES and in my own language/engine running on Dreamcast, Wii, Web and more.
You sure you're a gamer? I've been at it since about 1986.
I hadn’t heard about that - any details?
But I agree, that using an "AI" tool may be a serious temptation and thus way less new porting projects will be done with such care.
The whole thing (all banks) is more than 10,000 lines of assembly code. When I wrote assembly code for a university computer science course, it was hard to manage even 200 lines. I cannot imagine writing and managing 10,000 lines!
Impressive work, indeed. vermiceli the GOAT.
You said in another comment:
> Then, i spent some time in building a harness and collect telemetry data in Mesen. Once, i had that: i just played the game in the emulator and asked Claude Opus 5.5 to use this as verification.
Can you comment on how this verification process worked?
You'll have to forgive me for not trying to answer these questions myself by investigating the code/git history, but... I hope you understand.
Actually, I am peeking around the code a bit and it's a bit disappointing, but it's what I should have expected having tried a project like this myself with a Game Boy game. I would like to see what an AI-produced semantic (?) rewrite of a retro game would look like. That is, what a port/rewrite that wasn't so faithful/wedded to the original ROM layout or platform architecture. For example, the agent (and you, presumably) was satisfied with writing a sort of RP2C02 emulator facade instead of doing the hard work of translating the bytes into platform-agnostic graphics rendering code. So now any customization/extensions you write to the game are fundamentally constrained to the abstractions of a specific chip from the 80s.
You didn't port it at all. You had Claude do it for you.