MemArena: Remove the low mappings for our pointers

These are effectively unused, since the memmap already maps them in one
place. For 32-bit, they might have some slight advantage, but we already
special-case the regular "high-mem" pointer for 32-bit, so just use the
one we already have...
This commit is contained in:
Jasper St. Pierre 2014-10-28 04:02:12 -07:00
parent 8858dc7764
commit 6813473367
3 changed files with 39 additions and 68 deletions

View File

@ -170,8 +170,7 @@ u8* MemArena::Find4GBBase()
if (!(a_flags & MV_FAKE_VMEM) && (b_flags & MV_FAKE_VMEM)) \ if (!(a_flags & MV_FAKE_VMEM) && (b_flags & MV_FAKE_VMEM)) \
continue; \ continue; \
static bool Memory_TryBase(u8 *base, MemoryView *views, int num_views, u32 flags, MemArena *arena)
static bool Memory_TryBase(u8 *base, const MemoryView *views, int num_views, u32 flags, MemArena *arena)
{ {
// OK, we know where to find free space. Now grab it! // OK, we know where to find free space. Now grab it!
// We just mimic the popular BAT setup. // We just mimic the popular BAT setup.
@ -181,45 +180,38 @@ static bool Memory_TryBase(u8 *base, const MemoryView *views, int num_views, u32
// Zero all the pointers to be sure. // Zero all the pointers to be sure.
for (int i = 0; i < num_views; i++) for (int i = 0; i < num_views; i++)
{ {
if (views[i].out_ptr_low) views[i].mapped_ptr = nullptr;
*views[i].out_ptr_low = nullptr;
if (views[i].out_ptr)
*views[i].out_ptr = nullptr;
} }
int i; int i;
for (i = 0; i < num_views; i++) for (i = 0; i < num_views; i++)
{ {
SKIP(flags, views[i].flags); SKIP(flags, views[i].flags);
if (views[i].flags & MV_MIRROR_PREVIOUS) if (views[i].flags & MV_MIRROR_PREVIOUS)
{
position = last_position; position = last_position;
}
else
{
*(views[i].out_ptr_low) = (u8*)arena->CreateView(position, views[i].size);
if (!*views[i].out_ptr_low)
goto bail;
}
#if _ARCH_64 #if _ARCH_64
*views[i].out_ptr = (u8*)arena->CreateView( views[i].mapped_ptr = arena->CreateView(
position, views[i].size, base + views[i].virtual_address); position, views[i].size, base + views[i].virtual_address);
#else #else
if (views[i].flags & MV_MIRROR_PREVIOUS) if (views[i].flags & MV_MIRROR_PREVIOUS)
{ {
// No need to create multiple identical views. // No need to create multiple identical views.
*views[i].out_ptr = *views[i - 1].out_ptr; views[i].mapped_ptr = views[i - 1].mapped_ptr;
} }
else else
{ {
*views[i].out_ptr = (u8*)arena->CreateView( views[i].mapped_ptr = arena->CreateView(
position, views[i].size, base + (views[i].virtual_address & 0x3FFFFFFF)); position, views[i].size, base + (views[i].virtual_address & 0x3FFFFFFF));
} }
#endif #endif
if (!*views[i].out_ptr) if (!views[i].mapped_ptr)
goto bail; goto bail;
last_position = position; if (views[i].out_ptr)
*views[i].out_ptr = (u8*) views[i].mapped_ptr;
position += views[i].size; position += views[i].size;
} }
@ -231,7 +223,7 @@ bail:
return false; return false;
} }
u8 *MemoryMap_Setup(const MemoryView *views, int num_views, u32 flags, MemArena *arena) u8 *MemoryMap_Setup(MemoryView *views, int num_views, u32 flags, MemArena *arena)
{ {
u32 total_mem = 0; u32 total_mem = 0;
@ -258,21 +250,17 @@ u8 *MemoryMap_Setup(const MemoryView *views, int num_views, u32 flags, MemArena
return base; return base;
} }
void MemoryMap_Shutdown(const MemoryView *views, int num_views, u32 flags, MemArena *arena) void MemoryMap_Shutdown(MemoryView *views, int num_views, u32 flags, MemArena *arena)
{ {
std::set<void*> freeset; std::set<void*> freeset;
for (int i = 0; i < num_views; i++) for (int i = 0; i < num_views; i++)
{ {
const MemoryView* view = &views[i]; MemoryView* view = &views[i];
u8** outptrs[2] = {view->out_ptr_low, view->out_ptr}; if (view->mapped_ptr && *(u8*)view->mapped_ptr && !freeset.count(view->mapped_ptr))
for (auto outptr : outptrs)
{ {
if (outptr && *outptr && !freeset.count(*outptr)) arena->ReleaseView(view->mapped_ptr, view->size);
{ freeset.insert(view->mapped_ptr);
arena->ReleaseView(*outptr, view->size); view->mapped_ptr = nullptr;
freeset.insert(*outptr);
*outptr = nullptr;
}
} }
} }
} }

View File

@ -43,14 +43,14 @@ enum {
struct MemoryView struct MemoryView
{ {
u8 **out_ptr_low; u8** out_ptr;
u8 **out_ptr;
u32 virtual_address; u32 virtual_address;
u32 size; u32 size;
u32 flags; u32 flags;
void* mapped_ptr;
}; };
// Uses a memory arena to set up an emulator-friendly memory map according to // Uses a memory arena to set up an emulator-friendly memory map according to
// a passed-in list of MemoryView structures. // a passed-in list of MemoryView structures.
u8 *MemoryMap_Setup(const MemoryView *views, int num_views, u32 flags, MemArena *arena); u8 *MemoryMap_Setup(MemoryView *views, int num_views, u32 flags, MemArena *arena);
void MemoryMap_Shutdown(const MemoryView *views, int num_views, u32 flags, MemArena *arena); void MemoryMap_Shutdown(MemoryView *views, int num_views, u32 flags, MemArena *arena);

View File

@ -63,24 +63,11 @@ static MemArena g_arena;
static bool m_IsInitialized = false; // Save the Init(), Shutdown() state static bool m_IsInitialized = false; // Save the Init(), Shutdown() state
// END STATE_TO_SAVE // END STATE_TO_SAVE
// 64-bit: Pointers to low-mem (sub-0x10000000) mirror
// 32-bit: Same as the corresponding physical/virtual pointers.
u8* m_pRAM; u8* m_pRAM;
u8* m_pL1Cache; u8* m_pL1Cache;
u8* m_pEXRAM; u8* m_pEXRAM;
u8* m_pFakeVMEM; u8* m_pFakeVMEM;
// 64-bit: Pointers to high-mem mirrors
// 32-bit: Same as above
static u8* m_pPhysicalRAM;
static u8* m_pVirtualCachedRAM;
static u8* m_pVirtualUncachedRAM;
static u8* m_pPhysicalEXRAM; // wii only
static u8* m_pVirtualCachedEXRAM; // wii only
static u8* m_pVirtualUncachedEXRAM; // wii only
static u8* m_pVirtualL1Cache;
static u8* m_pVirtualFakeVMEM;
// MMIO mapping object. // MMIO mapping object.
MMIO::Mapping* mmio_mapping; MMIO::Mapping* mmio_mapping;
@ -116,19 +103,16 @@ bool IsInitialized()
// We don't declare the IO region in here since its handled by other means. // We don't declare the IO region in here since its handled by other means.
static const MemoryView views[] = static MemoryView views[] =
{ {
{&m_pRAM, &m_pPhysicalRAM, 0x00000000, RAM_SIZE, 0}, {&m_pRAM, 0x00000000, RAM_SIZE, 0},
{nullptr, &m_pVirtualCachedRAM, 0x80000000, RAM_SIZE, MV_MIRROR_PREVIOUS}, {nullptr, 0x80000000, RAM_SIZE, MV_MIRROR_PREVIOUS},
{nullptr, &m_pVirtualUncachedRAM, 0xC0000000, RAM_SIZE, MV_MIRROR_PREVIOUS}, {nullptr, 0xC0000000, RAM_SIZE, MV_MIRROR_PREVIOUS},
{&m_pL1Cache, 0xE0000000, L1_CACHE_SIZE, 0},
{&m_pL1Cache, &m_pVirtualL1Cache, 0xE0000000, L1_CACHE_SIZE, 0}, {&m_pFakeVMEM, 0x7E000000, FAKEVMEM_SIZE, MV_FAKE_VMEM},
{&m_pEXRAM, 0x10000000, EXRAM_SIZE, MV_WII_ONLY},
{&m_pFakeVMEM, &m_pVirtualFakeVMEM, 0x7E000000, FAKEVMEM_SIZE, MV_FAKE_VMEM}, {nullptr, 0x90000000, EXRAM_SIZE, MV_WII_ONLY | MV_MIRROR_PREVIOUS},
{nullptr, 0xD0000000, EXRAM_SIZE, MV_WII_ONLY | MV_MIRROR_PREVIOUS},
{&m_pEXRAM, &m_pPhysicalEXRAM, 0x10000000, EXRAM_SIZE, MV_WII_ONLY},
{nullptr, &m_pVirtualCachedEXRAM, 0x90000000, EXRAM_SIZE, MV_WII_ONLY | MV_MIRROR_PREVIOUS},
{nullptr, &m_pVirtualUncachedEXRAM, 0xD0000000, EXRAM_SIZE, MV_WII_ONLY | MV_MIRROR_PREVIOUS},
}; };
static const int num_views = sizeof(views) / sizeof(MemoryView); static const int num_views = sizeof(views) / sizeof(MemoryView);
@ -154,19 +138,18 @@ void Init()
else else
InitMMIO(mmio_mapping); InitMMIO(mmio_mapping);
INFO_LOG(MEMMAP, "Memory system initialized. RAM at %p (mirrors at 0 @ %p, 0x80000000 @ %p , 0xC0000000 @ %p)", INFO_LOG(MEMMAP, "Memory system initialized. RAM at %p", m_pRAM);
m_pRAM, m_pPhysicalRAM, m_pVirtualCachedRAM, m_pVirtualUncachedRAM);
m_IsInitialized = true; m_IsInitialized = true;
} }
void DoState(PointerWrap &p) void DoState(PointerWrap &p)
{ {
bool wii = SConfig::GetInstance().m_LocalCoreStartupParameter.bWii; bool wii = SConfig::GetInstance().m_LocalCoreStartupParameter.bWii;
p.DoArray(m_pPhysicalRAM, RAM_SIZE); p.DoArray(m_pRAM, RAM_SIZE);
p.DoArray(m_pVirtualL1Cache, L1_CACHE_SIZE); p.DoArray(m_pL1Cache, L1_CACHE_SIZE);
p.DoMarker("Memory RAM"); p.DoMarker("Memory RAM");
if (bFakeVMEM) if (bFakeVMEM)
p.DoArray(m_pVirtualFakeVMEM, FAKEVMEM_SIZE); p.DoArray(m_pFakeVMEM, FAKEVMEM_SIZE);
p.DoMarker("Memory FakeVMEM"); p.DoMarker("Memory FakeVMEM");
if (wii) if (wii)
p.DoArray(m_pEXRAM, EXRAM_SIZE); p.DoArray(m_pEXRAM, EXRAM_SIZE);
@ -328,7 +311,7 @@ u8* GetPointer(const u32 _Address)
case 0x0: case 0x0:
case 0x8: case 0x8:
if ((_Address & 0xfffffff) < REALRAM_SIZE) if ((_Address & 0xfffffff) < REALRAM_SIZE)
return m_pPhysicalRAM + (_Address & RAM_MASK); return m_pRAM + (_Address & RAM_MASK);
case 0xc: case 0xc:
switch (_Address >> 24) switch (_Address >> 24)
{ {
@ -341,7 +324,7 @@ u8* GetPointer(const u32 _Address)
default: default:
if ((_Address & 0xfffffff) < REALRAM_SIZE) if ((_Address & 0xfffffff) < REALRAM_SIZE)
return m_pPhysicalRAM + (_Address & RAM_MASK); return m_pRAM + (_Address & RAM_MASK);
} }
case 0x1: case 0x1:
@ -350,7 +333,7 @@ u8* GetPointer(const u32 _Address)
if (SConfig::GetInstance().m_LocalCoreStartupParameter.bWii) if (SConfig::GetInstance().m_LocalCoreStartupParameter.bWii)
{ {
if ((_Address & 0xfffffff) < EXRAM_SIZE) if ((_Address & 0xfffffff) < EXRAM_SIZE)
return m_pPhysicalEXRAM + (_Address & EXRAM_MASK); return m_pEXRAM + (_Address & EXRAM_MASK);
} }
else else
break; break;
@ -363,7 +346,7 @@ u8* GetPointer(const u32 _Address)
default: default:
if (bFakeVMEM) if (bFakeVMEM)
return m_pVirtualFakeVMEM + (_Address & FAKEVMEM_MASK); return m_pFakeVMEM + (_Address & FAKEVMEM_MASK);
} }
ERROR_LOG(MEMMAP, "Unknown Pointer %#8x PC %#8x LR %#8x", _Address, PC, LR); ERROR_LOG(MEMMAP, "Unknown Pointer %#8x PC %#8x LR %#8x", _Address, PC, LR);