[Mem] New handlers using if-range checks instead of switch
This commit is contained in:
@@ -36,10 +36,25 @@
|
||||
#define CART_REGION_END_1_2 0x1FBFFFFF
|
||||
#define CART_REGION_END_2_1 0x05FFFFFF
|
||||
#define CART_REGION_END_2_2 0x0FFFFFFF
|
||||
#define RSP_MEM_REGION_END 0x0403FFFF
|
||||
#define AI_REGION_START 0x04500000
|
||||
#define AI_REGION_END 0x045FFFFF
|
||||
#define MMIO_REGION_START_1 0x04040000
|
||||
#define MMIO_REGION_START_2 0x04300000
|
||||
#define MMIO_REGION_END_1 0x041FFFFF
|
||||
#define MMIO_REGION_END_2 0x048FFFFF
|
||||
#define UNUSED_START_1 0x00800000
|
||||
#define UNUSED_END_1 0x03EFFFFF
|
||||
#define UNUSED_START_2 0x04200000
|
||||
#define UNUSED_END_2 0x042FFFFF
|
||||
#define UNUSED_START_3 0x04900000
|
||||
#define UNUSED_END_3 0x04FFFFFF
|
||||
#define UNUSED_START_4 0x1FC00800
|
||||
#define UNUSED_END_4 0xFFFFFFFF
|
||||
|
||||
#define RDRAM_REGION RDRAM_REGION_START ... RDRAM_REGION_END
|
||||
#define RSP_MEM_REGION DMEM_REGION_START ... 0x0403FFFF
|
||||
#define MMIO_REGION 0x04040000 ... 0x041FFFFF : case 0x04300000 ... 0x048FFFFF
|
||||
#define RSP_MEM_REGION DMEM_REGION_START ... RSP_MEM_REGION_END
|
||||
#define MMIO_REGION MMIO_REGION_START_1 ... MMIO_REGION_END_1 : case MMIO_REGION_START_2 ... MMIO_REGION_END_2
|
||||
#define SP_REGION 0x04040000 ... 0x040FFFFF
|
||||
#define DP_CMD_REGION 0x04100000 ... 0x041FFFFF
|
||||
#define RSP_REGION 0x04040000 ... 0x040FFFFF
|
||||
|
||||
@@ -189,174 +189,144 @@ template <>
|
||||
u8 Mem::Read(Registers ®s, const u32 paddr) {
|
||||
const SI &si = mmio.si;
|
||||
|
||||
switch (paddr) {
|
||||
case RDRAM_REGION:
|
||||
return mmio.rdp.ReadRDRAM<u8>(paddr);
|
||||
case RSP_MEM_REGION:
|
||||
{
|
||||
if(Util::IsInsideRange(paddr, RDRAM_REGION_START, RDRAM_REGION_END)) return mmio.rdp.ReadRDRAM<u8>(paddr);
|
||||
if(Util::IsInsideRange(paddr, DMEM_REGION_START, RSP_MEM_REGION_END)) {
|
||||
const auto &src = paddr & 0x1000 ? mmio.rsp.imem : mmio.rsp.dmem;
|
||||
return src[BYTE_ADDRESS(paddr & 0xfff)];
|
||||
}
|
||||
case REGION_CART:
|
||||
return mmio.pi.BusRead<u8, false>(paddr);
|
||||
case 0x04040000 ... 0x040FFFFF:
|
||||
case 0x04100000 ... 0x041FFFFF:
|
||||
case 0x04600000 ... 0x048FFFFF:
|
||||
case 0x04300000 ... 0x044FFFFF:
|
||||
panic("MMIO Read<u8>!\n");
|
||||
case AI_REGION:
|
||||
{
|
||||
|
||||
if(Util::IsInsideRange(paddr, CART_REGION_START_2_1, CART_REGION_END_1_2)) return mmio.pi.BusRead<u8, false>(paddr);
|
||||
if(Util::IsInsideRange(paddr, AI_REGION_START, AI_REGION_END)) {
|
||||
const u32 w = mmio.ai.Read(paddr & ~3);
|
||||
const int offs = 3 - (paddr & 3);
|
||||
return w >> offs * 8 & 0xff;
|
||||
}
|
||||
case PIF_ROM_REGION:
|
||||
return si.pif.bootrom[BYTE_ADDRESS(paddr) - PIF_ROM_REGION_START];
|
||||
case PIF_RAM_REGION:
|
||||
return si.pif.ram[paddr - PIF_RAM_REGION_START];
|
||||
case 0x00800000 ... 0x03EFFFFF: // unused
|
||||
case 0x04200000 ... 0x042FFFFF: // unused
|
||||
case 0x04900000 ... 0x04FFFFFF: // unused
|
||||
case 0x1FC00800 ... 0xFFFFFFFF: // unused
|
||||
return 0;
|
||||
default:
|
||||
|
||||
if(Util::IsInsideRange(paddr, MMIO_REGION_START_1, MMIO_REGION_END_1) ||
|
||||
Util::IsInsideRange(paddr, MMIO_REGION_START_2, MMIO_REGION_END_2)) panic("MMIO Read<u8>!");
|
||||
|
||||
if(Util::IsInsideRange(paddr, PIF_ROM_REGION_START, PIF_ROM_REGION_END)) return si.pif.bootrom[BYTE_ADDRESS(paddr) - PIF_ROM_REGION_START];
|
||||
if(Util::IsInsideRange(paddr, PIF_RAM_REGION_START, PIF_RAM_REGION_END)) return si.pif.ram[paddr - PIF_RAM_REGION_START];
|
||||
if(Util::IsInsideRange(paddr, UNUSED_START_1, UNUSED_END_1) || // unused
|
||||
Util::IsInsideRange(paddr, UNUSED_START_2, UNUSED_END_2) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_3, UNUSED_END_3) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_4, UNUSED_END_4)) return 0;
|
||||
|
||||
panic("Unimplemented 8-bit read at address {:08X} (PC = {:016X})", paddr, (u64)regs.pc);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
template <>
|
||||
u16 Mem::Read(Registers ®s, const u32 paddr) {
|
||||
const SI &si = mmio.si;
|
||||
|
||||
switch (paddr) {
|
||||
case RDRAM_REGION:
|
||||
return mmio.rdp.ReadRDRAM<u16>(paddr);
|
||||
case RSP_MEM_REGION:
|
||||
{
|
||||
if(Util::IsInsideRange(paddr, RDRAM_REGION_START, RDRAM_REGION_END)) return mmio.rdp.ReadRDRAM<u16>(paddr);
|
||||
if(Util::IsInsideRange(paddr, DMEM_REGION_START, RSP_MEM_REGION_END)) {
|
||||
const auto &src = paddr & 0x1000 ? mmio.rsp.imem : mmio.rsp.dmem;
|
||||
return Util::ReadAccess<u16>(src, HALF_ADDRESS(paddr & 0xfff));
|
||||
}
|
||||
case MMIO_REGION:
|
||||
return mmio.Read(paddr);
|
||||
case REGION_CART:
|
||||
return mmio.pi.BusRead<u16, false>(paddr);
|
||||
case PIF_ROM_REGION:
|
||||
return Util::ReadAccess<u16>(si.pif.bootrom, HALF_ADDRESS(paddr) - PIF_ROM_REGION_START);
|
||||
case PIF_RAM_REGION:
|
||||
return std::byteswap(Util::ReadAccess<u16>(si.pif.ram, paddr - PIF_RAM_REGION_START));
|
||||
case 0x00800000 ... 0x03EFFFFF:
|
||||
case 0x04200000 ... 0x042FFFFF:
|
||||
case 0x04900000 ... 0x04FFFFFF:
|
||||
case 0x1FC00800 ... 0xFFFFFFFF:
|
||||
return 0;
|
||||
default:
|
||||
|
||||
if(Util::IsInsideRange(paddr, CART_REGION_START_2_1, CART_REGION_END_1_2)) return mmio.pi.BusRead<u16, false>(paddr);
|
||||
if(Util::IsInsideRange(paddr, MMIO_REGION_START_1, MMIO_REGION_END_1) ||
|
||||
Util::IsInsideRange(paddr, MMIO_REGION_START_2, MMIO_REGION_END_2)) return mmio.Read(paddr);
|
||||
if(Util::IsInsideRange(paddr, PIF_ROM_REGION_START, PIF_ROM_REGION_END)) return Util::ReadAccess<u16>(si.pif.bootrom, HALF_ADDRESS(paddr) - PIF_ROM_REGION_START);
|
||||
if(Util::IsInsideRange(paddr, PIF_RAM_REGION_START, PIF_RAM_REGION_END)) return std::byteswap(Util::ReadAccess<u16>(si.pif.ram, paddr - PIF_RAM_REGION_START));
|
||||
if(Util::IsInsideRange(paddr, UNUSED_START_1, UNUSED_END_1) || // unused
|
||||
Util::IsInsideRange(paddr, UNUSED_START_2, UNUSED_END_2) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_3, UNUSED_END_3) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_4, UNUSED_END_4)) return 0;
|
||||
|
||||
panic("Unimplemented 16-bit read at address {:08X} (PC = {:016X})", paddr, (u64)regs.pc);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
template <>
|
||||
u32 Mem::Read(Registers ®s, const u32 paddr) {
|
||||
const SI &si = mmio.si;
|
||||
|
||||
switch (paddr) {
|
||||
case RDRAM_REGION:
|
||||
return mmio.rdp.ReadRDRAM<u32>(paddr);
|
||||
case RSP_MEM_REGION:
|
||||
{
|
||||
if(Util::IsInsideRange(paddr, RDRAM_REGION_START, RDRAM_REGION_END)) return mmio.rdp.ReadRDRAM<u32>(paddr);
|
||||
if(Util::IsInsideRange(paddr, DMEM_REGION_START, RSP_MEM_REGION_END)) {
|
||||
const auto &src = paddr & 0x1000 ? mmio.rsp.imem : mmio.rsp.dmem;
|
||||
return Util::ReadAccess<u32>(src, paddr & 0xfff);
|
||||
}
|
||||
case MMIO_REGION:
|
||||
return mmio.Read(paddr);
|
||||
case REGION_CART:
|
||||
return mmio.pi.BusRead<u32, false>(paddr);
|
||||
case PIF_ROM_REGION:
|
||||
return Util::ReadAccess<u32>(si.pif.bootrom, paddr - PIF_ROM_REGION_START);
|
||||
case PIF_RAM_REGION:
|
||||
return std::byteswap(Util::ReadAccess<u32>(si.pif.ram, paddr - PIF_RAM_REGION_START));
|
||||
case 0x00800000 ... 0x03FFFFFF:
|
||||
case 0x04200000 ... 0x042FFFFF:
|
||||
case 0x04900000 ... 0x04FFFFFF:
|
||||
case 0x1FC00800 ... 0xFFFFFFFF:
|
||||
return 0;
|
||||
default:
|
||||
|
||||
if(Util::IsInsideRange(paddr, CART_REGION_START_2_1, CART_REGION_END_1_2)) return mmio.pi.BusRead<u32, false>(paddr);
|
||||
if(Util::IsInsideRange(paddr, MMIO_REGION_START_1, MMIO_REGION_END_1) ||
|
||||
Util::IsInsideRange(paddr, MMIO_REGION_START_2, MMIO_REGION_END_2)) return mmio.Read(paddr);
|
||||
|
||||
if(Util::IsInsideRange(paddr, PIF_ROM_REGION_START, PIF_ROM_REGION_END)) return Util::ReadAccess<u32>(si.pif.bootrom, paddr - PIF_ROM_REGION_START);
|
||||
if(Util::IsInsideRange(paddr, PIF_RAM_REGION_START, PIF_RAM_REGION_END)) return std::byteswap(Util::ReadAccess<u32>(si.pif.ram, paddr - PIF_RAM_REGION_START));
|
||||
if(Util::IsInsideRange(paddr, UNUSED_START_1, UNUSED_END_1) || // unused
|
||||
Util::IsInsideRange(paddr, UNUSED_START_2, UNUSED_END_2) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_3, UNUSED_END_3) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_4, UNUSED_END_4)) return 0;
|
||||
|
||||
panic("Unimplemented 32-bit read at address {:08X} (PC = {:016X})", paddr, (u64)regs.pc);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
template <>
|
||||
u64 Mem::Read(Registers ®s, const u32 paddr) {
|
||||
const SI &si = mmio.si;
|
||||
|
||||
switch (paddr) {
|
||||
case RDRAM_REGION:
|
||||
return mmio.rdp.ReadRDRAM<u64>(paddr);
|
||||
case RSP_MEM_REGION:
|
||||
{
|
||||
if(Util::IsInsideRange(paddr, RDRAM_REGION_START, RDRAM_REGION_END)) return mmio.rdp.ReadRDRAM<u64>(paddr);
|
||||
if(Util::IsInsideRange(paddr, DMEM_REGION_START, RSP_MEM_REGION_END)) {
|
||||
const auto &src = paddr & 0x1000 ? mmio.rsp.imem : mmio.rsp.dmem;
|
||||
return Util::ReadAccess<u64>(src, paddr & 0xfff);
|
||||
}
|
||||
case MMIO_REGION:
|
||||
return mmio.Read(paddr);
|
||||
case REGION_CART:
|
||||
return mmio.pi.BusRead<u64, false>(paddr);
|
||||
case PIF_ROM_REGION:
|
||||
return Util::ReadAccess<u64>(si.pif.bootrom, paddr - PIF_ROM_REGION_START);
|
||||
case PIF_RAM_REGION:
|
||||
return std::byteswap(Util::ReadAccess<u64>(si.pif.ram, paddr - PIF_RAM_REGION_START));
|
||||
case 0x00800000 ... 0x03EFFFFF:
|
||||
case 0x04200000 ... 0x042FFFFF:
|
||||
case 0x04900000 ... 0x04FFFFFF:
|
||||
case 0x1FC00800 ... 0xFFFFFFFF:
|
||||
|
||||
if(Util::IsInsideRange(paddr, CART_REGION_START_2_1, CART_REGION_END_1_2)) return mmio.pi.BusRead<u64, false>(paddr);
|
||||
if(Util::IsInsideRange(paddr, MMIO_REGION_START_1, MMIO_REGION_END_1) ||
|
||||
Util::IsInsideRange(paddr, MMIO_REGION_START_2, MMIO_REGION_END_2)) return mmio.Read(paddr);
|
||||
|
||||
if(Util::IsInsideRange(paddr, PIF_ROM_REGION_START, PIF_ROM_REGION_END)) return Util::ReadAccess<u64>(si.pif.bootrom, paddr - PIF_ROM_REGION_START);
|
||||
if(Util::IsInsideRange(paddr, PIF_RAM_REGION_START, PIF_RAM_REGION_END)) return std::byteswap(Util::ReadAccess<u64>(si.pif.ram, paddr - PIF_RAM_REGION_START));
|
||||
if(Util::IsInsideRange(paddr, UNUSED_START_1, UNUSED_END_1) || // unused
|
||||
Util::IsInsideRange(paddr, UNUSED_START_2, UNUSED_END_2) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_3, UNUSED_END_3) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_4, UNUSED_END_4)) return 0;
|
||||
|
||||
panic("Unimplemented 64-bit read at address {:08X} (PC = {:016X})", paddr, (u64)regs.pc);
|
||||
return 0;
|
||||
default:
|
||||
panic("Unimplemented 32-bit read at address {:08X} (PC = {:016X})", paddr, (u64)regs.pc);
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
template <>
|
||||
void Mem::WriteInterpreter<u8>(Registers ®s, u32 paddr, u32 val) {
|
||||
SI &si = mmio.si;
|
||||
|
||||
switch (paddr) {
|
||||
case RDRAM_REGION:
|
||||
mmio.rdp.WriteRDRAM<u8>(paddr, val);
|
||||
break;
|
||||
case RSP_MEM_REGION:
|
||||
{
|
||||
if(Util::IsInsideRange(paddr, RDRAM_REGION_START, RDRAM_REGION_END)) { mmio.rdp.WriteRDRAM<u8>(paddr, val); return; }
|
||||
if(Util::IsInsideRange(paddr, DMEM_REGION_START, RSP_MEM_REGION_END)) {
|
||||
val = val << (8 * (3 - (paddr & 3)));
|
||||
auto &dest = paddr & 0x1000 ? mmio.rsp.imem : mmio.rsp.dmem;
|
||||
paddr = (paddr & 0xFFF) & ~3;
|
||||
Util::WriteAccess<u32>(dest, paddr, val);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case REGION_CART:
|
||||
|
||||
if(Util::IsInsideRange(paddr, CART_REGION_START_2_1, CART_REGION_END_1_2)) {
|
||||
trace("BusWrite<u8> @ {:08X} = {:02X}", paddr, val);
|
||||
mmio.pi.BusWrite<u8, false>(paddr, val);
|
||||
break;
|
||||
case MMIO_REGION:
|
||||
panic("MMIO Write<u8>!");
|
||||
case PIF_RAM_REGION:
|
||||
return;
|
||||
}
|
||||
|
||||
if(Util::IsInsideRange(paddr, MMIO_REGION_START_1, MMIO_REGION_END_1) ||
|
||||
Util::IsInsideRange(paddr, MMIO_REGION_START_2, MMIO_REGION_END_2)) panic("MMIO Write<u8>!");
|
||||
|
||||
if(Util::IsInsideRange(paddr, PIF_RAM_REGION_START, PIF_RAM_REGION_END)) {
|
||||
val = val << (8 * (3 - (paddr & 3)));
|
||||
paddr = (paddr - PIF_RAM_REGION_START) & ~3;
|
||||
Util::WriteAccess<u32>(si.pif.ram, paddr, std::byteswap(val));
|
||||
si.pif.ProcessCommands(*this);
|
||||
break;
|
||||
case 0x00800000 ... 0x03EFFFFF:
|
||||
case 0x04200000 ... 0x042FFFFF:
|
||||
case 0x04900000 ... 0x04FFFFFF:
|
||||
case PIF_ROM_REGION:
|
||||
case 0x1FC00800 ... 0x7FFFFFFF:
|
||||
case 0x80000000 ... 0xFFFFFFFF:
|
||||
break;
|
||||
default:
|
||||
panic("Unimplemented 8-bit write at address {:08X} with value {:02X} (PC = {:016X})", paddr, val,
|
||||
(u64)regs.pc);
|
||||
return;
|
||||
}
|
||||
|
||||
if(Util::IsInsideRange(paddr, UNUSED_START_1, UNUSED_END_1) || // unused
|
||||
Util::IsInsideRange(paddr, UNUSED_START_2, UNUSED_END_2) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_3, UNUSED_END_3) ||
|
||||
Util::IsInsideRange(paddr, PIF_ROM_REGION_START, PIF_ROM_REGION_END) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_4, UNUSED_END_4)) return;
|
||||
|
||||
panic("Unimplemented 8-bit write at address {:08X} with value {:02X} (PC = {:016X})", paddr, val, (u64)regs.pc);
|
||||
}
|
||||
|
||||
#ifndef __aarch64__
|
||||
@@ -377,41 +347,39 @@ template <>
|
||||
void Mem::WriteInterpreter<u16>(Registers ®s, u32 paddr, u32 val) {
|
||||
SI &si = mmio.si;
|
||||
|
||||
switch (paddr) {
|
||||
case RDRAM_REGION:
|
||||
mmio.rdp.WriteRDRAM<u16>(paddr, val);
|
||||
break;
|
||||
case RSP_MEM_REGION:
|
||||
{
|
||||
if(Util::IsInsideRange(paddr, RDRAM_REGION_START, RDRAM_REGION_END)) { mmio.rdp.WriteRDRAM<u16>(paddr, val); return; }
|
||||
if(Util::IsInsideRange(paddr, DMEM_REGION_START, RSP_MEM_REGION_END)) {
|
||||
val = val << (16 * !(paddr & 2));
|
||||
auto &dest = paddr & 0x1000 ? mmio.rsp.imem : mmio.rsp.dmem;
|
||||
paddr = (paddr & 0xFFF) & ~3;
|
||||
Util::WriteAccess<u32>(dest, paddr, val);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case REGION_CART:
|
||||
|
||||
if(Util::IsInsideRange(paddr, CART_REGION_START_2_1, CART_REGION_END_1_2)) {
|
||||
trace("BusWrite<u8> @ {:08X} = {:04X}", paddr, val);
|
||||
mmio.pi.BusWrite<u16, false>(paddr, val);
|
||||
break;
|
||||
case MMIO_REGION:
|
||||
panic("MMIO Write<u16>!");
|
||||
case PIF_RAM_REGION:
|
||||
return;
|
||||
}
|
||||
|
||||
if(Util::IsInsideRange(paddr, MMIO_REGION_START_1, MMIO_REGION_END_1) ||
|
||||
Util::IsInsideRange(paddr, MMIO_REGION_START_2, MMIO_REGION_END_2)) panic("MMIO Write<u16>!");
|
||||
|
||||
if(Util::IsInsideRange(paddr, PIF_RAM_REGION_START, PIF_RAM_REGION_END)) {
|
||||
val = val << (16 * !(paddr & 2));
|
||||
paddr &= ~3;
|
||||
Util::WriteAccess<u32>(si.pif.ram, paddr - PIF_RAM_REGION_START, std::byteswap(val));
|
||||
si.pif.ProcessCommands(*this);
|
||||
break;
|
||||
case 0x00800000 ... 0x03EFFFFF:
|
||||
case 0x04200000 ... 0x042FFFFF:
|
||||
case 0x04900000 ... 0x04FFFFFF:
|
||||
case PIF_ROM_REGION:
|
||||
case 0x1FC00800 ... 0x7FFFFFFF:
|
||||
case 0x80000000 ... 0xFFFFFFFF:
|
||||
break;
|
||||
default:
|
||||
panic("Unimplemented 16-bit write at address {:08X} with value {:04X} (PC = {:016X})", paddr, val,
|
||||
(u64)regs.pc);
|
||||
return;
|
||||
}
|
||||
|
||||
if(Util::IsInsideRange(paddr, UNUSED_START_1, UNUSED_END_1) || // unused
|
||||
Util::IsInsideRange(paddr, UNUSED_START_2, UNUSED_END_2) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_3, UNUSED_END_3) ||
|
||||
Util::IsInsideRange(paddr, PIF_ROM_REGION_START, PIF_ROM_REGION_END) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_4, UNUSED_END_4)) return;
|
||||
|
||||
panic("Unimplemented 16-bit write at address {:08X} with value {:04X} (PC = {:016X})", paddr, val, (u64)regs.pc);
|
||||
}
|
||||
|
||||
#ifndef __aarch64__
|
||||
@@ -432,38 +400,35 @@ template <>
|
||||
void Mem::WriteInterpreter<u32>(Registers ®s, const u32 paddr, const u32 val) {
|
||||
SI &si = mmio.si;
|
||||
|
||||
switch (paddr) {
|
||||
case RDRAM_REGION:
|
||||
mmio.rdp.WriteRDRAM<u32>(paddr, val);
|
||||
break;
|
||||
case RSP_MEM_REGION:
|
||||
{
|
||||
if(Util::IsInsideRange(paddr, RDRAM_REGION_START, RDRAM_REGION_END)) { mmio.rdp.WriteRDRAM<u32>(paddr, val); return; }
|
||||
if(Util::IsInsideRange(paddr, DMEM_REGION_START, RSP_MEM_REGION_END)) {
|
||||
auto &dest = paddr & 0x1000 ? mmio.rsp.imem : mmio.rsp.dmem;
|
||||
Util::WriteAccess<u32>(dest, paddr & 0xfff, val);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case REGION_CART:
|
||||
|
||||
if(Util::IsInsideRange(paddr, CART_REGION_START_2_1, CART_REGION_END_1_2)) {
|
||||
trace("BusWrite<u8> @ {:08X} = {:08X}", paddr, val);
|
||||
mmio.pi.BusWrite<u32, false>(paddr, val);
|
||||
break;
|
||||
case MMIO_REGION:
|
||||
mmio.Write(paddr, val);
|
||||
break;
|
||||
case PIF_RAM_REGION:
|
||||
return;
|
||||
}
|
||||
|
||||
if(Util::IsInsideRange(paddr, MMIO_REGION_START_1, MMIO_REGION_END_1) ||
|
||||
Util::IsInsideRange(paddr, MMIO_REGION_START_2, MMIO_REGION_END_2)) { mmio.Write(paddr, val); return; }
|
||||
|
||||
if(Util::IsInsideRange(paddr, PIF_RAM_REGION_START, PIF_RAM_REGION_END)) {
|
||||
Util::WriteAccess<u32>(si.pif.ram, paddr - PIF_RAM_REGION_START, std::byteswap(val));
|
||||
si.pif.ProcessCommands(*this);
|
||||
break;
|
||||
case 0x00800000 ... 0x03EFFFFF:
|
||||
case 0x04200000 ... 0x042FFFFF:
|
||||
case 0x04900000 ... 0x04FFFFFF:
|
||||
case PIF_ROM_REGION:
|
||||
case 0x1FC00800 ... 0x7FFFFFFF:
|
||||
case 0x80000000 ... 0xFFFFFFFF:
|
||||
break;
|
||||
default:
|
||||
panic("Unimplemented 32-bit write at address {:08X} with value {:0X} (PC = {:016X})", paddr, val,
|
||||
(u64)regs.pc);
|
||||
return;
|
||||
}
|
||||
|
||||
if(Util::IsInsideRange(paddr, UNUSED_START_1, UNUSED_END_1) || // unused
|
||||
Util::IsInsideRange(paddr, UNUSED_START_2, UNUSED_END_2) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_3, UNUSED_END_3) ||
|
||||
Util::IsInsideRange(paddr, PIF_ROM_REGION_START, PIF_ROM_REGION_END) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_4, UNUSED_END_4)) return;
|
||||
|
||||
panic("Unimplemented 32-bit write at address {:08X} with value {:08X} (PC = {:016X})", paddr, val, (u64)regs.pc);
|
||||
}
|
||||
|
||||
#ifndef __aarch64__
|
||||
@@ -493,38 +458,36 @@ void Mem::Write(const Registers ®s, const u32 paddr, const u64 val) { WriteIn
|
||||
void Mem::WriteInterpreter(const Registers ®s, const u32 paddr, u64 val) {
|
||||
SI &si = mmio.si;
|
||||
|
||||
switch (paddr) {
|
||||
case RDRAM_REGION:
|
||||
mmio.rdp.WriteRDRAM<u64>(paddr, val);
|
||||
break;
|
||||
case RSP_MEM_REGION:
|
||||
{
|
||||
if(Util::IsInsideRange(paddr, RDRAM_REGION_START, RDRAM_REGION_END)) { mmio.rdp.WriteRDRAM<u64>(paddr, val); return; }
|
||||
if(Util::IsInsideRange(paddr, DMEM_REGION_START, RSP_MEM_REGION_END)) {
|
||||
auto &dest = paddr & 0x1000 ? mmio.rsp.imem : mmio.rsp.dmem;
|
||||
val >>= 32;
|
||||
Util::WriteAccess<u32>(dest, paddr & 0xfff, val);
|
||||
return;
|
||||
}
|
||||
break;
|
||||
case REGION_CART:
|
||||
trace("BusWrite<u8> @ {:08X} = {:016X}", paddr, val);
|
||||
|
||||
if(Util::IsInsideRange(paddr, CART_REGION_START_2_1, CART_REGION_END_1_2)) {
|
||||
trace("BusWrite<u64> @ {:08X} = {:016X}", paddr, val);
|
||||
mmio.pi.BusWrite<false>(paddr, val);
|
||||
break;
|
||||
case MMIO_REGION:
|
||||
panic("MMIO Write!");
|
||||
case PIF_RAM_REGION:
|
||||
return;
|
||||
}
|
||||
|
||||
if(Util::IsInsideRange(paddr, MMIO_REGION_START_1, MMIO_REGION_END_1) ||
|
||||
Util::IsInsideRange(paddr, MMIO_REGION_START_2, MMIO_REGION_END_2)) panic("MMIO Write<u64>!");
|
||||
|
||||
if(Util::IsInsideRange(paddr, PIF_RAM_REGION_START, PIF_RAM_REGION_END)) {
|
||||
Util::WriteAccess<u64>(si.pif.ram, paddr - PIF_RAM_REGION_START, std::byteswap(val));
|
||||
si.pif.ProcessCommands(*this);
|
||||
break;
|
||||
case 0x00800000 ... 0x03EFFFFF:
|
||||
case 0x04200000 ... 0x042FFFFF:
|
||||
case 0x04900000 ... 0x04FFFFFF:
|
||||
case 0x1FC00000 ... 0x1FC007BF:
|
||||
case 0x1FC00800 ... 0x7FFFFFFF:
|
||||
case 0x80000000 ... 0xFFFFFFFF:
|
||||
break;
|
||||
default:
|
||||
panic("Unimplemented 64-bit write at address {:08X} with value {:0X} (PC = {:016X})", paddr, val,
|
||||
(u64)regs.pc);
|
||||
return;
|
||||
}
|
||||
|
||||
if(Util::IsInsideRange(paddr, UNUSED_START_1, UNUSED_END_1) || // unused
|
||||
Util::IsInsideRange(paddr, UNUSED_START_2, UNUSED_END_2) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_3, UNUSED_END_3) ||
|
||||
Util::IsInsideRange(paddr, PIF_ROM_REGION_START, PIF_ROM_REGION_END) ||
|
||||
Util::IsInsideRange(paddr, UNUSED_START_4, UNUSED_END_4)) return;
|
||||
|
||||
panic("Unimplemented 64-bit write at address {:08X} with value {:016X} (PC = {:016X})", paddr, val, (u64)regs.pc);
|
||||
}
|
||||
|
||||
template <>
|
||||
|
||||
@@ -17,6 +17,12 @@ static FORCE_INLINE std::vector<u8> IntegralToBuffer(const std::integral auto &v
|
||||
return ret;
|
||||
}
|
||||
|
||||
static FORCE_INLINE constexpr bool IsInsideRange(const std::integral auto& addr,
|
||||
const std::integral auto& start,
|
||||
const std::integral auto& end) {
|
||||
return addr >= start && addr <= end;
|
||||
}
|
||||
|
||||
template <typename T>
|
||||
static constexpr FORCE_INLINE T ReadAccess(const u8 *data, const u32 index);
|
||||
template <typename T>
|
||||
|
||||
Reference in New Issue
Block a user