Core: Get Fast tlb to just be 32bit

This commit is contained in:
zilmar 2023-11-16 17:11:05 +10:30
parent dcb6969067
commit 8f4f434820
6 changed files with 54 additions and 40 deletions

View File

@ -94,7 +94,7 @@ void R4300iOp::ExecuteCPU()
{
if (!m_MMU.MemoryValue32(m_PROGRAM_COUNTER, m_Opcode.Value))
{
m_Reg.TriggerAddressException(m_PROGRAM_COUNTER, EXC_RMISS);
m_Reg.TriggerAddressException((int32_t)m_PROGRAM_COUNTER, EXC_RMISS);
m_PROGRAM_COUNTER = JumpToLocation;
PipelineStage = PIPELINE_STAGE_NORMAL;
continue;
@ -305,7 +305,7 @@ void R4300iOp::ExecuteOps(int32_t Cycles)
}
else
{
m_Reg.TriggerAddressException(m_PROGRAM_COUNTER, EXC_RMISS);
m_Reg.TriggerAddressException((int32_t)m_PROGRAM_COUNTER, EXC_RMISS);
m_PROGRAM_COUNTER = JumpToLocation;
PipelineStage = PIPELINE_STAGE_NORMAL;
}

View File

@ -647,7 +647,7 @@ bool CMipsMemoryVM::LB_VAddr32(uint32_t VAddr, uint8_t & Value)
uint32_t BaseAddress = m_TLB_ReadMap[VAddr >> 12];
if (BaseAddress == -1)
{
m_Reg.TriggerAddressException(VAddr, EXC_RMISS);
m_Reg.TriggerAddressException((int32_t)VAddr, EXC_RMISS);
return false;
}
return LB_PhysicalAddress(BaseAddress + VAddr, Value);
@ -658,7 +658,7 @@ bool CMipsMemoryVM::LH_VAddr32(uint32_t VAddr, uint16_t & Value)
uint32_t BaseAddress = m_TLB_ReadMap[VAddr >> 12];
if (BaseAddress == -1)
{
m_Reg.TriggerAddressException(VAddr, EXC_RMISS);
m_Reg.TriggerAddressException((int32_t)VAddr, EXC_RMISS);
return false;
}
return LH_PhysicalAddress(BaseAddress + VAddr, Value);
@ -669,7 +669,7 @@ bool CMipsMemoryVM::LW_VAddr32(uint32_t VAddr, uint32_t & Value)
uint32_t BaseAddress = m_TLB_ReadMap[VAddr >> 12];
if (BaseAddress == -1)
{
m_Reg.TriggerAddressException(VAddr, EXC_RMISS);
m_Reg.TriggerAddressException((int32_t)VAddr, EXC_RMISS);
return false;
}
return LW_PhysicalAddress(BaseAddress + VAddr, Value);
@ -680,7 +680,7 @@ bool CMipsMemoryVM::LD_VAddr32(uint32_t VAddr, uint64_t & Value)
uint32_t BaseAddress = m_TLB_ReadMap[VAddr >> 12];
if (BaseAddress == -1)
{
m_Reg.TriggerAddressException(VAddr, EXC_RMISS);
m_Reg.TriggerAddressException((int32_t)VAddr, EXC_RMISS);
return false;
}
return LD_PhysicalAddress(BaseAddress + VAddr, Value);
@ -821,7 +821,7 @@ bool CMipsMemoryVM::SB_VAddr32(uint32_t VAddr, uint32_t Value)
uint32_t BaseAddress = m_TLB_WriteMap[VAddr >> 12];
if (BaseAddress == -1)
{
m_Reg.TriggerAddressException(VAddr, EXC_WMISS);
m_Reg.TriggerAddressException((int32_t)VAddr, EXC_WMISS);
return false;
}
return SB_PhysicalAddress(BaseAddress + VAddr, Value);
@ -832,7 +832,7 @@ bool CMipsMemoryVM::SH_VAddr32(uint32_t VAddr, uint32_t Value)
uint32_t BaseAddress = m_TLB_WriteMap[VAddr >> 12];
if (BaseAddress == -1)
{
m_Reg.TriggerAddressException(VAddr, EXC_WMISS);
m_Reg.TriggerAddressException((int32_t)VAddr, EXC_WMISS);
return false;
}
return SH_PhysicalAddress(BaseAddress + VAddr, Value);
@ -843,7 +843,7 @@ bool CMipsMemoryVM::SW_VAddr32(uint32_t VAddr, uint32_t Value)
uint32_t BaseAddress = m_TLB_WriteMap[VAddr >> 12];
if (BaseAddress == -1)
{
m_Reg.TriggerAddressException(VAddr, EXC_WMISS);
m_Reg.TriggerAddressException((int32_t)VAddr, EXC_WMISS);
return false;
}
return SW_PhysicalAddress(BaseAddress + VAddr, Value);
@ -854,7 +854,7 @@ bool CMipsMemoryVM::SD_VAddr32(uint32_t VAddr, uint64_t Value)
uint32_t BaseAddress = m_TLB_WriteMap[VAddr >> 12];
if (BaseAddress == -1)
{
m_Reg.TriggerAddressException(VAddr, EXC_WMISS);
m_Reg.TriggerAddressException((int32_t)VAddr, EXC_WMISS);
return false;
}
return SD_PhysicalAddress(BaseAddress + VAddr, Value);
@ -1109,16 +1109,11 @@ const char * CMipsMemoryVM::LabelName(uint32_t Address) const
return m_strLabelName;
}
void CMipsMemoryVM::TLB_Mapped(uint64_t VAddr, uint32_t Len, uint32_t PAddr, bool bReadOnly)
void CMipsMemoryVM::TLB_Mapped(uint32_t VAddr, uint32_t Len, uint32_t PAddr, bool bReadOnly)
{
uint64_t VEnd = VAddr + Len;
for (uint64_t Address = VAddr; Address < VEnd; Address += 0x1000)
{
if ((uint64_t)((int32_t)Address) != Address)
{
break;
}
size_t Index = (size_t)(Address >> 12);
if ((Address - VAddr + PAddr) < m_AllocatedRdramSize)
{
@ -1136,15 +1131,11 @@ void CMipsMemoryVM::TLB_Mapped(uint64_t VAddr, uint32_t Len, uint32_t PAddr, boo
}
}
void CMipsMemoryVM::TLB_Unmaped(uint64_t Vaddr, uint32_t Len)
void CMipsMemoryVM::TLB_Unmaped(uint32_t Vaddr, uint32_t Len)
{
uint64_t End = Vaddr + Len;
for (uint64_t Address = Vaddr; Address < End && Address >= Vaddr; Address += 0x1000)
{
if ((uint64_t)((int32_t)Address) != Address)
{
continue;
}
size_t Index = (size_t)(Address >> 12);
m_MemoryReadMap[Index] = (size_t)-1;
m_MemoryWriteMap[Index] = (size_t)-1;

View File

@ -122,8 +122,8 @@ public:
void UnProtectMemory(uint32_t StartVaddr, uint32_t EndVaddr);
// Functions for TLB notification
void TLB_Mapped(uint64_t VAddr, uint32_t Len, uint32_t PAddr, bool bReadOnly);
void TLB_Unmaped(uint64_t Vaddr, uint32_t Len);
void TLB_Mapped(uint32_t VAddr, uint32_t Len, uint32_t PAddr, bool bReadOnly);
void TLB_Unmaped(uint32_t Vaddr, uint32_t Len);
bool ValidVaddr(uint32_t VAddr) const;
bool VAddrToPAddr(uint32_t VAddr, uint32_t & PAddr) const;

View File

@ -226,12 +226,13 @@ void CTLB::SetupTLB_Entry(uint32_t Index, bool Random)
TLB_Unmaped(m_FastTlb[FastIndx].VSTART, m_FastTlb[FastIndx].Length);
}
m_FastTlb[FastIndx].Length = (uint32_t)((m_tlb[Index].PageMask.Mask << 12) + 0xFFF);
m_FastTlb[FastIndx].VSTART = ((uint64_t)m_tlb[Index].EntryHi.R() << 62) | ((uint64_t)m_tlb[Index].EntryHi.VPN2() << 13);
m_FastTlb[FastIndx].Region = (uint8_t)m_tlb[Index].EntryHi.R();
m_FastTlb[FastIndx].VSTART = (uint32_t)(m_tlb[Index].EntryHi.VPN2() << 13);
m_FastTlb[FastIndx].VEND = m_FastTlb[FastIndx].VSTART + m_FastTlb[FastIndx].Length;
m_FastTlb[FastIndx].PHYSSTART = (uint32_t)(m_tlb[Index].EntryLo0.PFN << 12);
m_FastTlb[FastIndx].PHYSEND = m_FastTlb[FastIndx].PHYSSTART + m_FastTlb[FastIndx].Length;
m_FastTlb[FastIndx].VALID = m_tlb[Index].EntryLo0.V;
m_FastTlb[FastIndx].DIRTY = m_tlb[Index].EntryLo0.D;
m_FastTlb[FastIndx].VALID = m_tlb[Index].EntryLo0.V != 0;
m_FastTlb[FastIndx].DIRTY = m_tlb[Index].EntryLo0.D != 0;
m_FastTlb[FastIndx].GLOBAL = m_tlb[Index].EntryLo0.GLOBAL & m_tlb[Index].EntryLo1.GLOBAL;
m_FastTlb[FastIndx].ValidEntry = false;
m_FastTlb[FastIndx].Random = Random;
@ -243,12 +244,13 @@ void CTLB::SetupTLB_Entry(uint32_t Index, bool Random)
TLB_Unmaped(m_FastTlb[FastIndx].VSTART, m_FastTlb[FastIndx].Length);
}
m_FastTlb[FastIndx].Length = (uint32_t)((m_tlb[Index].PageMask.Mask << 12) + 0xFFF);
m_FastTlb[FastIndx].VSTART = ((uint64_t)m_tlb[Index].EntryHi.R() << 62 | ((uint64_t)m_tlb[Index].EntryHi.VPN2() << 13)) + (m_FastTlb[FastIndx].Length + 1);
m_FastTlb[FastIndx].Region = (uint8_t)m_tlb[Index].EntryHi.R();
m_FastTlb[FastIndx].VSTART = (uint32_t)(m_tlb[Index].EntryHi.VPN2() << 13) + (m_FastTlb[FastIndx].Length + 1);
m_FastTlb[FastIndx].VEND = m_FastTlb[FastIndx].VSTART + m_FastTlb[FastIndx].Length;
m_FastTlb[FastIndx].PHYSSTART = (uint32_t)m_tlb[Index].EntryLo1.PFN << 12;
m_FastTlb[FastIndx].PHYSEND = m_FastTlb[FastIndx].PHYSSTART + m_FastTlb[FastIndx].Length;
m_FastTlb[FastIndx].VALID = m_tlb[Index].EntryLo1.V;
m_FastTlb[FastIndx].DIRTY = m_tlb[Index].EntryLo1.D;
m_FastTlb[FastIndx].VALID = m_tlb[Index].EntryLo1.V != 0;
m_FastTlb[FastIndx].DIRTY = m_tlb[Index].EntryLo1.D != 0;
m_FastTlb[FastIndx].GLOBAL = m_tlb[Index].EntryLo0.GLOBAL & m_tlb[Index].EntryLo1.GLOBAL;
m_FastTlb[FastIndx].ValidEntry = false;
m_FastTlb[FastIndx].Random = Random;
@ -263,6 +265,16 @@ void CTLB::SetupTLB_Entry(uint32_t Index, bool Random)
continue;
}
if ((m_FastTlb[FastIndx].VSTART & 0x80000000) == 0 && m_FastTlb[FastIndx].Region != 0)
{
continue;
}
if ((m_FastTlb[FastIndx].VSTART & 0x80000000) != 0 && m_FastTlb[FastIndx].Region != 3)
{
continue;
}
if (m_FastTlb[FastIndx].VEND <= m_FastTlb[FastIndx].VSTART)
{
continue;
@ -282,10 +294,10 @@ void CTLB::SetupTLB_Entry(uint32_t Index, bool Random)
}
}
void CTLB::TLB_Unmaped(uint64_t VAddr, uint32_t Len)
void CTLB::TLB_Unmaped(uint32_t VAddr, uint32_t Len)
{
m_MMU.TLB_Unmaped(VAddr, Len);
if (m_Recomp && bSMM_TLB() && (uint64_t)((int32_t)VAddr) == VAddr)
if (m_Recomp && bSMM_TLB())
{
m_Recomp->ClearRecompCode_Virt((uint32_t)VAddr, Len, CRecompiler::Remove_TLB);
}
@ -302,17 +314,27 @@ bool CTLB::VAddrToPAddr(uint64_t VAddr, uint32_t & PAddr, bool & MemoryUnused)
MemorySegment Segment = VAddrMemorySegment(VAddr);
if (Segment == MemorySegment_Mapped)
{
for (int i = 0; i < 64; i++)
for (uint32_t i = 0; i < 32; i++)
{
if (m_FastTlb[i].ValidEntry == false)
if (m_tlb[i].EntryLo0.GLOBAL == 0)
{
continue;
}
if (VAddr >= m_FastTlb[i].VSTART && VAddr < m_FastTlb[i].VEND)
if ((VAddr & 0xE000000000000000) != ((uint64_t)m_tlb[i].EntryHi.R() << 62))
{
PAddr = (uint32_t)(m_FastTlb[i].PHYSSTART + (VAddr - m_FastTlb[i].VSTART));
return true;
continue;
}
uint64_t PageMask = (m_tlb[i].PageMask.Mask << 12);
uint64_t AddressMaskHi = ~(PageMask | 0x1fff) & 0xFFFFFFFFFF;
uint64_t AddressRegion = ((uint64_t)m_tlb[i].EntryHi.VPN2() << 13);
if ((VAddr & AddressMaskHi) != AddressRegion)
{
continue;
}
uint64_t AddressSelect = ((m_tlb[i].PageMask.Mask << 12) | 0xfff) + 1;
COP0EntryLo EntryLo = (VAddr & AddressSelect) != 0 ? m_tlb[i].EntryLo1 : m_tlb[i].EntryLo0;
PAddr = (uint32_t)((EntryLo.PFN << 12) + (VAddr & (PageMask | 0x1fff)));
return true;
}
return false;
}

View File

@ -35,11 +35,12 @@ class CTLB :
struct FASTTLB
{
uint64_t VSTART;
uint64_t VEND;
uint32_t VSTART;
uint32_t VEND;
uint32_t PHYSSTART;
uint32_t PHYSEND;
uint32_t Length;
uint8_t Region;
bool VALID;
bool DIRTY;
bool GLOBAL;
@ -73,7 +74,7 @@ private:
CTLB & operator=(const CTLB &);
void SetupTLB_Entry(uint32_t Index, bool Random);
void TLB_Unmaped(uint64_t VAddr, uint32_t Len);
void TLB_Unmaped(uint32_t VAddr, uint32_t Len);
MemorySegment VAddrMemorySegment(uint64_t VAddr);
PRIVILEGE_MODE m_PrivilegeMode;

View File

@ -265,7 +265,7 @@ void CDebugTlb::RefreshTLBWindow(void)
if (FastTlb[count].ValidEntry && FastTlb[count].VALID)
{
swprintf(Output, sizeof(Output), L"%llX:%llX -> %08X:%08X", FastTlb[count].VSTART, FastTlb[count].VEND,
swprintf(Output, sizeof(Output), L"%08X:%08X -> %08X:%08X", FastTlb[count].VSTART, FastTlb[count].VEND,
FastTlb[count].PHYSSTART, FastTlb[count].PHYSEND);
}
else