Live data from Hacker News

Show HN: Python running on the Super Nintendo (in-browser demo)

fabian-kuebler.com

1–10 of 10 posts

Show HN: Python running on the Super Nintendo (in-browser demo)

#1
MicroPython (lexer, compiler and VM) on the SNES: 3.58 MHz 65816, 56 KB Python heap, 16-bit int. The REPL runs right inside the post via EmulatorJS and also works on real hardware via flashcart.

I did this as a benchmark for Claude Fable. When the export ban hit, switching to Opus got the project stuck for three weeks; Fable came back and found the real bug in ninety minutes.

Along the way: 23 compiler bugs and 4 MicroPython bugs, each root-caused with a minimal reproducer and filed upstream.

If you run it on real hardware, I want a picture!

Show HN: Python running on the Super Nintendo (in-browser demo)
fabian-kuebler.com

Re: Show HN: Python running on the Super Nintendo (in-browser demo)

#4
post #3

That's absolutely crazy! Compiler bugs and micropython bugs??? On the other end of the cost scale right now, I'm running multiple Deepseek V4 Flash instances basically constantly practically for free (because I'm poor right now) and I'm impressed by that too.

The bug count surprised me too. Calypsi is a great compiler, but MicroPython is likely the largest program anyone has pushed through it: a huge interpreter switch, packed structs, setjmp/longjmp exception handling, far pointers everywhere. Corners like that had simply never been compiled before.

Re: Show HN: Python running on the Super Nintendo (in-browser demo)

#6
post #5

So this should be comfortably possible on GBA, yes?

Yes, definitely: the GBA is a 32-bit ARM with 256 KB of RAM and mature GCC support, so it sidesteps everything that made this hard: the 16-bit size_t, the far pointers, the barely-stress-tested compiler. The SNES was the fun target though ;)

Re: Show HN: Python running on the Super Nintendo (in-browser demo)

#7
post #5

So this should be comfortably possible on GBA, yes?

Yes, definitely: the GBA is a 32-bit ARM with 256 KB of RAM and mature GCC support, so it sidesteps everything that made this hard: the 16-bit size_t, the far pointers, the barely-stress-tested compiler. The SNES was the fun target though ;)

How do you deal with things like e.g. writing sprite bitmap data to specific locations in the VRAM from Python? Or handling the memory-mapped I/O?

Re: Show HN: Python running on the Super Nintendo (in-browser demo)

#8
post #7

Earlier quoted context omitted.

Yes, definitely: the GBA is a 32-bit ARM with 256 KB of RAM and mature GCC support, so it sidesteps everything that made this hard: the 16-bit size_t, the far pointers, the barely-stress-tested compiler. The SNES was the fun target though ;)

How do you deal with things like e.g. writing sprite bitmap data to specific locations in the VRAM from Python? Or handling the memory-mapped I/O?

Python never touches the PPU: the memory-mapped registers live entirely behind a thin C layer (_snesfb / _snesstage modules). Sprite/tile bitmap data gets packed into VRAM tile banks once at startup; at runtime Python only mutates shadow state (hardware tilemaps, an OAM shadow, a framebuf for the GUI stuff) and once per frame the C side DMAs the dirty buffers across during vblank.

Re: Show HN: Python running on the Super Nintendo (in-browser demo)

#9
post #7

Earlier quoted context omitted.

How do you deal with things like e.g. writing sprite bitmap data to specific locations in the VRAM from Python? Or handling the memory-mapped I/O?

Python never touches the PPU: the memory-mapped registers live entirely behind a thin C layer (_snesfb / _snesstage modules). Sprite/tile bitmap data gets packed into VRAM tile banks once at startup; at runtime Python only mutates shadow state (hardware tilemaps, an OAM shadow, a framebuf for the GUI stuff) and once per frame the C side DMAs the dirty buffers across during vblank.

(By the way, several of your posts seem to be getting automatically filtered. I vouched for this one; I see nothing wrong. Perhaps someone else thought it was AI-generated.)

Does MicroPython support some concept of an "extension module", at least? It would be nice to be able to load new sprites etc. from Python at runtime.

Re: Show HN: Python running on the Super Nintendo (in-browser demo)

#10
post #9

Earlier quoted context omitted.

Python never touches the PPU: the memory-mapped registers live entirely behind a thin C layer (_snesfb / _snesstage modules). Sprite/tile bitmap data gets packed into VRAM tile banks once at startup; at runtime Python only mutates shadow state (hardware tilemaps, an OAM shadow, a framebuf for the GUI stuff) and once per frame the C side DMAs the dirty buffers across during vblank.

(By the way, several of your posts seem to be getting automatically filtered. I vouched for this one; I see nothing wrong. Perhaps someone else thought it was AI-generated.) Does MicroPython support some concept of an "extension module", at least? It would be nice to be able to load new sprites etc. from Python at runtime.

(Thanks for vouching! I emailed the mods about my account. I think I tripped a filter with a clumsy submission start...)

About the sprites: loading them from Python at runtime actually works. Stage's Bank objects are plain Python bytes (2048 bytes = 16 tiles at 16x16, 4bpp) plus a palette; on first use, _snesstage.bank() converts them to SNES bitplane format and DMAs them into one of 8 VRAM slots.

On extension modules in general: MicroPython has compiled-in C "user modules" (that's what _snesfb/_snesstage are) and dynamically loadable native .mpy modules. But this needs per-architecture relocation support, and the 65816 isn't among the supported targets.