SPU2-X: Fix for occasional reset/restart crashes caused by invalid regtable lookups.

git-svn-id: http://pcsx2.googlecode.com/svn/trunk@2909 96395faa-99c1-11dd-bbfe-3dabce05a288
This commit is contained in:
Jake.Stine 2010-04-27 12:48:14 +00:00
parent 1a1234f6af
commit d33e2edb48
5 changed files with 29 additions and 38 deletions

View File

@ -334,10 +334,14 @@ EXPORT_C_(s32) SPU2init()
{
SysMessage("SPU2: Error allocating Memory\n"); return -1;
}
// Patch up a copy of regtable that directly maps "NULLs" to SPU2 memory.
memcpy(regtable, regtable_original, sizeof(regtable));
for(int mem=0;mem<0x800;mem++)
{
u16 *ptr=regtable[mem>>1];
u16 *ptr = regtable[mem>>1];
if(!ptr) {
regtable[mem>>1] = &(spu2Ru16(mem));
}

View File

@ -48,7 +48,9 @@
PCORE(c,Revb.n)+1, \
PCORE(c,Revb.n)
u16* regtable[0x401] =
u16* regtable[0x401];
u16 const* const regtable_original[0x401] =
{
// Voice Params: 8 params, 24 voices = 0x180 bytes
PVC(0, 0),PVC(0, 1),PVC(0, 2),PVC(0, 3),PVC(0, 4),PVC(0, 5),

View File

@ -236,7 +236,7 @@ StereoOut32 V_Core::DoReverb( const StereoOut32& Input )
// Notes:
// the first -1 is to adjust for the null padding in every other upbuf sample (which
// halves the overall volume).
// The second -1 divides by two, which is part of Neill's suggestion to divide by 3.
// The second +1 divides by two, which is part of Neill's suggestion to divide by 3.
//
// According Neill the final result should be divided by 3, but currently the output
// is way too quiet for that to fly. In fact no division at all might be better.

View File

@ -192,4 +192,5 @@ Core attributes (SD_C)
#define U16P_HI(x) ( ((u16*)&(x))+1 )
extern u16* regtable[0x401];
extern u16 const* const regtable_original[0x401];

View File

@ -288,7 +288,7 @@ __forceinline void TimeUpdate(u32 cClocks)
// timings from PCSX2), just mix out a little bit, skip the rest, and hope the ship
// "rights" itself later on.
if( dClocks > TickInterval*SanityInterval )
if( dClocks > (u32)(TickInterval*SanityInterval) )
{
ConLog( " * SPU2 > TimeUpdate Sanity Check (Tick Delta: %d) (PS2 Ticks: %d)\n", dClocks/TickInterval, cClocks/TickInterval );
dClocks = TickInterval * SanityInterval;
@ -1430,20 +1430,6 @@ static RegWriteHandler * const tbl_reg_writes[0x401] =
__forceinline void SPU2_FastWrite( u32 rmem, u16 value )
{
// Check for these 2 adresses and schedule an interrupt when they get written with 0x3fff.
// This is what peops spu2 does, and it helps silent hill origins start a bit more stuff.
// Update: 0x1f900400 is core0's volume register. Interrupting here is wrong.
// So SH:O just set the volume to max, which is a pretty normal operation anyway.
// Keeping this in for reference :p
//if (value == 0x3fff && (rmem == 0x1f900500 || rmem == 0x1f900400) ) {
// // no idea which core ><
// Spdif.Info |= 4 << 0;
// SetIrqCall();
// ConLog( "SPU2-X: Schedule IRQ for odd register write. rmem = %x , value = %x \n", rmem, value);
//}
tbl_reg_writes[(rmem&0x7ff)/2]( value );
}
@ -1459,23 +1445,22 @@ void StartVoices(int core, u32 value)
for( u8 vc=0; vc<V_Core::NumVoices; vc++ )
{
if ((value>>vc) & 1)
if( !(value>>vc) & 1 ) continue;
Cores[core].Voices[vc].Start();
if( IsDevBuild )
{
Cores[core].Voices[vc].Start();
V_Voice& thisvc( Cores[core].Voices[vc] );
if( IsDevBuild )
{
V_Voice& thisvc( Cores[core].Voices[vc] );
if(MsgKeyOnOff()) ConLog(" * SPU2: KeyOn: C%dV%02d: SSA: %8x; M: %s%s%s%s; H: %02x%02x; P: %04x V: %04x/%04x; ADSR: %04x%04x\n",
core,vc,thisvc.StartA,
(Cores[core].VoiceGates[vc].DryL)?"+":"-",(Cores[core].VoiceGates[vc].DryR)?"+":"-",
(Cores[core].VoiceGates[vc].WetL)?"+":"-",(Cores[core].VoiceGates[vc].WetR)?"+":"-",
*(u8*)GetMemPtr(thisvc.StartA),*(u8 *)GetMemPtr((thisvc.StartA)+1),
thisvc.Pitch,
thisvc.Volume.Left.Value>>16,thisvc.Volume.Right.Value>>16,
thisvc.ADSR.regADSR1,thisvc.ADSR.regADSR2);
}
if(MsgKeyOnOff()) ConLog(" * SPU2: KeyOn: C%dV%02d: SSA: %8x; M: %s%s%s%s; H: %02x%02x; P: %04x V: %04x/%04x; ADSR: %04x%04x\n",
core,vc,thisvc.StartA,
(Cores[core].VoiceGates[vc].DryL)?"+":"-",(Cores[core].VoiceGates[vc].DryR)?"+":"-",
(Cores[core].VoiceGates[vc].WetL)?"+":"-",(Cores[core].VoiceGates[vc].WetR)?"+":"-",
*(u8*)GetMemPtr(thisvc.StartA),*(u8 *)GetMemPtr((thisvc.StartA)+1),
thisvc.Pitch,
thisvc.Volume.Left.Value>>16,thisvc.Volume.Right.Value>>16,
thisvc.ADSR.regADSR1,thisvc.ADSR.regADSR2);
}
}
}
@ -1485,11 +1470,10 @@ void StopVoices(int core, u32 value)
if( value == 0 ) return;
for( u8 vc=0; vc<V_Core::NumVoices; vc++ )
{
if ((value>>vc) & 1)
{
Cores[core].Voices[vc].ADSR.Releasing = true;
//if(MsgKeyOnOff()) ConLog(" * SPU2: KeyOff: Core %d; Voice %d.\n",core,vc);
}
if( !(value>>vc) & 1 ) continue;
Cores[core].Voices[vc].ADSR.Releasing = true;
//if(MsgKeyOnOff()) ConLog(" * SPU2: KeyOff: Core %d; Voice %d.\n",core,vc);
}
}