summaryrefslogtreecommitdiffstats
path: root/src/audio_core/renderer
diff options
context:
space:
mode:
Diffstat (limited to 'src/audio_core/renderer')
-rw-r--r--src/audio_core/renderer/adsp/audio_renderer.cpp2
-rw-r--r--src/audio_core/renderer/command/command_buffer.cpp4
-rw-r--r--src/audio_core/renderer/command/command_generator.cpp2
-rw-r--r--src/audio_core/renderer/command/effect/aux_.cpp130
-rw-r--r--src/audio_core/renderer/command/effect/i3dl2_reverb.cpp8
-rw-r--r--src/audio_core/renderer/command/effect/reverb.cpp8
-rw-r--r--src/audio_core/renderer/command/resample/upsample.cpp12
-rw-r--r--src/audio_core/renderer/system.cpp2
-rw-r--r--src/audio_core/renderer/system_manager.cpp2
9 files changed, 111 insertions, 59 deletions
diff --git a/src/audio_core/renderer/adsp/audio_renderer.cpp b/src/audio_core/renderer/adsp/audio_renderer.cpp
index d982ef630..78c15629b 100644
--- a/src/audio_core/renderer/adsp/audio_renderer.cpp
+++ b/src/audio_core/renderer/adsp/audio_renderer.cpp
@@ -132,7 +132,7 @@ void AudioRenderer::CreateSinkStreams() {
}
void AudioRenderer::ThreadFunc() {
- constexpr char name[]{"AudioRenderer"};
+ static constexpr char name[]{"AudioRenderer"};
MicroProfileOnThreadCreate(name);
Common::SetCurrentThreadName(name);
Common::SetCurrentThreadPriority(Common::ThreadPriority::Critical);
diff --git a/src/audio_core/renderer/command/command_buffer.cpp b/src/audio_core/renderer/command/command_buffer.cpp
index 8c6fe97e7..0bd418306 100644
--- a/src/audio_core/renderer/command/command_buffer.cpp
+++ b/src/audio_core/renderer/command/command_buffer.cpp
@@ -251,8 +251,8 @@ void CommandBuffer::GenerateBiquadFilterCommand(const s32 node_id, EffectInfoBas
const auto& parameter{
*reinterpret_cast<BiquadFilterInfo::ParameterVersion1*>(effect_info.GetParameter())};
- const auto state{
- reinterpret_cast<VoiceState::BiquadFilterState*>(effect_info.GetStateBuffer())};
+ const auto state{reinterpret_cast<VoiceState::BiquadFilterState*>(
+ effect_info.GetStateBuffer() + channel * sizeof(VoiceState::BiquadFilterState))};
cmd.input = buffer_offset + parameter.inputs[channel];
cmd.output = buffer_offset + parameter.outputs[channel];
diff --git a/src/audio_core/renderer/command/command_generator.cpp b/src/audio_core/renderer/command/command_generator.cpp
index 2ea50d128..fba84c7bd 100644
--- a/src/audio_core/renderer/command/command_generator.cpp
+++ b/src/audio_core/renderer/command/command_generator.cpp
@@ -46,7 +46,7 @@ void CommandGenerator::GenerateDataSourceCommand(VoiceInfo& voice_info,
while (destination != nullptr) {
if (destination->IsConfigured()) {
auto mix_id{destination->GetMixId()};
- if (mix_id < mix_context.GetCount()) {
+ if (mix_id < mix_context.GetCount() && mix_id != UnusedSplitterId) {
auto mix_info{mix_context.GetInfo(mix_id)};
command_buffer.GenerateDepopPrepareCommand(
voice_info.node_id, voice_state, render_context.depop_buffer,
diff --git a/src/audio_core/renderer/command/effect/aux_.cpp b/src/audio_core/renderer/command/effect/aux_.cpp
index e76db893f..c5650effa 100644
--- a/src/audio_core/renderer/command/effect/aux_.cpp
+++ b/src/audio_core/renderer/command/effect/aux_.cpp
@@ -4,6 +4,7 @@
#include "audio_core/renderer/adsp/command_list_processor.h"
#include "audio_core/renderer/command/effect/aux_.h"
#include "audio_core/renderer/effect/aux_.h"
+#include "core/core.h"
#include "core/memory.h"
namespace AudioCore::AudioRenderer {
@@ -19,10 +20,24 @@ static void ResetAuxBufferDsp(Core::Memory::Memory& memory, const CpuAddr aux_in
return;
}
- auto info{reinterpret_cast<AuxInfo::AuxInfoDsp*>(memory.GetPointer(aux_info))};
- info->read_offset = 0;
- info->write_offset = 0;
- info->total_sample_count = 0;
+ AuxInfo::AuxInfoDsp info{};
+ auto info_ptr{&info};
+ bool host_safe{(aux_info & Core::Memory::YUZU_PAGEMASK) <=
+ (Core::Memory::YUZU_PAGESIZE - sizeof(AuxInfo::AuxInfoDsp))};
+
+ if (host_safe) [[likely]] {
+ info_ptr = memory.GetPointer<AuxInfo::AuxInfoDsp>(aux_info);
+ } else {
+ memory.ReadBlockUnsafe(aux_info, info_ptr, sizeof(AuxInfo::AuxInfoDsp));
+ }
+
+ info_ptr->read_offset = 0;
+ info_ptr->write_offset = 0;
+ info_ptr->total_sample_count = 0;
+
+ if (!host_safe) [[unlikely]] {
+ memory.WriteBlockUnsafe(aux_info, info_ptr, sizeof(AuxInfo::AuxInfoDsp));
+ }
}
/**
@@ -40,11 +55,10 @@ static void ResetAuxBufferDsp(Core::Memory::Memory& memory, const CpuAddr aux_in
* @param update_count - If non-zero, send_info_ will be updated.
* @return Number of samples written.
*/
-static u32 WriteAuxBufferDsp(Core::Memory::Memory& memory, const CpuAddr send_info_,
- [[maybe_unused]] u32 sample_count, const CpuAddr send_buffer,
- const u32 count_max, std::span<const s32> input,
- const u32 write_count_, const u32 write_offset,
- const u32 update_count) {
+static u32 WriteAuxBufferDsp(Core::Memory::Memory& memory, CpuAddr send_info_,
+ [[maybe_unused]] u32 sample_count, CpuAddr send_buffer, u32 count_max,
+ std::span<const s32> input, u32 write_count_, u32 write_offset,
+ u32 update_count) {
if (write_count_ > count_max) {
LOG_ERROR(Service_Audio,
"write_count must be smaller than count_max! write_count {}, count_max {}",
@@ -52,6 +66,11 @@ static u32 WriteAuxBufferDsp(Core::Memory::Memory& memory, const CpuAddr send_in
return 0;
}
+ if (send_info_ == 0) {
+ LOG_ERROR(Service_Audio, "send_info_ is 0!");
+ return 0;
+ }
+
if (input.empty()) {
LOG_ERROR(Service_Audio, "input buffer is empty!");
return 0;
@@ -67,33 +86,47 @@ static u32 WriteAuxBufferDsp(Core::Memory::Memory& memory, const CpuAddr send_in
}
AuxInfo::AuxInfoDsp send_info{};
- memory.ReadBlockUnsafe(send_info_, &send_info, sizeof(AuxInfo::AuxInfoDsp));
+ auto send_ptr = &send_info;
+ bool host_safe = (send_info_ & Core::Memory::YUZU_PAGEMASK) <=
+ (Core::Memory::YUZU_PAGESIZE - sizeof(AuxInfo::AuxInfoDsp));
- u32 target_write_offset{send_info.write_offset + write_offset};
- if (target_write_offset > count_max || write_count_ == 0) {
+ if (host_safe) [[likely]] {
+ send_ptr = memory.GetPointer<AuxInfo::AuxInfoDsp>(send_info_);
+ } else {
+ memory.ReadBlockUnsafe(send_info_, send_ptr, sizeof(AuxInfo::AuxInfoDsp));
+ }
+
+ u32 target_write_offset{send_ptr->write_offset + write_offset};
+ if (target_write_offset > count_max) {
return 0;
}
u32 write_count{write_count_};
- u32 write_pos{0};
+ u32 read_pos{0};
while (write_count > 0) {
u32 to_write{std::min(count_max - target_write_offset, write_count)};
-
- if (to_write > 0) {
+ const auto write_addr = send_buffer + target_write_offset * sizeof(s32);
+ bool write_safe{(write_addr & Core::Memory::YUZU_PAGEMASK) <=
+ (Core::Memory::YUZU_PAGESIZE - (write_addr + to_write * sizeof(s32)))};
+ if (write_safe) [[likely]] {
+ auto ptr = memory.GetPointer(write_addr);
+ std::memcpy(ptr, &input[read_pos], to_write * sizeof(s32));
+ } else {
memory.WriteBlockUnsafe(send_buffer + target_write_offset * sizeof(s32),
- &input[write_pos], to_write * sizeof(s32));
+ &input[read_pos], to_write * sizeof(s32));
}
-
target_write_offset = (target_write_offset + to_write) % count_max;
write_count -= to_write;
- write_pos += to_write;
+ read_pos += to_write;
}
if (update_count) {
- send_info.write_offset = (send_info.write_offset + update_count) % count_max;
+ send_ptr->write_offset = (send_ptr->write_offset + update_count) % count_max;
}
- memory.WriteBlockUnsafe(send_info_, &send_info, sizeof(AuxInfo::AuxInfoDsp));
+ if (!host_safe) [[unlikely]] {
+ memory.WriteBlockUnsafe(send_info_, send_ptr, sizeof(AuxInfo::AuxInfoDsp));
+ }
return write_count_;
}
@@ -102,7 +135,7 @@ static u32 WriteAuxBufferDsp(Core::Memory::Memory& memory, const CpuAddr send_in
* Read the given memory at return_buffer into the output mix buffer, and update return_info_ if
* update_count is set, to notify the game that an update happened.
*
- * @param memory - Core memory for writing.
+ * @param memory - Core memory for reading.
* @param return_info_ - Meta information for where to read the mix buffer.
* @param return_buffer - Memory address to read the samples from.
* @param count_max - Maximum number of samples in the receiving buffer.
@@ -112,16 +145,21 @@ static u32 WriteAuxBufferDsp(Core::Memory::Memory& memory, const CpuAddr send_in
* @param update_count - If non-zero, send_info_ will be updated.
* @return Number of samples read.
*/
-static u32 ReadAuxBufferDsp(Core::Memory::Memory& memory, const CpuAddr return_info_,
- const CpuAddr return_buffer, const u32 count_max, std::span<s32> output,
- const u32 count_, const u32 read_offset, const u32 update_count) {
+static u32 ReadAuxBufferDsp(Core::Memory::Memory& memory, CpuAddr return_info_,
+ CpuAddr return_buffer, u32 count_max, std::span<s32> output,
+ u32 read_count_, u32 read_offset, u32 update_count) {
if (count_max == 0) {
return 0;
}
- if (count_ > count_max) {
+ if (read_count_ > count_max) {
LOG_ERROR(Service_Audio, "count must be smaller than count_max! count {}, count_max {}",
- count_, count_max);
+ read_count_, count_max);
+ return 0;
+ }
+
+ if (return_info_ == 0) {
+ LOG_ERROR(Service_Audio, "return_info_ is 0!");
return 0;
}
@@ -136,35 +174,49 @@ static u32 ReadAuxBufferDsp(Core::Memory::Memory& memory, const CpuAddr return_i
}
AuxInfo::AuxInfoDsp return_info{};
- memory.ReadBlockUnsafe(return_info_, &return_info, sizeof(AuxInfo::AuxInfoDsp));
+ auto return_ptr = &return_info;
+ bool host_safe = (return_info_ & Core::Memory::YUZU_PAGEMASK) <=
+ (Core::Memory::YUZU_PAGESIZE - sizeof(AuxInfo::AuxInfoDsp));
+
+ if (host_safe) [[likely]] {
+ return_ptr = memory.GetPointer<AuxInfo::AuxInfoDsp>(return_info_);
+ } else {
+ memory.ReadBlockUnsafe(return_info_, return_ptr, sizeof(AuxInfo::AuxInfoDsp));
+ }
- u32 target_read_offset{return_info.read_offset + read_offset};
+ u32 target_read_offset{return_ptr->read_offset + read_offset};
if (target_read_offset > count_max) {
return 0;
}
- u32 read_count{count_};
- u32 read_pos{0};
+ u32 read_count{read_count_};
+ u32 write_pos{0};
while (read_count > 0) {
u32 to_read{std::min(count_max - target_read_offset, read_count)};
-
- if (to_read > 0) {
+ const auto read_addr = return_buffer + target_read_offset * sizeof(s32);
+ bool read_safe{(read_addr & Core::Memory::YUZU_PAGEMASK) <=
+ (Core::Memory::YUZU_PAGESIZE - (read_addr + to_read * sizeof(s32)))};
+ if (read_safe) [[likely]] {
+ auto ptr = memory.GetPointer(read_addr);
+ std::memcpy(&output[write_pos], ptr, to_read * sizeof(s32));
+ } else {
memory.ReadBlockUnsafe(return_buffer + target_read_offset * sizeof(s32),
- &output[read_pos], to_read * sizeof(s32));
+ &output[write_pos], to_read * sizeof(s32));
}
-
target_read_offset = (target_read_offset + to_read) % count_max;
read_count -= to_read;
- read_pos += to_read;
+ write_pos += to_read;
}
if (update_count) {
- return_info.read_offset = (return_info.read_offset + update_count) % count_max;
+ return_ptr->read_offset = (return_ptr->read_offset + update_count) % count_max;
}
- memory.WriteBlockUnsafe(return_info_, &return_info, sizeof(AuxInfo::AuxInfoDsp));
+ if (!host_safe) [[unlikely]] {
+ memory.WriteBlockUnsafe(return_info_, return_ptr, sizeof(AuxInfo::AuxInfoDsp));
+ }
- return count_;
+ return read_count_;
}
void AuxCommand::Dump([[maybe_unused]] const ADSP::CommandListProcessor& processor,
@@ -189,7 +241,7 @@ void AuxCommand::Process(const ADSP::CommandListProcessor& processor) {
update_count)};
if (read != processor.sample_count) {
- std::memset(&output_buffer[read], 0, processor.sample_count - read);
+ std::memset(&output_buffer[read], 0, (processor.sample_count - read) * sizeof(s32));
}
} else {
ResetAuxBufferDsp(*processor.memory, send_buffer_info);
diff --git a/src/audio_core/renderer/command/effect/i3dl2_reverb.cpp b/src/audio_core/renderer/command/effect/i3dl2_reverb.cpp
index 2187d8a65..27d8b9844 100644
--- a/src/audio_core/renderer/command/effect/i3dl2_reverb.cpp
+++ b/src/audio_core/renderer/command/effect/i3dl2_reverb.cpp
@@ -244,16 +244,16 @@ template <size_t NumChannels>
static void ApplyI3dl2ReverbEffect(I3dl2ReverbInfo::State& state,
std::span<std::span<const s32>> inputs,
std::span<std::span<s32>> outputs, const u32 sample_count) {
- constexpr std::array<u8, I3dl2ReverbInfo::MaxDelayTaps> OutTapIndexes1Ch{
+ static constexpr std::array<u8, I3dl2ReverbInfo::MaxDelayTaps> OutTapIndexes1Ch{
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
};
- constexpr std::array<u8, I3dl2ReverbInfo::MaxDelayTaps> OutTapIndexes2Ch{
+ static constexpr std::array<u8, I3dl2ReverbInfo::MaxDelayTaps> OutTapIndexes2Ch{
0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 1, 1, 1, 0, 0, 0, 0, 1, 1, 1,
};
- constexpr std::array<u8, I3dl2ReverbInfo::MaxDelayTaps> OutTapIndexes4Ch{
+ static constexpr std::array<u8, I3dl2ReverbInfo::MaxDelayTaps> OutTapIndexes4Ch{
0, 0, 0, 1, 1, 1, 1, 2, 2, 2, 1, 1, 1, 0, 0, 0, 0, 3, 3, 3,
};
- constexpr std::array<u8, I3dl2ReverbInfo::MaxDelayTaps> OutTapIndexes6Ch{
+ static constexpr std::array<u8, I3dl2ReverbInfo::MaxDelayTaps> OutTapIndexes6Ch{
2, 0, 0, 1, 1, 1, 1, 4, 4, 4, 1, 1, 1, 0, 0, 0, 0, 5, 5, 5,
};
diff --git a/src/audio_core/renderer/command/effect/reverb.cpp b/src/audio_core/renderer/command/effect/reverb.cpp
index 427489214..6fe844ff0 100644
--- a/src/audio_core/renderer/command/effect/reverb.cpp
+++ b/src/audio_core/renderer/command/effect/reverb.cpp
@@ -252,16 +252,16 @@ template <size_t NumChannels>
static void ApplyReverbEffect(const ReverbInfo::ParameterVersion2& params, ReverbInfo::State& state,
std::vector<std::span<const s32>>& inputs,
std::vector<std::span<s32>>& outputs, const u32 sample_count) {
- constexpr std::array<u8, ReverbInfo::MaxDelayTaps> OutTapIndexes1Ch{
+ static constexpr std::array<u8, ReverbInfo::MaxDelayTaps> OutTapIndexes1Ch{
0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
};
- constexpr std::array<u8, ReverbInfo::MaxDelayTaps> OutTapIndexes2Ch{
+ static constexpr std::array<u8, ReverbInfo::MaxDelayTaps> OutTapIndexes2Ch{
0, 0, 1, 1, 0, 1, 0, 0, 1, 1,
};
- constexpr std::array<u8, ReverbInfo::MaxDelayTaps> OutTapIndexes4Ch{
+ static constexpr std::array<u8, ReverbInfo::MaxDelayTaps> OutTapIndexes4Ch{
0, 0, 1, 1, 0, 1, 2, 2, 3, 3,
};
- constexpr std::array<u8, ReverbInfo::MaxDelayTaps> OutTapIndexes6Ch{
+ static constexpr std::array<u8, ReverbInfo::MaxDelayTaps> OutTapIndexes6Ch{
0, 0, 1, 1, 2, 2, 4, 4, 5, 5,
};
diff --git a/src/audio_core/renderer/command/resample/upsample.cpp b/src/audio_core/renderer/command/resample/upsample.cpp
index 5f7db12ca..86ddee1a4 100644
--- a/src/audio_core/renderer/command/resample/upsample.cpp
+++ b/src/audio_core/renderer/command/resample/upsample.cpp
@@ -19,24 +19,24 @@ namespace AudioCore::AudioRenderer {
static void SrcProcessFrame(std::span<s32> output, std::span<const s32> input,
const u32 target_sample_count, const u32 source_sample_count,
UpsamplerState* state) {
- constexpr u32 WindowSize = 10;
- constexpr std::array<Common::FixedPoint<17, 15>, WindowSize> WindowedSinc1{
+ static constexpr u32 WindowSize = 10;
+ static constexpr std::array<Common::FixedPoint<17, 15>, WindowSize> WindowedSinc1{
0.95376587f, -0.12872314f, 0.060028076f, -0.032470703f, 0.017669678f,
-0.009124756f, 0.004272461f, -0.001739502f, 0.000579834f, -0.000091552734f,
};
- constexpr std::array<Common::FixedPoint<17, 15>, WindowSize> WindowedSinc2{
+ static constexpr std::array<Common::FixedPoint<17, 15>, WindowSize> WindowedSinc2{
0.8230896f, -0.19161987f, 0.093444824f, -0.05090332f, 0.027557373f,
-0.014038086f, 0.0064697266f, -0.002532959f, 0.00079345703f, -0.00012207031f,
};
- constexpr std::array<Common::FixedPoint<17, 15>, WindowSize> WindowedSinc3{
+ static constexpr std::array<Common::FixedPoint<17, 15>, WindowSize> WindowedSinc3{
0.6298828f, -0.19274902f, 0.09725952f, -0.05319214f, 0.028625488f,
-0.014373779f, 0.006500244f, -0.0024719238f, 0.0007324219f, -0.000091552734f,
};
- constexpr std::array<Common::FixedPoint<17, 15>, WindowSize> WindowedSinc4{
+ static constexpr std::array<Common::FixedPoint<17, 15>, WindowSize> WindowedSinc4{
0.4057312f, -0.1468811f, 0.07601929f, -0.041656494f, 0.022216797f,
-0.011016846f, 0.004852295f, -0.0017700195f, 0.00048828125f, -0.000030517578f,
};
- constexpr std::array<Common::FixedPoint<17, 15>, WindowSize> WindowedSinc5{
+ static constexpr std::array<Common::FixedPoint<17, 15>, WindowSize> WindowedSinc5{
0.1854248f, -0.075164795f, 0.03967285f, -0.021728516f, 0.011474609f,
-0.005584717f, 0.0024108887f, -0.0008239746f, 0.00021362305f, 0.0f,
};
diff --git a/src/audio_core/renderer/system.cpp b/src/audio_core/renderer/system.cpp
index 4fac30c7c..31cbee282 100644
--- a/src/audio_core/renderer/system.cpp
+++ b/src/audio_core/renderer/system.cpp
@@ -127,7 +127,7 @@ Result System::Initialize(const AudioRendererParameterInternal& params,
render_device = params.rendering_device;
execution_mode = params.execution_mode;
- core.Memory().ZeroBlock(*core.Kernel().CurrentProcess(), transfer_memory->GetSourceAddress(),
+ core.Memory().ZeroBlock(*core.ApplicationProcess(), transfer_memory->GetSourceAddress(),
transfer_memory_size);
// Note: We're not actually using the transfer memory because it's a pain to code for.
diff --git a/src/audio_core/renderer/system_manager.cpp b/src/audio_core/renderer/system_manager.cpp
index f66b2b890..ce631f810 100644
--- a/src/audio_core/renderer/system_manager.cpp
+++ b/src/audio_core/renderer/system_manager.cpp
@@ -94,7 +94,7 @@ bool SystemManager::Remove(System& system_) {
}
void SystemManager::ThreadFunc() {
- constexpr char name[]{"AudioRenderSystemManager"};
+ static constexpr char name[]{"AudioRenderSystemManager"};
MicroProfileOnThreadCreate(name);
Common::SetCurrentThreadName(name);
Common::SetCurrentThreadPriority(Common::ThreadPriority::High);