Converted IOP to use a static/global hardware register allocation. (same as I did for the EE a few weeks ago).

git-svn-id: http://pcsx2.googlecode.com/svn/trunk@3826 96395faa-99c1-11dd-bbfe-3dabce05a288
This commit is contained in:
Jake.Stine 2010-09-23 19:44:55 +00:00
parent cfca4ccdd0
commit 36d1503581
11 changed files with 77 additions and 87 deletions

View File

@ -27,7 +27,7 @@ void psxHwReset() {
/* if (Config.Sio) psxHu32(0x1070) |= 0x80; /* if (Config.Sio) psxHu32(0x1070) |= 0x80;
if (Config.SpuIrq) psxHu32(0x1070) |= 0x200;*/ if (Config.SpuIrq) psxHu32(0x1070) |= 0x200;*/
memzero_ptr<0x10000>(psxH); memzero_ptr<0x10000>(iopHw);
// mdecInit(); //initialize mdec decoder // mdecInit(); //initialize mdec decoder
cdrReset(); cdrReset();

View File

@ -229,18 +229,19 @@ struct dma_mbct
wxString desc() const { return wxsFormat(L"madr: 0x%x bcr: 0x%x chcr: 0x%x tadr: 0x%x", madr, bcr, chcr, tadr); } wxString desc() const { return wxsFormat(L"madr: 0x%x bcr: 0x%x chcr: 0x%x tadr: 0x%x", madr, bcr, chcr, tadr); }
}; };
#define hw_dma0 (*(dma_mbc*) &psxH[0x1080]) static dma_mbc& hw_dma0 = (dma_mbc&) iopHw[0x1080];
#define hw_dma1 (*(dma_mbc*) &psxH[0x1090]) static dma_mbc& hw_dma1 = (dma_mbc&) iopHw[0x1090];
#define hw_dma2 (*(dma_mbct*)&psxH[0x10a0]) static dma_mbct& hw_dma2 = (dma_mbct&)iopHw[0x10a0];
#define hw_dma3 (*(dma_mbc*) &psxH[0x10b0]) static dma_mbc& hw_dma3 = (dma_mbc&) iopHw[0x10b0];
#define hw_dma4 (*(dma_mbct*)&psxH[0x10c0]) static dma_mbct& hw_dma4 = (dma_mbct&)iopHw[0x10c0];
#define hw_dma6 (*(dma_mbc*) &psxH[0x10e0]) static dma_mbc& hw_dma6 = (dma_mbc&) iopHw[0x10e0];
#define hw_dma7 (*(dma_mbc*) &psxH[0x1500]) static dma_mbc& hw_dma7 = (dma_mbc&) iopHw[0x1500];
#define hw_dma8 (*(dma_mbc*) &psxH[0x1510]) static dma_mbc& hw_dma8 = (dma_mbc&) iopHw[0x1510];
#define hw_dma9 (*(dma_mbct*)&psxH[0x1520]) static dma_mbct& hw_dma9 = (dma_mbct&)iopHw[0x1520];
#define hw_dma10 (*(dma_mbc*) &psxH[0x1530]) static dma_mbc& hw_dma10 = (dma_mbc&) iopHw[0x1530];
#define hw_dma11 (*(dma_mbc*) &psxH[0x1540]) static dma_mbc& hw_dma11 = (dma_mbc&) iopHw[0x1540];
#define hw_dma12 (*(dma_mbc*) &psxH[0x1550]) static dma_mbc& hw_dma12 = (dma_mbc&) iopHw[0x1550];
#define hw_dma(x) hw_dma##x #define hw_dma(x) hw_dma##x
#define HW_DMA0_MADR (psxHu32(0x1080)) // MDEC in DMA #define HW_DMA0_MADR (psxHu32(0x1080)) // MDEC in DMA

View File

