Track a separate IWRAM latch with known lanes and transactional updates. Sequential Thumb prefetches and IWRAM byte/halfword/word reads and writes drive only addressed lanes. Other regions and host inspection do not replace the latch. Failed instructions discard staged changes. Keep cold, refill, discontinuous-entry, IRQ, and DMA-transition history conservative. Share Thumb refill classification with nominal timing, including PC writes to fallthrough. Successful DMA and accepted machine IRQs invalidate history; failed DMA preserves it. Document source evidence, bounded scope, and remaining hardware-validation limits. Add original lane, alignment, mirror/wrap, signed/unaligned-load, mode, block-transfer, rollback, isolation, control-flow, IRQ/DMA, and nominal-cost regressions. Darwin arm64 validation: 905 workspace tests and 836 core/demo tests per debug/release profile; 39 preparation tests; native ROM windows in both profiles; ten graphics/window smoke modes; fmt, clippy, and rustdoc. Public ARM, Thumb, memory, and BIOS reports remain identical to prior passing reports and between profiles.
5.4 KiB
IWRAM Thumb bus history
Finding
Internal work RAM (IWRAM) retains its own bus lanes. A previous CPU load result is not a universal replacement. An IWRAM byte, halfword, or word access updates only the addressed lanes of that latch. A Thumb fetch updates one halfword. Reads and writes elsewhere do not replace the IWRAM latch. This distinction matters when Thumb code reads another memory region before an unused-memory read.
For sequential Thumb execution at P, the fetch at P+4 updates:
- Bits 0–15 when P is word-aligned.
- Bits 16–31 when P has only halfword alignment.
The other halfword retains its previous IWRAM value. Without intervening IWRAM data accesses, consecutive fetches produce GBATEK's usual P+2/P+4 combination. Using current bytes at P+2 would lose observed history and ignore data-access changes.
Evidence
- GBATEK documents the two Thumb IWRAM lanes and warns about overwritten history.
- mGBA issue 1575 reports hardware-based alignment expectations and read/write effects on IWRAM open bus.
- ares IWRAM access implementation retains separate IWRAM lanes for byte, halfword, and word reads and writes. Its bus implementation distinguishes this latch from the general data bus and debugger access.
- jgenesis issue 676 identifies failures after byte/halfword reads from other regions. The correction at fab6e2cc adds a separate IWRAM latch. The commit reports that its openbuster tests pass. That report is upstream evidence, not a test run by this project.
These sources support a separate lane-retaining latch, rather than a copy of the last CPU destination register. Our implementation and synthetic programs are original. No external source code or test ROM was imported. No physical-hardware measurement or external emulator differential run was performed here.
Bounded implementation
memory/iwram_bus.rs records lane values and a known-bit mask during consecutive Thumb instructions in IWRAM.
Before execution, the mapped PC+4 halfword updates its addressed lanes.
During execution, successful IWRAM bus reads and writes update the staged lanes at their actual aligned addresses and widths.
The latch sees raw bus data before CPU load rotation and sign extension.
Other-region accesses and host inspection do not change it.
A completed sequential instruction commits the staged history for the next exact virtual PC. A failed instruction discards all staged changes and preserves the last committed history. The existing whole-instruction diagnostic policy still applies; this is not hardware data-abort behavior. All unused-memory reads within one instruction use its entry snapshot.
The model starts with unknown lanes. An unused-memory load requires a complete known word, even for a narrower load. Ordinary instructions and mapped data accesses can establish history without requiring a prior complete word. Consecutive halfword fetches or an IWRAM word access can make every lane known. Missing lookahead and 16 MiB region-crossing fetches retain diagnostics.
Successful branches and other refill instructions invalidate continuation history, even when the target equals the next sequential address. The existing Thumb timing classifier identifies these refills for both timed and untimed CPU stepping. Execution outside Thumb IWRAM also ends this bounded history sequence. An accepted machine IRQ and each successful DMA unit invalidate the history. Failed DMA units preserve it. The implementation does not guess refill or DMA latch contents.
This is not a full IWRAM bus model across all CPU states. ARM access history, refill fetches, and DMA-to-CPU ordering remain incomplete. It is not a persistent instruction pipeline. Self-modifying instruction execution and exact per-access device timing remain unverified.
Original regression coverage
- Both code alignments, IWRAM mirrors, and physical RAM wrap.
- Captured halfwords that remain unchanged by host inspection or later host writes.
- Byte/halfword/word data reads and writes, sign extension, load rotation, and all processor modes.
- Other-region accesses that leave IWRAM lanes unchanged.
- Multiple-register transfers, final-word retention, and writeback.
- Unknown lanes, establishment of known history, staged-access rollback, and retry.
- Taken and untaken branches, PC writes to fallthrough, discontinuities, IRQ entry, and DMA success/failure.
- Equal timed/untimed CPU results and unchanged nominal data/device costs.
Validation result
The sequential-history regressions reproduced the old unsupported-read failures before implementation. Workspace and core/demo tests pass on Darwin arm64 in debug and release builds. Formatting, lint checks, rustdoc, preparation tests, native ROM windows, and graphics smoke modes also pass. Public ARM, Thumb, memory, and BIOS reports match their previous passing results exactly. Debug and release reports also match for the same fixture paths.
Those public suites remain regression checks, not independent IWRAM-history conformance tests.