retro-silicon

Components

memory/cache

A read cache for memory/sdram's byte port, in front of a memory that reads whole 8-byte lines

Board verified Sim: passing (6 passed). Used by Nintendo Entertainment System. Source.

BoardStateRun
TUL PYNQ-Z2verified2026-10-30, at 0a03732

Verified: the latest run on that board of a system using it passed every test, and the component hasn't changed since. Stale: it has changed since that run.

README

A read cache for memory/sdram’s byte port, in front of a memory that reads whole 8-byte lines, such as memory/axi-bridge (its rdata_d). For memory far slower to answer than a system’s cycle: DDR behind a processor, where one read through the Zynq-7000’s HP port takes longer than an NES CPU cycle can wait.

Module mem_cache.

Ports

PortDirWidthMeaning
clk, rstin1Clock; synchronous reset (the cache empties)
req, we, addr, wdatain1, 1, AW, 8The user’s access, held until ack; req may still be high while ack is
ack, rdata, rdata_wout1, 8, 32One-clock pulse when it’s done; a read’s byte, and the 32-bit half of its line, with it
readyout1Accesses may start
d_req, d_we, d_addr, d_wdataout1, 1, AW, 8The memory’s access: a line’s first byte for a read, the byte for a write
d_ack, d_rdata, d_readyin1, 64, 1The memory’s acknowledge, a read’s whole line (byte 0 in bits 7-0), and its ready
hits, misses, prefetchesout32 eachSince reset: reads answered from the cache (or the prefetch buffer), reads that went to the memory, lines prefetched

Parameters

ParameterDefaultMeaning
AW23Byte address width
IDX122^IDX lines: 32 KB
PREFETCH1Fetch the next line after a miss, and after the first read of a prefetched line

Status

Sim tests (AW = 16, IDX = 6), with and without prefetch, behind a memory that answers in 2 to 15 clocks and checks that each access’s address, write enable and data hold from its request to its ack:

The bench caught four bugs planted in it: a hit that ignores the tag, a write that leaves the cached line stale, a write that leaves the prefetch buffer stale, and the buffer going in under the wrong line. It also caught one real bug: the first read of a prefetched line could start the next prefetch while one was still out, changing the address of the read in flight. A 256 KB MMC1 ROM in the NES’s AXI sim then hung, as on the PYNQ-Z2.

In systems/nes (nes_axi), in front of the PYNQ-Z2’s DDR3: without prefetch, the NES waits no clocks for memory in its HDMI runs, where without the cache it waited 117,000 a frame.