SPU: Ignore End+Mute flag for noise channels

Fixes the noise effects cutting out too early in Motor Toon Grand Prix.
This commit is contained in:
Stenzek 2024-03-29 15:08:12 +10:00
parent d4d3518e68
commit f9f9447013
No known key found for this signature in database

View file

@ -430,10 +430,10 @@ void SPU::Initialize()
void SPU::CreateOutputStream()
{
Log_InfoPrintf(
"Creating '%s' audio stream, sample rate = %u, channels = %u, buffer = %u, latency = %u, stretching = %s",
Settings::GetAudioBackendName(g_settings.audio_backend), SAMPLE_RATE, NUM_CHANNELS, g_settings.audio_buffer_ms,
g_settings.audio_output_latency_ms, AudioStream::GetStretchModeName(g_settings.audio_stretch_mode));
Log_InfoFmt("Creating '{}' audio stream, sample rate = {}, channels = {}, buffer = {}, latency = {}, stretching = {}",
Settings::GetAudioBackendName(g_settings.audio_backend), static_cast<u32>(SAMPLE_RATE),
static_cast<u32>(NUM_CHANNELS), g_settings.audio_buffer_ms, g_settings.audio_output_latency_ms,
AudioStream::GetStretchModeName(g_settings.audio_stretch_mode));
s_audio_stream =
Host::CreateAudioStream(g_settings.audio_backend, SAMPLE_RATE, NUM_CHANNELS, g_settings.audio_buffer_ms,
@ -656,28 +656,28 @@ u16 SPU::ReadRegister(u32 offset)
return s_reverb_registers.mBASE;
case 0x1F801DA4 - SPU_BASE:
Log_TracePrintf("SPU IRQ address -> 0x%04X", ZeroExtend32(s_irq_address));
Log_TraceFmt("SPU IRQ address -> 0x{:04X}", s_irq_address);
return s_irq_address;
case 0x1F801DA6 - SPU_BASE:
Log_TracePrintf("SPU transfer address register -> 0x%04X", ZeroExtend32(s_transfer_address_reg));
Log_TraceFmt("SPU transfer address register -> 0x{:04X}", s_transfer_address_reg);
return s_transfer_address_reg;
case 0x1F801DA8 - SPU_BASE:
Log_TracePrintf("SPU transfer data register read");
Log_TraceFmt("SPU transfer data register read");
return UINT16_C(0xFFFF);
case 0x1F801DAA - SPU_BASE:
Log_TracePrintf("SPU control register -> 0x%04X", ZeroExtend32(s_SPUCNT.bits));
Log_TraceFmt("SPU control register -> 0x{:04X}", s_SPUCNT.bits);
return s_SPUCNT.bits;
case 0x1F801DAC - SPU_BASE:
Log_TracePrintf("SPU transfer control register -> 0x%04X", ZeroExtend32(s_transfer_control.bits));
Log_TraceFmt("SPU transfer control register -> 0x{:04X}", s_transfer_control.bits);
return s_transfer_control.bits;
case 0x1F801DAE - SPU_BASE:
GeneratePendingSamples();
Log_TracePrintf("SPU status register -> 0x%04X", ZeroExtend32(s_SPUCNT.bits));
Log_TraceFmt("SPU status register -> 0x{:04X}", s_SPUCNT.bits);
return s_SPUSTAT.bits;
case 0x1F801DB0 - SPU_BASE:
@ -718,7 +718,7 @@ u16 SPU::ReadRegister(u32 offset)
return s_voices[voice_index].right_volume.current_level;
}
Log_DevPrintf("Unknown SPU register read: offset 0x%X (address 0x%08X)", offset, offset | SPU_BASE);
Log_DevFmt("Unknown SPU register read: offset 0x{:X} (address 0x{:08X})", offset, offset | SPU_BASE);
return UINT16_C(0xFFFF);
}
}
@ -730,7 +730,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
{
case 0x1F801D80 - SPU_BASE:
{
Log_DebugPrintf("SPU main volume left <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU main volume left <- 0x{:04X}", value);
GeneratePendingSamples();
s_main_volume_left_reg.bits = value;
s_main_volume_left.Reset(s_main_volume_left_reg);
@ -739,7 +739,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801D82 - SPU_BASE:
{
Log_DebugPrintf("SPU main volume right <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU main volume right <- 0x{:04X}", value);
GeneratePendingSamples();
s_main_volume_right_reg.bits = value;
s_main_volume_right.Reset(s_main_volume_right_reg);
@ -748,7 +748,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801D84 - SPU_BASE:
{
Log_DebugPrintf("SPU reverb output volume left <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU reverb output volume left <- 0x{:04X}", value);
GeneratePendingSamples();
s_reverb_registers.vLOUT = value;
return;
@ -756,7 +756,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801D86 - SPU_BASE:
{
Log_DebugPrintf("SPU reverb output volume right <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU reverb output volume right <- 0x{:04X}", value);
GeneratePendingSamples();
s_reverb_registers.vROUT = value;
return;
@ -764,7 +764,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801D88 - SPU_BASE:
{
Log_DebugPrintf("SPU key on low <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU key on low <- 0x{:04X}", value);
GeneratePendingSamples();
s_key_on_register = (s_key_on_register & 0xFFFF0000) | ZeroExtend32(value);
}
@ -772,7 +772,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801D8A - SPU_BASE:
{
Log_DebugPrintf("SPU key on high <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU key on high <- 0x{:04X}", value);
GeneratePendingSamples();
s_key_on_register = (s_key_on_register & 0x0000FFFF) | (ZeroExtend32(value) << 16);
}
@ -780,7 +780,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801D8C - SPU_BASE:
{
Log_DebugPrintf("SPU key off low <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU key off low <- 0x{:04X}", value);
GeneratePendingSamples();
s_key_off_register = (s_key_off_register & 0xFFFF0000) | ZeroExtend32(value);
}
@ -788,7 +788,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801D8E - SPU_BASE:
{
Log_DebugPrintf("SPU key off high <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU key off high <- 0x{:04X}", value);
GeneratePendingSamples();
s_key_off_register = (s_key_off_register & 0x0000FFFF) | (ZeroExtend32(value) << 16);
}
@ -798,7 +798,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
{
GeneratePendingSamples();
s_pitch_modulation_enable_register = (s_pitch_modulation_enable_register & 0xFFFF0000) | ZeroExtend32(value);
Log_DebugPrintf("SPU pitch modulation enable register <- 0x%08X", s_pitch_modulation_enable_register);
Log_DebugFmt("SPU pitch modulation enable register <- 0x{:08X}", s_pitch_modulation_enable_register);
}
break;
@ -807,13 +807,13 @@ void SPU::WriteRegister(u32 offset, u16 value)
GeneratePendingSamples();
s_pitch_modulation_enable_register =
(s_pitch_modulation_enable_register & 0x0000FFFF) | (ZeroExtend32(value) << 16);
Log_DebugPrintf("SPU pitch modulation enable register <- 0x%08X", s_pitch_modulation_enable_register);
Log_DebugFmt("SPU pitch modulation enable register <- 0x{:08X}", s_pitch_modulation_enable_register);
}
break;
case 0x1F801D94 - SPU_BASE:
{
Log_DebugPrintf("SPU noise mode register <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU noise mode register <- 0x{:04X}", value);
GeneratePendingSamples();
s_noise_mode_register = (s_noise_mode_register & 0xFFFF0000) | ZeroExtend32(value);
}
@ -821,7 +821,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801D96 - SPU_BASE:
{
Log_DebugPrintf("SPU noise mode register <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU noise mode register <- 0x{:04X}", value);
GeneratePendingSamples();
s_noise_mode_register = (s_noise_mode_register & 0x0000FFFF) | (ZeroExtend32(value) << 16);
}
@ -829,7 +829,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801D98 - SPU_BASE:
{
Log_DebugPrintf("SPU reverb on register <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU reverb on register <- 0x{:04X}", value);
GeneratePendingSamples();
s_reverb_on_register = (s_reverb_on_register & 0xFFFF0000) | ZeroExtend32(value);
}
@ -837,7 +837,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801D9A - SPU_BASE:
{
Log_DebugPrintf("SPU reverb on register <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU reverb on register <- 0x{:04X}", value);
GeneratePendingSamples();
s_reverb_on_register = (s_reverb_on_register & 0x0000FFFF) | (ZeroExtend32(value) << 16);
}
@ -845,7 +845,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801DA2 - SPU_BASE:
{
Log_DebugPrintf("SPU reverb base address < 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU reverb base address < 0x{:04X}", value);
GeneratePendingSamples();
s_reverb_registers.mBASE = value;
s_reverb_base_address = ZeroExtend32(value << 2) & 0x3FFFFu;
@ -855,7 +855,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801DA4 - SPU_BASE:
{
Log_DebugPrintf("SPU IRQ address register <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU IRQ address register <- 0x{:04X}", value);
GeneratePendingSamples();
s_irq_address = value;
@ -867,14 +867,14 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801DA6 - SPU_BASE:
{
Log_DebugPrintf("SPU transfer address register <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU transfer address register <- 0x{:04X}", value);
s_transfer_event->InvokeEarly();
s_transfer_address_reg = value;
s_transfer_address = ZeroExtend32(value) * 8;
if (IsRAMIRQTriggerable() && CheckRAMIRQ(s_transfer_address))
{
Log_DebugPrintf("Trigger IRQ @ %08X %04X from transfer address reg set", s_transfer_address,
s_transfer_address / 8);
Log_DebugFmt("Trigger IRQ @ {:08X} {:04X} from transfer address reg set", s_transfer_address,
s_transfer_address / 8);
TriggerRAMIRQ();
}
return;
@ -882,8 +882,8 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801DA8 - SPU_BASE:
{
Log_TracePrintf("SPU transfer data register <- 0x%04X (RAM offset 0x%08X)", ZeroExtend32(value),
s_transfer_address);
Log_TraceFmt("SPU transfer data register <- 0x{:04X} (RAM offset 0x{:08X})", ZeroExtend32(value),
s_transfer_address);
ManualTransferWrite(value);
return;
@ -891,7 +891,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801DAA - SPU_BASE:
{
Log_DebugPrintf("SPU control register <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU control register <- 0x{:04X}", value);
GeneratePendingSamples();
const SPUCNT new_value{value};
@ -905,14 +905,14 @@ void SPU::WriteRegister(u32 offset, u16 value)
{
// I would guess on the console it would gradually write the FIFO out. Hopefully nothing relies on this
// level of timing granularity if we force it all out here.
Log_WarningPrintf("Draining write SPU transfer FIFO with %u bytes left", s_transfer_fifo.GetSize());
Log_WarningFmt("Draining write SPU transfer FIFO with {} bytes left", s_transfer_fifo.GetSize());
TickCount ticks = std::numeric_limits<TickCount>::max();
ExecuteFIFOWriteToRAM(ticks);
DebugAssert(s_transfer_fifo.IsEmpty());
}
else
{
Log_DebugPrintf("Clearing read SPU transfer FIFO with %u bytes left", s_transfer_fifo.GetSize());
Log_DebugFmt("Clearing read SPU transfer FIFO with {} bytes left", s_transfer_fifo.GetSize());
s_transfer_fifo.Clear();
}
}
@ -947,14 +947,14 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801DAC - SPU_BASE:
{
Log_DebugPrintf("SPU transfer control register <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU transfer control register <- 0x{:04X}", value);
s_transfer_control.bits = value;
return;
}
case 0x1F801DB0 - SPU_BASE:
{
Log_DebugPrintf("SPU left cd audio register <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU left cd audio register <- 0x{:04X}", value);
GeneratePendingSamples();
s_cd_audio_volume_left = value;
}
@ -962,7 +962,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801DB2 - SPU_BASE:
{
Log_DebugPrintf("SPU right cd audio register <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU right cd audio register <- 0x{:04X}", value);
GeneratePendingSamples();
s_cd_audio_volume_right = value;
}
@ -971,7 +971,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801DB4 - SPU_BASE:
{
// External volumes aren't used, so don't bother syncing.
Log_DebugPrintf("SPU left external volume register <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU left external volume register <- 0x{:04X}", value);
s_external_volume_left = value;
}
break;
@ -979,7 +979,7 @@ void SPU::WriteRegister(u32 offset, u16 value)
case 0x1F801DB6 - SPU_BASE:
{
// External volumes aren't used, so don't bother syncing.
Log_DebugPrintf("SPU right external volume register <- 0x%04X", ZeroExtend32(value));
Log_DebugFmt("SPU right external volume register <- 0x{:04X}", value);
s_external_volume_right = value;
}
break;
@ -1001,14 +1001,14 @@ void SPU::WriteRegister(u32 offset, u16 value)
if (offset >= (0x1F801DC0 - SPU_BASE) && offset < (0x1F801E00 - SPU_BASE))
{
const u32 reg = (offset - (0x1F801DC0 - SPU_BASE)) / 2;
Log_DebugPrintf("SPU reverb register %u <- 0x%04X", reg, value);
Log_DebugFmt("SPU reverb register {} <- 0x{:04X}", reg, value);
GeneratePendingSamples();
s_reverb_registers.rev[reg] = value;
return;
}
Log_DevPrintf("Unknown SPU register write: offset 0x%X (address 0x%08X) value 0x%04X", offset, offset | SPU_BASE,
ZeroExtend32(value));
Log_DevFmt("Unknown SPU register write: offset 0x{:X} (address 0x{:08X}) value 0x{:04X}", offset,
offset | SPU_BASE, value);
return;
}
}
@ -1025,7 +1025,7 @@ u16 SPU::ReadVoiceRegister(u32 offset)
if (reg_index >= 6 && (voice.IsOn() || s_key_on_register & (1u << voice_index)))
GeneratePendingSamples();
Log_TracePrintf("Read voice %u register %u -> 0x%02X", voice_index, reg_index, voice.regs.index[reg_index]);
Log_TraceFmt("Read voice {} register {} -> 0x{:02X}", voice_index, reg_index, voice.regs.index[reg_index]);
return voice.regs.index[reg_index];
}
@ -1044,7 +1044,7 @@ void SPU::WriteVoiceRegister(u32 offset, u16 value)
{
case 0x00: // volume left
{
Log_DebugPrintf("SPU voice %u volume left <- 0x%04X", voice_index, value);
Log_DebugFmt("SPU voice {} volume left <- 0x{:04X}", voice_index, value);
voice.regs.volume_left.bits = value;
voice.left_volume.Reset(voice.regs.volume_left);
}
@ -1052,7 +1052,7 @@ void SPU::WriteVoiceRegister(u32 offset, u16 value)
case 0x02: // volume right
{
Log_DebugPrintf("SPU voice %u volume right <- 0x%04X", voice_index, value);
Log_DebugFmt("SPU voice {} volume right <- 0x{:04X}", voice_index, value);
voice.regs.volume_right.bits = value;
voice.right_volume.Reset(voice.regs.volume_right);
}
@ -1060,21 +1060,21 @@ void SPU::WriteVoiceRegister(u32 offset, u16 value)
case 0x04: // sample rate
{
Log_DebugPrintf("SPU voice %u ADPCM sample rate <- 0x%04X", voice_index, value);
Log_DebugFmt("SPU voice {} ADPCM sample rate <- 0x{:04X}", voice_index, value);
voice.regs.adpcm_sample_rate = value;
}
break;
case 0x06: // start address
{
Log_DebugPrintf("SPU voice %u ADPCM start address <- 0x%04X", voice_index, value);
Log_DebugFmt("SPU voice {} ADPCM start address <- 0x{:04X}", voice_index, value);
voice.regs.adpcm_start_address = value;
}
break;
case 0x08: // adsr low
{
Log_DebugPrintf("SPU voice %u ADSR low <- 0x%04X (was 0x%04X)", voice_index, value, voice.regs.adsr.bits_low);
Log_DebugFmt("SPU voice {} ADSR low <- 0x{:04X} (was 0x{:04X})", voice_index, value, voice.regs.adsr.bits_low);
voice.regs.adsr.bits_low = value;
if (voice.IsOn())
voice.UpdateADSREnvelope();
@ -1083,7 +1083,7 @@ void SPU::WriteVoiceRegister(u32 offset, u16 value)
case 0x0A: // adsr high
{
Log_DebugPrintf("SPU voice %u ADSR high <- 0x%04X (was 0x%04X)", voice_index, value, voice.regs.adsr.bits_low);
Log_DebugFmt("SPU voice {} ADSR high <- 0x{:04X} (was 0x{:04X})", voice_index, value, voice.regs.adsr.bits_low);
voice.regs.adsr.bits_high = value;
if (voice.IsOn())
voice.UpdateADSREnvelope();
@ -1092,7 +1092,7 @@ void SPU::WriteVoiceRegister(u32 offset, u16 value)
case 0x0C: // adsr volume
{
Log_DebugPrintf("SPU voice %u ADSR volume <- 0x%04X (was 0x%04X)", voice_index, value, voice.regs.adsr_volume);
Log_DebugFmt("SPU voice {} ADSR volume <- 0x{:04X} (was 0x{:04X})", voice_index, value, voice.regs.adsr_volume);
voice.regs.adsr_volume = value;
}
break;
@ -1106,22 +1106,22 @@ void SPU::WriteVoiceRegister(u32 offset, u16 value)
// - Valkyrie Profile
const bool ignore_loop_address = voice.IsOn() && !voice.is_first_block;
Log_DebugPrintf("SPU voice %u ADPCM repeat address <- 0x%04X", voice_index, value);
Log_DebugFmt("SPU voice {} ADPCM repeat address <- 0x{:04X}", voice_index, value);
voice.regs.adpcm_repeat_address = value;
voice.ignore_loop_address |= ignore_loop_address;
if (!ignore_loop_address)
{
Log_DevPrintf("Not ignoring loop address, the ADPCM repeat address of 0x%04X for voice %u will be overwritten",
value, voice_index);
Log_DevFmt("Not ignoring loop address, the ADPCM repeat address of 0x{:04X} for voice {} will be overwritten",
value, voice_index);
}
}
break;
default:
{
Log_ErrorPrintf("Unknown SPU voice %u register write: offset 0x%X (address 0x%08X) value 0x%04X", offset,
voice_index, offset | SPU_BASE, ZeroExtend32(value));
Log_ErrorFmt("Unknown SPU voice {} register write: offset 0x%X (address 0x{:08X}) value 0x{:04X}", offset,
voice_index, offset | SPU_BASE, ZeroExtend32(value));
}
break;
}
@ -1168,7 +1168,7 @@ void SPU::CheckForLateRAMIRQs()
{
if (CheckRAMIRQ(s_transfer_address))
{
Log_DebugPrintf("Trigger IRQ @ %08X %04X from late transfer", s_transfer_address, s_transfer_address / 8);
Log_DebugFmt("Trigger IRQ @ {:08X} {:04X} from late transfer", s_transfer_address, s_transfer_address / 8);
TriggerRAMIRQ();
return;
}
@ -1184,7 +1184,7 @@ void SPU::CheckForLateRAMIRQs()
const u32 address = v.current_address * 8;
if (CheckRAMIRQ(address) || CheckRAMIRQ((address + 8) & RAM_MASK))
{
Log_DebugPrintf("Trigger IRQ @ %08X %04X from late", address, address / 8);
Log_DebugFmt("Trigger IRQ @ {:08X} ({:04X}) from late", address, address / 8);
TriggerRAMIRQ();
return;
}
@ -1194,11 +1194,11 @@ void SPU::CheckForLateRAMIRQs()
void SPU::WriteToCaptureBuffer(u32 index, s16 value)
{
const u32 ram_address = (index * CAPTURE_BUFFER_SIZE_PER_CHANNEL) | ZeroExtend16(s_capture_buffer_position);
// Log_DebugPrintf("write to capture buffer %u (0x%08X) <- 0x%04X", index, ram_address, u16(value));
// Log_DebugFmt("write to capture buffer {} (0x{:08X}) <- 0x{:04X}", index, ram_address, u16(value));
std::memcpy(&s_ram[ram_address], &value, sizeof(value));
if (IsRAMIRQTriggerable() && CheckRAMIRQ(ram_address))
{
Log_DebugPrintf("Trigger IRQ @ %08X %04X from capture buffer", ram_address, ram_address / 8);
Log_DebugFmt("Trigger IRQ @ {:08X} ({:04X}) from capture buffer", ram_address, ram_address / 8);
TriggerRAMIRQ();
}
}
@ -1222,7 +1222,7 @@ ALWAYS_INLINE_RELEASE void SPU::ExecuteFIFOReadFromRAM(TickCount& ticks)
if (IsRAMIRQTriggerable() && CheckRAMIRQ(s_transfer_address))
{
Log_DebugPrintf("Trigger IRQ @ %08X %04X from transfer read", s_transfer_address, s_transfer_address / 8);
Log_DebugFmt("Trigger IRQ @ {:08X} ({:04X}) from transfer read", s_transfer_address, s_transfer_address / 8);
TriggerRAMIRQ();
}
}
@ -1239,7 +1239,7 @@ ALWAYS_INLINE_RELEASE void SPU::ExecuteFIFOWriteToRAM(TickCount& ticks)
if (IsRAMIRQTriggerable() && CheckRAMIRQ(s_transfer_address))
{
Log_DebugPrintf("Trigger IRQ @ %08X %04X from transfer write", s_transfer_address, s_transfer_address / 8);
Log_DebugFmt("Trigger IRQ @ {:08X} ({:04X}) from transfer write", s_transfer_address, s_transfer_address / 8);
TriggerRAMIRQ();
}
}
@ -1303,7 +1303,7 @@ void SPU::ManualTransferWrite(u16 value)
{
if (!s_transfer_fifo.IsEmpty() && s_SPUCNT.ram_transfer_mode != RAMTransferMode::DMARead)
{
Log_WarningPrintf("FIFO not empty on manual SPU write, draining to hopefully avoid corruption. Game is silly.");
Log_WarningPrint("FIFO not empty on manual SPU write, draining to hopefully avoid corruption. Game is silly.");
if (s_SPUCNT.ram_transfer_mode != RAMTransferMode::Stopped)
ExecuteTransfer(nullptr, std::numeric_limits<s32>::max(), 0);
}
@ -1313,7 +1313,7 @@ void SPU::ManualTransferWrite(u16 value)
if (IsRAMIRQTriggerable() && CheckRAMIRQ(s_transfer_address))
{
Log_DebugPrintf("Trigger IRQ @ %08X %04X from manual write", s_transfer_address, s_transfer_address / 8);
Log_DebugFmt("Trigger IRQ @ {:08X} ({:04X}) from manual write", s_transfer_address, s_transfer_address / 8);
TriggerRAMIRQ();
}
}
@ -1431,7 +1431,7 @@ void SPU::DMARead(u32* words, u32 word_count)
fill_value = halfwords[size - 1];
}
Log_WarningPrintf("Transfer FIFO underflow, filling with 0x%04X", fill_value);
Log_WarningFmt("Transfer FIFO underflow, filling with 0x{:04X}", fill_value);
std::fill_n(&halfwords[size], halfword_count - size, fill_value);
}
else
@ -1452,7 +1452,7 @@ void SPU::DMAWrite(const u32* words, u32 word_count)
s_transfer_fifo.PushRange(halfwords, words_to_transfer);
if (words_to_transfer != halfword_count) [[unlikely]]
Log_WarningPrintf("Transfer FIFO overflow, dropping %u halfwords", halfword_count - words_to_transfer);
Log_WarningFmt("Transfer FIFO overflow, dropping {} halfwords", halfword_count - words_to_transfer);
UpdateDMARequest();
UpdateTransferEvent();
@ -1491,7 +1491,7 @@ bool SPU::StartDumpingAudio(const char* filename)
s_dump_writer = std::make_unique<WAVWriter>();
if (!s_dump_writer->Open(filename, SAMPLE_RATE, 2))
{
Log_ErrorPrintf("Failed to open '%s'", filename);
Log_ErrorFmt("Failed to open '{}'", filename);
s_dump_writer.reset();
return false;
}
@ -1511,7 +1511,7 @@ bool SPU::StartDumpingAudio(const char* filename)
const std::string voice_filename = Path::ReplaceExtension(filename, new_suffix);
if (!s_voice_dump_writers[i]->Open(voice_filename.c_str(), SAMPLE_RATE, 2))
{
Log_ErrorPrintf("Failed to open voice dump filename '%s'", voice_filename.c_str());
Log_ErrorFmt("Failed to open voice dump filename '{}'", voice_filename.c_str());
s_voice_dump_writers[i].reset();
}
}
@ -1916,7 +1916,7 @@ void SPU::ReadADPCMBlock(u16 address, ADPCMBlock* block)
u32 ram_address = (ZeroExtend32(address) * 8) & RAM_MASK;
if (IsRAMIRQTriggerable() && (CheckRAMIRQ(ram_address) || CheckRAMIRQ((ram_address + 8) & RAM_MASK)))
{
Log_DebugPrintf("Trigger IRQ @ %08X %04X from ADPCM reader", ram_address, ram_address / 8);
Log_DebugFmt("Trigger IRQ @ {:08X} ({:04X}) from ADPCM reader", ram_address, ram_address / 8);
TriggerRAMIRQ();
}
@ -1965,7 +1965,7 @@ ALWAYS_INLINE_RELEASE std::tuple<s32, s32> SPU::SampleVoice(u32 voice_index)
if (voice.current_block_flags.loop_start && !voice.ignore_loop_address)
{
Log_TracePrintf("Voice %u loop start @ 0x%08X", voice_index, ZeroExtend32(voice.current_address));
Log_TraceFmt("Voice {} loop start @ 0x{:08X}", voice_index, voice.current_address);
voice.regs.adpcm_repeat_address = voice.current_address;
}
}
@ -2024,12 +2024,20 @@ ALWAYS_INLINE_RELEASE std::tuple<s32, s32> SPU::SampleVoice(u32 voice_index)
if (!voice.current_block_flags.loop_repeat)
{
Log_TracePrintf("Voice %u loop end+mute @ 0x%08X", voice_index, ZeroExtend32(voice.current_address));
voice.ForceOff();
// End+Mute flags are ignored when noise is enabled. ADPCM data is still decoded.
if (!IsVoiceNoiseEnabled(voice_index))
{
Log_TraceFmt("Voice {} loop end+mute @ 0x{:04X}", voice_index, voice.current_address);
voice.ForceOff();
}
else
{
Log_TraceFmt("IGNORING voice {} loop end+mute @ 0x{:04X}", voice_index, voice.current_address);
}
}
else
{
Log_TracePrintf("Voice %u loop end+repeat @ 0x%08X", voice_index, ZeroExtend32(voice.current_address));
Log_TraceFmt("Voice {} loop end+repeat @ 0x{:04X}", voice_index, voice.current_address);
}
}
}