October 12, 2026 at 12:00:00 AM UTC
SMBC: NES APU synthesis and host audio output
SMBC makes sound (#35). hw/apu now keeps a per-frame write log so the synth sees mid-frame register traffic, and $4015 reads report channel status instead of the last written value. hw/apu_synth.c models the four channels the game uses: two pulses with duty, envelope, sweep and length counters; triangle with its linear counter; noise with both feedback modes. The 4-step frame sequencer free-runs at NTSC frame boundaries, and the non-linear NESdev mixer combines the channels.
Synthesis is cycle-stepped at the CPU clock (1789773 Hz) and resampled to 44.1 kHz. host/audio.c is now a lock-free SPSC ring on C11 atomics: the frontend pushes each frame's samples after smbc_frame, the SDL callback drains. Engine-driven smoke: starting a game and running 1300 frames yields 1291 audible frames of the overworld theme at a peak of 0.51 — no clipping. Twelve white-box test groups cover envelope decay and loop, length halt and clocking, sweep, the linear counter, noise modes and the mixer.
One test-data bug worth noting: 0x9f is 10011111b — d5 clear — so the halt-flag probe needed 0xbf. Reading hex bitfields by eye remains a reliable way to lie to yourself.
all entries