mirror of https://github.com/PCSX2/pcsx2.git
SPU2: Minor improvements to ADMA Timing
This commit is contained in:
parent
c7267d3665
commit
e15807eff8
|
@ -97,14 +97,14 @@ void V_Core::LogAutoDMA(FILE* fp)
|
|||
|
||||
void V_Core::AutoDMAReadBuffer(int mode) //mode: 0= split stereo; 1 = do not split stereo
|
||||
{
|
||||
int spos = ActiveTSA & 0x100; // Starting position passed by TSA
|
||||
bool leftbuffer = !(ActiveTSA & 0x80);
|
||||
if (spos == (OutPos & 0x100))
|
||||
{
|
||||
//ConLog("Ignoring buffer update Pos %x OutPos %x\n", spos, OutPos);
|
||||
int spos = InputPosWrite & 0x100; // Starting position passed by TSA
|
||||
bool leftbuffer = !(InputPosWrite & 0x80);
|
||||
|
||||
if (InputPosWrite == 0xFFFF) // Data request not made yet
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
AutoDMACtrl &= 0x3;
|
||||
|
||||
int size = std::min(InputDataLeft, (u32)0x200);
|
||||
if (!leftbuffer)
|
||||
size = 0x100;
|
||||
|
@ -117,7 +117,6 @@ void V_Core::AutoDMAReadBuffer(int mode) //mode: 0= split stereo; 1 = do not spl
|
|||
if (mode)
|
||||
{
|
||||
if (DMAPtr != nullptr)
|
||||
//memcpy((ADMATempBuffer+(spos<<1)),DMAPtr+InputDataProgress,0x400);
|
||||
memcpy(GetMemPtr(0x2000 + (Index << 10) + spos), DMAPtr + InputDataProgress, size);
|
||||
MADR += size;
|
||||
InputDataLeft -= 0x200;
|
||||
|
@ -131,20 +130,19 @@ void V_Core::AutoDMAReadBuffer(int mode) //mode: 0= split stereo; 1 = do not spl
|
|||
spos |= 0x200;
|
||||
else
|
||||
spos &= ~0x200;
|
||||
//ConLog("Filling %s buffer\n", leftbuffer ? "Left" : "Right");
|
||||
|
||||
if (DMAPtr != nullptr)
|
||||
//memcpy((ADMATempBuffer+spos),DMAPtr+InputDataProgress,0x200);
|
||||
memcpy(GetMemPtr(0x2000 + (Index << 10) + spos), DMAPtr + InputDataProgress, 0x200);
|
||||
MADR += 0x200;
|
||||
InputDataLeft -= 0x100;
|
||||
InputDataProgress += 0x100;
|
||||
leftbuffer = !leftbuffer;
|
||||
size -= 0x100;
|
||||
ActiveTSA += 0x80;
|
||||
ActiveTSA &= ~0x200;
|
||||
TSA = ActiveTSA;
|
||||
InputPosWrite += 0x80;
|
||||
}
|
||||
}
|
||||
if (!(InputPosWrite & 0x80))
|
||||
InputPosWrite = 0xFFFF;
|
||||
}
|
||||
|
||||
void V_Core::StartADMAWrite(u16* pMem, u32 sz)
|
||||
|
@ -159,6 +157,7 @@ void V_Core::StartADMAWrite(u16* pMem, u32 sz)
|
|||
GetDmaIndexChar(), size << 1, ActiveTSA, DMABits, AutoDMACtrl, (~Regs.ATTR) & 0xffff, OutPos);
|
||||
|
||||
InputDataProgress = 0;
|
||||
TADR = MADR + (size << 1);
|
||||
if ((AutoDMACtrl & (Index + 1)) == 0)
|
||||
{
|
||||
ActiveTSA = 0x2000 + (Index << 10);
|
||||
|
@ -168,8 +167,7 @@ void V_Core::StartADMAWrite(u16* pMem, u32 sz)
|
|||
else if (size >= 256)
|
||||
{
|
||||
InputDataLeft = size;
|
||||
AutoDMACtrl &= 3;
|
||||
if (AdmaInProgress == 0)
|
||||
if (InputPosWrite != 0xFFFF)
|
||||
{
|
||||
#ifdef PCM24_S1_INTERLEAVE
|
||||
if ((Index == 1) && ((PlayMode & 8) == 8))
|
||||
|
@ -184,16 +182,15 @@ void V_Core::StartADMAWrite(u16* pMem, u32 sz)
|
|||
AutoDMAReadBuffer(0);
|
||||
#endif
|
||||
|
||||
AdmaInProgress = 1;
|
||||
|
||||
if (!InputDataLeft)
|
||||
{
|
||||
DMAICounter = size * 4;
|
||||
LastClock = *cyclePtr;
|
||||
AdmaInProgress = 0;
|
||||
AutoDMACtrl |= ~3;
|
||||
}
|
||||
}
|
||||
AdmaInProgress = 1;
|
||||
}
|
||||
else
|
||||
{
|
||||
|
@ -202,7 +199,6 @@ void V_Core::StartADMAWrite(u16* pMem, u32 sz)
|
|||
DMAICounter = size * 4;
|
||||
LastClock = *cyclePtr;
|
||||
}
|
||||
TADR = MADR + (size << 1);
|
||||
}
|
||||
|
||||
void V_Core::PlainDMAWrite(u16* pMem, u32 size)
|
||||
|
@ -245,8 +241,6 @@ void V_Core::PlainDMAWrite(u16* pMem, u32 size)
|
|||
|
||||
void V_Core::FinishDMAwrite()
|
||||
{
|
||||
if (ActiveTSA != TSA)
|
||||
ConLog("Write WTF TSA %x Active %x\n", TSA, ActiveTSA);
|
||||
if (Index == 0)
|
||||
DMA4LogWrite(DMAPtr, ReadSize << 1);
|
||||
else
|
||||
|
|
|
@ -70,7 +70,6 @@ StereoOut32 V_Core::ReadInput_HiFi()
|
|||
ConLog("WARNING: adma buffer didn't finish with a whole block!!\n");
|
||||
}
|
||||
}
|
||||
AdmaInProgress = 0;
|
||||
InputDataLeft = 0;
|
||||
DMAICounter = 0x200 * 4;
|
||||
LastClock = *cyclePtr;
|
||||
|
@ -99,22 +98,20 @@ StereoOut32 V_Core::ReadInput()
|
|||
DebugCores[Index].admaWaveformL[OutPos % 0x100] = retval.Left;
|
||||
DebugCores[Index].admaWaveformR[OutPos % 0x100] = retval.Right;
|
||||
#endif
|
||||
|
||||
if (OutPos == 0xFF || OutPos == 0x1FF || OutPos == 0x7F || OutPos == 0x17F)
|
||||
|
||||
if (OutPos == 0x100 || OutPos == 0x0 || OutPos == 0x80 || OutPos == 0x180)
|
||||
{
|
||||
if (OutPos == 0x100)
|
||||
InputPosWrite = 0;
|
||||
else if (OutPos == 0)
|
||||
InputPosWrite = 0x100;
|
||||
|
||||
if (InputDataLeft >= 0x100)
|
||||
{
|
||||
//u8 k=InputDataLeft>=InputDataProgress;
|
||||
int oldOutPos = OutPos;
|
||||
OutPos = (OutPos + 1) & 0x1FF;
|
||||
AutoDMAReadBuffer(0);
|
||||
OutPos = oldOutPos;
|
||||
AdmaInProgress = 1;
|
||||
if (InputDataLeft < 0x100)
|
||||
{
|
||||
if ((AutoDMACtrl & (Index + 1)))
|
||||
AutoDMACtrl |= ~3;
|
||||
|
||||
if (IsDevBuild)
|
||||
{
|
||||
FileLog("[%10d] AutoDMA%c block end.\n", Cycles, GetDmaIndexChar());
|
||||
|
@ -124,12 +121,15 @@ StereoOut32 V_Core::ReadInput()
|
|||
ConLog("WARNING: adma buffer didn't finish with a whole block!!\n");
|
||||
}
|
||||
}
|
||||
AdmaInProgress = 0;
|
||||
|
||||
InputDataLeft = 0;
|
||||
DMAICounter = 0x200 * 4;
|
||||
LastClock = *cyclePtr;
|
||||
}
|
||||
}
|
||||
else
|
||||
if ((AutoDMACtrl & (Index + 1)))
|
||||
AutoDMACtrl |= ~3;
|
||||
}
|
||||
return retval;
|
||||
}
|
||||
|
|
|
@ -132,7 +132,8 @@ void SPU2writeDMA4Mem(u16* pMem, u32 size) // size now in 16bit units
|
|||
void SPU2interruptDMA4()
|
||||
{
|
||||
FileLog("[%10d] SPU2 interruptDMA4\n", Cycles);
|
||||
Cores[0].Regs.STATX |= 0x80;
|
||||
if(Cores[0].DmaMode)
|
||||
Cores[0].Regs.STATX |= 0x80;
|
||||
Cores[0].Regs.STATX &= ~0x400;
|
||||
Cores[0].TSA = Cores[0].ActiveTSA;
|
||||
}
|
||||
|
@ -140,7 +141,8 @@ void SPU2interruptDMA4()
|
|||
void SPU2interruptDMA7()
|
||||
{
|
||||
FileLog("[%10d] SPU2 interruptDMA7\n", Cycles);
|
||||
Cores[1].Regs.STATX |= 0x80;
|
||||
if (Cores[1].DmaMode)
|
||||
Cores[1].Regs.STATX |= 0x80;
|
||||
Cores[1].Regs.STATX &= ~0x400;
|
||||
Cores[1].TSA = Cores[1].ActiveTSA;
|
||||
}
|
||||
|
|
|
@ -438,7 +438,9 @@ __forceinline void TimeUpdate(u32 cClocks)
|
|||
const u32 amt = std::min(*cyclePtr - Cores[0].LastClock, (u32)Cores[0].DMAICounter);
|
||||
Cores[0].DMAICounter -= amt;
|
||||
Cores[0].LastClock = *cyclePtr;
|
||||
Cores[0].MADR += amt / 2;
|
||||
if(!Cores[0].AdmaInProgress)
|
||||
Cores[0].MADR += amt / 2;
|
||||
|
||||
if (Cores[0].DMAICounter <= 0)
|
||||
{
|
||||
if (((Cores[0].AutoDMACtrl & 1) != 1) && Cores[0].ReadSize)
|
||||
|
@ -463,7 +465,7 @@ __forceinline void TimeUpdate(u32 cClocks)
|
|||
}
|
||||
}
|
||||
}
|
||||
if (!Cores[0].DMAICounter)
|
||||
if (Cores[0].DMAICounter <= 0)
|
||||
{
|
||||
Cores[0].MADR = Cores[0].TADR;
|
||||
if (!SPU2_dummy_callback)
|
||||
|
@ -493,7 +495,8 @@ __forceinline void TimeUpdate(u32 cClocks)
|
|||
const u32 amt = std::min(*cyclePtr - Cores[1].LastClock, (u32)Cores[1].DMAICounter);
|
||||
Cores[1].DMAICounter -= amt;
|
||||
Cores[1].LastClock = *cyclePtr;
|
||||
Cores[1].MADR += amt / 2;
|
||||
if (!Cores[1].AdmaInProgress)
|
||||
Cores[1].MADR += amt / 2;
|
||||
if (Cores[1].DMAICounter <= 0)
|
||||
{
|
||||
if (((Cores[1].AutoDMACtrl & 2) != 2) && Cores[1].ReadSize)
|
||||
|
@ -519,7 +522,7 @@ __forceinline void TimeUpdate(u32 cClocks)
|
|||
}
|
||||
}
|
||||
|
||||
if (!Cores[1].DMAICounter)
|
||||
if (Cores[1].DMAICounter <= 0)
|
||||
{
|
||||
Cores[1].MADR = Cores[1].TADR;
|
||||
if (!SPU2_dummy_callback)
|
||||
|
@ -1521,11 +1524,12 @@ static void __fastcall RegWrite_Core(u16 value)
|
|||
return;
|
||||
}
|
||||
thiscore.AutoDMACtrl = value;
|
||||
if (value == 0 && thiscore.AdmaInProgress)
|
||||
if (!(value & 0x3) && thiscore.AdmaInProgress)
|
||||
{
|
||||
// Kill the current transfer so it doesn't continue
|
||||
thiscore.AdmaInProgress = 0;
|
||||
thiscore.InputDataLeft = 0;
|
||||
thiscore.DMAICounter = 0;
|
||||
}
|
||||
break;
|
||||
|
||||
|
|
Loading…
Reference in New Issue