- more accurate IPC FIFO & Geometry Commands FIFO;
This commit is contained in:
mtabachenko 2008-12-27 09:24:05 +00:00
parent 93af0a8e36
commit 43cd2fd665
8 changed files with 984 additions and 797 deletions

View File

@ -23,77 +23,144 @@
#include "FIFO.h" #include "FIFO.h"
#include <string.h> #include <string.h>
#include "armcpu.h"
#include "debug.h" #include "debug.h"
#include "mem.h"
#include "MMU.h"
// ========================================================= IPC FIFO // ========================================================= IPC FIFO
void IPC_FIFOclear(IPC_FIFO * fifo) IPC_FIFO ipc_fifo;
{
memset(fifo, 0, sizeof(IPC_FIFO));
fifo->empty = TRUE; void IPC_FIFOclear()
{
memset(&ipc_fifo, 0, sizeof(IPC_FIFO));
//LOG("FIFO is cleared\n"); //LOG("FIFO is cleared\n");
} }
void IPC_FIFOadd(IPC_FIFO * fifo, u32 val)
void IPC_FIFOsend(u8 proc, u32 val)
{ {
if (fifo->full) //LOG("IPC%s send FIFO 0x%08X\n", proc?"7":"9", val);
u16 cnt_l = T1ReadWord(MMU.MMU_MEM[proc][0x40], 0x184);
if (!(cnt_l & 0x8000)) return; // FIFO disabled
u16 cnt_r = T1ReadWord(MMU.MMU_MEM[proc^1][0x40], 0x184);
if (ipc_fifo.sendTail[proc] < 16) // last full == error
{ {
//LOG("FIFO send is full\n"); ipc_fifo.sendBuf[proc][ipc_fifo.sendTail[proc]] = val;
fifo->error = true; ipc_fifo.sendTail[proc]++;
return; if (ipc_fifo.sendTail[proc] == 16) cnt_l |= 0x02; // full
cnt_l &= 0xFFFE;
if (ipc_fifo.recvTail[proc^1] < 16) // last full == error
{
ipc_fifo.recvBuf[proc^1][ipc_fifo.recvTail[proc^1]] = val;
ipc_fifo.recvTail[proc^1]++;
if (ipc_fifo.recvTail[proc^1] == 16) cnt_r |= 0x0200; // full
cnt_r &= 0xFEFF;
} }
else
cnt_r |= 0x4200;
}
else
cnt_l |= 0x4002;
//LOG("IPC FIFO add value 0x%08X in pos %i\n", val, fifo->size); // save in mem
T1WriteWord(MMU.MMU_MEM[proc][0x40], 0x184, cnt_l);
T1WriteWord(MMU.MMU_MEM[proc^1][0x40], 0x184, cnt_r);
fifo->buf[fifo->size] = val; if ((cnt_r & (1<<10)))
fifo->size++; NDS_makeInt(proc^1, 18);
if (fifo->size == 16)
fifo->full = TRUE;
fifo->empty = FALSE;
} }
u32 IPC_FIFOget(IPC_FIFO * fifo) u32 IPC_FIFOrecv(u8 proc)
{ {
if (fifo->empty) //LOG("IPC%s recv FIFO:\n", proc?"7":"9");
{ u32 val = 0;
fifo->error = true; u16 cnt_l = T1ReadWord(MMU.MMU_MEM[proc][0x40], 0x184);
//LOG("FIFO get is empty\n"); u16 cnt_r = T1ReadWord(MMU.MMU_MEM[proc^1][0x40], 0x184);
return(0);
}
u32 val = fifo->buf[0]; if (ipc_fifo.recvTail[proc] > 0) // not empty
//LOG("IPC FIFO get value 0x%08X in pos %i\n", val, fifo->size); {
for (int i = 0; i < fifo->size; i++) val = ipc_fifo.recvBuf[proc][0];
fifo->buf[i] = fifo->buf[i+1]; for (int i = 0; i < ipc_fifo.recvTail[proc]; i++)
fifo->size--; ipc_fifo.recvBuf[proc][i] = ipc_fifo.recvBuf[proc][i+1];
if (fifo->size == 0) ipc_fifo.recvTail[proc]--;
fifo->empty = TRUE; if (ipc_fifo.recvTail[proc] == 0) // empty
return val; cnt_l |= 0x0100;
// remove from head
for (int i = 0; i < ipc_fifo.sendTail[proc^1]; i++)
ipc_fifo.sendBuf[proc^1][i] = ipc_fifo.sendBuf[proc^1][i+1];
ipc_fifo.sendTail[proc^1]--;
if (ipc_fifo.sendTail[proc^1] == 0) // empty
cnt_r |= 0x0001;
}
else
cnt_l |= 0x4100;
T1WriteWord(MMU.MMU_MEM[proc][0x40], 0x184, cnt_l);
T1WriteWord(MMU.MMU_MEM[proc^1][0x40], 0x184, cnt_r);
if ((cnt_l & (1<<3)))
NDS_makeInt(proc, 19);
return (val);
}
void IPC_FIFOcnt(u8 proc, u16 val)
{
//LOG("IPC%s FIFO context 0x%X\n", proc?"7":"9", val);
u16 cnt_l = T1ReadWord(MMU.MMU_MEM[proc][0x40], 0x184);
cnt_l &= ~0x8404;
cnt_l |= (val & 0x8404);
cnt_l &= (~(val & 0x4000));
if (val & 0x0008)
{
IPC_FIFOclear();
cnt_l |= 0x0101;
}
T1WriteWord(MMU.MMU_MEM[proc][0x40], 0x184, cnt_l);
if ((cnt_l & 0x0004))
NDS_makeInt(proc, 18);
} }
// ========================================================= GFX FIFO // ========================================================= GFX FIFO
void GFX_FIFOclear(GFX_FIFO * fifo) GFX_FIFO gxFIFO;
{
memset(fifo, 0, sizeof(GFX_FIFO));
fifo->empty = TRUE; void GFX_FIFOclear()
fifo->half = TRUE; {
u32 gxstat = T1ReadLong(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x600);
memset(&gxFIFO, 0, sizeof(GFX_FIFO));
// TODO: irq handle
gxstat &= 0x0000FF00;
gxstat |= 0x00000002; // this is hack
gxstat |= 0x86000000;
T1WriteLong(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x600, gxstat);
} }
void GFX_FIFOadd(GFX_FIFO * fifo) void GFX_FIFOsend(u32 cmd, u32 param)
{ {
if (fifo->full) u32 gxstat = T1ReadLong(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x600);
gxstat &= 0x0000FF00;
gxstat |= 0x00000002; // this is hack
if (gxFIFO.tail < 260)
{ {
//INFO("GFX FIFO send is full\n"); gxFIFO.cmd[gxFIFO.tail] = cmd & 0xFF;
fifo->error = true; gxFIFO.param[gxFIFO.tail] = param;
return; gxFIFO.tail++;
// TODO: irq handle
if (gxFIFO.tail < 130)
gxstat |= 0x72000000;
if (gxFIFO.tail == 16)
gxstat |= 0x01000000;
} }
else
gxstat |= 0x01000000;
fifo->size++; T1WriteLong(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x600, gxstat);
if (fifo->size > 127)
fifo->half = FALSE;
if (fifo->size == 256)
fifo->full = TRUE;
fifo->empty = FALSE;
} }

