diff options
Diffstat (limited to '')
| -rw-r--r-- | src/audio_core/common.h | 2 | ||||
| -rw-r--r-- | src/core/hle/ipc_helpers.h | 8 | ||||
| -rw-r--r-- | src/core/hle/service/aoc/aoc_u.cpp | 10 | ||||
| -rw-r--r-- | src/core/hle/service/aoc/aoc_u.h | 1 | ||||
| -rw-r--r-- | src/core/hle/service/audio/hwopus.cpp | 45 | ||||
| -rw-r--r-- | src/core/hle/service/audio/hwopus.h | 4 |
6 files changed, 61 insertions, 9 deletions
diff --git a/src/audio_core/common.h b/src/audio_core/common.h index fe546c55d..1ab537588 100644 --- a/src/audio_core/common.h +++ b/src/audio_core/common.h | |||
| @@ -15,7 +15,7 @@ constexpr ResultCode ERR_INVALID_PARAMETERS{ErrorModule::Audio, 41}; | |||
| 15 | constexpr ResultCode ERR_SPLITTER_SORT_FAILED{ErrorModule::Audio, 43}; | 15 | constexpr ResultCode ERR_SPLITTER_SORT_FAILED{ErrorModule::Audio, 43}; |
| 16 | } // namespace Audren | 16 | } // namespace Audren |
| 17 | 17 | ||
| 18 | constexpr u32_le CURRENT_PROCESS_REVISION = Common::MakeMagic('R', 'E', 'V', '8'); | 18 | constexpr u32_le CURRENT_PROCESS_REVISION = Common::MakeMagic('R', 'E', 'V', '9'); |
| 19 | constexpr std::size_t MAX_MIX_BUFFERS = 24; | 19 | constexpr std::size_t MAX_MIX_BUFFERS = 24; |
| 20 | constexpr std::size_t MAX_BIQUAD_FILTERS = 2; | 20 | constexpr std::size_t MAX_BIQUAD_FILTERS = 2; |
| 21 | constexpr std::size_t MAX_CHANNEL_COUNT = 6; | 21 | constexpr std::size_t MAX_CHANNEL_COUNT = 6; |
diff --git a/src/core/hle/ipc_helpers.h b/src/core/hle/ipc_helpers.h index 61bda3786..ceff2532d 100644 --- a/src/core/hle/ipc_helpers.h +++ b/src/core/hle/ipc_helpers.h | |||
| @@ -345,8 +345,12 @@ public: | |||
| 345 | explicit RequestParser(u32* command_buffer) : RequestHelperBase(command_buffer) {} | 345 | explicit RequestParser(u32* command_buffer) : RequestHelperBase(command_buffer) {} |
| 346 | 346 | ||
| 347 | explicit RequestParser(Kernel::HLERequestContext& ctx) : RequestHelperBase(ctx) { | 347 | explicit RequestParser(Kernel::HLERequestContext& ctx) : RequestHelperBase(ctx) { |
| 348 | ASSERT_MSG(ctx.GetDataPayloadOffset(), "context is incomplete"); | 348 | // TIPC does not have data payload offset |
| 349 | Skip(ctx.GetDataPayloadOffset(), false); | 349 | if (!ctx.IsTipc()) { |
| 350 | ASSERT_MSG(ctx.GetDataPayloadOffset(), "context is incomplete"); | ||
| 351 | Skip(ctx.GetDataPayloadOffset(), false); | ||
| 352 | } | ||
| 353 | |||
| 350 | // Skip the u64 command id, it's already stored in the context | 354 | // Skip the u64 command id, it's already stored in the context |
| 351 | static constexpr u32 CommandIdSize = 2; | 355 | static constexpr u32 CommandIdSize = 2; |
| 352 | Skip(CommandIdSize, false); | 356 | Skip(CommandIdSize, false); |
diff --git a/src/core/hle/service/aoc/aoc_u.cpp b/src/core/hle/service/aoc/aoc_u.cpp index fec704c65..dd945e058 100644 --- a/src/core/hle/service/aoc/aoc_u.cpp +++ b/src/core/hle/service/aoc/aoc_u.cpp | |||
| @@ -117,7 +117,7 @@ AOC_U::AOC_U(Core::System& system_) | |||
| 117 | {7, &AOC_U::PrepareAddOnContent, "PrepareAddOnContent"}, | 117 | {7, &AOC_U::PrepareAddOnContent, "PrepareAddOnContent"}, |
| 118 | {8, &AOC_U::GetAddOnContentListChangedEvent, "GetAddOnContentListChangedEvent"}, | 118 | {8, &AOC_U::GetAddOnContentListChangedEvent, "GetAddOnContentListChangedEvent"}, |
| 119 | {9, nullptr, "GetAddOnContentLostErrorCode"}, | 119 | {9, nullptr, "GetAddOnContentLostErrorCode"}, |
| 120 | {10, nullptr, "GetAddOnContentListChangedEventWithProcessId"}, | 120 | {10, &AOC_U::GetAddOnContentListChangedEventWithProcessId, "GetAddOnContentListChangedEventWithProcessId"}, |
| 121 | {100, &AOC_U::CreateEcPurchasedEventManager, "CreateEcPurchasedEventManager"}, | 121 | {100, &AOC_U::CreateEcPurchasedEventManager, "CreateEcPurchasedEventManager"}, |
| 122 | {101, &AOC_U::CreatePermanentEcPurchasedEventManager, "CreatePermanentEcPurchasedEventManager"}, | 122 | {101, &AOC_U::CreatePermanentEcPurchasedEventManager, "CreatePermanentEcPurchasedEventManager"}, |
| 123 | {110, nullptr, "CreateContentsServiceManager"}, | 123 | {110, nullptr, "CreateContentsServiceManager"}, |
| @@ -257,6 +257,14 @@ void AOC_U::GetAddOnContentListChangedEvent(Kernel::HLERequestContext& ctx) { | |||
| 257 | rb.PushCopyObjects(aoc_change_event.GetReadableEvent()); | 257 | rb.PushCopyObjects(aoc_change_event.GetReadableEvent()); |
| 258 | } | 258 | } |
| 259 | 259 | ||
| 260 | void AOC_U::GetAddOnContentListChangedEventWithProcessId(Kernel::HLERequestContext& ctx) { | ||
| 261 | LOG_WARNING(Service_AOC, "(STUBBED) called"); | ||
| 262 | |||
| 263 | IPC::ResponseBuilder rb{ctx, 2, 1}; | ||
| 264 | rb.Push(ResultSuccess); | ||
| 265 | rb.PushCopyObjects(aoc_change_event.GetReadableEvent()); | ||
| 266 | } | ||
| 267 | |||
| 260 | void AOC_U::CreateEcPurchasedEventManager(Kernel::HLERequestContext& ctx) { | 268 | void AOC_U::CreateEcPurchasedEventManager(Kernel::HLERequestContext& ctx) { |
| 261 | LOG_WARNING(Service_AOC, "(STUBBED) called"); | 269 | LOG_WARNING(Service_AOC, "(STUBBED) called"); |
| 262 | 270 | ||
diff --git a/src/core/hle/service/aoc/aoc_u.h b/src/core/hle/service/aoc/aoc_u.h index 65095baa2..bb6ffb8eb 100644 --- a/src/core/hle/service/aoc/aoc_u.h +++ b/src/core/hle/service/aoc/aoc_u.h | |||
| @@ -28,6 +28,7 @@ private: | |||
| 28 | void GetAddOnContentBaseId(Kernel::HLERequestContext& ctx); | 28 | void GetAddOnContentBaseId(Kernel::HLERequestContext& ctx); |
| 29 | void PrepareAddOnContent(Kernel::HLERequestContext& ctx); | 29 | void PrepareAddOnContent(Kernel::HLERequestContext& ctx); |
| 30 | void GetAddOnContentListChangedEvent(Kernel::HLERequestContext& ctx); | 30 | void GetAddOnContentListChangedEvent(Kernel::HLERequestContext& ctx); |
| 31 | void GetAddOnContentListChangedEventWithProcessId(Kernel::HLERequestContext& ctx); | ||
| 31 | void CreateEcPurchasedEventManager(Kernel::HLERequestContext& ctx); | 32 | void CreateEcPurchasedEventManager(Kernel::HLERequestContext& ctx); |
| 32 | void CreatePermanentEcPurchasedEventManager(Kernel::HLERequestContext& ctx); | 33 | void CreatePermanentEcPurchasedEventManager(Kernel::HLERequestContext& ctx); |
| 33 | 34 | ||
diff --git a/src/core/hle/service/audio/hwopus.cpp b/src/core/hle/service/audio/hwopus.cpp index 10e6f7a64..33a6dbbb6 100644 --- a/src/core/hle/service/audio/hwopus.cpp +++ b/src/core/hle/service/audio/hwopus.cpp | |||
| @@ -253,7 +253,11 @@ void HwOpus::GetWorkBufferSize(Kernel::HLERequestContext& ctx) { | |||
| 253 | rb.Push<u32>(worker_buffer_sz); | 253 | rb.Push<u32>(worker_buffer_sz); |
| 254 | } | 254 | } |
| 255 | 255 | ||
| 256 | void HwOpus::OpenOpusDecoder(Kernel::HLERequestContext& ctx) { | 256 | void HwOpus::GetWorkBufferSizeEx(Kernel::HLERequestContext& ctx) { |
| 257 | GetWorkBufferSize(ctx); | ||
| 258 | } | ||
| 259 | |||
| 260 | void HwOpus::OpenHardwareOpusDecoder(Kernel::HLERequestContext& ctx) { | ||
| 257 | IPC::RequestParser rp{ctx}; | 261 | IPC::RequestParser rp{ctx}; |
| 258 | const auto sample_rate = rp.Pop<u32>(); | 262 | const auto sample_rate = rp.Pop<u32>(); |
| 259 | const auto channel_count = rp.Pop<u32>(); | 263 | const auto channel_count = rp.Pop<u32>(); |
| @@ -291,14 +295,47 @@ void HwOpus::OpenOpusDecoder(Kernel::HLERequestContext& ctx) { | |||
| 291 | system, OpusDecoderState{std::move(decoder), sample_rate, channel_count}); | 295 | system, OpusDecoderState{std::move(decoder), sample_rate, channel_count}); |
| 292 | } | 296 | } |
| 293 | 297 | ||
| 298 | void HwOpus::OpenHardwareOpusDecoderEx(Kernel::HLERequestContext& ctx) { | ||
| 299 | IPC::RequestParser rp{ctx}; | ||
| 300 | const auto sample_rate = rp.Pop<u32>(); | ||
| 301 | const auto channel_count = rp.Pop<u32>(); | ||
| 302 | |||
| 303 | LOG_CRITICAL(Audio, "called sample_rate={}, channel_count={}", sample_rate, channel_count); | ||
| 304 | |||
| 305 | ASSERT_MSG(sample_rate == 48000 || sample_rate == 24000 || sample_rate == 16000 || | ||
| 306 | sample_rate == 12000 || sample_rate == 8000, | ||
| 307 | "Invalid sample rate"); | ||
| 308 | ASSERT_MSG(channel_count == 1 || channel_count == 2, "Invalid channel count"); | ||
| 309 | |||
| 310 | const int num_stereo_streams = channel_count == 2 ? 1 : 0; | ||
| 311 | const auto mapping_table = CreateMappingTable(channel_count); | ||
| 312 | |||
| 313 | int error = 0; | ||
| 314 | OpusDecoderPtr decoder{ | ||
| 315 | opus_multistream_decoder_create(sample_rate, static_cast<int>(channel_count), 1, | ||
| 316 | num_stereo_streams, mapping_table.data(), &error)}; | ||
| 317 | if (error != OPUS_OK || decoder == nullptr) { | ||
| 318 | LOG_ERROR(Audio, "Failed to create Opus decoder (error={}).", error); | ||
| 319 | IPC::ResponseBuilder rb{ctx, 2}; | ||
| 320 | // TODO(ogniK): Use correct error code | ||
| 321 | rb.Push(ResultUnknown); | ||
| 322 | return; | ||
| 323 | } | ||
| 324 | |||
| 325 | IPC::ResponseBuilder rb{ctx, 2, 0, 1}; | ||
| 326 | rb.Push(ResultSuccess); | ||
| 327 | rb.PushIpcInterface<IHardwareOpusDecoderManager>( | ||
| 328 | system, OpusDecoderState{std::move(decoder), sample_rate, channel_count}); | ||
| 329 | } | ||
| 330 | |||
| 294 | HwOpus::HwOpus(Core::System& system_) : ServiceFramework{system_, "hwopus"} { | 331 | HwOpus::HwOpus(Core::System& system_) : ServiceFramework{system_, "hwopus"} { |
| 295 | static const FunctionInfo functions[] = { | 332 | static const FunctionInfo functions[] = { |
| 296 | {0, &HwOpus::OpenOpusDecoder, "OpenOpusDecoder"}, | 333 | {0, &HwOpus::OpenHardwareOpusDecoder, "OpenHardwareOpusDecoder"}, |
| 297 | {1, &HwOpus::GetWorkBufferSize, "GetWorkBufferSize"}, | 334 | {1, &HwOpus::GetWorkBufferSize, "GetWorkBufferSize"}, |
| 298 | {2, nullptr, "OpenOpusDecoderForMultiStream"}, | 335 | {2, nullptr, "OpenOpusDecoderForMultiStream"}, |
| 299 | {3, nullptr, "GetWorkBufferSizeForMultiStream"}, | 336 | {3, nullptr, "GetWorkBufferSizeForMultiStream"}, |
| 300 | {4, nullptr, "OpenHardwareOpusDecoderEx"}, | 337 | {4, &HwOpus::OpenHardwareOpusDecoderEx, "OpenHardwareOpusDecoderEx"}, |
| 301 | {5, nullptr, "GetWorkBufferSizeEx"}, | 338 | {5, &HwOpus::GetWorkBufferSizeEx, "GetWorkBufferSizeEx"}, |
| 302 | {6, nullptr, "OpenHardwareOpusDecoderForMultiStreamEx"}, | 339 | {6, nullptr, "OpenHardwareOpusDecoderForMultiStreamEx"}, |
| 303 | {7, nullptr, "GetWorkBufferSizeForMultiStreamEx"}, | 340 | {7, nullptr, "GetWorkBufferSizeForMultiStreamEx"}, |
| 304 | }; | 341 | }; |
diff --git a/src/core/hle/service/audio/hwopus.h b/src/core/hle/service/audio/hwopus.h index 4f921f18e..b74824ff3 100644 --- a/src/core/hle/service/audio/hwopus.h +++ b/src/core/hle/service/audio/hwopus.h | |||
| @@ -18,8 +18,10 @@ public: | |||
| 18 | ~HwOpus() override; | 18 | ~HwOpus() override; |
| 19 | 19 | ||
| 20 | private: | 20 | private: |
| 21 | void OpenOpusDecoder(Kernel::HLERequestContext& ctx); | 21 | void OpenHardwareOpusDecoder(Kernel::HLERequestContext& ctx); |
| 22 | void OpenHardwareOpusDecoderEx(Kernel::HLERequestContext& ctx); | ||
| 22 | void GetWorkBufferSize(Kernel::HLERequestContext& ctx); | 23 | void GetWorkBufferSize(Kernel::HLERequestContext& ctx); |
| 24 | void GetWorkBufferSizeEx(Kernel::HLERequestContext& ctx); | ||
| 23 | }; | 25 | }; |
| 24 | 26 | ||
| 25 | } // namespace Service::Audio | 27 | } // namespace Service::Audio |