Repository navigation
Preserve AI FIFO addresses and RDRAM memory mapping in rollback states - #213
Conversation
Synchronize RDRAM memory mapping after rollbackUnderlying issueMupen uses memory handlers to determine how reads and writes to each emulated N64 address range should behave. During boot, the N64 IPL configures the RDRAM chips through their mode registers. Certain configurations cause Mupen to install a special corrupted-RDRAM read handler. The core tracks the currently installed handler separately from the RDRAM register values. During normal execution, writing an RDRAM mode register updates both:
Savestate loading restores the registers through direct assignment, bypassing the normal register-write side effects. A rollback could therefore produce an inconsistent state: This is particularly relevant during early boot, while the IPL is configuring RDRAM. A stale handler could make memory reads behave differently from what the restored registers specify, potentially causing incorrect execution or a black-screen startup stall. FixAfter all RDRAM registers have been restored, rollback loading now recalculates the required memory mapping from those registers. If the calculated state differs from the currently installed handler, the correct normal or corrupted-RDRAM handler is installed. The same synchronization function is also used by normal RDRAM mode-register writes, ensuring that both paths derive the mapping consistently. Implementation approachThe memory-handler selection is reconstructed rather than serialized because it is derived emulator bookkeeping, not independent N64 hardware state. This ensures:
|
NOTE: These are really two separate fixes in one. This first writeup describes the first problem and fix. The next comment describes a similarly-related problem and fix.
Summary
This fixes a rollback-state serialization bug that could cause incorrect audio to play after a rollback, including Smash Remix unexpectedly playing the “INCREDIBLE!” announcer sound during boot.
Rollback savestates now preserve and restore both AI DMA FIFO addresses instead of reconstructing them from the current AI register state.
Underlying issue
The N64 Audio Interface maintains a two-entry DMA FIFO. Each entry contains several pieces of state:
The existing savestate format stored the FIFO lengths and durations, but did not store their corresponding RDRAM addresses.
When loading a savestate, both missing addresses were reconstructed using the current
AI_DRAM_ADDR_REGvalue:That register value is not necessarily the address associated with either saved FIFO entry. In particular, the second queued DMA may point somewhere different from the currently visible register value.
After a rollback, the emulator could therefore retain the saved transfer lengths and timing while reading audio data from the wrong location in RDRAM. This could produce a pop, unrelated PCM data, or—as observed with Smash Remix—a valid but completely unintended announcer sample.
This also explains several characteristics of the failure:
.krecreplay would not necessarily reproduce it because ordinary playback does not recreate the same network rollback and savestate-load sequence.Fix
Rollback savestates now store an additional eight bytes:
When restoring a new rollback savestate, both addresses are copied back into their original FIFO entries. This keeps each FIFO entry’s address, length, and duration synchronized across rollback.
A new rollback-state header flag indicates that the saved state contains these addresses.