View File

@ -29,38 +29,31 @@
//=================================================== IPC FIFO //=================================================== IPC FIFO
typedef struct typedef struct
{ {
u32 buf[16]; // 64K u32 sendBuf[2][16];
u8 size; // tail u32 recvBuf[2][16];
BOOL empty; u8 sendTail[2];
BOOL full; u8 recvTail[2];
BOOL error;
} IPC_FIFO; } IPC_FIFO;
extern void IPC_FIFOclear(IPC_FIFO * fifo); extern IPC_FIFO ipc_fifo;
extern void IPC_FIFOadd(IPC_FIFO * fifo, u32 val); extern void IPC_FIFOclear();
extern u32 IPC_FIFOget(IPC_FIFO * fifo); extern void IPC_FIFOsend(u8 proc, u32 val);
extern u32 IPC_FIFOrecv(u8 proc);
extern void IPC_FIFOcnt(u8 proc, u16 val);
//=================================================== GFX FIFO //=================================================== GFX FIFO
typedef struct typedef struct
{ {
u32 size; // tail u32 cmd[261];
u32 param[261];
BOOL empty; u32 tail; // tail
BOOL half;
BOOL full;
BOOL error;
u8 irq;
u32 pipe[4]; // additional 4 entries
u8 pipe_size; // pipe tail
BOOL pipe_empty;
BOOL pipe_half;
BOOL pipe_full;
} GFX_FIFO; } GFX_FIFO;
extern void GFX_FIFOclear(GFX_FIFO * fifo);
extern void GFX_FIFOadd(GFX_FIFO * fifo); extern GFX_FIFO gxFIFO;
extern void GFX_FIFOclear();
extern void GFX_FIFOsend(u32 cmd, u32 param);
//=================================================== Display memory FIFO //=================================================== Display memory FIFO
#if 0 #if 0

