diff --git a/pcsx2/SPU2/Mixer.cpp b/pcsx2/SPU2/Mixer.cpp index e6dff6b010403..509ac0b452833 100644 --- a/pcsx2/SPU2/Mixer.cpp +++ b/pcsx2/SPU2/Mixer.cpp @@ -576,14 +576,6 @@ StereoOut32 V_Core::Mix(const VoiceMixSet& inVoices, const StereoOut32& Input, c // // On the other hand, updating the buffer is cheap and easy, so might as well. ;) - Reverb_AdvanceBuffer(); // Updates the reverb work area as well, if needed. - - // ToDo: - // Bad EndA causes memory corruption. Bad for us, unknown on PS2! - // According to no$psx, effects always run but don't always write back, so the FxEnable check may be wrong - if (!FxEnable || EffectsEndA >= 0x100000) - return TD; - StereoOut32 TW; // Mix Input, Voice, and External data: diff --git a/pcsx2/SPU2/RegTable.cpp b/pcsx2/SPU2/RegTable.cpp index 3962d0d7066e7..65c090b4c335c 100644 --- a/pcsx2/SPU2/RegTable.cpp +++ b/pcsx2/SPU2/RegTable.cpp @@ -100,8 +100,8 @@ static std::array ComputeRegTable() PVCA(0, 12), PVCA(0, 13), PVCA(0, 14), PVCA(0, 15), PVCA(0, 16), PVCA(0, 17), PVCA(0, 18), PVCA(0, 19), PVCA(0, 20), PVCA(0, 21), PVCA(0, 22), PVCA(0, 23), - PCORE(0, ExtEffectsStartA) + 1, - PCORE(0, ExtEffectsStartA), + PCORE(0, EffectsStartA) + 1, + PCORE(0, EffectsStartA), PREVB_REG(0, APF1_SIZE), PREVB_REG(0, APF2_SIZE), @@ -126,8 +126,8 @@ static std::array ComputeRegTable() PREVB_REG(0, APF2_L_DST), PREVB_REG(0, APF2_R_DST), - PCORE(0, ExtEffectsEndA) + 1, - PCORE(0, ExtEffectsEndA), + PCORE(0, EffectsEndA) + 1, + PCORE(0, EffectsEndA), PCORE(0, Regs.ENDX), PCORE(0, Regs.ENDX) + 1, @@ -203,8 +203,8 @@ static std::array ComputeRegTable() PVCA(1, 12), PVCA(1, 13), PVCA(1, 14), PVCA(1, 15), PVCA(1, 16), PVCA(1, 17), PVCA(1, 18), PVCA(1, 19), PVCA(1, 20), PVCA(1, 21), PVCA(1, 22), PVCA(1, 23), - PCORE(1, ExtEffectsStartA) + 1, - PCORE(1, ExtEffectsStartA), + PCORE(1, EffectsStartA) + 1, + PCORE(1, EffectsStartA), PREVB_REG(1, APF1_SIZE), PREVB_REG(1, APF2_SIZE), @@ -229,8 +229,8 @@ static std::array ComputeRegTable() PREVB_REG(1, APF2_L_DST), PREVB_REG(1, APF2_R_DST), - PCORE(1, ExtEffectsEndA) + 1, - PCORE(1, ExtEffectsEndA), + PCORE(1, EffectsEndA) + 1, + PCORE(1, EffectsEndA), PCORE(1, Regs.ENDX), PCORE(1, Regs.ENDX) + 1, diff --git a/pcsx2/SPU2/Reverb.cpp b/pcsx2/SPU2/Reverb.cpp index a3e3f5ab8b8c7..2f007df04d9fa 100644 --- a/pcsx2/SPU2/Reverb.cpp +++ b/pcsx2/SPU2/Reverb.cpp @@ -17,38 +17,42 @@ #include "Global.h" #include -__forceinline s32 V_Core::RevbGetIndexer(s32 offset) -{ - u32 pos = ReverbX + offset; - - // Fast and simple single step wrapping, made possible by the preparation of the - // effects buffer addresses. - - if (pos > EffectsEndA) - { - pos -= EffectsEndA + 1; - pos += EffectsStartA; - } - assert(pos >= EffectsStartA && pos <= EffectsEndA); - return pos; -} - -void V_Core::Reverb_AdvanceBuffer() +void V_Core::AnalyzeReverbPreset() { - if (RevBuffers.NeedsUpdated) - UpdateEffectsBufferSize(); - - if ((Cycles & 1) && (EffectsBufferSize > 0)) - { - ReverbX += 1; - if (ReverbX >= (u32)EffectsBufferSize) - ReverbX = 0; - } + Console.WriteLn("Reverb Parameter Update for Core %d:", Index); + Console.WriteLn("----------------------------------------------------------"); + + Console.WriteLn(" IN_COEF_L, IN_COEF_R 0x%08x, 0x%08x", Revb.IN_COEF_L, Revb.IN_COEF_R); + Console.WriteLn(" APF1_SIZE, APF2_SIZE 0x%08x, 0x%08x", Revb.APF1_SIZE, Revb.APF2_SIZE); + Console.WriteLn(" APF1_VOL, APF2_VOL 0x%08x, 0x%08x", Revb.APF1_VOL, Revb.APF2_VOL); + + Console.WriteLn(" COMB1_VOL 0x%08x", Revb.COMB1_VOL); + Console.WriteLn(" COMB2_VOL 0x%08x", Revb.COMB2_VOL); + Console.WriteLn(" COMB3_VOL 0x%08x", Revb.COMB3_VOL); + Console.WriteLn(" COMB4_VOL 0x%08x", Revb.COMB4_VOL); + + Console.WriteLn(" COMB1_L_SRC, COMB1_R_SRC 0x%08x, 0x%08x", Revb.COMB1_L_SRC, Revb.COMB1_R_SRC); + Console.WriteLn(" COMB2_L_SRC, COMB2_R_SRC 0x%08x, 0x%08x", Revb.COMB2_L_SRC, Revb.COMB2_R_SRC); + Console.WriteLn(" COMB3_L_SRC, COMB3_R_SRC 0x%08x, 0x%08x", Revb.COMB3_L_SRC, Revb.COMB3_R_SRC); + Console.WriteLn(" COMB4_L_SRC, COMB4_R_SRC 0x%08x, 0x%08x", Revb.COMB4_L_SRC, Revb.COMB4_R_SRC); + + Console.WriteLn(" SAME_L_SRC, SAME_R_SRC 0x%08x, 0x%08x", Revb.SAME_L_SRC, Revb.SAME_R_SRC); + Console.WriteLn(" DIFF_L_SRC, DIFF_R_SRC 0x%08x, 0x%08x", Revb.DIFF_L_SRC, Revb.DIFF_R_SRC); + Console.WriteLn(" SAME_L_DST, SAME_R_DST 0x%08x, 0x%08x", Revb.SAME_L_DST, Revb.SAME_R_DST); + Console.WriteLn(" DIFF_L_DST, DIFF_R_DST 0x%08x, 0x%08x", Revb.DIFF_L_DST, Revb.DIFF_R_DST); + Console.WriteLn(" IIR_VOL, WALL_VOL 0x%08x, 0x%08x", Revb.IIR_VOL, Revb.WALL_VOL); + + Console.WriteLn(" APF1_L_DST 0x%08x", Revb.APF1_L_DST); + Console.WriteLn(" APF1_R_DST 0x%08x", Revb.APF1_R_DST); + Console.WriteLn(" APF2_L_DST 0x%08x", Revb.APF2_L_DST); + Console.WriteLn(" APF2_R_DST 0x%08x", Revb.APF2_R_DST); + + Console.WriteLn(" EffectStartA 0x%x", EffectsStartA & 0x3f'ffff); + Console.WriteLn(" EffectsEndA 0x%x", EffectsEndA & 0x3f'ffff); + Console.WriteLn("----------------------------------------------------------"); } - - static constexpr u32 NUM_TAPS = 39; // 39 tap filter, the 0's could be optimized out static constexpr std::array filter_coefs = { @@ -112,7 +116,6 @@ s32 __forceinline V_Core::ReverbDownsample(bool right) return out; } - StereoOut32 __forceinline V_Core::ReverbUpsample(bool phase) { s32 ls = 0, rs = 0; @@ -124,7 +127,6 @@ StereoOut32 __forceinline V_Core::ReverbUpsample(bool phase) } else { - for (u32 i = 0; i < (NUM_TAPS >> 1) + 1; i++) { ls += RevbUpBuf[0][(((RevbSampleBufPos - NUM_TAPS) >> 1) + i) & 63] * filter_coefs[i * 2]; @@ -140,14 +142,24 @@ StereoOut32 __forceinline V_Core::ReverbUpsample(bool phase) rs >>= 14; rs = std::clamp(rs, INT16_MIN, INT16_MAX); - return StereoOut32(ls, rs); + return {ls, rs}; } -///////////////////////////////////////////////////////////////////////////////////////// +__forceinline s32 V_Core::RevbGetIndexer(s32 offset) +{ + u32 start = EffectsStartA & 0x3f'ffff; + u32 end = (EffectsEndA & 0x3f'ffff) | 0xffff; + + u32 x = ((Cycles >> 1) + offset) % ((end - start) + 1); + + x += start; + + return x & 0xf'ffff; +} StereoOut32 V_Core::DoReverb(const StereoOut32& Input) { - if (EffectsBufferSize <= 0) + if (EffectsStartA >= EffectsEndA) { return StereoOut32::Empty; } @@ -159,23 +171,23 @@ StereoOut32 V_Core::DoReverb(const StereoOut32& Input) // Calculate the read/write addresses we'll be needing for this session of reverb. - const u32 same_src = RevbGetIndexer(R ? RevBuffers.SAME_R_SRC : RevBuffers.SAME_L_SRC); - const u32 same_dst = RevbGetIndexer(R ? RevBuffers.SAME_R_DST : RevBuffers.SAME_L_DST); - const u32 same_prv = RevbGetIndexer(R ? RevBuffers.SAME_R_PRV : RevBuffers.SAME_L_PRV); + const u32 same_src = RevbGetIndexer(R ? Revb.SAME_R_SRC : Revb.SAME_L_SRC); + const u32 same_dst = RevbGetIndexer(R ? Revb.SAME_R_DST : Revb.SAME_L_DST); + const u32 same_prv = RevbGetIndexer(R ? Revb.SAME_R_DST - 1 : Revb.SAME_L_DST - 1); - const u32 diff_src = RevbGetIndexer(R ? RevBuffers.DIFF_L_SRC : RevBuffers.DIFF_R_SRC); - const u32 diff_dst = RevbGetIndexer(R ? RevBuffers.DIFF_R_DST : RevBuffers.DIFF_L_DST); - const u32 diff_prv = RevbGetIndexer(R ? RevBuffers.DIFF_R_PRV : RevBuffers.DIFF_L_PRV); + const u32 diff_src = RevbGetIndexer(R ? Revb.DIFF_L_SRC : Revb.DIFF_R_SRC); + const u32 diff_dst = RevbGetIndexer(R ? Revb.DIFF_R_DST : Revb.DIFF_L_DST); + const u32 diff_prv = RevbGetIndexer(R ? Revb.DIFF_R_DST - 1 : Revb.DIFF_L_DST - 1); - const u32 comb1_src = RevbGetIndexer(R ? RevBuffers.COMB1_R_SRC : RevBuffers.COMB1_L_SRC); - const u32 comb2_src = RevbGetIndexer(R ? RevBuffers.COMB2_R_SRC : RevBuffers.COMB2_L_SRC); - const u32 comb3_src = RevbGetIndexer(R ? RevBuffers.COMB3_R_SRC : RevBuffers.COMB3_L_SRC); - const u32 comb4_src = RevbGetIndexer(R ? RevBuffers.COMB4_R_SRC : RevBuffers.COMB4_L_SRC); + const u32 comb1_src = RevbGetIndexer(R ? Revb.COMB1_R_SRC : Revb.COMB1_L_SRC); + const u32 comb2_src = RevbGetIndexer(R ? Revb.COMB2_R_SRC : Revb.COMB2_L_SRC); + const u32 comb3_src = RevbGetIndexer(R ? Revb.COMB3_R_SRC : Revb.COMB3_L_SRC); + const u32 comb4_src = RevbGetIndexer(R ? Revb.COMB4_R_SRC : Revb.COMB4_L_SRC); - const u32 apf1_src = RevbGetIndexer(R ? RevBuffers.APF1_R_SRC : RevBuffers.APF1_L_SRC); - const u32 apf1_dst = RevbGetIndexer(R ? RevBuffers.APF1_R_DST : RevBuffers.APF1_L_DST); - const u32 apf2_src = RevbGetIndexer(R ? RevBuffers.APF2_R_SRC : RevBuffers.APF2_L_SRC); - const u32 apf2_dst = RevbGetIndexer(R ? RevBuffers.APF2_R_DST : RevBuffers.APF2_L_DST); + const u32 apf1_src = RevbGetIndexer(R ? (Revb.APF1_R_DST - Revb.APF1_SIZE) : (Revb.APF1_L_DST - Revb.APF1_SIZE)); + const u32 apf1_dst = RevbGetIndexer(R ? Revb.APF1_R_DST : Revb.APF1_L_DST); + const u32 apf2_src = RevbGetIndexer(R ? (Revb.APF2_R_DST - Revb.APF2_SIZE) : (Revb.APF2_L_DST - Revb.APF2_SIZE)); + const u32 apf2_dst = RevbGetIndexer(R ? Revb.APF2_R_DST : Revb.APF2_L_DST); // ----------------------------------------- // Optimized IRQ Testing ! diff --git a/pcsx2/SPU2/defs.h b/pcsx2/SPU2/defs.h index 69c659914ad6f..21108dd3379a7 100644 --- a/pcsx2/SPU2/defs.h +++ b/pcsx2/SPU2/defs.h @@ -279,44 +279,6 @@ struct V_Reverb u32 APF2_R_DST; }; -struct V_ReverbBuffers -{ - s32 SAME_L_SRC; - s32 SAME_R_SRC; - s32 DIFF_R_SRC; - s32 DIFF_L_SRC; - s32 SAME_L_DST; - s32 SAME_R_DST; - s32 DIFF_L_DST; - s32 DIFF_R_DST; - - s32 COMB1_L_SRC; - s32 COMB1_R_SRC; - s32 COMB2_L_SRC; - s32 COMB2_R_SRC; - s32 COMB3_L_SRC; - s32 COMB3_R_SRC; - s32 COMB4_L_SRC; - s32 COMB4_R_SRC; - - s32 APF1_L_DST; - s32 APF1_R_DST; - s32 APF2_L_DST; - s32 APF2_R_DST; - - s32 SAME_L_PRV; - s32 SAME_R_PRV; - s32 DIFF_L_PRV; - s32 DIFF_R_PRV; - - s32 APF1_L_SRC; - s32 APF1_R_SRC; - s32 APF2_L_SRC; - s32 APF2_R_SRC; - - bool NeedsUpdated; -}; - struct V_SPDIF { u16 Out; @@ -425,22 +387,12 @@ struct V_Core u32 InputDataProgress; V_Reverb Revb; // Reverb Registers - V_ReverbBuffers RevBuffers; // buffer pointers for reverb, pre-calculated and pre-clipped. s32 RevbDownBuf[2][64]; // Downsample buffer for reverb, one for each channel s32 RevbUpBuf[2][64]; // Upsample buffer for reverb, one for each channel u32 RevbSampleBufPos; u32 EffectsStartA; u32 EffectsEndA; - u32 ExtEffectsStartA; - u32 ExtEffectsEndA; - u32 ReverbX; - - // Current size of and position of the effects buffer. Pre-caculated when the effects start - // or end position registers are written. CAN BE NEGATIVE OR ZERO, in which - // case reverb should be disabled. - s32 EffectsBufferSize; - u32 EffectsBufferStart; V_CoreRegs Regs; // Registers @@ -490,8 +442,6 @@ struct V_Core void UpdateEffectsBufferSize(); void AnalyzeReverbPreset(); - s32 EffectsBufferIndexer(s32 offset) const; - void WriteRegPS1(u32 mem, u16 value); u16 ReadRegPS1(u32 mem); @@ -500,7 +450,6 @@ struct V_Core // -------------------------------------------------------------------------------------- StereoOut32 Mix(const VoiceMixSet& inVoices, const StereoOut32& Input, const StereoOut32& Ext); - void Reverb_AdvanceBuffer(); StereoOut32 DoReverb(const StereoOut32& Input); s32 RevbGetIndexer(s32 offset); diff --git a/pcsx2/SPU2/spu2sys.cpp b/pcsx2/SPU2/spu2sys.cpp index 78890ecfa78f1..7e77f8d7b2390 100644 --- a/pcsx2/SPU2/spu2sys.cpp +++ b/pcsx2/SPU2/spu2sys.cpp @@ -141,7 +141,6 @@ void V_Core::Init(int index) InputPosWrite = 0x100; InputDataProgress = 0; InputDataTransferred = 0; - ReverbX = 0; LastEffect.Left = 0; LastEffect.Right = 0; CoreEnabled = 0; @@ -182,8 +181,6 @@ void V_Core::Init(int index) Regs.VMIXER = 0xFFFFFF; EffectsStartA = c ? 0xFFFF8 : 0xEFFF8; EffectsEndA = c ? 0xFFFFF : 0xEFFFF; - ExtEffectsStartA = EffectsStartA; - ExtEffectsEndA = EffectsEndA; FxEnable = false; // Uninitialized it's 0 for both cores. Resetting libs however may set this to 0 or 1. // These are real PS2 values, mainly constant apart from a few bits: 0x3220EAA4, 0x40505E9C. @@ -221,112 +218,9 @@ void V_Core::Init(int index) Regs.STATX = 0x80; Regs.ENDX = 0xffffff; // PS2 confirmed - RevBuffers.NeedsUpdated = true; RevbSampleBufPos = 0; memset(RevbDownBuf, 0, sizeof(RevbDownBuf)); memset(RevbUpBuf, 0, sizeof(RevbUpBuf)); - - UpdateEffectsBufferSize(); -} - -void V_Core::AnalyzeReverbPreset() -{ - SPU2::ConLog("Reverb Parameter Update for Core %d:\n", Index); - SPU2::ConLog("----------------------------------------------------------\n"); - - SPU2::ConLog(" IN_COEF_L, IN_COEF_R 0x%08x, 0x%08x\n", Revb.IN_COEF_L, Revb.IN_COEF_R); - SPU2::ConLog(" APF1_SIZE, APF2_SIZE 0x%08x, 0x%08x\n", Revb.APF1_SIZE, Revb.APF2_SIZE); - SPU2::ConLog(" APF1_VOL, APF2_VOL 0x%08x, 0x%08x\n", Revb.APF1_VOL, Revb.APF2_VOL); - - SPU2::ConLog(" COMB1_VOL 0x%08x\n", Revb.COMB1_VOL); - SPU2::ConLog(" COMB2_VOL 0x%08x\n", Revb.COMB2_VOL); - SPU2::ConLog(" COMB3_VOL 0x%08x\n", Revb.COMB3_VOL); - SPU2::ConLog(" COMB4_VOL 0x%08x\n", Revb.COMB4_VOL); - - SPU2::ConLog(" COMB1_L_SRC, COMB1_R_SRC 0x%08x, 0x%08x\n", Revb.COMB1_L_SRC, Revb.COMB1_R_SRC); - SPU2::ConLog(" COMB2_L_SRC, COMB2_R_SRC 0x%08x, 0x%08x\n", Revb.COMB2_L_SRC, Revb.COMB2_R_SRC); - SPU2::ConLog(" COMB3_L_SRC, COMB3_R_SRC 0x%08x, 0x%08x\n", Revb.COMB3_L_SRC, Revb.COMB3_R_SRC); - SPU2::ConLog(" COMB4_L_SRC, COMB4_R_SRC 0x%08x, 0x%08x\n", Revb.COMB4_L_SRC, Revb.COMB4_R_SRC); - - SPU2::ConLog(" SAME_L_SRC, SAME_R_SRC 0x%08x, 0x%08x\n", Revb.SAME_L_SRC, Revb.SAME_R_SRC); - SPU2::ConLog(" DIFF_L_SRC, DIFF_R_SRC 0x%08x, 0x%08x\n", Revb.DIFF_L_SRC, Revb.DIFF_R_SRC); - SPU2::ConLog(" SAME_L_DST, SAME_R_DST 0x%08x, 0x%08x\n", Revb.SAME_L_DST, Revb.SAME_R_DST); - SPU2::ConLog(" DIFF_L_DST, DIFF_R_DST 0x%08x, 0x%08x\n", Revb.DIFF_L_DST, Revb.DIFF_R_DST); - SPU2::ConLog(" IIR_VOL, WALL_VOL 0x%08x, 0x%08x\n", Revb.IIR_VOL, Revb.WALL_VOL); - - SPU2::ConLog(" APF1_L_DST 0x%08x\n", Revb.APF1_L_DST); - SPU2::ConLog(" APF1_R_DST 0x%08x\n", Revb.APF1_R_DST); - SPU2::ConLog(" APF2_L_DST 0x%08x\n", Revb.APF2_L_DST); - SPU2::ConLog(" APF2_R_DST 0x%08x\n", Revb.APF2_R_DST); - - SPU2::ConLog(" EffectsBufferSize 0x%x\n", EffectsBufferSize); - SPU2::ConLog("----------------------------------------------------------\n"); -} -s32 V_Core::EffectsBufferIndexer(s32 offset) const -{ - // Should offsets be multipled by 4 or not? Reverse-engineering of IOP code reveals - // that it *4's all addresses before upping them to the SPU2 -- so our buffers are - // already x4'd. It doesn't really make sense that we should x4 them again, and this - // seems to work. (feedback-free in bios and DDS) --air - - // Need to use modulus here, because games can and will drop the buffer size - // without notice, and it leads to offsets several times past the end of the buffer. - - if (static_cast(offset) >= static_cast(EffectsBufferSize)) - return EffectsStartA + (offset % EffectsBufferSize) + (offset < 0 ? EffectsBufferSize : 0); - else - return EffectsStartA + offset; -} - -void V_Core::UpdateEffectsBufferSize() -{ - const s32 newbufsize = EffectsEndA - EffectsStartA + 1; - - RevBuffers.NeedsUpdated = false; - EffectsBufferSize = newbufsize; - EffectsBufferStart = EffectsStartA; - - if (EffectsBufferSize <= 0) - return; - - // debug: shows reverb parameters in console - if (SPU2::MsgToConsole()) - AnalyzeReverbPreset(); - - // Rebuild buffer indexers. - RevBuffers.COMB1_L_SRC = EffectsBufferIndexer(Revb.COMB1_L_SRC); - RevBuffers.COMB1_R_SRC = EffectsBufferIndexer(Revb.COMB1_R_SRC); - RevBuffers.COMB2_L_SRC = EffectsBufferIndexer(Revb.COMB2_L_SRC); - RevBuffers.COMB2_R_SRC = EffectsBufferIndexer(Revb.COMB2_R_SRC); - RevBuffers.COMB3_L_SRC = EffectsBufferIndexer(Revb.COMB3_L_SRC); - RevBuffers.COMB3_R_SRC = EffectsBufferIndexer(Revb.COMB3_R_SRC); - RevBuffers.COMB4_L_SRC = EffectsBufferIndexer(Revb.COMB4_L_SRC); - RevBuffers.COMB4_R_SRC = EffectsBufferIndexer(Revb.COMB4_R_SRC); - - RevBuffers.SAME_L_DST = EffectsBufferIndexer(Revb.SAME_L_DST); - RevBuffers.SAME_R_DST = EffectsBufferIndexer(Revb.SAME_R_DST); - RevBuffers.DIFF_L_DST = EffectsBufferIndexer(Revb.DIFF_L_DST); - RevBuffers.DIFF_R_DST = EffectsBufferIndexer(Revb.DIFF_R_DST); - - RevBuffers.SAME_L_SRC = EffectsBufferIndexer(Revb.SAME_L_SRC); - RevBuffers.SAME_R_SRC = EffectsBufferIndexer(Revb.SAME_R_SRC); - RevBuffers.DIFF_L_SRC = EffectsBufferIndexer(Revb.DIFF_L_SRC); - RevBuffers.DIFF_R_SRC = EffectsBufferIndexer(Revb.DIFF_R_SRC); - - RevBuffers.APF1_L_DST = EffectsBufferIndexer(Revb.APF1_L_DST); - RevBuffers.APF1_R_DST = EffectsBufferIndexer(Revb.APF1_R_DST); - RevBuffers.APF2_L_DST = EffectsBufferIndexer(Revb.APF2_L_DST); - RevBuffers.APF2_R_DST = EffectsBufferIndexer(Revb.APF2_R_DST); - - RevBuffers.SAME_L_PRV = EffectsBufferIndexer(Revb.SAME_L_DST - 1); - RevBuffers.SAME_R_PRV = EffectsBufferIndexer(Revb.SAME_R_DST - 1); - RevBuffers.DIFF_L_PRV = EffectsBufferIndexer(Revb.DIFF_L_DST - 1); - RevBuffers.DIFF_R_PRV = EffectsBufferIndexer(Revb.DIFF_R_DST - 1); - - RevBuffers.APF1_L_SRC = EffectsBufferIndexer(Revb.APF1_L_DST - Revb.APF1_SIZE); - RevBuffers.APF1_R_SRC = EffectsBufferIndexer(Revb.APF1_R_DST - Revb.APF1_SIZE); - RevBuffers.APF2_L_SRC = EffectsBufferIndexer(Revb.APF2_L_DST - Revb.APF2_SIZE); - RevBuffers.APF2_R_SRC = EffectsBufferIndexer(Revb.APF2_R_DST - Revb.APF2_SIZE); } void V_Voice::Start() @@ -776,12 +670,7 @@ void V_Core::WriteRegPS1(u32 mem, u16 value) break; case 0x1da2: // Reverb work area start - { EffectsStartA = map_spu1to2(value); - //EffectsEndA = 0xFFFFF; // fixed EndA in psx mode - Cores[0].RevBuffers.NeedsUpdated = true; - ReverbX = 0; - } break; case 0x1da4: @@ -1285,7 +1174,7 @@ static void RegWrite_Core(u16 value) { bool irqe = thiscore.IRQEnable; int bit0 = thiscore.AttrBit0; - bool fxenable = thiscore.FxEnable; + bool oldFXenable = thiscore.FxEnable; u8 oldDmaMode = thiscore.DmaMode; thiscore.AttrBit0 = (value >> 0) & 0x01; //1 bit @@ -1300,12 +1189,10 @@ static void RegWrite_Core(u16 value) // no clue thiscore.Regs.ATTR = value & 0xffff; - if (fxenable && !thiscore.FxEnable && (thiscore.EffectsStartA != thiscore.ExtEffectsStartA || thiscore.EffectsEndA != thiscore.ExtEffectsEndA)) + if (thiscore.FxEnable && !oldFXenable) { - thiscore.EffectsStartA = thiscore.ExtEffectsStartA; - thiscore.EffectsEndA = thiscore.ExtEffectsEndA; - thiscore.ReverbX = 0; - thiscore.RevBuffers.NeedsUpdated = true; + if (SPU2::MsgToConsole()) + thiscore.AnalyzeReverbPreset(); } if (!thiscore.DmaMode && !(thiscore.Regs.STATX & 0x400)) @@ -1464,48 +1351,6 @@ static void RegWrite_Core(u16 value) thiscore.Regs.ENDX &= 0xffff; break; - // Reverb Start and End Address Writes! - // * These regs are only writable when Effects are *DISABLED* (FxEnable is false). - // Writes while enabled should be ignored. - // NOTE: Above is false by testing but there are references saying this, so for - // now we think that writing is allowed but the internal register doesn't reflect - // the value until effects area writing is disabled. - // * Yes, these are backwards from all the volumes -- the hiword comes FIRST (wtf!) - // * End position is a hiword only! Loword is always ffff. - // * The Reverb buffer position resets on writes to StartA. It probably resets - // on writes to End too. Docs don't say, but they're for PSX, which couldn't - // change the end address anyway. - // - case REG_A_ESA: - SetHiWord(thiscore.ExtEffectsStartA, value & 0xF); - if (!thiscore.FxEnable) - { - thiscore.EffectsStartA = thiscore.ExtEffectsStartA; - thiscore.ReverbX = 0; - thiscore.RevBuffers.NeedsUpdated = true; - } - break; - - case (REG_A_ESA + 2): - SetLoWord(thiscore.ExtEffectsStartA, value); - if (!thiscore.FxEnable) - { - thiscore.EffectsStartA = thiscore.ExtEffectsStartA; - thiscore.ReverbX = 0; - thiscore.RevBuffers.NeedsUpdated = true; - } - break; - - case REG_A_EEA: - thiscore.ExtEffectsEndA = ((u32)(value & 0xF) << 16) | 0xFFFF; - if (!thiscore.FxEnable) - { - thiscore.EffectsEndA = thiscore.ExtEffectsEndA; - thiscore.ReverbX = 0; - thiscore.RevBuffers.NeedsUpdated = true; - } - break; - case REG_S_ADMAS: if (SPU2::MsgToConsole()) { @@ -1523,12 +1368,6 @@ static void RegWrite_Core(u16 value) Cores[1].FxEnable = 0; Cores[1].EffectsStartA = 0x7FFF8; // park core1 effect area in inaccessible mem Cores[1].EffectsEndA = 0x7FFFF; - Cores[1].ExtEffectsStartA = 0x7FFF8; - Cores[1].ExtEffectsEndA = 0x7FFFF; - Cores[1].ReverbX = 0; - Cores[1].RevBuffers.NeedsUpdated = true; - Cores[0].ReverbX = 0; - Cores[0].RevBuffers.NeedsUpdated = true; for (uint v = 0; v < 24; ++v) { Cores[1].Voices[v].Volume = V_VolumeSlideLR(0, 0); // V_VolumeSlideLR::Max; diff --git a/pcsx2/SaveState.h b/pcsx2/SaveState.h index 722b091671284..9edfad771176e 100644 --- a/pcsx2/SaveState.h +++ b/pcsx2/SaveState.h @@ -37,7 +37,7 @@ enum class FreezeAction // [SAVEVERSION+] // This informs the auto updater that the users savestates will be invalidated. -static const u32 g_SaveVersion = (0x9A41 << 16) | 0x0000; +static const u32 g_SaveVersion = (0x9A42 << 16) | 0x0000; // the freezing data between submodules and core