007. CPU 总线 ROM
将 FakeROM 映射到 CPU 程序 ROM 地址范围。
第 7 / 356 · tests/chapter_01_cpu/test_007_cpu_bus_rom.py
需要更新的文件
emulator/bus/cpu_bus.py位置
class CpuBus参考
https://en.wikibooks.org/wiki/NES_Programming/Memory_Map此步骤存在的原因
CPU 地址 $8000-$FFFF 必须从本地 FakeROM 偏移 $0000-$7FFF 中取出程序字节。这一转换由总线负责;内存设备只能看到本地偏移。
完整示例实现
from dataclasses import dataclass, field
from typing import Optional
from emulator.memory.memory_device import MemoryDevice
from emulator.memory.ram import RAM
@dataclass
class CpuBus:
program_rom: Optional[MemoryDevice] = None
ram: RAM = field(default_factory=RAM)
def read(self, addr: int) -> int:
if 0x0000 <= addr <= 0x1FFF:
return self.ram.read(addr & 0x07FF)
if 0x8000 <= addr <= 0xFFFF:
if self.program_rom is None:
raise ValueError("No program ROM attached")
return self.program_rom.read(addr - 0x8000)
raise ValueError(f"Unsupported CPU bus read: {addr:04X}")
def write(self, addr: int, value: int) -> None:
if 0x0000 <= addr <= 0x1FFF:
self.ram.write(addr & 0x07FF, value)
return
raise ValueError(f"Unsupported CPU bus write: {addr:04X}")重要不变量
rom_offset = cpu_address - 0x8000常见误解
复位向量所在的 CPU 地址 $FFFC 并不是 FakeROM 中索引 $FFFC 的位置。经过总线转换后,它对应本地索引 $7FFC。
范围之外
- CPU 复位
- 真实卡带解析和映射器
- 对卡带空间的写入
运行本课
uv run pytest tests/chapter_01_cpu/test_007_cpu_bus_rom.py -v