@ -17,34 +17,17 @@
#include "PrecompiledHeader.h" #include "PrecompiledHeader.h"
#include "IopCommon.h" #include "IopCommon.h"
u8 *psxM = NULL;
u8 *psxP = NULL;
u8 *psxH = NULL; // standard hardware registers (0x000->0x3ff is the scratchpad)
u8 *psxS = NULL; // 'undocumented' SIF communication registers
uptr *psxMemWLUT = NULL; uptr *psxMemWLUT = NULL;
const uptr *psxMemRLUT = NULL; const uptr *psxMemRLUT = NULL;
static u8* m_psxAllMem = NULL; IopVM_MemoryAllocMess* iopMem = NULL;
static const uint m_psxMemSize =
Ps2MemSize::IopRam + __pagealigned u8 iopHw[Ps2MemSize::IopHardware];
Ps2MemSize::IopHardware +
0x00010000 + // psxP
0x00000100 ; // psxS
void psxMemAlloc() void psxMemAlloc()
{ {
if( m_psxAllMem == NULL ) if( iopMem == NULL )
m_psxAllMem = vtlb_malloc( m_psxMemSize, 4096 ); iopMem = (IopVM_MemoryAllocMess*)vtlb_malloc( sizeof(*iopMem), 4096 );
if( m_psxAllMem == NULL)
throw Exception::OutOfMemory( L"IOP system ram (and roms)" );
u8* curpos = m_psxAllMem;
psxM = curpos; curpos += Ps2MemSize::IopRam;
psxP = curpos; curpos += 0x00010000;
psxH = curpos; curpos += Ps2MemSize::IopHardware;
psxS = curpos; //curpos += 0x00010000;
psxMemWLUT = (uptr*)_aligned_malloc(0x2000 * sizeof(uptr) * 2, 16); psxMemWLUT = (uptr*)_aligned_malloc(0x2000 * sizeof(uptr) * 2, 16);
psxMemRLUT = psxMemWLUT + 0x2000; //(uptr*)_aligned_malloc(0x10000 * sizeof(uptr),16); psxMemRLUT = psxMemWLUT + 0x2000; //(uptr*)_aligned_malloc(0x10000 * sizeof(uptr),16);
@ -55,12 +38,12 @@ void psxMemAlloc()
void psxMemReset() void psxMemReset()
{ {
pxAssume( psxMemWLUT != NULL ); pxAssume( psxMemWLUT != NULL );
pxAssume( m_psxAllMem != NULL ); pxAssume( iopMem != NULL );
DbgCon.WriteLn( "IOP Resetting physical ram..." ); DbgCon.WriteLn( "IOP Resetting physical ram..." );
memzero_ptr<0x2000 * sizeof(uptr) * 2>( psxMemWLUT ); // clears both allocations, RLUT and WLUT memzero_ptr<0x2000 * sizeof(uptr) * 2>( psxMemWLUT ); // clears both allocations, RLUT and WLUT
memzero_ptr<m_psxMemSize>( m_psxAllMem ); memzero( *iopMem );
// Trick! We're accessing RLUT here through WLUT, since it's the non-const pointer. // Trick! We're accessing RLUT here through WLUT, since it's the non-const pointer.
// So the ones with a 0x2000 prefixed are RLUT tables. // So the ones with a 0x2000 prefixed are RLUT tables.
@ -69,20 +52,20 @@ void psxMemReset()
// at 0x0, 0x8000, and 0xa000: // at 0x0, 0x8000, and 0xa000:
for (int i=0; i<0x0080; i++) for (int i=0; i<0x0080; i++)
{ {
psxMemWLUT[i + 0x0000] = (uptr)&psxM[(i & 0x1f) << 16]; psxMemWLUT[i + 0x0000] = (uptr)&iopMem->Main[(i & 0x1f) << 16];
// RLUTs, accessed through WLUT. // RLUTs, accessed through WLUT.
psxMemWLUT[i + 0x2000] = (uptr)&psxM[(i & 0x1f) << 16]; psxMemWLUT[i + 0x2000] = (uptr)&iopMem->Main[(i & 0x1f) << 16];
} }
// A few single-page allocations for things we store in special locations. // A few single-page allocations for things we store in special locations.
psxMemWLUT[0x2000 + 0x1f00] = (uptr)psxP; psxMemWLUT[0x2000 + 0x1f00] = (uptr)iopMem->P;
psxMemWLUT[0x2000 + 0x1f80] = (uptr)psxH; psxMemWLUT[0x2000 + 0x1f80] = (uptr)iopHw;
//psxMemWLUT[0x1bf80] = (uptr)psxH; //psxMemWLUT[0x1bf80] = (uptr)iopHw;
psxMemWLUT[0x1f00] = (uptr)psxP; psxMemWLUT[0x1f00] = (uptr)iopMem->P;
psxMemWLUT[0x1f80] = (uptr)psxH; psxMemWLUT[0x1f80] = (uptr)iopHw;
//psxMemWLUT[0xbf80] = (uptr)psxH; //psxMemWLUT[0xbf80] = (uptr)iopHw;
// Read-only memory areas, so don't map WLUT for these... // Read-only memory areas, so don't map WLUT for these...
for (int i=0; i<0x0040; i++) for (int i=0; i<0x0040; i++)
@ -96,8 +79,8 @@ void psxMemReset()
} }
// sif!! (which is read only? (air)) // sif!! (which is read only? (air))
psxMemWLUT[0x2000 + 0x1d00] = (uptr)psxS; psxMemWLUT[0x2000 + 0x1d00] = (uptr)iopMem->Sif;
//psxMemWLUT[0x1bd00] = (uptr)psxS; //psxMemWLUT[0x1bd00] = (uptr)iopMem->Sif;
// this one looks like an old hack for some special write-only memory area, // this one looks like an old hack for some special write-only memory area,
// but leaving it in for reference (air) // but leaving it in for reference (air)
@ -106,10 +89,8 @@ void psxMemReset()
void psxMemShutdown() void psxMemShutdown()
{ {
vtlb_free( m_psxAllMem, m_psxMemSize ); vtlb_free( iopMem, sizeof(*iopMem) );
m_psxAllMem = NULL; iopMem = NULL;
psxM = psxP = psxH = psxS = NULL;
safe_aligned_free(psxMemWLUT); safe_aligned_free(psxMemWLUT);
psxMemRLUT = NULL; psxMemRLUT = NULL;

View File

@ -17,10 +17,6 @@
#include "MemoryTypes.h" #include "MemoryTypes.h"
extern u8 *psxM;
extern u8 *psxP;
extern u8 *psxH;
extern u8 *psxS;
extern uptr *psxMemWLUT; extern uptr *psxMemWLUT;
extern const uptr *psxMemRLUT; extern const uptr *psxMemRLUT;
@ -51,29 +47,29 @@ static __fi const T* iopVirtMemR( u32 mem )
// Obtains a pointer to the IOP's physical mapping (bypasses the TLB) // Obtains a pointer to the IOP's physical mapping (bypasses the TLB)
static __fi u8* iopPhysMem( u32 addr ) static __fi u8* iopPhysMem( u32 addr )
{ {
return &psxM[addr & 0x1fffff]; return &iopMem->Main[addr & 0x1fffff];
} }
#define psxSs8(mem) psxS[(mem) & 0x00ff] #define psxSs8(mem) iopMem->Sif[(mem) & 0x00ff]
#define psxSs16(mem) (*(s16*)&psxS[(mem) & 0x00ff]) #define psxSs16(mem) (*(s16*)&iopMem->Sif[(mem) & 0x00ff])
#define psxSs32(mem) (*(s32*)&psxS[(mem) & 0x00ff]) #define psxSs32(mem) (*(s32*)&iopMem->Sif[(mem) & 0x00ff])
#define psxSu8(mem) (*(u8*) &psxS[(mem) & 0x00ff]) #define psxSu8(mem) (*(u8*) &iopMem->Sif[(mem) & 0x00ff])
#define psxSu16(mem) (*(u16*)&psxS[(mem) & 0x00ff]) #define psxSu16(mem) (*(u16*)&iopMem->Sif[(mem) & 0x00ff])
#define psxSu32(mem) (*(u32*)&psxS[(mem) & 0x00ff]) #define psxSu32(mem) (*(u32*)&iopMem->Sif[(mem) & 0x00ff])
#define psxPs8(mem) psxP[(mem) & 0xffff] #define psxPs8(mem) iopMem->P[(mem) & 0xffff]
#define psxPs16(mem) (*(s16*)&psxP[(mem) & 0xffff]) #define psxPs16(mem) (*(s16*)&iopMem->P[(mem) & 0xffff])
#define psxPs32(mem) (*(s32*)&psxP[(mem) & 0xffff]) #define psxPs32(mem) (*(s32*)&iopMem->P[(mem) & 0xffff])
#define psxPu8(mem) (*(u8*) &psxP[(mem) & 0xffff]) #define psxPu8(mem) (*(u8*) &iopMem->P[(mem) & 0xffff])
#define psxPu16(mem) (*(u16*)&psxP[(mem) & 0xffff]) #define psxPu16(mem) (*(u16*)&iopMem->P[(mem) & 0xffff])
#define psxPu32(mem) (*(u32*)&psxP[(mem) & 0xffff]) #define psxPu32(mem) (*(u32*)&iopMem->P[(mem) & 0xffff])
#define psxHs8(mem) psxH[(mem) & 0xffff] #define psxHs8(mem) iopHw[(mem) & 0xffff]
#define psxHs16(mem) (*(s16*)&psxH[(mem) & 0xffff]) #define psxHs16(mem) (*(s16*)&iopHw[(mem) & 0xffff])
#define psxHs32(mem) (*(s32*)&psxH[(mem) & 0xffff]) #define psxHs32(mem) (*(s32*)&iopHw[(mem) & 0xffff])
#define psxHu8(mem) (*(u8*) &psxH[(mem) & 0xffff]) #define psxHu8(mem) (*(u8*) &iopHw[(mem) & 0xffff])
#define psxHu16(mem) (*(u16*)&psxH[(mem) & 0xffff]) #define psxHu16(mem) (*(u16*)&iopHw[(mem) & 0xffff])
#define psxHu32(mem) (*(u32*)&psxH[(mem) & 0xffff]) #define psxHu32(mem) (*(u32*)&iopHw[(mem) & 0xffff])
extern void psxMemAlloc(); extern void psxMemAlloc();
extern void psxMemReset(); extern void psxMemReset();

View File

@ -150,7 +150,7 @@ void memMapPhy()
// IOP memory // IOP memory
// (used by the EE Bios Kernel during initial hardware initialization, Apps/Games // (used by the EE Bios Kernel during initial hardware initialization, Apps/Games
// are "supposed" to use the thread-safe SIF instead.) // are "supposed" to use the thread-safe SIF instead.)
vtlb_MapBlock(psxM,0x1c000000,0x00800000); vtlb_MapBlock(iopMem->Main,0x1c000000,0x00800000);
// Generic Handlers; These fallback to mem* stuff... // Generic Handlers; These fallback to mem* stuff...
vtlb_MapHandler(tlb_fallback_7,0x14000000,0x10000); vtlb_MapHandler(tlb_fallback_7,0x14000000,0x10000);
@ -647,7 +647,9 @@ void memReset()
// rest of the emu is not really set up to support a "soft" reset of that sort // rest of the emu is not really set up to support a "soft" reset of that sort
// we opt for the hard/safe version. // we opt for the hard/safe version.
pxAssume( eeMem != NULL );
memzero( *eeMem ); memzero( *eeMem );
#ifdef ENABLECACHE #ifdef ENABLECACHE
memset(pCache,0,sizeof(_cacheS)*64); memset(pCache,0,sizeof(_cacheS)*64);
#endif #endif

View File

@ -98,11 +98,21 @@ struct EEVM_MemoryAllocMess
#endif #endif
// EE Hardware registers. struct IopVM_MemoryAllocMess
// DevNote: These are done as a static array instead of a pointer in order to allow for simpler {
// macros and reference handles to be defined (we can safely use compile-time references to u8 Main[Ps2MemSize::IopRam]; // Main memory (hard-wired to 2MB)
// registers instead of having to use instance variables). u8 P[0x00010000]; // I really have no idea what this is... --air
u8 Sif[0x100]; // a few special SIF/SBUS registers (likely not needed)
};
// DevNote: EE and IOP hardware registers are done as a static array instead of a pointer in
// order to allow for simpler macros and reference handles to be defined (we can safely use
// compile-time references to registers instead of having to use instance variables).
extern __pagealigned u8 eeHw[Ps2MemSize::Hardware]; extern __pagealigned u8 eeHw[Ps2MemSize::Hardware];
extern __pagealigned u8 iopHw[Ps2MemSize::IopHardware];
extern EEVM_MemoryAllocMess* eeMem; extern EEVM_MemoryAllocMess* eeMem;
extern IopVM_MemoryAllocMess* iopMem;

View File

@ -1048,7 +1048,7 @@ bool SysCorePlugins::OpenPlugin_SPU2()
SPU2irqCallback( spu2Irq ); SPU2irqCallback( spu2Irq );
#else #else
SPU2irqCallback( spu2Irq, spu2DMA4Irq, spu2DMA7Irq ); SPU2irqCallback( spu2Irq, spu2DMA4Irq, spu2DMA7Irq );
if( SPU2setDMABaseAddr != NULL ) SPU2setDMABaseAddr((uptr)psxM); if( SPU2setDMABaseAddr != NULL ) SPU2setDMABaseAddr((uptr)iopMem->Main);
#endif #endif
if( SPU2setClockPtr != NULL ) SPU2setClockPtr(&psxRegs.cycle); if( SPU2setClockPtr != NULL ) SPU2setClockPtr(&psxRegs.cycle);
return true; return true;
@ -1072,7 +1072,7 @@ bool SysCorePlugins::OpenPlugin_USB()
USBirqCallback( usbIrq ); USBirqCallback( usbIrq );
usbHandler = USBirqHandler(); usbHandler = USBirqHandler();
if( USBsetRAM != NULL ) if( USBsetRAM != NULL )
USBsetRAM(psxM); USBsetRAM(iopMem->Main);
return true; return true;
} }

View File

@ -156,9 +156,9 @@ void SaveStateBase::FreezeMainMemory()
FreezeMem(eeMem->Scratch, Ps2MemSize::Scratch); // scratch pad FreezeMem(eeMem->Scratch, Ps2MemSize::Scratch); // scratch pad
FreezeMem(eeHw, Ps2MemSize::Hardware); // hardware memory FreezeMem(eeHw, Ps2MemSize::Hardware); // hardware memory
FreezeMem(psxM, Ps2MemSize::IopRam); // 2 MB main memory FreezeMem(iopMem->Main, Ps2MemSize::IopRam); // 2 MB main memory
FreezeMem(psxH, Ps2MemSize::IopHardware); // hardware memory FreezeMem(iopHw, Ps2MemSize::IopHardware); // hardware memory
FreezeMem(psxS, 0x000100); // iop's sif memory FreezeMem(iopMem->Sif, 0x000100); // iop's sif memory
} }
void SaveStateBase::FreezeRegisters() void SaveStateBase::FreezeRegisters()