View File

@ -311,9 +311,8 @@ void MMU_Init(void) {
MMU.DTCMRegion = 0x027C0000; MMU.DTCMRegion = 0x027C0000;
MMU.ITCMRegion = 0x00000000; MMU.ITCMRegion = 0x00000000;
IPC_FIFOclear(&MMU.ipc_fifo[ARMCPU_ARM9]); IPC_FIFOclear();
IPC_FIFOclear(&MMU.ipc_fifo[ARMCPU_ARM7]); GFX_FIFOclear();
GFX_FIFOclear(&MMU.gfx_fifo);
mc_init(&MMU.fw, MC_TYPE_FLASH); /* init fw device */ mc_init(&MMU.fw, MC_TYPE_FLASH); /* init fw device */
mc_alloc(&MMU.fw, NDS_FW_SIZE_V1); mc_alloc(&MMU.fw, NDS_FW_SIZE_V1);
@ -368,9 +367,8 @@ void MMU_clearMem()
memset(MMU.ARM7_ERAM, 0, 0x010000); memset(MMU.ARM7_ERAM, 0, 0x010000);
memset(MMU.ARM7_REG, 0, 0x010000); memset(MMU.ARM7_REG, 0, 0x010000);
IPC_FIFOclear(&MMU.ipc_fifo[ARMCPU_ARM9]); IPC_FIFOclear();
IPC_FIFOclear(&MMU.ipc_fifo[ARMCPU_ARM7]); GFX_FIFOclear();
GFX_FIFOclear(&MMU.gfx_fifo);
MMU.DTCMRegion = 0x027C0000; MMU.DTCMRegion = 0x027C0000;
MMU.ITCMRegion = 0x00000000; MMU.ITCMRegion = 0x00000000;
@ -1586,6 +1584,22 @@ static void FASTCALL _MMU_ARM9_write08(u32 adr, u8 val)
MMU.MMU_MEM[ARMCPU_ARM9][adr>>20][adr&MMU.MMU_MASK[ARMCPU_ARM9][adr>>20]]=val; MMU.MMU_MEM[ARMCPU_ARM9][adr>>20][adr&MMU.MMU_MASK[ARMCPU_ARM9][adr>>20]]=val;
} }
static INLINE void MMU_IPCSync(u8 proc, u32 val)
{
//INFO("IPC%s sync 0x%08X\n", proc?"7":"9", val);
u32 IPCSYNC_local = T1ReadLong(MMU.MMU_MEM[proc][0x40], 0x180) & 0xFFFF;
u32 IPCSYNC_remote = T1ReadLong(MMU.MMU_MEM[proc^1][0x40], 0x180);
IPCSYNC_local = (IPCSYNC_local&0x6000)|(val&0xf00)|(IPCSYNC_local&0xf);
IPCSYNC_remote =(IPCSYNC_remote&0x6f00)|(val>>8)&0xf;
T1WriteLong(MMU.MMU_MEM[proc][0x40], 0x180, IPCSYNC_local);
T1WriteLong(MMU.MMU_MEM[proc^1][0x40], 0x180, IPCSYNC_remote);
if ((val & 0x2000) && (IPCSYNC_remote & 0x4000))
NDS_makeInt(proc^1, 17);
}
//================================================= MMU ARM9 write 16 //================================================= MMU ARM9 write 16
static void FASTCALL _MMU_ARM9_write16(u32 adr, u16 val) static void FASTCALL _MMU_ARM9_write16(u32 adr, u16 val)
{ {
@ -1938,42 +1952,11 @@ static void FASTCALL _MMU_ARM9_write16(u32 adr, u16 val)
return; return;
case REG_IPCSYNC : case REG_IPCSYNC :
{ MMU_IPCSync(ARMCPU_ARM9, val);
u16 IPCSYNC_remote = T1ReadWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x180);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x180, (val&0xFFF0)|((IPCSYNC_remote>>8)&0x0F));
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x180, (IPCSYNC_remote&0xFFF0)|((val>>8)&0x0F));
MMU.reg_IF[ARMCPU_ARM9] |= ((IPCSYNC_remote & (1<<14))<<2);
MMU.reg_IF[ARMCPU_ARM7] |= ((val & (1<<13))<<3);
//MMU.reg_IF[ARMCPU_ARM7] |= ((IPCSYNC_remote & (1<<14))<<2) & ((val & (1<<13))<<3);
}
return; return;
case REG_IPCFIFOCNT : case REG_IPCFIFOCNT :
{ IPC_FIFOcnt(ARMCPU_ARM9, val);
//LOG("IPC9 write16 context 0x%X\n", val);
u32 cnt_l = T1ReadLong(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184) & 0xFFFF;
u32 cnt_r = T1ReadLong(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184) & 0xFFFF;
/*
if ((val & 0x8000) && !(cnt_l & 0x8000))
{
// this is the first init, the other side didnt init yet
// so do a complete init
IPC_FIFOclear(&MMU.ipc_fifo);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184,0x8101) ;
// and then handle it as usual
}*/
if (val & 0x4008) // clear FIFO
{
IPC_FIFOclear(&MMU.ipc_fifo[ARMCPU_ARM9]);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184, (cnt_l & 0x0301) | (val & 0x8404) | 1);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184, (cnt_r & 0xC507) | 0x100);
MMU.reg_IF[ARMCPU_ARM9] |= ((val & 4)<<15);
//T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184, val);
return;
}
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184, cnt_l | (val & 0xBFF4));
}
return; return;
case REG_TM0CNTL : case REG_TM0CNTL :
case REG_TM1CNTL : case REG_TM1CNTL :
@ -2202,26 +2185,34 @@ static void FASTCALL _MMU_ARM9_write32(u32 adr, u32 val)
if((adr>>24)==4) if((adr>>24)==4)
{ {
if(adr >= 0x04000380 && adr <= 0x040003BC) if( (adr >= 0x04000330) && (adr < 0x04000340) ) //edge color table
{ {
//toon table ((u32 *)(MMU.MMU_MEM[ARMCPU_ARM9][0x40]))[(adr & 0xFFF) >> 2] = val;
((u32 *)(MMU.MMU_MEM[ARMCPU_ARM9][0x40]))[(adr-0x04000000)>>2] = val; return;
}
if( (adr >= 0x04000360) && (adr < 0x04000380) ) //fog table
{
((u32 *)(MMU.MMU_MEM[ARMCPU_ARM9][0x40]))[(adr & 0xFFF) >> 2] = val;
return;
}
if( (adr >= 0x04000380) && (adr <= 0x40003BC) ) //toon table
{
((u32 *)(MMU.MMU_MEM[ARMCPU_ARM9][0x40]))[(adr & 0xFFF) >> 2] = val;
gfx3d_UpdateToonTable(&((MMU.MMU_MEM[ARMCPU_ARM9][0x40]))[(0x380)]); gfx3d_UpdateToonTable(&((MMU.MMU_MEM[ARMCPU_ARM9][0x40]))[(0x380)]);
return; return;
} }
if (adr >= 0x04000400 && adr < 0x04000440) if ( (adr >= 0x04000400) && (adr < 0x04000440) )
{ {
// Geometry commands (aka Dislay Lists) - Parameters:X gfx3d_sendCommandToFIFO(val);
((u32 *)(MMU.MMU_MEM[ARMCPU_ARM9][0x40]))[(adr-0x04000000)>>2] = val;
gfx3d_Add_Command(val);
return; return;
} }
if (adr >= 0x04000440 && adr < 0x04000600) if ( (adr >= 0x04000440) && (adr < 0x04000600) )
{ {
((u32 *)(MMU.MMU_MEM[ARMCPU_ARM9][0x40]))[(adr-0x04000000)>>2] = val; gfx3d_sendCommand(adr, val);
gfx3d_Add_Command_Direct((adr - 0x04000400) >> 2, val);
return; return;
} }
@ -2262,12 +2253,6 @@ static void FASTCALL _MMU_ARM9_write32(u32 adr, u32 val)
return; return;
} }
case 0x04000600: // Geometry Engine Status Register (R and R/W)
{
((u32 *)(MMU.MMU_MEM[ARMCPU_ARM9][0x40]))[0x600>>2] = val;
return;
}
case REG_DISPA_WININ: case REG_DISPA_WININ:
{ {
GPU_setWININ(MainScreen.gpu, val & 0xFFFF) ; GPU_setWININ(MainScreen.gpu, val & 0xFFFF) ;
@ -2459,60 +2444,11 @@ static void FASTCALL _MMU_ARM9_write32(u32 adr, u32 val)
return; return;
} }
case REG_IPCSYNC : case REG_IPCSYNC :
{ MMU_IPCSync(ARMCPU_ARM9, val);
LOG("MMU write 32 IPCSYNC\n");
u32 IPCSYNC_remote = T1ReadLong(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x180);
T1WriteLong(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x180, (val&0xFFF0)|((IPCSYNC_remote>>8)&0xF));
T1WriteLong(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x180, (IPCSYNC_remote&0xFFF0)|((val>>8)&0xF));
MMU.reg_IF[ARMCPU_ARM9] |= ((IPCSYNC_remote & (1<<14))<<2);
MMU.reg_IF[ARMCPU_ARM7] |= ((val & (1<<13))<<3);
//MMU.reg_IF[ARMCPU_ARM7] |= ((IPCSYNC_remote & (1<<14))<<2) & ((val & (1<<13))<<3);
}
return; return;
case REG_IPCFIFOCNT :
{
//LOG("IPC9 write32 context 0x%X\n", val);
u32 cnt_l = T1ReadLong(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184) & 0xFFFF;
u32 cnt_r = T1ReadLong(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184) & 0xFFFF;
/*if ((val & 0x8000) && !(cnt_l & 0x8000))
{
// this is the first init, the other side didnt init yet
// so do a complete init
IPC_FIFOclear(&MMU.ipc_fifo);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184,0x8101) ;
// and then handle it as usual
}*/
if(val & 0x4008)
{
IPC_FIFOclear(&MMU.ipc_fifo[ARMCPU_ARM9]);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184, (cnt_l & 0x0301) | (val & 0x8404) | 1);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184, (cnt_r & 0xC507) | 0x100);
MMU.reg_IF[ARMCPU_ARM9] |= ((val & 4)<<15);// & (MMU.reg_IME[ARMCPU_ARM9]<<17);// & (MMU.reg_IE[ARMCPU_ARM9]&0x20000);//
return;
}
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184, val & 0xBFF4);
return;
}
case REG_IPCFIFOSEND : case REG_IPCFIFOSEND :
{ IPC_FIFOsend(ARMCPU_ARM9, val);
//INFO("IPC9 write32\n");
u32 cnt_l = T1ReadLong(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184) & 0xFFFF;
if (!(cnt_l & 0x8000)) return; //FIFO disabled
u32 cnt_r = T1ReadLong(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184) & 0xFFFF;
IPC_FIFOadd(&MMU.ipc_fifo[ARMCPU_ARM7], val);
cnt_l = (cnt_l & 0xFFFC) | (MMU.ipc_fifo[ARMCPU_ARM9].full?0x0002:0);
cnt_r = (cnt_r & 0xFCFF) | (MMU.ipc_fifo[ARMCPU_ARM9].full?0x0200:0);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184, cnt_l);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184, cnt_r);
//MMU.reg_IF[ARMCPU_ARM7] |= ((cnt_r & (1<<10))<<8);
if (cnt_r & 0x400)
{
MMU.reg_IF[ARMCPU_ARM7] |= ((cnt_r & (1<<10))<<8); // FIFO remote not empty
NDS_makeARM7Int(18);
}
}
return; return;
case REG_DMA0CNTL : case REG_DMA0CNTL :
//LOG("32 bit dma0 %04X\r\n", val); //LOG("32 bit dma0 %04X\r\n", val);
@ -2738,7 +2674,6 @@ static u16 FASTCALL _MMU_ARM9_read16(u32 adr)
case 0x04000606: case 0x04000606:
return (gfx3d_GetNumVertex()&8191); return (gfx3d_GetNumVertex()&8191);
// ============================================= 3D end // ============================================= 3D end
case REG_IME : case REG_IME :
return (u16)MMU.reg_IME[ARMCPU_ARM9]; return (u16)MMU.reg_IME[ARMCPU_ARM9];
@ -2803,7 +2738,15 @@ static u32 FASTCALL _MMU_ARM9_read32(u32 adr)
switch(adr) switch(adr)
{ {
case 0x04000600: // Geometry Engine Status Register (R and R/W) case 0x04000600: // Geometry Engine Status Register (R and R/W)
return gfx3d_GetGXstatus(); {
u32 gxstat = T1ReadLong(MMU.MMU_MEM[ARMCPU_ARM9][(adr >> 20)],
adr & MMU.MMU_MASK[ARMCPU_ARM9][(adr >> 20)]);
// this is hack
gxstat |= 0x00000002;
return gxstat;
}
case 0x04000640: case 0x04000640:
case 0x04000644: case 0x04000644:
@ -2853,28 +2796,7 @@ static u32 FASTCALL _MMU_ARM9_read32(u32 adr)
case REG_IF : case REG_IF :
return MMU.reg_IF[ARMCPU_ARM9]; return MMU.reg_IF[ARMCPU_ARM9];
case REG_IPCFIFORECV : case REG_IPCFIFORECV :
{ return IPC_FIFOrecv(ARMCPU_ARM9);
//INFO("IPC9 read32\n");
u32 cnt_l = T1ReadWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184) & 0xFFFF;
if (!(cnt_l & 0x8000)) return 0; // FIFO disabled
u32 cnt_r = T1ReadWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184) & 0xFFFF;
u32 val = IPC_FIFOget(&MMU.ipc_fifo[ARMCPU_ARM9]);
cnt_l |= (MMU.ipc_fifo[ARMCPU_ARM9].empty?0x0100:0) | (MMU.ipc_fifo[ARMCPU_ARM9].full?0x0200:0) | (MMU.ipc_fifo[ARMCPU_ARM9].error?0x4000:0);
cnt_r |= (MMU.ipc_fifo[ARMCPU_ARM9].empty?0x0001:0) | (MMU.ipc_fifo[ARMCPU_ARM9].full?0x0002:0);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184, cnt_l);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184, cnt_r);
if ((MMU.ipc_fifo[ARMCPU_ARM7].empty) && (cnt_l & BIT(2)))
{
MMU.reg_IF[ARMCPU_ARM7] |= ((cnt_r & (1<<8))<<7); // FIFO empty
NDS_makeARM7Int(17) ; // SEND FIFO EMPTY
}
return val;
}
return 0;
case REG_TM0CNTL : case REG_TM0CNTL :
case REG_TM1CNTL : case REG_TM1CNTL :
case REG_TM2CNTL : case REG_TM2CNTL :
@ -3207,41 +3129,11 @@ static void FASTCALL _MMU_ARM7_write16(u32 adr, u16 val)
return; return;
case REG_IPCSYNC : case REG_IPCSYNC :
{ MMU_IPCSync(ARMCPU_ARM7, val);
u16 IPCSYNC_remote = T1ReadWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x180);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x180, (val&0xFFF0)|((IPCSYNC_remote>>8)&0xF));
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x180, (IPCSYNC_remote&0xFFF0)|((val>>8)&0xF));
MMU.reg_IF[ARMCPU_ARM9] |= ((IPCSYNC_remote & (1<<14))<<2) & ((val & (1<<13))<<3);// & (MMU.reg_IME[remote] << 16);// & (MMU.reg_IE[remote] & (1<<16));//
//execute = FALSE;
}
return; return;
case REG_IPCFIFOCNT : case REG_IPCFIFOCNT :
{ IPC_FIFOcnt(ARMCPU_ARM7, val);
//LOG("IPC7 write16 context 0x%X\n", val);
u32 cnt_l = T1ReadLong(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184) & 0xFFFF;
u32 cnt_r = T1ReadLong(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184) & 0xFFFF;
/*
if ((val & 0x8000) && !(cnt_l & 0x8000))
{
// this is the first init, the other side didnt init yet
// so do a complete init
IPC_FIFOclear(&MMU.ipc_fifo);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184,0x8101) ;
// and then handle it as usual
}*/
if (val & 0x4008) // clear FIFO
{
IPC_FIFOclear(&MMU.ipc_fifo[ARMCPU_ARM7]);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184, (cnt_l & 0x0301) | (val & 0x8404) | 1);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184, (cnt_r & 0xC507) | 0x100);
MMU.reg_IF[ARMCPU_ARM7] |= ((val & 4)<<15);
//T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184, val);
return;
}
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184, cnt_l | (val & 0xBFF4));
}
return; return;
case REG_TM0CNTL : case REG_TM0CNTL :
case REG_TM1CNTL : case REG_TM1CNTL :
@ -3496,61 +3388,11 @@ static void FASTCALL _MMU_ARM7_write32(u32 adr, u32 val)
} }
case REG_IPCSYNC : case REG_IPCSYNC :
{ MMU_IPCSync(ARMCPU_ARM7, val);
//execute=FALSE;
LOG("MMU write 32 IPCSYNC\n");
u32 IPCSYNC_remote = T1ReadLong(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x180);
T1WriteLong(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x180, (val&0xFFF0)|((IPCSYNC_remote>>8)&0xF));
T1WriteLong(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x180, (IPCSYNC_remote&0xFFF0)|((val>>8)&0xF));
MMU.reg_IF[ARMCPU_ARM9] |= ((IPCSYNC_remote & (1<<14))<<2) & ((val & (1<<13))<<3);// & (MMU.reg_IME[remote] << 16);// & (MMU.reg_IE[remote] & (1<<16));//
}
return; return;
case REG_IPCFIFOCNT :
{
//LOG("IPC7 write32 context 0x%X\n", val);
u32 cnt_l = T1ReadWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184) & 0xFFFF ;
u32 cnt_r = T1ReadWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184) & 0xFFFF ;
/*
if ((val & 0x8000) && !(cnt_l & 0x8000))
{
// this is the first init, the other side didnt init yet
// so do a complete init
IPC_FIFOclear(&MMU.ipc_fifo);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184,0x8101) ;
// and then handle it as usual
}
*/
if(val & 0x4008)
{
IPC_FIFOclear(&MMU.ipc_fifo[ARMCPU_ARM7]);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184, (cnt_l & 0x0301) | (val & 0x8404) | 1);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184, (cnt_r & 0xC507) | 0x100);
MMU.reg_IF[ARMCPU_ARM7] |= ((val & 4)<<15);// & (MMU.reg_IME[ARMCPU_ARM7]<<17);// & (MMU.reg_IE[ARMCPU_ARM7]&0x20000);//
return;
}
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184, val & 0xBFF4);
//execute = FALSE;
return;
}
case REG_IPCFIFOSEND : case REG_IPCFIFOSEND :
{ IPC_FIFOsend(ARMCPU_ARM7, val);
//INFO("IPC7 write32\n");
u32 cnt_l = T1ReadWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184) & 0xFFFF;
if (!(cnt_l & 0x8000)) return; //FIFO disabled
u32 cnt_r = T1ReadWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184) & 0xFFFF;
IPC_FIFOadd(&MMU.ipc_fifo[ARMCPU_ARM9], val);
cnt_l = (cnt_l & 0xFFFC) | (MMU.ipc_fifo[ARMCPU_ARM7].full?0x0002:0);
cnt_r = (cnt_r & 0xFCFF) | (MMU.ipc_fifo[ARMCPU_ARM7].full?0x0200:0);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184, cnt_l);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184, cnt_r);
//MMU.reg_IF[ARMCPU_ARM9] |= ((cnt_r & (1<<10))<<8);
if (cnt_r & 0x400)
{
MMU.reg_IF[ARMCPU_ARM9] |= ((cnt_r & (1<<10))<<8); // FIFO remote not empty
NDS_makeARM9Int(18);
}
}
return; return;
case REG_DMA0CNTL : case REG_DMA0CNTL :
//LOG("32 bit dma0 %04X\r\n", val); //LOG("32 bit dma0 %04X\r\n", val);
@ -3780,31 +3622,7 @@ static u32 FASTCALL _MMU_ARM7_read32(u32 adr)
case REG_IF : case REG_IF :
return MMU.reg_IF[ARMCPU_ARM7]; return MMU.reg_IF[ARMCPU_ARM7];
case REG_IPCFIFORECV : case REG_IPCFIFORECV :
{ return IPC_FIFOrecv(ARMCPU_ARM7);
//INFO("IPC7 read32\n");
u32 cnt_l = T1ReadLong(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184) & 0xFFFF;
if (!(cnt_l & 0x8000)) return 0; // FIFO disabled
u32 cnt_r = T1ReadWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184) & 0xFFFF;
u32 val = IPC_FIFOget(&MMU.ipc_fifo[ARMCPU_ARM7]);
cnt_l |= (MMU.ipc_fifo[ARMCPU_ARM7].empty?0x0100:0) | (MMU.ipc_fifo[ARMCPU_ARM7].full?0x0200:0) | (MMU.ipc_fifo[ARMCPU_ARM7].error?0x4000:0);
cnt_r |= (MMU.ipc_fifo[ARMCPU_ARM7].empty?0x0001:0) | (MMU.ipc_fifo[ARMCPU_ARM7].full?0x0002:0);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM7][0x40], 0x184, cnt_l);
T1WriteWord(MMU.MMU_MEM[ARMCPU_ARM9][0x40], 0x184, cnt_r);
if ((MMU.ipc_fifo[ARMCPU_ARM9].empty) && (cnt_l & BIT(2)))
{
MMU.reg_IF[ARMCPU_ARM9] |= ((cnt_r & (1<<8))<<7); // FIFO empty
NDS_makeARM9Int(17) ; // SEND FIFO EMPTY
}
//if ((MMU.ipc_fifo.empty) && (cnt_l & BIT(2)))
// NDS_makeInt(ARMCPU_ARM9,17) ; // remote: SEND FIFO EMPTY
return val;
}
return 0;
case REG_TM0CNTL : case REG_TM0CNTL :
case REG_TM1CNTL : case REG_TM1CNTL :
case REG_TM2CNTL : case REG_TM2CNTL :

