diff options
author | Liam <byteslice@airmail.cc> | 2024-02-12 02:12:09 +0100 |
---|---|---|
committer | Liam <byteslice@airmail.cc> | 2024-02-12 15:16:02 +0100 |
commit | c7e94e2175c02fe22846d89915b08d8b1802ef4f (patch) | |
tree | 674cbe3c536331516fa8995214104d6d9a01b7ec /src/core/hle/service | |
parent | am: rewrite ILibraryAppletCreator (diff) | |
download | yuzu-c7e94e2175c02fe22846d89915b08d8b1802ef4f.tar yuzu-c7e94e2175c02fe22846d89915b08d8b1802ef4f.tar.gz yuzu-c7e94e2175c02fe22846d89915b08d8b1802ef4f.tar.bz2 yuzu-c7e94e2175c02fe22846d89915b08d8b1802ef4f.tar.lz yuzu-c7e94e2175c02fe22846d89915b08d8b1802ef4f.tar.xz yuzu-c7e94e2175c02fe22846d89915b08d8b1802ef4f.tar.zst yuzu-c7e94e2175c02fe22846d89915b08d8b1802ef4f.zip |
Diffstat (limited to 'src/core/hle/service')
7 files changed, 406 insertions, 385 deletions
diff --git a/src/core/hle/service/am/library_applet_self_accessor.cpp b/src/core/hle/service/am/library_applet_self_accessor.cpp deleted file mode 100644 index b560f580b..000000000 --- a/src/core/hle/service/am/library_applet_self_accessor.cpp +++ /dev/null @@ -1,338 +0,0 @@ -// SPDX-FileCopyrightText: Copyright 2024 yuzu Emulator Project -// SPDX-License-Identifier: GPL-2.0-or-later - -#include "common/scope_exit.h" -#include "core/core_timing.h" -#include "core/file_sys/control_metadata.h" -#include "core/file_sys/patch_manager.h" -#include "core/file_sys/registered_cache.h" -#include "core/hle/service/acc/profile_manager.h" -#include "core/hle/service/am/am_results.h" -#include "core/hle/service/am/applet_data_broker.h" -#include "core/hle/service/am/applet_manager.h" -#include "core/hle/service/am/frontend/applet_cabinet.h" -#include "core/hle/service/am/frontend/applet_controller.h" -#include "core/hle/service/am/frontend/applet_mii_edit_types.h" -#include "core/hle/service/am/frontend/applet_software_keyboard_types.h" -#include "core/hle/service/am/frontend/applets.h" -#include "core/hle/service/am/library_applet_self_accessor.h" -#include "core/hle/service/am/storage.h" -#include "core/hle/service/ipc_helpers.h" -#include "core/hle/service/ns/ns.h" -#include "core/hle/service/sm/sm.h" -#include "hid_core/hid_types.h" - -namespace Service::AM { - -namespace { - -AppletIdentityInfo GetCallerIdentity(std::shared_ptr<Applet> applet) { - if (const auto caller_applet = applet->caller_applet.lock(); caller_applet) { - // TODO: is this actually the application ID? - return { - .applet_id = caller_applet->applet_id, - .application_id = caller_applet->program_id, - }; - } else { - return { - .applet_id = AppletId::QLaunch, - .application_id = 0x0100000000001000ull, - }; - } -} - -} // namespace - -ILibraryAppletSelfAccessor::ILibraryAppletSelfAccessor(Core::System& system_, - std::shared_ptr<Applet> applet_) - : ServiceFramework{system_, "ILibraryAppletSelfAccessor"}, applet{std::move(applet_)}, - broker{applet->caller_applet_broker} { - // clang-format off - static const FunctionInfo functions[] = { - {0, &ILibraryAppletSelfAccessor::PopInData, "PopInData"}, - {1, &ILibraryAppletSelfAccessor::PushOutData, "PushOutData"}, - {2, &ILibraryAppletSelfAccessor::PopInteractiveInData, "PopInteractiveInData"}, - {3, &ILibraryAppletSelfAccessor::PushInteractiveOutData, "PushInteractiveOutData"}, - {5, &ILibraryAppletSelfAccessor::GetPopInDataEvent, "GetPopInDataEvent"}, - {6, &ILibraryAppletSelfAccessor::GetPopInteractiveInDataEvent, "GetPopInteractiveInDataEvent"}, - {10, &ILibraryAppletSelfAccessor::ExitProcessAndReturn, "ExitProcessAndReturn"}, - {11, &ILibraryAppletSelfAccessor::GetLibraryAppletInfo, "GetLibraryAppletInfo"}, - {12, &ILibraryAppletSelfAccessor::GetMainAppletIdentityInfo, "GetMainAppletIdentityInfo"}, - {13, &ILibraryAppletSelfAccessor::CanUseApplicationCore, "CanUseApplicationCore"}, - {14, &ILibraryAppletSelfAccessor::GetCallerAppletIdentityInfo, "GetCallerAppletIdentityInfo"}, - {15, nullptr, "GetMainAppletApplicationControlProperty"}, - {16, nullptr, "GetMainAppletStorageId"}, - {17, nullptr, "GetCallerAppletIdentityInfoStack"}, - {18, nullptr, "GetNextReturnDestinationAppletIdentityInfo"}, - {19, &ILibraryAppletSelfAccessor::GetDesirableKeyboardLayout, "GetDesirableKeyboardLayout"}, - {20, nullptr, "PopExtraStorage"}, - {25, nullptr, "GetPopExtraStorageEvent"}, - {30, nullptr, "UnpopInData"}, - {31, nullptr, "UnpopExtraStorage"}, - {40, nullptr, "GetIndirectLayerProducerHandle"}, - {50, nullptr, "ReportVisibleError"}, - {51, nullptr, "ReportVisibleErrorWithErrorContext"}, - {60, &ILibraryAppletSelfAccessor::GetMainAppletApplicationDesiredLanguage, "GetMainAppletApplicationDesiredLanguage"}, - {70, &ILibraryAppletSelfAccessor::GetCurrentApplicationId, "GetCurrentApplicationId"}, - {80, nullptr, "RequestExitToSelf"}, - {90, nullptr, "CreateApplicationAndPushAndRequestToLaunch"}, - {100, nullptr, "CreateGameMovieTrimmer"}, - {101, nullptr, "ReserveResourceForMovieOperation"}, - {102, nullptr, "UnreserveResourceForMovieOperation"}, - {110, &ILibraryAppletSelfAccessor::GetMainAppletAvailableUsers, "GetMainAppletAvailableUsers"}, - {120, nullptr, "GetLaunchStorageInfoForDebug"}, - {130, nullptr, "GetGpuErrorDetectedSystemEvent"}, - {140, nullptr, "SetApplicationMemoryReservation"}, - {150, &ILibraryAppletSelfAccessor::ShouldSetGpuTimeSliceManually, "ShouldSetGpuTimeSliceManually"}, - {160, &ILibraryAppletSelfAccessor::Cmd160, "Cmd160"}, - }; - // clang-format on - RegisterHandlers(functions); -} - -ILibraryAppletSelfAccessor::~ILibraryAppletSelfAccessor() = default; - -void ILibraryAppletSelfAccessor::PopInData(HLERequestContext& ctx) { - LOG_INFO(Service_AM, "called"); - - std::shared_ptr<IStorage> data; - const auto res = broker->GetInData().Pop(&data); - - if (res.IsSuccess()) { - IPC::ResponseBuilder rb{ctx, 2, 0, 1}; - rb.Push(res); - rb.PushIpcInterface(std::move(data)); - } else { - IPC::ResponseBuilder rb{ctx, 2}; - rb.Push(res); - } -} - -void ILibraryAppletSelfAccessor::PushOutData(HLERequestContext& ctx) { - LOG_INFO(Service_AM, "called"); - - IPC::RequestParser rp{ctx}; - broker->GetOutData().Push(rp.PopIpcInterface<IStorage>().lock()); - - IPC::ResponseBuilder rb{ctx, 2}; - rb.Push(ResultSuccess); -} - -void ILibraryAppletSelfAccessor::PopInteractiveInData(HLERequestContext& ctx) { - LOG_INFO(Service_AM, "called"); - - std::shared_ptr<IStorage> data; - const auto res = broker->GetInteractiveInData().Pop(&data); - - if (res.IsSuccess()) { - IPC::ResponseBuilder rb{ctx, 2, 0, 1}; - rb.Push(res); - rb.PushIpcInterface(std::move(data)); - } else { - IPC::ResponseBuilder rb{ctx, 2}; - rb.Push(res); - } -} - -void ILibraryAppletSelfAccessor::PushInteractiveOutData(HLERequestContext& ctx) { - LOG_INFO(Service_AM, "called"); - - IPC::RequestParser rp{ctx}; - broker->GetInteractiveOutData().Push(rp.PopIpcInterface<IStorage>().lock()); - - IPC::ResponseBuilder rb{ctx, 2}; - rb.Push(ResultSuccess); -} - -void ILibraryAppletSelfAccessor::GetPopInDataEvent(HLERequestContext& ctx) { - LOG_INFO(Service_AM, "called"); - - IPC::ResponseBuilder rb{ctx, 2, 1}; - rb.Push(ResultSuccess); - rb.PushCopyObjects(broker->GetInData().GetEvent()); -} - -void ILibraryAppletSelfAccessor::GetPopInteractiveInDataEvent(HLERequestContext& ctx) { - LOG_INFO(Service_AM, "called"); - - IPC::ResponseBuilder rb{ctx, 2, 1}; - rb.Push(ResultSuccess); - rb.PushCopyObjects(broker->GetInteractiveInData().GetEvent()); -} - -void ILibraryAppletSelfAccessor::ExitProcessAndReturn(HLERequestContext& ctx) { - LOG_INFO(Service_AM, "called"); - - system.GetAppletManager().TerminateAndRemoveApplet(applet->aruid); - broker->SignalCompletion(); - - IPC::ResponseBuilder rb{ctx, 2}; - rb.Push(ResultSuccess); -} - -void ILibraryAppletSelfAccessor::GetLibraryAppletInfo(HLERequestContext& ctx) { - struct LibraryAppletInfo { - AppletId applet_id; - LibraryAppletMode library_applet_mode; - }; - - LOG_WARNING(Service_AM, "(STUBBED) called"); - - const LibraryAppletInfo applet_info{ - .applet_id = applet->applet_id, - .library_applet_mode = applet->library_applet_mode, - }; - - IPC::ResponseBuilder rb{ctx, 4}; - rb.Push(ResultSuccess); - rb.PushRaw(applet_info); -} - -void ILibraryAppletSelfAccessor::GetMainAppletIdentityInfo(HLERequestContext& ctx) { - LOG_WARNING(Service_AM, "(STUBBED) called"); - - const AppletIdentityInfo applet_info{ - .applet_id = AppletId::QLaunch, - .application_id = 0x0100000000001000ull, - }; - - IPC::ResponseBuilder rb{ctx, 6}; - rb.Push(ResultSuccess); - rb.PushRaw(applet_info); -} - -void ILibraryAppletSelfAccessor::CanUseApplicationCore(HLERequestContext& ctx) { - LOG_WARNING(Service_AM, "(STUBBED) called"); - - // TODO: This appears to read the NPDM from state and check the core mask of the applet. - IPC::ResponseBuilder rb{ctx, 3}; - rb.Push(ResultSuccess); - rb.Push<u8>(0); -} - -void ILibraryAppletSelfAccessor::GetCallerAppletIdentityInfo(HLERequestContext& ctx) { - LOG_WARNING(Service_AM, "(STUBBED) called"); - - IPC::ResponseBuilder rb{ctx, 6}; - rb.Push(ResultSuccess); - rb.PushRaw(GetCallerIdentity(applet)); -} - -void ILibraryAppletSelfAccessor::GetDesirableKeyboardLayout(HLERequestContext& ctx) { - LOG_WARNING(Service_AM, "(STUBBED) called"); - - IPC::ResponseBuilder rb{ctx, 3}; - rb.Push(ResultSuccess); - rb.Push<u32>(0); -} - -void ILibraryAppletSelfAccessor::GetMainAppletApplicationDesiredLanguage(HLERequestContext& ctx) { - // FIXME: this is copied from IApplicationFunctions::GetDesiredLanguage - auto identity = GetCallerIdentity(applet); - - // TODO(bunnei): This should be configurable - LOG_DEBUG(Service_AM, "called"); - - // Get supported languages from NACP, if possible - // Default to 0 (all languages supported) - u32 supported_languages = 0; - - const auto res = [this, identity] { - const FileSys::PatchManager pm{identity.application_id, system.GetFileSystemController(), - system.GetContentProvider()}; - auto metadata = pm.GetControlMetadata(); - if (metadata.first != nullptr) { - return metadata; - } - - const FileSys::PatchManager pm_update{FileSys::GetUpdateTitleID(identity.application_id), - system.GetFileSystemController(), - system.GetContentProvider()}; - return pm_update.GetControlMetadata(); - }(); - - if (res.first != nullptr) { - supported_languages = res.first->GetSupportedLanguages(); - } - - // Call IApplicationManagerInterface implementation. - auto& service_manager = system.ServiceManager(); - auto ns_am2 = service_manager.GetService<NS::NS>("ns:am2"); - auto app_man = ns_am2->GetApplicationManagerInterface(); - - // Get desired application language - u8 desired_language{}; - const auto res_lang = - app_man->GetApplicationDesiredLanguage(&desired_language, supported_languages); - if (res_lang != ResultSuccess) { - IPC::ResponseBuilder rb{ctx, 2}; - rb.Push(res_lang); - return; - } - - // Convert to settings language code. - u64 language_code{}; - const auto res_code = - app_man->ConvertApplicationLanguageToLanguageCode(&language_code, desired_language); - if (res_code != ResultSuccess) { - IPC::ResponseBuilder rb{ctx, 2}; - rb.Push(res_code); - return; - } - - LOG_DEBUG(Service_AM, "got desired_language={:016X}", language_code); - - IPC::ResponseBuilder rb{ctx, 4}; - rb.Push(ResultSuccess); - rb.Push(language_code); -} - -void ILibraryAppletSelfAccessor::GetCurrentApplicationId(HLERequestContext& ctx) { - LOG_WARNING(Service_AM, "(STUBBED) called"); - - u64 application_id = 0; - if (auto caller_applet = applet->caller_applet.lock(); caller_applet) { - application_id = caller_applet->program_id; - } - - IPC::ResponseBuilder rb{ctx, 4}; - rb.Push(ResultSuccess); - rb.Push(application_id); -} - -void ILibraryAppletSelfAccessor::GetMainAppletAvailableUsers(HLERequestContext& ctx) { - const Service::Account::ProfileManager manager{}; - bool is_empty{true}; - s32 user_count{-1}; - - LOG_INFO(Service_AM, "called"); - - if (manager.GetUserCount() > 0) { - is_empty = false; - user_count = static_cast<s32>(manager.GetUserCount()); - ctx.WriteBuffer(manager.GetAllUsers()); - } - - IPC::ResponseBuilder rb{ctx, 4}; - rb.Push(ResultSuccess); - rb.Push<u8>(is_empty); - rb.Push(user_count); -} - -void ILibraryAppletSelfAccessor::ShouldSetGpuTimeSliceManually(HLERequestContext& ctx) { - LOG_WARNING(Service_AM, "(STUBBED) called"); - - IPC::ResponseBuilder rb{ctx, 3}; - rb.Push(ResultSuccess); - rb.Push<u8>(0); -} - -void ILibraryAppletSelfAccessor::Cmd160(HLERequestContext& ctx) { - LOG_WARNING(Service_AM, "(STUBBED) called"); - - IPC::ResponseBuilder rb{ctx, 4}; - rb.Push(ResultSuccess); - rb.Push<u64>(0); -} - -} // namespace Service::AM diff --git a/src/core/hle/service/am/library_applet_self_accessor.h b/src/core/hle/service/am/library_applet_self_accessor.h deleted file mode 100644 index 8717a989a..000000000 --- a/src/core/hle/service/am/library_applet_self_accessor.h +++ /dev/null @@ -1,44 +0,0 @@ -// SPDX-FileCopyrightText: Copyright 2024 yuzu Emulator Project -// SPDX-License-Identifier: GPL-2.0-or-later - -#pragma once - -#include <deque> -#include <vector> - -#include "core/hle/service/service.h" - -namespace Service::AM { - -class AppletDataBroker; -struct Applet; - -class ILibraryAppletSelfAccessor final : public ServiceFramework<ILibraryAppletSelfAccessor> { -public: - explicit ILibraryAppletSelfAccessor(Core::System& system_, std::shared_ptr<Applet> applet_); - ~ILibraryAppletSelfAccessor() override; - -private: - void PopInData(HLERequestContext& ctx); - void PushOutData(HLERequestContext& ctx); - void PopInteractiveInData(HLERequestContext& ctx); - void PushInteractiveOutData(HLERequestContext& ctx); - void GetPopInDataEvent(HLERequestContext& ctx); - void GetPopInteractiveInDataEvent(HLERequestContext& ctx); - void GetLibraryAppletInfo(HLERequestContext& ctx); - void GetMainAppletIdentityInfo(HLERequestContext& ctx); - void CanUseApplicationCore(HLERequestContext& ctx); - void ExitProcessAndReturn(HLERequestContext& ctx); - void GetCallerAppletIdentityInfo(HLERequestContext& ctx); - void GetDesirableKeyboardLayout(HLERequestContext& ctx); - void GetMainAppletApplicationDesiredLanguage(HLERequestContext& ctx); - void GetCurrentApplicationId(HLERequestContext& ctx); - void GetMainAppletAvailableUsers(HLERequestContext& ctx); - void ShouldSetGpuTimeSliceManually(HLERequestContext& ctx); - void Cmd160(HLERequestContext& ctx); - - const std::shared_ptr<Applet> applet; - const std::shared_ptr<AppletDataBroker> broker; -}; - -} // namespace Service::AM diff --git a/src/core/hle/service/am/service/application_proxy.cpp b/src/core/hle/service/am/service/application_proxy.cpp index 26a818f14..c9b872887 100644 --- a/src/core/hle/service/am/service/application_proxy.cpp +++ b/src/core/hle/service/am/service/application_proxy.cpp @@ -1,7 +1,6 @@ // SPDX-FileCopyrightText: Copyright 2024 yuzu Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later -#include "core/hle/service/am/library_applet_self_accessor.h" #include "core/hle/service/am/process_winding_controller.h" #include "core/hle/service/am/self_controller.h" #include "core/hle/service/am/service/applet_common_functions.h" diff --git a/src/core/hle/service/am/service/library_applet_proxy.cpp b/src/core/hle/service/am/service/library_applet_proxy.cpp index f1a13a331..9506739e9 100644 --- a/src/core/hle/service/am/service/library_applet_proxy.cpp +++ b/src/core/hle/service/am/service/library_applet_proxy.cpp @@ -1,7 +1,6 @@ // SPDX-FileCopyrightText: Copyright 2024 yuzu Emulator Project // SPDX-License-Identifier: GPL-2.0-or-later -#include "core/hle/service/am/library_applet_self_accessor.h" #include "core/hle/service/am/process_winding_controller.h" #include "core/hle/service/am/self_controller.h" #include "core/hle/service/am/service/applet_common_functions.h" @@ -13,6 +12,7 @@ #include "core/hle/service/am/service/home_menu_functions.h" #include "core/hle/service/am/service/library_applet_creator.h" #include "core/hle/service/am/service/library_applet_proxy.h" +#include "core/hle/service/am/service/library_applet_self_accessor.h" #include "core/hle/service/am/window_controller.h" #include "core/hle/service/cmif_serialization.h" diff --git a/src/core/hle/service/am/service/library_applet_self_accessor.cpp b/src/core/hle/service/am/service/library_applet_self_accessor.cpp new file mode 100644 index 000000000..a432a79ba --- /dev/null +++ b/src/core/hle/service/am/service/library_applet_self_accessor.cpp @@ -0,0 +1,322 @@ +// SPDX-FileCopyrightText: Copyright 2024 yuzu Emulator Project +// SPDX-License-Identifier: GPL-2.0-or-later + +#include "core/core_timing.h" +#include "core/file_sys/control_metadata.h" +#include "core/file_sys/patch_manager.h" +#include "core/file_sys/registered_cache.h" +#include "core/hle/service/acc/profile_manager.h" +#include "core/hle/service/am/applet_data_broker.h" +#include "core/hle/service/am/applet_manager.h" +#include "core/hle/service/am/frontend/applets.h" +#include "core/hle/service/am/service/library_applet_self_accessor.h" +#include "core/hle/service/am/storage.h" +#include "core/hle/service/cmif_serialization.h" +#include "core/hle/service/filesystem/filesystem.h" +#include "core/hle/service/glue/glue_manager.h" +#include "core/hle/service/ns/ns.h" +#include "core/hle/service/sm/sm.h" + +namespace Service::AM { + +namespace { + +AppletIdentityInfo GetCallerIdentity(Applet& applet) { + if (const auto caller_applet = applet.caller_applet.lock(); caller_applet) { + // TODO: is this actually the application ID? + return { + .applet_id = caller_applet->applet_id, + .application_id = caller_applet->program_id, + }; + } else { + return { + .applet_id = AppletId::QLaunch, + .application_id = 0x0100000000001000ull, + }; + } +} + +} // namespace + +ILibraryAppletSelfAccessor::ILibraryAppletSelfAccessor(Core::System& system_, + std::shared_ptr<Applet> applet) + : ServiceFramework{system_, "ILibraryAppletSelfAccessor"}, m_applet{std::move(applet)}, + m_broker{m_applet->caller_applet_broker} { + // clang-format off + static const FunctionInfo functions[] = { + {0, D<&ILibraryAppletSelfAccessor::PopInData>, "PopInData"}, + {1, D<&ILibraryAppletSelfAccessor::PushOutData>, "PushOutData"}, + {2, D<&ILibraryAppletSelfAccessor::PopInteractiveInData>, "PopInteractiveInData"}, + {3, D<&ILibraryAppletSelfAccessor::PushInteractiveOutData>, "PushInteractiveOutData"}, + {5, D<&ILibraryAppletSelfAccessor::GetPopInDataEvent>, "GetPopInDataEvent"}, + {6, D<&ILibraryAppletSelfAccessor::GetPopInteractiveInDataEvent>, "GetPopInteractiveInDataEvent"}, + {10, D<&ILibraryAppletSelfAccessor::ExitProcessAndReturn>, "ExitProcessAndReturn"}, + {11, D<&ILibraryAppletSelfAccessor::GetLibraryAppletInfo>, "GetLibraryAppletInfo"}, + {12, D<&ILibraryAppletSelfAccessor::GetMainAppletIdentityInfo>, "GetMainAppletIdentityInfo"}, + {13, D<&ILibraryAppletSelfAccessor::CanUseApplicationCore>, "CanUseApplicationCore"}, + {14, D<&ILibraryAppletSelfAccessor::GetCallerAppletIdentityInfo>, "GetCallerAppletIdentityInfo"}, + {15, D<&ILibraryAppletSelfAccessor::GetMainAppletApplicationControlProperty>, "GetMainAppletApplicationControlProperty"}, + {16, D<&ILibraryAppletSelfAccessor::GetMainAppletStorageId>, "GetMainAppletStorageId"}, + {17, D<&ILibraryAppletSelfAccessor::GetCallerAppletIdentityInfoStack>, "GetCallerAppletIdentityInfoStack"}, + {18, nullptr, "GetNextReturnDestinationAppletIdentityInfo"}, + {19, D<&ILibraryAppletSelfAccessor::GetDesirableKeyboardLayout>, "GetDesirableKeyboardLayout"}, + {20, nullptr, "PopExtraStorage"}, + {25, nullptr, "GetPopExtraStorageEvent"}, + {30, nullptr, "UnpopInData"}, + {31, nullptr, "UnpopExtraStorage"}, + {40, nullptr, "GetIndirectLayerProducerHandle"}, + {50, D<&ILibraryAppletSelfAccessor::ReportVisibleError>, "ReportVisibleError"}, + {51, D<&ILibraryAppletSelfAccessor::ReportVisibleErrorWithErrorContext>, "ReportVisibleErrorWithErrorContext"}, + {60, D<&ILibraryAppletSelfAccessor::GetMainAppletApplicationDesiredLanguage>, "GetMainAppletApplicationDesiredLanguage"}, + {70, D<&ILibraryAppletSelfAccessor::GetCurrentApplicationId>, "GetCurrentApplicationId"}, + {80, nullptr, "RequestExitToSelf"}, + {90, nullptr, "CreateApplicationAndPushAndRequestToLaunch"}, + {100, nullptr, "CreateGameMovieTrimmer"}, + {101, nullptr, "ReserveResourceForMovieOperation"}, + {102, nullptr, "UnreserveResourceForMovieOperation"}, + {110, D<&ILibraryAppletSelfAccessor::GetMainAppletAvailableUsers>, "GetMainAppletAvailableUsers"}, + {120, nullptr, "GetLaunchStorageInfoForDebug"}, + {130, nullptr, "GetGpuErrorDetectedSystemEvent"}, + {140, nullptr, "SetApplicationMemoryReservation"}, + {150, D<&ILibraryAppletSelfAccessor::ShouldSetGpuTimeSliceManually>, "ShouldSetGpuTimeSliceManually"}, + {160, D<&ILibraryAppletSelfAccessor::Cmd160>, "Cmd160"}, + }; + // clang-format on + RegisterHandlers(functions); +} + +ILibraryAppletSelfAccessor::~ILibraryAppletSelfAccessor() = default; + +Result ILibraryAppletSelfAccessor::PopInData(Out<SharedPointer<IStorage>> out_storage) { + LOG_INFO(Service_AM, "called"); + R_RETURN(m_broker->GetInData().Pop(out_storage)); +} + +Result ILibraryAppletSelfAccessor::PushOutData(SharedPointer<IStorage> storage) { + LOG_INFO(Service_AM, "called"); + m_broker->GetOutData().Push(storage); + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::PopInteractiveInData(Out<SharedPointer<IStorage>> out_storage) { + LOG_INFO(Service_AM, "called"); + R_RETURN(m_broker->GetInteractiveInData().Pop(out_storage)); +} + +Result ILibraryAppletSelfAccessor::PushInteractiveOutData(SharedPointer<IStorage> storage) { + LOG_INFO(Service_AM, "called"); + m_broker->GetInteractiveOutData().Push(storage); + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::GetPopInDataEvent( + OutCopyHandle<Kernel::KReadableEvent> out_event) { + LOG_INFO(Service_AM, "called"); + *out_event = m_broker->GetInData().GetEvent(); + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::GetPopInteractiveInDataEvent( + OutCopyHandle<Kernel::KReadableEvent> out_event) { + LOG_INFO(Service_AM, "called"); + *out_event = m_broker->GetInteractiveInData().GetEvent(); + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::GetLibraryAppletInfo( + Out<LibraryAppletInfo> out_library_applet_info) { + LOG_INFO(Service_AM, "called"); + *out_library_applet_info = { + .applet_id = m_applet->applet_id, + .library_applet_mode = m_applet->library_applet_mode, + }; + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::GetMainAppletIdentityInfo( + Out<AppletIdentityInfo> out_identity_info) { + LOG_WARNING(Service_AM, "(STUBBED) called"); + *out_identity_info = { + .applet_id = AppletId::QLaunch, + .application_id = 0x0100000000001000ull, + }; + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::CanUseApplicationCore(Out<bool> out_can_use_application_core) { + // TODO: This appears to read the NPDM from state and check the core mask of the applet. + LOG_WARNING(Service_AM, "(STUBBED) called"); + *out_can_use_application_core = false; + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::GetMainAppletApplicationControlProperty( + OutLargeData<std::array<u8, 0x4000>, BufferAttr_HipcMapAlias> out_nacp) { + LOG_WARNING(Service_AM, "(STUBBED) called"); + + // TODO: this should be the main applet, not the caller applet + const auto application = GetCallerIdentity(*m_applet); + std::vector<u8> nacp; + const auto result = + system.GetARPManager().GetControlProperty(&nacp, application.application_id); + + if (R_SUCCEEDED(result)) { + std::memcpy(out_nacp->data(), nacp.data(), std::min(nacp.size(), out_nacp->size())); + } + + R_RETURN(result); +} + +Result ILibraryAppletSelfAccessor::GetMainAppletStorageId(Out<FileSys::StorageId> out_storage_id) { + LOG_INFO(Service_AM, "(STUBBED) called"); + *out_storage_id = FileSys::StorageId::NandUser; + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::ExitProcessAndReturn() { + LOG_INFO(Service_AM, "called"); + system.GetAppletManager().TerminateAndRemoveApplet(m_applet->aruid); + m_broker->SignalCompletion(); + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::GetCallerAppletIdentityInfo( + Out<AppletIdentityInfo> out_identity_info) { + LOG_INFO(Service_AM, "called"); + *out_identity_info = GetCallerIdentity(*m_applet); + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::GetCallerAppletIdentityInfoStack( + Out<s32> out_count, OutArray<AppletIdentityInfo, BufferAttr_HipcMapAlias> out_identity_info) { + LOG_INFO(Service_AM, "called"); + + std::shared_ptr<Applet> applet = m_applet; + *out_count = 0; + + do { + if (*out_count >= static_cast<s32>(out_identity_info.size())) { + break; + } + out_identity_info[(*out_count)++] = GetCallerIdentity(*applet); + } while ((applet = applet->caller_applet.lock())); + + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::GetDesirableKeyboardLayout(Out<u32> out_desirable_layout) { + LOG_WARNING(Service_AM, "(STUBBED) called"); + *out_desirable_layout = 0; + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::ReportVisibleError(ErrorCode error_code) { + LOG_WARNING(Service_AM, "(STUBBED) called, error {}-{}", error_code.category, + error_code.number); + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::ReportVisibleErrorWithErrorContext( + ErrorCode error_code, InLargeData<ErrorContext, BufferAttr_HipcMapAlias> error_context) { + LOG_WARNING(Service_AM, "(STUBBED) called, error {}-{}", error_code.category, + error_code.number); + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::GetMainAppletApplicationDesiredLanguage( + Out<u64> out_desired_language) { + // FIXME: this is copied from IApplicationFunctions::GetDesiredLanguage + // FIXME: all of this stuff belongs to ns + auto identity = GetCallerIdentity(*m_applet); + + // TODO(bunnei): This should be configurable + LOG_DEBUG(Service_AM, "called"); + + // Get supported languages from NACP, if possible + // Default to 0 (all languages supported) + u32 supported_languages = 0; + + const auto res = [this, identity] { + const FileSys::PatchManager pm{identity.application_id, system.GetFileSystemController(), + system.GetContentProvider()}; + auto metadata = pm.GetControlMetadata(); + if (metadata.first != nullptr) { + return metadata; + } + + const FileSys::PatchManager pm_update{FileSys::GetUpdateTitleID(identity.application_id), + system.GetFileSystemController(), + system.GetContentProvider()}; + return pm_update.GetControlMetadata(); + }(); + + if (res.first != nullptr) { + supported_languages = res.first->GetSupportedLanguages(); + } + + // Call IApplicationManagerInterface implementation. + auto& service_manager = system.ServiceManager(); + auto ns_am2 = service_manager.GetService<NS::NS>("ns:am2"); + auto app_man = ns_am2->GetApplicationManagerInterface(); + + // Get desired application language + u8 desired_language{}; + R_TRY(app_man->GetApplicationDesiredLanguage(&desired_language, supported_languages)); + + // Convert to settings language code. + u64 language_code{}; + R_TRY(app_man->ConvertApplicationLanguageToLanguageCode(&language_code, desired_language)); + + LOG_DEBUG(Service_AM, "got desired_language={:016X}", language_code); + + *out_desired_language = language_code; + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::GetCurrentApplicationId(Out<u64> out_application_id) { + LOG_WARNING(Service_AM, "(STUBBED) called"); + + // TODO: this should be the main applet, not the caller applet + const auto main_applet = GetCallerIdentity(*m_applet); + *out_application_id = main_applet.application_id; + + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::GetMainAppletAvailableUsers( + Out<bool> out_no_users_available, Out<s32> out_users_count, + OutArray<Common::UUID, BufferAttr_HipcMapAlias> out_users) { + const Service::Account::ProfileManager manager{}; + + *out_no_users_available = true; + *out_users_count = -1; + + LOG_INFO(Service_AM, "called"); + + if (manager.GetUserCount() > 0) { + *out_no_users_available = false; + *out_users_count = static_cast<s32>(manager.GetUserCount()); + + const auto users = manager.GetAllUsers(); + for (size_t i = 0; i < users.size() && i < out_users.size(); i++) { + out_users[i] = users[i]; + } + } + + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::ShouldSetGpuTimeSliceManually( + Out<bool> out_should_set_gpu_time_slice_manually) { + LOG_INFO(Service_AM, "(STUBBED) called"); + *out_should_set_gpu_time_slice_manually = false; + R_SUCCEED(); +} + +Result ILibraryAppletSelfAccessor::Cmd160(Out<u64> out_unknown0) { + LOG_WARNING(Service_AM, "(STUBBED) called"); + *out_unknown0 = 0; + R_SUCCEED(); +} + +} // namespace Service::AM diff --git a/src/core/hle/service/am/service/library_applet_self_accessor.h b/src/core/hle/service/am/service/library_applet_self_accessor.h new file mode 100644 index 000000000..a9743569f --- /dev/null +++ b/src/core/hle/service/am/service/library_applet_self_accessor.h @@ -0,0 +1,83 @@ +// SPDX-FileCopyrightText: Copyright 2024 yuzu Emulator Project +// SPDX-License-Identifier: GPL-2.0-or-later + +#pragma once + +#include "common/uuid.h" +#include "core/hle/service/am/am_types.h" +#include "core/hle/service/cmif_types.h" +#include "core/hle/service/service.h" + +namespace FileSys { +enum class StorageId : u8; +} + +namespace Kernel { +class KReadableEvent; +} + +namespace Service::AM { + +class AppletDataBroker; +struct Applet; +class IStorage; + +struct LibraryAppletInfo { + AppletId applet_id; + LibraryAppletMode library_applet_mode; +}; +static_assert(sizeof(LibraryAppletInfo) == 0x8, "LibraryAppletInfo has incorrect size."); + +struct ErrorCode { + u32 category; + u32 number; +}; +static_assert(sizeof(ErrorCode) == 0x8, "ErrorCode has incorrect size."); + +struct ErrorContext { + u8 type; + INSERT_PADDING_BYTES_NOINIT(0x7); + std::array<u8, 0x1f4> data; + Result result; +}; +static_assert(sizeof(ErrorContext) == 0x200, "ErrorContext has incorrect size."); + +class ILibraryAppletSelfAccessor final : public ServiceFramework<ILibraryAppletSelfAccessor> { +public: + explicit ILibraryAppletSelfAccessor(Core::System& system_, std::shared_ptr<Applet> applet); + ~ILibraryAppletSelfAccessor() override; + +private: + Result PopInData(Out<SharedPointer<IStorage>> out_storage); + Result PushOutData(SharedPointer<IStorage> storage); + Result PopInteractiveInData(Out<SharedPointer<IStorage>> out_storage); + Result PushInteractiveOutData(SharedPointer<IStorage> storage); + Result GetPopInDataEvent(OutCopyHandle<Kernel::KReadableEvent> out_event); + Result GetPopInteractiveInDataEvent(OutCopyHandle<Kernel::KReadableEvent> out_event); + Result GetLibraryAppletInfo(Out<LibraryAppletInfo> out_library_applet_info); + Result GetMainAppletIdentityInfo(Out<AppletIdentityInfo> out_identity_info); + Result CanUseApplicationCore(Out<bool> out_can_use_application_core); + Result GetMainAppletApplicationControlProperty( + OutLargeData<std::array<u8, 0x4000>, BufferAttr_HipcMapAlias> out_nacp); + Result GetMainAppletStorageId(Out<FileSys::StorageId> out_storage_id); + Result ExitProcessAndReturn(); + Result GetCallerAppletIdentityInfo(Out<AppletIdentityInfo> out_identity_info); + Result GetCallerAppletIdentityInfoStack( + Out<s32> out_count, + OutArray<AppletIdentityInfo, BufferAttr_HipcMapAlias> out_identity_info); + Result GetDesirableKeyboardLayout(Out<u32> out_desirable_layout); + Result ReportVisibleError(ErrorCode error_code); + Result ReportVisibleErrorWithErrorContext( + ErrorCode error_code, InLargeData<ErrorContext, BufferAttr_HipcMapAlias> error_context); + Result GetMainAppletApplicationDesiredLanguage(Out<u64> out_desired_language); + Result GetCurrentApplicationId(Out<u64> out_application_id); + Result GetMainAppletAvailableUsers(Out<bool> out_no_users_available, Out<s32> out_users_count, + OutArray<Common::UUID, BufferAttr_HipcMapAlias> out_users); + Result ShouldSetGpuTimeSliceManually(Out<bool> out_should_set_gpu_time_slice_manually); + Result Cmd160(Out<u64> out_unknown0); + + const std::shared_ptr<Applet> m_applet; + const std::shared_ptr<AppletDataBroker> m_broker; +}; + +} // namespace Service::AM diff --git a/src/core/hle/service/am/service/system_applet_proxy.cpp b/src/core/hle/service/am/service/system_applet_proxy.cpp index 59d5b2a23..1e931dec7 100644 --- a/src/core/hle/service/am/service/system_applet_proxy.cpp +++ b/src/core/hle/service/am/service/system_applet_proxy.cpp @@ -2,7 +2,6 @@ // SPDX-License-Identifier: GPL-2.0-or-later #include "core/hle/service/am/application_creator.h" -#include "core/hle/service/am/library_applet_self_accessor.h" #include "core/hle/service/am/process_winding_controller.h" #include "core/hle/service/am/self_controller.h" #include "core/hle/service/am/service/applet_common_functions.h" |