diff --git a/desmume/src/FIFO.cpp b/desmume/src/FIFO.cpp index a0297c7c7..0ab5b3daa 100644 --- a/desmume/src/FIFO.cpp +++ b/desmume/src/FIFO.cpp @@ -1,33 +1,33 @@ -/* Copyright (C) 2006 yopyop - yopyop156@ifrance.com - yopyop156.ifrance.com - - Copyright (C) 2007 shash - - This file is part of DeSmuME - - DeSmuME is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - DeSmuME is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with DeSmuME; if not, write to the Free Software - Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA -*/ - -#include "FIFO.h" +/* Copyright (C) 2006 yopyop + yopyop156@ifrance.com + yopyop156.ifrance.com + + Copyright (C) 2007 shash + + This file is part of DeSmuME + + DeSmuME is free software; you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation; either version 2 of the License, or + (at your option) any later version. + + DeSmuME is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with DeSmuME; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA +*/ + +#include "FIFO.h" #include #include "armcpu.h" #include "debug.h" #include "mem.h" -#include "MMU.h" - +#include "MMU.h" + // ========================================================= IPC FIFO IPC_FIFO ipc_fifo[2]; // 0 - ARM9 // 1 - ARM7 @@ -47,23 +47,24 @@ void IPC_FIFOsend(u8 proc, u32 val) { u16 cnt_l = T1ReadWord(MMU.MMU_MEM[proc][0x40], 0x184); if (!(cnt_l & 0x8000)) return; // FIFO disabled + u8 proc_remote = proc ^ 1; - if (FIFO_IS_FULL(proc)) // FIFO error + if (FIFO_IS_FULL(proc_remote)) // FIFO error { cnt_l |= 0x4000; T1WriteWord(MMU.MMU_MEM[proc][0x40], 0x184, cnt_l); return; } - u16 cnt_r = T1ReadWord(MMU.MMU_MEM[proc^1][0x40], 0x184); - cnt_l &= 0xFFFE; // clear send empty bit - cnt_r &= 0xFEFF; // set recv empty bit - ipc_fifo[proc].buf[ipc_fifo[proc].tail] = val; - ipc_fifo[proc].tail++; - if (ipc_fifo[proc].tail == 16) - ipc_fifo[proc].tail = 0; + u16 cnt_r = T1ReadWord(MMU.MMU_MEM[proc_remote][0x40], 0x184); + cnt_l &= 0xFFFC; // clear send empty bit & full + cnt_r &= 0xFCFF; // set recv empty bit & full + ipc_fifo[proc_remote].buf[ipc_fifo[proc_remote].tail] = val; + ipc_fifo[proc_remote].tail++; + if (ipc_fifo[proc_remote].tail == 16) + ipc_fifo[proc_remote].tail = 0; - if (FIFO_IS_FULL(proc)) + if (FIFO_IS_FULL(proc_remote)) { cnt_l |= 0x0002; // set send full bit cnt_r |= 0x0200; // set recv full bit @@ -72,16 +73,17 @@ void IPC_FIFOsend(u8 proc, u32 val) //LOG("IPC%s send FIFO 0x%08X (l 0x%X, r 0x%X), head %02i, tail %02i\n", proc?"7":"9", val, cnt_l, cnt_r, ipc_fifo[proc].head, ipc_fifo[proc].tail); T1WriteWord(MMU.MMU_MEM[proc][0x40], 0x184, cnt_l); - T1WriteWord(MMU.MMU_MEM[proc^1][0x40], 0x184, cnt_r); + T1WriteWord(MMU.MMU_MEM[proc_remote][0x40], 0x184, cnt_r); - MMU.reg_IF[proc^1] |= ( (cnt_r & 0x0400) << 8 ); + MMU.reg_IF[proc_remote] |= ( (cnt_r & 0x0400) << 8 ); } u32 IPC_FIFOrecv(u8 proc) { u32 val = 0; u16 cnt_l = T1ReadWord(MMU.MMU_MEM[proc][0x40], 0x184); - if (!(cnt_l & 0x8000)) return (val); // FIFO disabled + if (!(cnt_l & 0x8000)) return (0); // FIFO disabled + u8 proc_remote = proc ^ 1; if ( ipc_fifo[proc].head == ipc_fifo[proc].tail ) // FIFO error { @@ -90,10 +92,10 @@ u32 IPC_FIFOrecv(u8 proc) return (val); } - u16 cnt_r = T1ReadWord(MMU.MMU_MEM[proc^1][0x40], 0x184); + u16 cnt_r = T1ReadWord(MMU.MMU_MEM[proc_remote][0x40], 0x184); - cnt_l &= 0xFFFD; // clear send full bit - cnt_r &= 0xFDFF; // set recv full bit + cnt_l &= 0xFCFF; // clear send full bit & empty + cnt_r &= 0xFFFC; // set recv full bit & empty val = ipc_fifo[proc].buf[ipc_fifo[proc].head]; ipc_fifo[proc].head++; @@ -101,15 +103,16 @@ u32 IPC_FIFOrecv(u8 proc) ipc_fifo[proc].head = 0; if ( ipc_fifo[proc].head == ipc_fifo[proc].tail ) // FIFO empty { - cnt_l |= 0x0001; - cnt_r |= 0x0100; + cnt_l |= 0x0100; + cnt_r |= 0x0001; } - //LOG("IPC%s recv FIFO 0x%08X (l 0x%X, r 0x%X), head %02i, tail %02i\n", proc?"9":"7", val, cnt_l, cnt_r, ipc_fifo[proc].head, ipc_fifo[proc].tail); + //LOG("IPC%s recv FIFO 0x%08X (l 0x%X, r 0x%X), head %02i, tail %02i\n", proc?"7":"9", val, cnt_l, cnt_r, ipc_fifo[proc].head, ipc_fifo[proc].tail); T1WriteWord(MMU.MMU_MEM[proc][0x40], 0x184, cnt_l); - T1WriteWord(MMU.MMU_MEM[proc^1][0x40], 0x184, cnt_r); + T1WriteWord(MMU.MMU_MEM[proc_remote][0x40], 0x184, cnt_r); - MMU.reg_IF[proc^1] |= ( (cnt_r & 0x0004) << 9 ); + if ((cnt_l & 0x0100) && (cnt_l & BIT(2)) ) + MMU.reg_IF[proc_remote] |= ( 1<<17 ); return (val); } @@ -135,7 +138,7 @@ void IPC_FIFOcnt(u8 proc, u16 val) T1WriteWord(MMU.MMU_MEM[proc^1][0x40], 0x184, cnt_r); MMU.reg_IF[proc] |= ((cnt_l & 0x0004) << 16); } - + // ========================================================= GFX FIFO GFX_FIFO gxFIFO; diff --git a/desmume/src/MMU.cpp b/desmume/src/MMU.cpp index 7529a61b3..ca33de994 100644 --- a/desmume/src/MMU.cpp +++ b/desmume/src/MMU.cpp @@ -2927,7 +2927,7 @@ static u32 FASTCALL _MMU_ARM9_read32(u32 adr) case REG_IF : return MMU.reg_IF[ARMCPU_ARM9]; case REG_IPCFIFORECV : - return IPC_FIFOrecv(ARMCPU_ARM7); + return IPC_FIFOrecv(ARMCPU_ARM9); case REG_TM0CNTL : case REG_TM1CNTL : case REG_TM2CNTL : @@ -3787,14 +3787,14 @@ static u32 FASTCALL _MMU_ARM7_read32(u32 adr) /* Address is an IO register */ switch(adr) { - case REG_IME : + case REG_IME : return MMU.reg_IME[ARMCPU_ARM7]; case REG_IE : return MMU.reg_IE[ARMCPU_ARM7]; case REG_IF : return MMU.reg_IF[ARMCPU_ARM7]; case REG_IPCFIFORECV : - return IPC_FIFOrecv(ARMCPU_ARM9); + return IPC_FIFOrecv(ARMCPU_ARM7); case REG_TM0CNTL : case REG_TM1CNTL : case REG_TM2CNTL : diff --git a/desmume/src/MMU.h b/desmume/src/MMU.h index fd8835c54..0b742a64e 100644 --- a/desmume/src/MMU.h +++ b/desmume/src/MMU.h @@ -39,10 +39,7 @@ extern char szRomBaseName[512]; /* theses ones for reading in rom data */ #define ROM_8(m, a) (((u8*)(m))[(a)]) - -//#define IPCFIFO 0 -//#define MAIN_MEMORY_DISP_FIFO 2 - + typedef const u32 TWaitState; struct MMU_struct {