View File

@ -24,7 +24,7 @@ namespace IopMemory {
using namespace Internal; using namespace Internal;
// Template-compatible version of the psxHu macro. Used for writing. // Template-compatible version of the psxHu macro. Used for writing.
#define psxHu(mem) (*(u32*)&psxH[(mem) & 0xffff]) #define psxHu(mem) (*(u32*)&iopHw[(mem) & 0xffff])
////////////////////////////////////////////////////////////////////////////////////////// //////////////////////////////////////////////////////////////////////////////////////////

View File

@ -432,7 +432,7 @@ BOOL CALLBACK FinderProc(HWND hWnd,UINT uMsg,WPARAM wParam,LPARAM lParam)
case WM_INITDIALOG: case WM_INITDIALOG:
mptr[0]=eeMem->Main; mptr[0]=eeMem->Main;
mptr[1]=psxM; mptr[1]=iopMem->Main;
hWndFinder=hWnd; hWndFinder=hWnd;

View File

@ -688,7 +688,7 @@ static void rpsxLW()
// read from psM directly // read from psM directly
AND32ItoR(ECX, 0x1fffff); AND32ItoR(ECX, 0x1fffff);
ADD32ItoR(ECX, (uptr)psxM); ADD32ItoR(ECX, (uptr)iopMem->Main);
MOV32RmtoR( ECX, ECX ); MOV32RmtoR( ECX, ECX );
MOV32RtoM( (uptr)&psxRegs.GPR.r[_Rt_], ECX); MOV32RtoM( (uptr)&psxRegs.GPR.r[_Rt_], ECX);