mirror of
https://github.com/RetroDECK/Duckstation.git
synced 2024-11-29 17:15:40 +00:00
Bus: Relax memory timing
Formulas from Mednafen.
This commit is contained in:
parent
8fb4f73d17
commit
b5c799ba81
|
@ -104,7 +104,6 @@ private:
|
|||
|
||||
enum : u32
|
||||
{
|
||||
RAM_ACCESS_DELAY = 6, // Nocash docs say RAM takes 6 cycles to access.
|
||||
MEMCTRL_REG_COUNT = 9
|
||||
};
|
||||
|
||||
|
|
|
@ -22,6 +22,8 @@ TickCount Bus::DoRAMAccess(u32 offset, u32& value)
|
|||
{
|
||||
std::memcpy(&value, &m_ram[offset], sizeof(u32));
|
||||
}
|
||||
|
||||
return 3;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -38,10 +40,10 @@ TickCount Bus::DoRAMAccess(u32 offset, u32& value)
|
|||
{
|
||||
std::memcpy(&m_ram[offset], &value, sizeof(u32));
|
||||
}
|
||||
}
|
||||
|
||||
// Nocash docs say RAM takes 6 cycles to access.
|
||||
return RAM_ACCESS_DELAY;
|
||||
// Technically RAM writes are buffered, and there's a maximum number of in-flight writes.
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
template<MemoryAccessType type, MemoryAccessSize size>
|
||||
|
@ -105,25 +107,33 @@ TickCount Bus::DispatchAccess(PhysicalMemoryAddress address, u32& value)
|
|||
else
|
||||
DoWriteMemoryControl(size, address & PAD_MASK, value);
|
||||
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
else if (address < (PAD_BASE + PAD_SIZE))
|
||||
{
|
||||
if constexpr (type == MemoryAccessType::Read)
|
||||
{
|
||||
value = DoReadPad(size, address & PAD_MASK);
|
||||
return 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
DoWritePad(size, address & PAD_MASK, value);
|
||||
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else if (address < (SIO_BASE + SIO_SIZE))
|
||||
{
|
||||
if constexpr (type == MemoryAccessType::Read)
|
||||
{
|
||||
value = DoReadSIO(size, address & SIO_MASK);
|
||||
return 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
DoWriteSIO(size, address & SIO_MASK, value);
|
||||
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else if (address < (MEMCTRL2_BASE + MEMCTRL2_SIZE))
|
||||
{
|
||||
|
@ -132,34 +142,46 @@ TickCount Bus::DispatchAccess(PhysicalMemoryAddress address, u32& value)
|
|||
else
|
||||
DoWriteMemoryControl2(size, address & PAD_MASK, value);
|
||||
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
else if (address < (INTERRUPT_CONTROLLER_BASE + INTERRUPT_CONTROLLER_SIZE))
|
||||
{
|
||||
if constexpr (type == MemoryAccessType::Read)
|
||||
{
|
||||
value = DoReadInterruptController(size, address & INTERRUPT_CONTROLLER_MASK);
|
||||
return 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
DoWriteInterruptController(size, address & INTERRUPT_CONTROLLER_MASK, value);
|
||||
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else if (address < (DMA_BASE + DMA_SIZE))
|
||||
{
|
||||
if constexpr (type == MemoryAccessType::Read)
|
||||
{
|
||||
value = DoReadDMA(size, address & DMA_MASK);
|
||||
return 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
DoWriteDMA(size, address & DMA_MASK, value);
|
||||
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else if (address < (TIMERS_BASE + TIMERS_SIZE))
|
||||
{
|
||||
if constexpr (type == MemoryAccessType::Read)
|
||||
{
|
||||
value = DoReadTimers(size, address & TIMERS_MASK);
|
||||
return 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
DoWriteTimers(size, address & TIMERS_MASK, value);
|
||||
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else if (address < CDROM_BASE)
|
||||
{
|
||||
|
@ -168,29 +190,41 @@ TickCount Bus::DispatchAccess(PhysicalMemoryAddress address, u32& value)
|
|||
else if (address < (CDROM_BASE + GPU_SIZE))
|
||||
{
|
||||
if constexpr (type == MemoryAccessType::Read)
|
||||
{
|
||||
value = DoReadCDROM(size, address & CDROM_MASK);
|
||||
return (TickCount(1) << static_cast<u8>(size));
|
||||
}
|
||||
else
|
||||
{
|
||||
DoWriteCDROM(size, address & CDROM_MASK, value);
|
||||
|
||||
return m_cdrom_access_time[static_cast<u32>(size)];
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else if (address < (GPU_BASE + GPU_SIZE))
|
||||
{
|
||||
if constexpr (type == MemoryAccessType::Read)
|
||||
{
|
||||
value = DoReadGPU(size, address & GPU_MASK);
|
||||
return 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
DoWriteGPU(size, address & GPU_MASK, value);
|
||||
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else if (address < (MDEC_BASE + MDEC_SIZE))
|
||||
{
|
||||
if constexpr (type == MemoryAccessType::Read)
|
||||
{
|
||||
value = DoReadMDEC(size, address & MDEC_MASK);
|
||||
return 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
DoWriteMDEC(size, address & MDEC_MASK, value);
|
||||
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else if (address < SPU_BASE)
|
||||
{
|
||||
|
@ -199,11 +233,15 @@ TickCount Bus::DispatchAccess(PhysicalMemoryAddress address, u32& value)
|
|||
else if (address < (SPU_BASE + SPU_SIZE))
|
||||
{
|
||||
if constexpr (type == MemoryAccessType::Read)
|
||||
{
|
||||
value = DoReadSPU(size, address & SPU_MASK);
|
||||
return (size == MemoryAccessSize::Word) ? 36 : 16;
|
||||
}
|
||||
else
|
||||
{
|
||||
DoWriteSPU(size, address & SPU_MASK, value);
|
||||
|
||||
return m_spu_access_time[static_cast<u32>(size)];
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
else if (address < EXP2_BASE)
|
||||
{
|
||||
|
|
|
@ -128,7 +128,7 @@ bool Core::ReadMemoryByte(VirtualMemoryAddress addr, u8* value)
|
|||
return false;
|
||||
}
|
||||
|
||||
AddTicks(cycles - 1);
|
||||
AddTicks(cycles);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -146,7 +146,7 @@ bool Core::ReadMemoryHalfWord(VirtualMemoryAddress addr, u16* value)
|
|||
return false;
|
||||
}
|
||||
|
||||
AddTicks(cycles - 1);
|
||||
AddTicks(cycles);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -162,7 +162,7 @@ bool Core::ReadMemoryWord(VirtualMemoryAddress addr, u32* value)
|
|||
return false;
|
||||
}
|
||||
|
||||
AddTicks(cycles - 1);
|
||||
AddTicks(cycles);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -176,7 +176,7 @@ bool Core::WriteMemoryByte(VirtualMemoryAddress addr, u8 value)
|
|||
return false;
|
||||
}
|
||||
|
||||
AddTicks(cycles - 1);
|
||||
AddTicks(cycles);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
@ -193,7 +193,7 @@ bool Core::WriteMemoryHalfWord(VirtualMemoryAddress addr, u16 value)
|
|||
return false;
|
||||
}
|
||||
|
||||
AddTicks(cycles - 1);
|
||||
AddTicks(cycles);
|
||||
return cycles;
|
||||
}
|
||||
|
||||
|
@ -209,7 +209,7 @@ bool Core::WriteMemoryWord(VirtualMemoryAddress addr, u32 value)
|
|||
return false;
|
||||
}
|
||||
|
||||
AddTicks(cycles - 1);
|
||||
AddTicks(cycles);
|
||||
return true;
|
||||
}
|
||||
|
||||
|
|
|
@ -15,14 +15,14 @@ TickCount Core::DoMemoryAccess(VirtualMemoryAddress address, u32& value)
|
|||
if constexpr (type == MemoryAccessType::Write)
|
||||
{
|
||||
if (m_cop0_regs.sr.Isc)
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
const PhysicalMemoryAddress phys_addr = address & UINT32_C(0x1FFFFFFF);
|
||||
if ((phys_addr & DCACHE_LOCATION_MASK) == DCACHE_LOCATION)
|
||||
{
|
||||
DoScratchpadAccess<type, size>(phys_addr, value);
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
return m_bus->DispatchAccess<type, size>(phys_addr, value);
|
||||
|
@ -41,14 +41,14 @@ TickCount Core::DoMemoryAccess(VirtualMemoryAddress address, u32& value)
|
|||
if constexpr (type == MemoryAccessType::Write)
|
||||
{
|
||||
if (m_cop0_regs.sr.Isc)
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
const PhysicalMemoryAddress phys_addr = address & UINT32_C(0x1FFFFFFF);
|
||||
if ((phys_addr & DCACHE_LOCATION_MASK) == DCACHE_LOCATION)
|
||||
{
|
||||
DoScratchpadAccess<type, size>(phys_addr, value);
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
|
||||
return m_bus->DispatchAccess<type, size>(phys_addr, value);
|
||||
|
@ -72,7 +72,7 @@ TickCount Core::DoMemoryAccess(VirtualMemoryAddress address, u32& value)
|
|||
else
|
||||
WriteCacheControl(value);
|
||||
|
||||
return 1;
|
||||
return 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
|
Loading…
Reference in a new issue