audio_renderer.cpp 9.0 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293
  1. // Copyright 2018 yuzu Emulator Project
  2. // Licensed under GPLv2 or any later version
  3. // Refer to the license.txt file included.
  4. #include "audio_core/algorithm/interpolate.h"
  5. #include "audio_core/audio_out.h"
  6. #include "audio_core/audio_renderer.h"
  7. #include "audio_core/codec.h"
  8. #include "common/assert.h"
  9. #include "common/logging/log.h"
  10. #include "core/hle/kernel/event.h"
  11. #include "core/memory.h"
  12. namespace AudioCore {
  13. constexpr u32 STREAM_SAMPLE_RATE{48000};
  14. constexpr u32 STREAM_NUM_CHANNELS{2};
  15. class AudioRenderer::VoiceState {
  16. public:
  17. bool IsPlaying() const {
  18. return is_in_use && info.play_state == PlayState::Started;
  19. }
  20. const VoiceOutStatus& GetOutStatus() const {
  21. return out_status;
  22. }
  23. const VoiceInfo& GetInfo() const {
  24. return info;
  25. }
  26. VoiceInfo& Info() {
  27. return info;
  28. }
  29. void SetWaveIndex(std::size_t index);
  30. std::vector<s16> DequeueSamples(std::size_t sample_count);
  31. void UpdateState();
  32. void RefreshBuffer();
  33. private:
  34. bool is_in_use{};
  35. bool is_refresh_pending{};
  36. std::size_t wave_index{};
  37. std::size_t offset{};
  38. Codec::ADPCMState adpcm_state{};
  39. InterpolationState interp_state{};
  40. std::vector<s16> samples;
  41. VoiceOutStatus out_status{};
  42. VoiceInfo info{};
  43. };
  44. AudioRenderer::AudioRenderer(AudioRendererParameter params,
  45. Kernel::SharedPtr<Kernel::Event> buffer_event)
  46. : worker_params{params}, buffer_event{buffer_event}, voices(params.voice_count) {
  47. audio_out = std::make_unique<AudioCore::AudioOut>();
  48. stream = audio_out->OpenStream(STREAM_SAMPLE_RATE, STREAM_NUM_CHANNELS, "AudioRenderer",
  49. [=]() { buffer_event->Signal(); });
  50. audio_out->StartStream(stream);
  51. QueueMixedBuffer(0);
  52. QueueMixedBuffer(1);
  53. QueueMixedBuffer(2);
  54. }
  55. AudioRenderer::~AudioRenderer() = default;
  56. u32 AudioRenderer::GetSampleRate() const {
  57. return worker_params.sample_rate;
  58. }
  59. u32 AudioRenderer::GetSampleCount() const {
  60. return worker_params.sample_count;
  61. }
  62. u32 AudioRenderer::GetMixBufferCount() const {
  63. return worker_params.mix_buffer_count;
  64. }
  65. Stream::State AudioRenderer::GetStreamState() const {
  66. return stream->GetState();
  67. }
  68. std::vector<u8> AudioRenderer::UpdateAudioRenderer(const std::vector<u8>& input_params) {
  69. // Copy UpdateDataHeader struct
  70. UpdateDataHeader config{};
  71. std::memcpy(&config, input_params.data(), sizeof(UpdateDataHeader));
  72. u32 memory_pool_count = worker_params.effect_count + (worker_params.voice_count * 4);
  73. // Copy MemoryPoolInfo structs
  74. std::vector<MemoryPoolInfo> mem_pool_info(memory_pool_count);
  75. std::memcpy(mem_pool_info.data(),
  76. input_params.data() + sizeof(UpdateDataHeader) + config.behavior_size,
  77. memory_pool_count * sizeof(MemoryPoolInfo));
  78. // Copy VoiceInfo structs
  79. std::size_t offset{sizeof(UpdateDataHeader) + config.behavior_size + config.memory_pools_size +
  80. config.voice_resource_size};
  81. for (auto& voice : voices) {
  82. std::memcpy(&voice.Info(), input_params.data() + offset, sizeof(VoiceInfo));
  83. offset += sizeof(VoiceInfo);
  84. }
  85. // Update voices
  86. for (auto& voice : voices) {
  87. voice.UpdateState();
  88. if (!voice.GetInfo().is_in_use) {
  89. continue;
  90. }
  91. if (voice.GetInfo().is_new) {
  92. voice.SetWaveIndex(voice.GetInfo().wave_buffer_head);
  93. }
  94. }
  95. // Update memory pool state
  96. std::vector<MemoryPoolEntry> memory_pool(memory_pool_count);
  97. for (std::size_t index = 0; index < memory_pool.size(); ++index) {
  98. if (mem_pool_info[index].pool_state == MemoryPoolStates::RequestAttach) {
  99. memory_pool[index].state = MemoryPoolStates::Attached;
  100. } else if (mem_pool_info[index].pool_state == MemoryPoolStates::RequestDetach) {
  101. memory_pool[index].state = MemoryPoolStates::Detached;
  102. }
  103. }
  104. // Release previous buffers and queue next ones for playback
  105. ReleaseAndQueueBuffers();
  106. // Copy output header
  107. UpdateDataHeader response_data{worker_params};
  108. std::vector<u8> output_params(response_data.total_size);
  109. std::memcpy(output_params.data(), &response_data, sizeof(UpdateDataHeader));
  110. // Copy output memory pool entries
  111. std::memcpy(output_params.data() + sizeof(UpdateDataHeader), memory_pool.data(),
  112. response_data.memory_pools_size);
  113. // Copy output voice status
  114. std::size_t voice_out_status_offset{sizeof(UpdateDataHeader) + response_data.memory_pools_size};
  115. for (const auto& voice : voices) {
  116. std::memcpy(output_params.data() + voice_out_status_offset, &voice.GetOutStatus(),
  117. sizeof(VoiceOutStatus));
  118. voice_out_status_offset += sizeof(VoiceOutStatus);
  119. }
  120. return output_params;
  121. }
  122. void AudioRenderer::VoiceState::SetWaveIndex(std::size_t index) {
  123. wave_index = index & 3;
  124. is_refresh_pending = true;
  125. }
  126. std::vector<s16> AudioRenderer::VoiceState::DequeueSamples(std::size_t sample_count) {
  127. if (!IsPlaying()) {
  128. return {};
  129. }
  130. if (is_refresh_pending) {
  131. RefreshBuffer();
  132. }
  133. const std::size_t max_size{samples.size() - offset};
  134. const std::size_t dequeue_offset{offset};
  135. std::size_t size{sample_count * STREAM_NUM_CHANNELS};
  136. if (size > max_size) {
  137. size = max_size;
  138. }
  139. out_status.played_sample_count += size / STREAM_NUM_CHANNELS;
  140. offset += size;
  141. const auto& wave_buffer{info.wave_buffer[wave_index]};
  142. if (offset == samples.size()) {
  143. offset = 0;
  144. if (!wave_buffer.is_looping) {
  145. SetWaveIndex(wave_index + 1);
  146. }
  147. out_status.wave_buffer_consumed++;
  148. if (wave_buffer.end_of_stream) {
  149. info.play_state = PlayState::Paused;
  150. }
  151. }
  152. return {samples.begin() + dequeue_offset, samples.begin() + dequeue_offset + size};
  153. }
  154. void AudioRenderer::VoiceState::UpdateState() {
  155. if (is_in_use && !info.is_in_use) {
  156. // No longer in use, reset state
  157. is_refresh_pending = true;
  158. wave_index = 0;
  159. offset = 0;
  160. out_status = {};
  161. }
  162. is_in_use = info.is_in_use;
  163. }
  164. void AudioRenderer::VoiceState::RefreshBuffer() {
  165. std::vector<s16> new_samples(info.wave_buffer[wave_index].buffer_sz / sizeof(s16));
  166. Memory::ReadBlock(info.wave_buffer[wave_index].buffer_addr, new_samples.data(),
  167. info.wave_buffer[wave_index].buffer_sz);
  168. switch (static_cast<Codec::PcmFormat>(info.sample_format)) {
  169. case Codec::PcmFormat::Int16: {
  170. // PCM16 is played as-is
  171. break;
  172. }
  173. case Codec::PcmFormat::Adpcm: {
  174. // Decode ADPCM to PCM16
  175. Codec::ADPCM_Coeff coeffs;
  176. Memory::ReadBlock(info.additional_params_addr, coeffs.data(), sizeof(Codec::ADPCM_Coeff));
  177. new_samples = Codec::DecodeADPCM(reinterpret_cast<u8*>(new_samples.data()),
  178. new_samples.size() * sizeof(s16), coeffs, adpcm_state);
  179. break;
  180. }
  181. default:
  182. LOG_CRITICAL(Audio, "Unimplemented sample_format={}", info.sample_format);
  183. UNREACHABLE();
  184. break;
  185. }
  186. switch (info.channel_count) {
  187. case 1:
  188. // 1 channel is upsampled to 2 channel
  189. samples.resize(new_samples.size() * 2);
  190. for (std::size_t index = 0; index < new_samples.size(); ++index) {
  191. samples[index * 2] = new_samples[index];
  192. samples[index * 2 + 1] = new_samples[index];
  193. }
  194. break;
  195. case 2: {
  196. // 2 channel is played as is
  197. samples = std::move(new_samples);
  198. break;
  199. }
  200. default:
  201. LOG_CRITICAL(Audio, "Unimplemented channel_count={}", info.channel_count);
  202. UNREACHABLE();
  203. break;
  204. }
  205. samples = Interpolate(interp_state, std::move(samples), Info().sample_rate, STREAM_SAMPLE_RATE);
  206. is_refresh_pending = false;
  207. }
  208. static constexpr s16 ClampToS16(s32 value) {
  209. return static_cast<s16>(std::clamp(value, -32768, 32767));
  210. }
  211. void AudioRenderer::QueueMixedBuffer(Buffer::Tag tag) {
  212. constexpr std::size_t BUFFER_SIZE{512};
  213. std::vector<s16> buffer(BUFFER_SIZE * stream->GetNumChannels());
  214. for (auto& voice : voices) {
  215. if (!voice.IsPlaying()) {
  216. continue;
  217. }
  218. std::size_t offset{};
  219. s64 samples_remaining{BUFFER_SIZE};
  220. while (samples_remaining > 0) {
  221. const std::vector<s16> samples{voice.DequeueSamples(samples_remaining)};
  222. if (samples.empty()) {
  223. break;
  224. }
  225. samples_remaining -= samples.size() / stream->GetNumChannels();
  226. for (const auto& sample : samples) {
  227. const s32 buffer_sample{buffer[offset]};
  228. buffer[offset++] =
  229. ClampToS16(buffer_sample + static_cast<s32>(sample * voice.GetInfo().volume));
  230. }
  231. }
  232. }
  233. audio_out->QueueBuffer(stream, tag, std::move(buffer));
  234. }
  235. void AudioRenderer::ReleaseAndQueueBuffers() {
  236. const auto released_buffers{audio_out->GetTagsAndReleaseBuffers(stream, 2)};
  237. for (const auto& tag : released_buffers) {
  238. QueueMixedBuffer(tag);
  239. }
  240. }
  241. } // namespace AudioCore