View File

@ -77,12 +77,6 @@ struct MMU_struct {
u8 ARM9_RW_MODE; u8 ARM9_RW_MODE;
// IPC FIFO
IPC_FIFO ipc_fifo[2]; // 0 - ARM9 FIFO
// 1 - ARM7 FIFO
// GFX FIFO
GFX_FIFO gfx_fifo;
static TWaitState MMU_WAIT16[2][16]; static TWaitState MMU_WAIT16[2][16];
static TWaitState MMU_WAIT32[2][16]; static TWaitState MMU_WAIT32[2][16];

View File

@ -144,7 +144,8 @@ struct NDS_fw_touchscreen_cal {
*/ */
enum nds_fw_ds_type { enum nds_fw_ds_type {
NDS_FW_DS_TYPE_FAT, NDS_FW_DS_TYPE_FAT,
NDS_FW_DS_TYPE_LITE NDS_FW_DS_TYPE_LITE,
NDS_FW_DS_TYPE_iQue
}; };
#define MAX_FW_NICKNAME_LENGTH 10 #define MAX_FW_NICKNAME_LENGTH 10

File diff suppressed because it is too large Load Diff

View File

@ -197,8 +197,8 @@ void gfx3d_VBlankSignal();
void gfx3d_VBlankEndSignal(); void gfx3d_VBlankEndSignal();
void gfx3d_Control(unsigned long v); void gfx3d_Control(unsigned long v);
u32 gfx3d_GetGXstatus(); u32 gfx3d_GetGXstatus();
void gfx3d_Add_Command_Direct(u32 cmd, u32 val); void gfx3d_sendCommandToFIFO(u32 val);
void gfx3d_Add_Command(u32 val); void gfx3d_sendCommand(u32 cmd, u32 param);
//other misc stuff //other misc stuff
void gfx3d_glGetMatrix(unsigned int mode, int index, float* dest); void gfx3d_glGetMatrix(unsigned int mode, int index, float* dest);

View File

@ -220,16 +220,12 @@ SFORMAT SF_MMU[]={
{ "MCHD", 4, 1, &MMU.CheckDMAs}, { "MCHD", 4, 1, &MMU.CheckDMAs},
//fifos //fifos
{ "F0ER", 4, 1, &MMU.ipc_fifo[0].error}, { "F0ST", 1, 1, ipc_fifo.sendTail},
{ "F0EM", 4, 1, &MMU.ipc_fifo[0].empty}, { "F0RT", 1, 1, ipc_fifo.recvTail},
{ "F0FU", 4, 1, &MMU.ipc_fifo[0].full}, { "FSB0", 4, 16, &ipc_fifo.sendBuf[0]},
{ "F0SZ", 1, 1, &MMU.ipc_fifo[0].size}, { "FRB0", 4, 16, &ipc_fifo.recvBuf[0]},
{ "F0BU", 4, 16, &MMU.ipc_fifo[0].buf}, { "FSB1", 4, 16, &ipc_fifo.sendBuf[1]},
{ "F1ER", 4, 1, &MMU.ipc_fifo[1].error}, { "FRB1", 4, 16, &ipc_fifo.recvBuf[1]},
{ "F1EM", 4, 1, &MMU.ipc_fifo[1].empty},
{ "F1FU", 4, 1, &MMU.ipc_fifo[1].full},
{ "F1SZ", 1, 1, &MMU.ipc_fifo[1].size},
{ "F1BU", 4, 16, &MMU.ipc_fifo[1].buf},
{ 0 } { 0 }
}; };