some vif/vu changes...

git-svn-id: http://pcsx2.googlecode.com/svn/trunk@2517 96395faa-99c1-11dd-bbfe-3dabce05a288
This commit is contained in:
cottonvibes 2010-01-25 06:42:09 +00:00
parent 34fa47eba1
commit 5fa30179a8
6 changed files with 32 additions and 68 deletions

View File

@ -60,7 +60,7 @@ void COP2_Unknown()
//**************************************************************************** //****************************************************************************
__forceinline void _vu0run(bool breakOnMbit) { __forceinline void _vu0run(bool breakOnMbit, bool addCycles) {
if (!(VU0.VI[REG_VPU_STAT].UL & 1)) return; if (!(VU0.VI[REG_VPU_STAT].UL & 1)) return;
@ -70,19 +70,20 @@ __forceinline void _vu0run(bool breakOnMbit) {
do { do {
// knockout kings 2002 loops here with sVU // knockout kings 2002 loops here with sVU
if (breakOnMbit && (VU0.cycle-startcycle > 0x1000)) { if (breakOnMbit && (VU0.cycle-startcycle > 0x1000)) {
Console.Warning("VU0 perma-stall, breaking execution..."); Console.Warning("VU0 stuck in infinite loop? Breaking execution!");
break; // mVU will never get here (it handles mBit internally) break; // Do games still need this?
} }
CpuVU0->ExecuteBlock(); CpuVU0->ExecuteBlock();
} while ((VU0.VI[REG_VPU_STAT].UL & 1) // E-bit Termination } while ((VU0.VI[REG_VPU_STAT].UL & 1) // E-bit Termination
&& (!breakOnMbit || !(VU0.flags & VUFLAG_MFLAGSET))); // M-bit Break && (!breakOnMbit || !(VU0.flags & VUFLAG_MFLAGSET))); // M-bit Break
//NEW // Add cycles if called from EE's COP2
cpuRegs.cycle += (VU0.cycle-startcycle)*2; if (addCycles) cpuRegs.cycle += (VU0.cycle-startcycle)*2;
} }
void _vu0WaitMicro() { _vu0run(1); } // Runs VU0 Micro Until E-bit or M-Bit End void _vu0WaitMicro() { _vu0run(1, 1); } // Runs VU0 Micro Until E-bit or M-Bit End
void _vu0FinishMicro() { _vu0run(0); } // Runs VU0 Micro Until E-Bit End void _vu0FinishMicro() { _vu0run(0, 1); } // Runs VU0 Micro Until E-Bit End
void vu0Finish() { _vu0run(0, 0); } // Runs VU0 Micro Until E-Bit End (doesn't stall EE)
namespace R5900 { namespace R5900 {
namespace Interpreter{ namespace Interpreter{
@ -333,31 +334,3 @@ void VFCSET() { VU0.code = cpuRegs.code; _vuFCSET(&VU0); }
void VFCGET() { VU0.code = cpuRegs.code; _vuFCGET(&VU0); } void VFCGET() { VU0.code = cpuRegs.code; _vuFCGET(&VU0); }
void VXITOP() { VU0.code = cpuRegs.code; _vuXITOP(&VU0); } void VXITOP() { VU0.code = cpuRegs.code; _vuXITOP(&VU0); }
// fixme: Shouldn't anything calling this function be calling vu0WaitMicro instead?
// Meaning that this function stalls, but doesn't increment the cpuRegs.cycle like
// you would think it should.
// Well, we can always test that out...
//#define USE_WAIT_MICRO
void vu0Finish()
{
#ifdef USE_WAIT_MICRO
_vu0WaitMicro();
#else
if( (VU0.VI[REG_VPU_STAT].UL & 0x1) ) {
int i = 0;
while(i++ < 32) {
CpuVU0->ExecuteBlock();
if(!(VU0.VI[REG_VPU_STAT].UL & 0x1))
break;
}
if(VU0.VI[REG_VPU_STAT].UL & 0x1) {
VU0.VI[REG_VPU_STAT].UL &= ~1;
// this log tends to spam a lot (MGS3)
//Console.Warning("vu0Finish > stall aborted by force.");
}
}
#endif
}

View File

@ -50,11 +50,11 @@ void __fastcall vu0ExecMicro(u32 addr) {
DevCon.Warning("vu0ExecMicro > Stalling for previous microprogram to finish"); DevCon.Warning("vu0ExecMicro > Stalling for previous microprogram to finish");
vu0Finish(); vu0Finish();
} }
VU0.VI[REG_VPU_STAT].UL|= 0x1;
VU0.VI[REG_VPU_STAT].UL&= ~0xAE;
// If an unsigned variable isn't -1? --arcum42 VU0.VI[REG_VPU_STAT].UL &= ~0xFF;
if (addr != (u32)-1) VU0.VI[REG_TPC].UL = addr; VU0.VI[REG_VPU_STAT].UL |= 0x01;
if ((s32)addr != -1) VU0.VI[REG_TPC].UL = addr;
_vuExecMicroDebug(VU0); _vuExecMicroDebug(VU0);
CpuVU0->ExecuteBlock(); CpuVU0->ExecuteBlock();

View File

@ -44,8 +44,7 @@ static int count;
void __fastcall vu1ExecMicro(u32 addr) void __fastcall vu1ExecMicro(u32 addr)
{ {
while(VU0.VI[REG_VPU_STAT].UL & 0x100) while(VU0.VI[REG_VPU_STAT].UL & 0x100) {
{
VUM_LOG("vu1ExecMicro > Stalling until current microprogram finishes"); VUM_LOG("vu1ExecMicro > Stalling until current microprogram finishes");
CpuVU1->ExecuteBlock(); CpuVU1->ExecuteBlock();
} }
@ -53,10 +52,11 @@ void __fastcall vu1ExecMicro(u32 addr)
VUM_LOG("vu1ExecMicro %x", addr); VUM_LOG("vu1ExecMicro %x", addr);
VUM_LOG("vu1ExecMicro %x (count=%d)", addr, count++); VUM_LOG("vu1ExecMicro %x (count=%d)", addr, count++);
VU0.VI[REG_VPU_STAT].UL|= 0x100; VU0.VI[REG_VPU_STAT].UL &= ~0xFF00;
VU0.VI[REG_VPU_STAT].UL&= ~0x7E000; VU0.VI[REG_VPU_STAT].UL |= 0x0100;
vif1Regs->stat.VEW = true; vif1Regs->stat.VEW = true;
if (addr != -1) VU1.VI[REG_TPC].UL = addr; if ((s32)addr != -1) VU1.VI[REG_TPC].UL = addr;
_vuExecMicroDebug(VU1); _vuExecMicroDebug(VU1);
CpuVU1->ExecuteBlock(); CpuVU1->ExecuteBlock();

View File

@ -26,10 +26,8 @@ vifStruct vif0;
__forceinline void vif0FLUSH() __forceinline void vif0FLUSH()
{ {
int _cycles = VU0.cycle; int _cycles = VU0.cycle;
// Run VU0 until finish, don't add cycles to EE
// fixme: this code should call _vu0WaitMicro instead? I'm not sure if // because its vif stalling not the EE core...
// it's purposefully ignoring ee cycles or not (see below for more)
vu0Finish(); vu0Finish();
g_vifCycles += (VU0.cycle - _cycles) * BIAS; g_vifCycles += (VU0.cycle - _cycles) * BIAS;
} }

View File

@ -31,13 +31,8 @@ __forceinline void vif1FLUSH()
{ {
int _cycles = VU1.cycle; int _cycles = VU1.cycle;
// fixme: Same as above, is this a "stalling" offense? I think the cycles should if (VU0.VI[REG_VPU_STAT].UL & 0x100) {
// be added to cpuRegs.cycle instead of g_vifCycles, but not sure (air) do {
if (VU0.VI[REG_VPU_STAT].UL & 0x100)
{
do
{
CpuVU1->ExecuteBlock(); CpuVU1->ExecuteBlock();
} }
while (VU0.VI[REG_VPU_STAT].UL & 0x100); while (VU0.VI[REG_VPU_STAT].UL & 0x100);

View File

@ -29,10 +29,14 @@
_vifT void vifCMD_Null(); _vifT void vifCMD_Null();
_f void vuExecMicro(int idx, u32 addr) { _f void vifFlush(int idx) {
VURegs* VU = nVif[idx].VU;
if (!idx) vif0FLUSH(); if (!idx) vif0FLUSH();
else vif1FLUSH(); else vif1FLUSH();
}
_f void vuExecMicro(int idx, u32 addr) {
VURegs* VU = nVif[idx].VU;
vifFlush(idx);
if (VU->vifRegs->itops > (idx ? 0x3ffu : 0xffu)) { if (VU->vifRegs->itops > (idx ? 0x3ffu : 0xffu)) {
Console.WriteLn("VIF%d ITOP overrun! %x", idx, VU->vifRegs->itops); Console.WriteLn("VIF%d ITOP overrun! %x", idx, VU->vifRegs->itops);
@ -62,11 +66,6 @@ _f void vuExecMicro(int idx, u32 addr) {
else vu1ExecMicro(addr); else vu1ExecMicro(addr);
} }
_f void vifFlush(int idx) {
if (!idx) vif0FLUSH();
else vif1FLUSH();
}
u8 schedulepath3msk = 0; u8 schedulepath3msk = 0;
void Vif1MskPath3() { void Vif1MskPath3() {
@ -354,7 +353,7 @@ _vifT void vifCMD_Mark()
_vifT void vifCMD_MPG() _vifT void vifCMD_MPG()
{ {
if (!idx) vifFlush(idx); // Only Vif0 Flush!? vifFlush(idx);
int vifNum = (u8)(vifXRegs->code >> 16); int vifNum = (u8)(vifXRegs->code >> 16);
if(!vifNum) vifNum = 256; if(!vifNum) vifNum = 256;
@ -364,7 +363,6 @@ _vifT void vifCMD_MPG()
_vifT void vifCMD_MSCALF() _vifT void vifCMD_MSCALF()
{ {
if (idx) vif1FLUSH(); // Only Vif1 Flush!?
vuExecMicro(idx, (u16)(vifXRegs->code) << 3); vuExecMicro(idx, (u16)(vifXRegs->code) << 3);
vifX.cmd &= ~0x7f; vifX.cmd &= ~0x7f;
} }
@ -410,8 +408,8 @@ _vifT void vifCMD_Null() // invalid opcode
_vifT void vifCMD_Offset() _vifT void vifCMD_Offset()
{ {
vif1Only(); vif1Only();
vif1Regs->ofst = vif1Regs->code & 0x3ff;
vif1Regs->stat.DBF = false; vif1Regs->stat.DBF = false;
vif1Regs->ofst = vif1Regs->code & 0x3ff;
vif1Regs->tops = vif1Regs->base; vif1Regs->tops = vif1Regs->base;
vif1.cmd &= ~0x7f; vif1.cmd &= ~0x7f;
} }