mirror of
				https://git.zaroz.cloud/nintendo-back-up/yuzu/yuzu.git
				synced 2025-05-12 00:45:25 +00:00 
			
		
		
		
	Service/am: Add AppletAE service (#153)
* Add AppletAE, step 1: move common interfaces to am.h * Add AppletAE, step 2
This commit is contained in:
		
							parent
							
								
									5ad9b3e19d
								
							
						
					
					
						commit
						1a8f5bfb8e
					
				@ -84,6 +84,8 @@ add_library(core STATIC
 | 
				
			|||||||
    hle/service/acc/acc_u0.h
 | 
					    hle/service/acc/acc_u0.h
 | 
				
			||||||
    hle/service/am/am.cpp
 | 
					    hle/service/am/am.cpp
 | 
				
			||||||
    hle/service/am/am.h
 | 
					    hle/service/am/am.h
 | 
				
			||||||
 | 
					    hle/service/am/applet_ae.cpp
 | 
				
			||||||
 | 
					    hle/service/am/applet_ae.h
 | 
				
			||||||
    hle/service/am/applet_oe.cpp
 | 
					    hle/service/am/applet_oe.cpp
 | 
				
			||||||
    hle/service/am/applet_oe.h
 | 
					    hle/service/am/applet_oe.h
 | 
				
			||||||
    hle/service/aoc/aoc_u.cpp
 | 
					    hle/service/aoc/aoc_u.cpp
 | 
				
			||||||
 | 
				
			|||||||
@ -2,14 +2,347 @@
 | 
				
			|||||||
// Licensed under GPLv2 or any later version
 | 
					// Licensed under GPLv2 or any later version
 | 
				
			||||||
// Refer to the license.txt file included.
 | 
					// Refer to the license.txt file included.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include "core/hle/ipc_helpers.h"
 | 
				
			||||||
 | 
					#include "core/hle/kernel/event.h"
 | 
				
			||||||
#include "core/hle/service/am/am.h"
 | 
					#include "core/hle/service/am/am.h"
 | 
				
			||||||
 | 
					#include "core/hle/service/am/applet_ae.h"
 | 
				
			||||||
#include "core/hle/service/am/applet_oe.h"
 | 
					#include "core/hle/service/am/applet_oe.h"
 | 
				
			||||||
 | 
					#include "core/hle/service/apm/apm.h"
 | 
				
			||||||
 | 
					#include "core/hle/service/nvflinger/nvflinger.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
namespace Service {
 | 
					namespace Service {
 | 
				
			||||||
namespace AM {
 | 
					namespace AM {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					IWindowController::IWindowController() : ServiceFramework("IWindowController") {
 | 
				
			||||||
 | 
					    static const FunctionInfo functions[] = {
 | 
				
			||||||
 | 
					        {1, &IWindowController::GetAppletResourceUserId, "GetAppletResourceUserId"},
 | 
				
			||||||
 | 
					        {10, &IWindowController::AcquireForegroundRights, "AcquireForegroundRights"},
 | 
				
			||||||
 | 
					    };
 | 
				
			||||||
 | 
					    RegisterHandlers(functions);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void IWindowController::GetAppletResourceUserId(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 4};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					    rb.Push<u64>(0);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void IWindowController::AcquireForegroundRights(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 2};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					IAudioController::IAudioController() : ServiceFramework("IAudioController") {}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					IDisplayController::IDisplayController() : ServiceFramework("IDisplayController") {}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					IDebugFunctions::IDebugFunctions() : ServiceFramework("IDebugFunctions") {}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					ISelfController::ISelfController(std::shared_ptr<NVFlinger::NVFlinger> nvflinger)
 | 
				
			||||||
 | 
					    : ServiceFramework("ISelfController"), nvflinger(std::move(nvflinger)) {
 | 
				
			||||||
 | 
					    static const FunctionInfo functions[] = {
 | 
				
			||||||
 | 
					        {1, &ISelfController::LockExit, "LockExit"},
 | 
				
			||||||
 | 
					        {2, &ISelfController::UnlockExit, "UnlockExit"},
 | 
				
			||||||
 | 
					        {11, &ISelfController::SetOperationModeChangedNotification,
 | 
				
			||||||
 | 
					         "SetOperationModeChangedNotification"},
 | 
				
			||||||
 | 
					        {12, &ISelfController::SetPerformanceModeChangedNotification,
 | 
				
			||||||
 | 
					         "SetPerformanceModeChangedNotification"},
 | 
				
			||||||
 | 
					        {13, &ISelfController::SetFocusHandlingMode, "SetFocusHandlingMode"},
 | 
				
			||||||
 | 
					        {14, &ISelfController::SetRestartMessageEnabled, "SetRestartMessageEnabled"},
 | 
				
			||||||
 | 
					        {16, &ISelfController::SetOutOfFocusSuspendingEnabled, "SetOutOfFocusSuspendingEnabled"},
 | 
				
			||||||
 | 
					        {40, &ISelfController::CreateManagedDisplayLayer, "CreateManagedDisplayLayer"},
 | 
				
			||||||
 | 
					    };
 | 
				
			||||||
 | 
					    RegisterHandlers(functions);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void ISelfController::SetFocusHandlingMode(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    // Takes 3 input u8s with each field located immediately after the previous u8, these are
 | 
				
			||||||
 | 
					    // bool flags. No output.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    IPC::RequestParser rp{ctx};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    struct FocusHandlingModeParams {
 | 
				
			||||||
 | 
					        u8 unknown0;
 | 
				
			||||||
 | 
					        u8 unknown1;
 | 
				
			||||||
 | 
					        u8 unknown2;
 | 
				
			||||||
 | 
					    };
 | 
				
			||||||
 | 
					    auto flags = rp.PopRaw<FocusHandlingModeParams>();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 2};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void ISelfController::SetRestartMessageEnabled(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 2};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void ISelfController::SetPerformanceModeChangedNotification(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    IPC::RequestParser rp{ctx};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    bool flag = rp.Pop<bool>();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 2};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called flag=%u", static_cast<u32>(flag));
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void ISelfController::SetOperationModeChangedNotification(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    IPC::RequestParser rp{ctx};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    bool flag = rp.Pop<bool>();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 2};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called flag=%u", static_cast<u32>(flag));
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void ISelfController::SetOutOfFocusSuspendingEnabled(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    // Takes 3 input u8s with each field located immediately after the previous u8, these are
 | 
				
			||||||
 | 
					    // bool flags. No output.
 | 
				
			||||||
 | 
					    IPC::RequestParser rp{ctx};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    bool enabled = rp.Pop<bool>();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 2};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called enabled=%u", static_cast<u32>(enabled));
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void ISelfController::LockExit(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 2};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void ISelfController::UnlockExit(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 2};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void ISelfController::CreateManagedDisplayLayer(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    // TODO(Subv): Find out how AM determines the display to use, for now just create the layer
 | 
				
			||||||
 | 
					    // in the Default display.
 | 
				
			||||||
 | 
					    u64 display_id = nvflinger->OpenDisplay("Default");
 | 
				
			||||||
 | 
					    u64 layer_id = nvflinger->CreateLayer(display_id);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 4};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					    rb.Push(layer_id);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					ICommonStateGetter::ICommonStateGetter() : ServiceFramework("ICommonStateGetter") {
 | 
				
			||||||
 | 
					    static const FunctionInfo functions[] = {
 | 
				
			||||||
 | 
					        {0, &ICommonStateGetter::GetEventHandle, "GetEventHandle"},
 | 
				
			||||||
 | 
					        {1, &ICommonStateGetter::ReceiveMessage, "ReceiveMessage"},
 | 
				
			||||||
 | 
					        {5, &ICommonStateGetter::GetOperationMode, "GetOperationMode"},
 | 
				
			||||||
 | 
					        {6, &ICommonStateGetter::GetPerformanceMode, "GetPerformanceMode"},
 | 
				
			||||||
 | 
					        {9, &ICommonStateGetter::GetCurrentFocusState, "GetCurrentFocusState"},
 | 
				
			||||||
 | 
					    };
 | 
				
			||||||
 | 
					    RegisterHandlers(functions);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    event = Kernel::Event::Create(Kernel::ResetType::OneShot, "ICommonStateGetter:Event");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void ICommonStateGetter::GetEventHandle(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    event->Signal();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 2, 1};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					    rb.PushCopyObjects(event);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void ICommonStateGetter::ReceiveMessage(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 3};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					    rb.Push<u32>(15);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void ICommonStateGetter::GetCurrentFocusState(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 3};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					    rb.Push(static_cast<u8>(FocusState::InFocus));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void ICommonStateGetter::GetOperationMode(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 3};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					    rb.Push(static_cast<u8>(OperationMode::Handheld));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void ICommonStateGetter::GetPerformanceMode(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 3};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					    rb.Push(static_cast<u32>(APM::PerformanceMode::Handheld));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					ILibraryAppletCreator::ILibraryAppletCreator() : ServiceFramework("ILibraryAppletCreator") {}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class IStorageAccessor final : public ServiceFramework<IStorageAccessor> {
 | 
				
			||||||
 | 
					public:
 | 
				
			||||||
 | 
					    explicit IStorageAccessor(std::vector<u8> buffer)
 | 
				
			||||||
 | 
					        : ServiceFramework("IStorageAccessor"), buffer(std::move(buffer)) {
 | 
				
			||||||
 | 
					        static const FunctionInfo functions[] = {
 | 
				
			||||||
 | 
					            {0, &IStorageAccessor::GetSize, "GetSize"},
 | 
				
			||||||
 | 
					            {11, &IStorageAccessor::Read, "Read"},
 | 
				
			||||||
 | 
					        };
 | 
				
			||||||
 | 
					        RegisterHandlers(functions);
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					private:
 | 
				
			||||||
 | 
					    std::vector<u8> buffer;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    void GetSize(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					        IPC::ResponseBuilder rb{ctx, 4};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					        rb.Push(static_cast<u64>(buffer.size()));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        LOG_DEBUG(Service, "called");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    void Read(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					        IPC::RequestParser rp{ctx};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        u64 offset = rp.Pop<u64>();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        const auto& output_buffer = ctx.BufferDescriptorC()[0];
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        ASSERT(offset + output_buffer.Size() <= buffer.size());
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        Memory::WriteBlock(output_buffer.Address(), buffer.data() + offset, output_buffer.Size());
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        IPC::ResponseBuilder rb{ctx, 2};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        LOG_DEBUG(Service, "called");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class IStorage final : public ServiceFramework<IStorage> {
 | 
				
			||||||
 | 
					public:
 | 
				
			||||||
 | 
					    explicit IStorage(std::vector<u8> buffer)
 | 
				
			||||||
 | 
					        : ServiceFramework("IStorage"), buffer(std::move(buffer)) {
 | 
				
			||||||
 | 
					        static const FunctionInfo functions[] = {
 | 
				
			||||||
 | 
					            {0, &IStorage::Open, "Open"},
 | 
				
			||||||
 | 
					        };
 | 
				
			||||||
 | 
					        RegisterHandlers(functions);
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					private:
 | 
				
			||||||
 | 
					    std::vector<u8> buffer;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    void Open(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					        IPC::ResponseBuilder rb{ctx, 2, 0, 1};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					        rb.PushIpcInterface<AM::IStorageAccessor>(buffer);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        LOG_DEBUG(Service, "called");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					IApplicationFunctions::IApplicationFunctions() : ServiceFramework("IApplicationFunctions") {
 | 
				
			||||||
 | 
					    static const FunctionInfo functions[] = {
 | 
				
			||||||
 | 
					        {1, &IApplicationFunctions::PopLaunchParameter, "PopLaunchParameter"},
 | 
				
			||||||
 | 
					        {21, &IApplicationFunctions::GetDesiredLanguage, "GetDesiredLanguage"},
 | 
				
			||||||
 | 
					        {22, &IApplicationFunctions::SetTerminateResult, "SetTerminateResult"},
 | 
				
			||||||
 | 
					        {66, &IApplicationFunctions::InitializeGamePlayRecording, "InitializeGamePlayRecording"},
 | 
				
			||||||
 | 
					        {67, &IApplicationFunctions::SetGamePlayRecordingState, "SetGamePlayRecordingState"},
 | 
				
			||||||
 | 
					        {40, &IApplicationFunctions::NotifyRunning, "NotifyRunning"},
 | 
				
			||||||
 | 
					    };
 | 
				
			||||||
 | 
					    RegisterHandlers(functions);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void IApplicationFunctions::PopLaunchParameter(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    constexpr u8 data[0x88] = {
 | 
				
			||||||
 | 
					        0xca, 0x97, 0x94, 0xc7, // Magic
 | 
				
			||||||
 | 
					        1,    0,    0,    0,    // IsAccountSelected (bool)
 | 
				
			||||||
 | 
					        1,    0,    0,    0,    // User Id (word 0)
 | 
				
			||||||
 | 
					        0,    0,    0,    0,    // User Id (word 1)
 | 
				
			||||||
 | 
					        0,    0,    0,    0,    // User Id (word 2)
 | 
				
			||||||
 | 
					        0,    0,    0,    0     // User Id (word 3)
 | 
				
			||||||
 | 
					    };
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    std::vector<u8> buffer(data, data + sizeof(data));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 2, 0, 1};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					    rb.PushIpcInterface<AM::IStorage>(buffer);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_DEBUG(Service, "called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void IApplicationFunctions::SetTerminateResult(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    // Takes an input u32 Result, no output.
 | 
				
			||||||
 | 
					    // For example, in some cases official apps use this with error 0x2A2 then uses svcBreak.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    IPC::RequestParser rp{ctx};
 | 
				
			||||||
 | 
					    u32 result = rp.Pop<u32>();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 2};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called, result=0x%08X", result);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void IApplicationFunctions::GetDesiredLanguage(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 4};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					    rb.Push<u64>(SystemLanguage::English);
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void IApplicationFunctions::InitializeGamePlayRecording(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 2};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void IApplicationFunctions::SetGamePlayRecordingState(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 2};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void IApplicationFunctions::NotifyRunning(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 3};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					    rb.Push<u8>(0); // Unknown, seems to be ignored by official processes
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    LOG_WARNING(Service, "(STUBBED) called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void InstallInterfaces(SM::ServiceManager& service_manager,
 | 
					void InstallInterfaces(SM::ServiceManager& service_manager,
 | 
				
			||||||
                       std::shared_ptr<NVFlinger::NVFlinger> nvflinger) {
 | 
					                       std::shared_ptr<NVFlinger::NVFlinger> nvflinger) {
 | 
				
			||||||
 | 
					    std::make_shared<AppletAE>(nvflinger)->InstallAsService(service_manager);
 | 
				
			||||||
    std::make_shared<AppletOE>(nvflinger)->InstallAsService(service_manager);
 | 
					    std::make_shared<AppletOE>(nvflinger)->InstallAsService(service_manager);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
				
			|||||||
@ -7,6 +7,10 @@
 | 
				
			|||||||
#include <memory>
 | 
					#include <memory>
 | 
				
			||||||
#include "core/hle/service/service.h"
 | 
					#include "core/hle/service/service.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					namespace Kernel {
 | 
				
			||||||
 | 
					class Event;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
namespace Service {
 | 
					namespace Service {
 | 
				
			||||||
namespace NVFlinger {
 | 
					namespace NVFlinger {
 | 
				
			||||||
class NVFlinger;
 | 
					class NVFlinger;
 | 
				
			||||||
@ -14,6 +18,95 @@ class NVFlinger;
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
namespace AM {
 | 
					namespace AM {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// TODO: Add more languages
 | 
				
			||||||
 | 
					enum SystemLanguage {
 | 
				
			||||||
 | 
					    Japanese = 0,
 | 
				
			||||||
 | 
					    English = 1,
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class IWindowController final : public ServiceFramework<IWindowController> {
 | 
				
			||||||
 | 
					public:
 | 
				
			||||||
 | 
					    IWindowController();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					private:
 | 
				
			||||||
 | 
					    void GetAppletResourceUserId(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void AcquireForegroundRights(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class IAudioController final : public ServiceFramework<IAudioController> {
 | 
				
			||||||
 | 
					public:
 | 
				
			||||||
 | 
					    IAudioController();
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class IDisplayController final : public ServiceFramework<IDisplayController> {
 | 
				
			||||||
 | 
					public:
 | 
				
			||||||
 | 
					    IDisplayController();
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class IDebugFunctions final : public ServiceFramework<IDebugFunctions> {
 | 
				
			||||||
 | 
					public:
 | 
				
			||||||
 | 
					    IDebugFunctions();
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class ISelfController final : public ServiceFramework<ISelfController> {
 | 
				
			||||||
 | 
					public:
 | 
				
			||||||
 | 
					    ISelfController(std::shared_ptr<NVFlinger::NVFlinger> nvflinger);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					private:
 | 
				
			||||||
 | 
					    void SetFocusHandlingMode(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void SetRestartMessageEnabled(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void SetPerformanceModeChangedNotification(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void SetOperationModeChangedNotification(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void SetOutOfFocusSuspendingEnabled(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void LockExit(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void UnlockExit(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void CreateManagedDisplayLayer(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    std::shared_ptr<NVFlinger::NVFlinger> nvflinger;
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class ICommonStateGetter final : public ServiceFramework<ICommonStateGetter> {
 | 
				
			||||||
 | 
					public:
 | 
				
			||||||
 | 
					    ICommonStateGetter();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					private:
 | 
				
			||||||
 | 
					    enum class FocusState : u8 {
 | 
				
			||||||
 | 
					        InFocus = 1,
 | 
				
			||||||
 | 
					        NotInFocus = 2,
 | 
				
			||||||
 | 
					    };
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    enum class OperationMode : u8 {
 | 
				
			||||||
 | 
					        Handheld = 0,
 | 
				
			||||||
 | 
					        Docked = 1,
 | 
				
			||||||
 | 
					    };
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    void GetEventHandle(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void ReceiveMessage(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void GetCurrentFocusState(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void GetOperationMode(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void GetPerformanceMode(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    Kernel::SharedPtr<Kernel::Event> event;
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class ILibraryAppletCreator final : public ServiceFramework<ILibraryAppletCreator> {
 | 
				
			||||||
 | 
					public:
 | 
				
			||||||
 | 
					    ILibraryAppletCreator();
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class IApplicationFunctions final : public ServiceFramework<IApplicationFunctions> {
 | 
				
			||||||
 | 
					public:
 | 
				
			||||||
 | 
					    IApplicationFunctions();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					private:
 | 
				
			||||||
 | 
					    void PopLaunchParameter(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void SetTerminateResult(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void GetDesiredLanguage(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void InitializeGamePlayRecording(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void SetGamePlayRecordingState(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					    void NotifyRunning(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
/// Registers all AM services with the specified service manager.
 | 
					/// Registers all AM services with the specified service manager.
 | 
				
			||||||
void InstallInterfaces(SM::ServiceManager& service_manager,
 | 
					void InstallInterfaces(SM::ServiceManager& service_manager,
 | 
				
			||||||
                       std::shared_ptr<NVFlinger::NVFlinger> nvflinger);
 | 
					                       std::shared_ptr<NVFlinger::NVFlinger> nvflinger);
 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										112
									
								
								src/core/hle/service/am/applet_ae.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										112
									
								
								src/core/hle/service/am/applet_ae.cpp
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,112 @@
 | 
				
			|||||||
 | 
					// Copyright 2018 yuzu emulator team
 | 
				
			||||||
 | 
					// Licensed under GPLv2 or any later version
 | 
				
			||||||
 | 
					// Refer to the license.txt file included.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include "common/logging/log.h"
 | 
				
			||||||
 | 
					#include "core/hle/ipc_helpers.h"
 | 
				
			||||||
 | 
					#include "core/hle/service/am/am.h"
 | 
				
			||||||
 | 
					#include "core/hle/service/am/applet_ae.h"
 | 
				
			||||||
 | 
					#include "core/hle/service/nvflinger/nvflinger.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					namespace Service {
 | 
				
			||||||
 | 
					namespace AM {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class ILibraryAppletProxy final : public ServiceFramework<ILibraryAppletProxy> {
 | 
				
			||||||
 | 
					public:
 | 
				
			||||||
 | 
					    ILibraryAppletProxy(std::shared_ptr<NVFlinger::NVFlinger> nvflinger)
 | 
				
			||||||
 | 
					        : ServiceFramework("ILibraryAppletProxy"), nvflinger(std::move(nvflinger)) {
 | 
				
			||||||
 | 
					        static const FunctionInfo functions[] = {
 | 
				
			||||||
 | 
					            {0, &ILibraryAppletProxy::GetCommonStateGetter, "GetCommonStateGetter"},
 | 
				
			||||||
 | 
					            {1, &ILibraryAppletProxy::GetSelfController, "GetSelfController"},
 | 
				
			||||||
 | 
					            {2, &ILibraryAppletProxy::GetWindowController, "GetWindowController"},
 | 
				
			||||||
 | 
					            {3, &ILibraryAppletProxy::GetAudioController, "GetAudioController"},
 | 
				
			||||||
 | 
					            {4, &ILibraryAppletProxy::GetDisplayController, "GetDisplayController"},
 | 
				
			||||||
 | 
					            {11, &ILibraryAppletProxy::GetLibraryAppletCreator, "GetLibraryAppletCreator"},
 | 
				
			||||||
 | 
					            {20, &ILibraryAppletProxy::GetApplicationFunctions, "GetApplicationFunctions"},
 | 
				
			||||||
 | 
					            {1000, &ILibraryAppletProxy::GetDebugFunctions, "GetDebugFunctions"},
 | 
				
			||||||
 | 
					        };
 | 
				
			||||||
 | 
					        RegisterHandlers(functions);
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					private:
 | 
				
			||||||
 | 
					    void GetCommonStateGetter(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					        IPC::ResponseBuilder rb{ctx, 2, 0, 1};
 | 
				
			||||||
 | 
					        rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					        rb.PushIpcInterface<ICommonStateGetter>();
 | 
				
			||||||
 | 
					        LOG_DEBUG(Service, "called");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    void GetSelfController(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					        IPC::ResponseBuilder rb{ctx, 2, 0, 1};
 | 
				
			||||||
 | 
					        rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					        rb.PushIpcInterface<ISelfController>(nvflinger);
 | 
				
			||||||
 | 
					        LOG_DEBUG(Service, "called");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    void GetWindowController(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					        IPC::ResponseBuilder rb{ctx, 2, 0, 1};
 | 
				
			||||||
 | 
					        rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					        rb.PushIpcInterface<IWindowController>();
 | 
				
			||||||
 | 
					        LOG_DEBUG(Service, "called");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    void GetAudioController(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					        IPC::ResponseBuilder rb{ctx, 2, 0, 1};
 | 
				
			||||||
 | 
					        rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					        rb.PushIpcInterface<IAudioController>();
 | 
				
			||||||
 | 
					        LOG_DEBUG(Service, "called");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    void GetDisplayController(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					        IPC::ResponseBuilder rb{ctx, 2, 0, 1};
 | 
				
			||||||
 | 
					        rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					        rb.PushIpcInterface<IDisplayController>();
 | 
				
			||||||
 | 
					        LOG_DEBUG(Service, "called");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    void GetDebugFunctions(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					        IPC::ResponseBuilder rb{ctx, 2, 0, 1};
 | 
				
			||||||
 | 
					        rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					        rb.PushIpcInterface<IDebugFunctions>();
 | 
				
			||||||
 | 
					        LOG_DEBUG(Service, "called");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    void GetLibraryAppletCreator(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					        IPC::ResponseBuilder rb{ctx, 2, 0, 1};
 | 
				
			||||||
 | 
					        rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					        rb.PushIpcInterface<ILibraryAppletCreator>();
 | 
				
			||||||
 | 
					        LOG_DEBUG(Service, "called");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    void GetApplicationFunctions(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					        IPC::ResponseBuilder rb{ctx, 2, 0, 1};
 | 
				
			||||||
 | 
					        rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					        rb.PushIpcInterface<IApplicationFunctions>();
 | 
				
			||||||
 | 
					        LOG_DEBUG(Service, "called");
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    std::shared_ptr<NVFlinger::NVFlinger> nvflinger;
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					void AppletAE::OpenLibraryAppletProxyOld(Kernel::HLERequestContext& ctx) {
 | 
				
			||||||
 | 
					    IPC::ResponseBuilder rb{ctx, 2, 0, 1};
 | 
				
			||||||
 | 
					    rb.Push(RESULT_SUCCESS);
 | 
				
			||||||
 | 
					    rb.PushIpcInterface<ILibraryAppletProxy>(nvflinger);
 | 
				
			||||||
 | 
					    LOG_DEBUG(Service, "called");
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					AppletAE::AppletAE(std::shared_ptr<NVFlinger::NVFlinger> nvflinger)
 | 
				
			||||||
 | 
					    : ServiceFramework("appletAE"), nvflinger(std::move(nvflinger)) {
 | 
				
			||||||
 | 
					    static const FunctionInfo functions[] = {
 | 
				
			||||||
 | 
					        {100, nullptr, "OpenSystemAppletProxy"},
 | 
				
			||||||
 | 
					        {200, &AppletAE::OpenLibraryAppletProxyOld, "OpenLibraryAppletProxyOld"},
 | 
				
			||||||
 | 
					        {201, nullptr, "OpenLibraryAppletProxy"},
 | 
				
			||||||
 | 
					        {300, nullptr, "OpenOverlayAppletProxy"},
 | 
				
			||||||
 | 
					        {350, nullptr, "OpenSystemApplicationProxy"},
 | 
				
			||||||
 | 
					        {400, nullptr, "CreateSelfLibraryAppletCreatorForDevelop"},
 | 
				
			||||||
 | 
					    };
 | 
				
			||||||
 | 
					    RegisterHandlers(functions);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					} // namespace AM
 | 
				
			||||||
 | 
					} // namespace Service
 | 
				
			||||||
							
								
								
									
										30
									
								
								src/core/hle/service/am/applet_ae.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										30
									
								
								src/core/hle/service/am/applet_ae.h
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,30 @@
 | 
				
			|||||||
 | 
					// Copyright 2018 yuzu emulator team
 | 
				
			||||||
 | 
					// Licensed under GPLv2 or any later version
 | 
				
			||||||
 | 
					// Refer to the license.txt file included.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#pragma once
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#include <memory>
 | 
				
			||||||
 | 
					#include "core/hle/kernel/hle_ipc.h"
 | 
				
			||||||
 | 
					#include "core/hle/service/service.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					namespace Service {
 | 
				
			||||||
 | 
					namespace NVFlinger {
 | 
				
			||||||
 | 
					class NVFlinger;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					namespace AM {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class AppletAE final : public ServiceFramework<AppletAE> {
 | 
				
			||||||
 | 
					public:
 | 
				
			||||||
 | 
					    AppletAE(std::shared_ptr<NVFlinger::NVFlinger> nvflinger);
 | 
				
			||||||
 | 
					    ~AppletAE() = default;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					private:
 | 
				
			||||||
 | 
					    void OpenLibraryAppletProxyOld(Kernel::HLERequestContext& ctx);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    std::shared_ptr<NVFlinger::NVFlinger> nvflinger;
 | 
				
			||||||
 | 
					};
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					} // namespace AM
 | 
				
			||||||
 | 
					} // namespace Service
 | 
				
			||||||
@ -4,385 +4,13 @@
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
#include "common/logging/log.h"
 | 
					#include "common/logging/log.h"
 | 
				
			||||||
#include "core/hle/ipc_helpers.h"
 | 
					#include "core/hle/ipc_helpers.h"
 | 
				
			||||||
#include "core/hle/kernel/event.h"
 | 
					#include "core/hle/service/am/am.h"
 | 
				
			||||||
#include "core/hle/service/am/applet_oe.h"
 | 
					#include "core/hle/service/am/applet_oe.h"
 | 
				
			||||||
#include "core/hle/service/apm/apm.h"
 | 
					 | 
				
			||||||
#include "core/hle/service/nvflinger/nvflinger.h"
 | 
					#include "core/hle/service/nvflinger/nvflinger.h"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
namespace Service {
 | 
					namespace Service {
 | 
				
			||||||
namespace AM {
 | 
					namespace AM {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
class IWindowController final : public ServiceFramework<IWindowController> {
 | 
					 | 
				
			||||||
public:
 | 
					 | 
				
			||||||
    IWindowController() : ServiceFramework("IWindowController") {
 | 
					 | 
				
			||||||
        static const FunctionInfo functions[] = {
 | 
					 | 
				
			||||||
            {1, &IWindowController::GetAppletResourceUserId, "GetAppletResourceUserId"},
 | 
					 | 
				
			||||||
            {10, &IWindowController::AcquireForegroundRights, "AcquireForegroundRights"},
 | 
					 | 
				
			||||||
        };
 | 
					 | 
				
			||||||
        RegisterHandlers(functions);
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
private:
 | 
					 | 
				
			||||||
    void GetAppletResourceUserId(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 4};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
        rb.Push<u64>(0);
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void AcquireForegroundRights(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 2};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
class IAudioController final : public ServiceFramework<IAudioController> {
 | 
					 | 
				
			||||||
public:
 | 
					 | 
				
			||||||
    IAudioController() : ServiceFramework("IAudioController") {}
 | 
					 | 
				
			||||||
};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
class IDisplayController final : public ServiceFramework<IDisplayController> {
 | 
					 | 
				
			||||||
public:
 | 
					 | 
				
			||||||
    IDisplayController() : ServiceFramework("IDisplayController") {}
 | 
					 | 
				
			||||||
};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
class IDebugFunctions final : public ServiceFramework<IDebugFunctions> {
 | 
					 | 
				
			||||||
public:
 | 
					 | 
				
			||||||
    IDebugFunctions() : ServiceFramework("IDebugFunctions") {}
 | 
					 | 
				
			||||||
};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
class ISelfController final : public ServiceFramework<ISelfController> {
 | 
					 | 
				
			||||||
public:
 | 
					 | 
				
			||||||
    ISelfController(std::shared_ptr<NVFlinger::NVFlinger> nvflinger)
 | 
					 | 
				
			||||||
        : ServiceFramework("ISelfController"), nvflinger(std::move(nvflinger)) {
 | 
					 | 
				
			||||||
        static const FunctionInfo functions[] = {
 | 
					 | 
				
			||||||
            {1, &ISelfController::LockExit, "LockExit"},
 | 
					 | 
				
			||||||
            {2, &ISelfController::UnlockExit, "UnlockExit"},
 | 
					 | 
				
			||||||
            {11, &ISelfController::SetOperationModeChangedNotification,
 | 
					 | 
				
			||||||
             "SetOperationModeChangedNotification"},
 | 
					 | 
				
			||||||
            {12, &ISelfController::SetPerformanceModeChangedNotification,
 | 
					 | 
				
			||||||
             "SetPerformanceModeChangedNotification"},
 | 
					 | 
				
			||||||
            {13, &ISelfController::SetFocusHandlingMode, "SetFocusHandlingMode"},
 | 
					 | 
				
			||||||
            {14, &ISelfController::SetRestartMessageEnabled, "SetRestartMessageEnabled"},
 | 
					 | 
				
			||||||
            {16, &ISelfController::SetOutOfFocusSuspendingEnabled,
 | 
					 | 
				
			||||||
             "SetOutOfFocusSuspendingEnabled"},
 | 
					 | 
				
			||||||
            {40, &ISelfController::CreateManagedDisplayLayer, "CreateManagedDisplayLayer"},
 | 
					 | 
				
			||||||
        };
 | 
					 | 
				
			||||||
        RegisterHandlers(functions);
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
private:
 | 
					 | 
				
			||||||
    void SetFocusHandlingMode(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        // Takes 3 input u8s with each field located immediately after the previous u8, these are
 | 
					 | 
				
			||||||
        // bool flags. No output.
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        IPC::RequestParser rp{ctx};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        struct FocusHandlingModeParams {
 | 
					 | 
				
			||||||
            u8 unknown0;
 | 
					 | 
				
			||||||
            u8 unknown1;
 | 
					 | 
				
			||||||
            u8 unknown2;
 | 
					 | 
				
			||||||
        };
 | 
					 | 
				
			||||||
        auto flags = rp.PopRaw<FocusHandlingModeParams>();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 2};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void SetRestartMessageEnabled(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 2};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void SetPerformanceModeChangedNotification(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::RequestParser rp{ctx};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        bool flag = rp.Pop<bool>();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 2};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called flag=%u", static_cast<u32>(flag));
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void SetOperationModeChangedNotification(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::RequestParser rp{ctx};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        bool flag = rp.Pop<bool>();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 2};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called flag=%u", static_cast<u32>(flag));
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void SetOutOfFocusSuspendingEnabled(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        // Takes 3 input u8s with each field located immediately after the previous u8, these are
 | 
					 | 
				
			||||||
        // bool flags. No output.
 | 
					 | 
				
			||||||
        IPC::RequestParser rp{ctx};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        bool enabled = rp.Pop<bool>();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 2};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called enabled=%u", static_cast<u32>(enabled));
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void LockExit(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 2};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void UnlockExit(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 2};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void CreateManagedDisplayLayer(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        // TODO(Subv): Find out how AM determines the display to use, for now just create the layer
 | 
					 | 
				
			||||||
        // in the Default display.
 | 
					 | 
				
			||||||
        u64 display_id = nvflinger->OpenDisplay("Default");
 | 
					 | 
				
			||||||
        u64 layer_id = nvflinger->CreateLayer(display_id);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 4};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
        rb.Push(layer_id);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    std::shared_ptr<NVFlinger::NVFlinger> nvflinger;
 | 
					 | 
				
			||||||
};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
class ICommonStateGetter final : public ServiceFramework<ICommonStateGetter> {
 | 
					 | 
				
			||||||
public:
 | 
					 | 
				
			||||||
    ICommonStateGetter() : ServiceFramework("ICommonStateGetter") {
 | 
					 | 
				
			||||||
        static const FunctionInfo functions[] = {
 | 
					 | 
				
			||||||
            {0, &ICommonStateGetter::GetEventHandle, "GetEventHandle"},
 | 
					 | 
				
			||||||
            {1, &ICommonStateGetter::ReceiveMessage, "ReceiveMessage"},
 | 
					 | 
				
			||||||
            {5, &ICommonStateGetter::GetOperationMode, "GetOperationMode"},
 | 
					 | 
				
			||||||
            {6, &ICommonStateGetter::GetPerformanceMode, "GetPerformanceMode"},
 | 
					 | 
				
			||||||
            {9, &ICommonStateGetter::GetCurrentFocusState, "GetCurrentFocusState"},
 | 
					 | 
				
			||||||
        };
 | 
					 | 
				
			||||||
        RegisterHandlers(functions);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        event = Kernel::Event::Create(Kernel::ResetType::OneShot, "ICommonStateGetter:Event");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
private:
 | 
					 | 
				
			||||||
    enum class FocusState : u8 {
 | 
					 | 
				
			||||||
        InFocus = 1,
 | 
					 | 
				
			||||||
        NotInFocus = 2,
 | 
					 | 
				
			||||||
    };
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    enum class OperationMode : u8 {
 | 
					 | 
				
			||||||
        Handheld = 0,
 | 
					 | 
				
			||||||
        Docked = 1,
 | 
					 | 
				
			||||||
    };
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void GetEventHandle(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        event->Signal();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 2, 1};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
        rb.PushCopyObjects(event);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void ReceiveMessage(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 3};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
        rb.Push<u32>(15);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void GetCurrentFocusState(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 3};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
        rb.Push(static_cast<u8>(FocusState::InFocus));
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void GetOperationMode(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 3};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
        rb.Push(static_cast<u8>(OperationMode::Handheld));
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void GetPerformanceMode(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 3};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
        rb.Push(static_cast<u32>(APM::PerformanceMode::Handheld));
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    Kernel::SharedPtr<Kernel::Event> event;
 | 
					 | 
				
			||||||
};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
class IStorageAccessor final : public ServiceFramework<IStorageAccessor> {
 | 
					 | 
				
			||||||
public:
 | 
					 | 
				
			||||||
    explicit IStorageAccessor(std::vector<u8> buffer)
 | 
					 | 
				
			||||||
        : ServiceFramework("IStorageAccessor"), buffer(std::move(buffer)) {
 | 
					 | 
				
			||||||
        static const FunctionInfo functions[] = {
 | 
					 | 
				
			||||||
            {0, &IStorageAccessor::GetSize, "GetSize"},
 | 
					 | 
				
			||||||
            {11, &IStorageAccessor::Read, "Read"},
 | 
					 | 
				
			||||||
        };
 | 
					 | 
				
			||||||
        RegisterHandlers(functions);
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
private:
 | 
					 | 
				
			||||||
    std::vector<u8> buffer;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void GetSize(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 4};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
        rb.Push(static_cast<u64>(buffer.size()));
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_DEBUG(Service, "called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void Read(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::RequestParser rp{ctx};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        u64 offset = rp.Pop<u64>();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        const auto& output_buffer = ctx.BufferDescriptorC()[0];
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        ASSERT(offset + output_buffer.Size() <= buffer.size());
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        Memory::WriteBlock(output_buffer.Address(), buffer.data() + offset, output_buffer.Size());
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 2};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_DEBUG(Service, "called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
class IStorage final : public ServiceFramework<IStorage> {
 | 
					 | 
				
			||||||
public:
 | 
					 | 
				
			||||||
    explicit IStorage(std::vector<u8> buffer)
 | 
					 | 
				
			||||||
        : ServiceFramework("IStorage"), buffer(std::move(buffer)) {
 | 
					 | 
				
			||||||
        static const FunctionInfo functions[] = {
 | 
					 | 
				
			||||||
            {0, &IStorage::Open, "Open"},
 | 
					 | 
				
			||||||
        };
 | 
					 | 
				
			||||||
        RegisterHandlers(functions);
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
private:
 | 
					 | 
				
			||||||
    std::vector<u8> buffer;
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void Open(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 2, 0, 1};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
        rb.PushIpcInterface<AM::IStorageAccessor>(buffer);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_DEBUG(Service, "called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
class IApplicationFunctions final : public ServiceFramework<IApplicationFunctions> {
 | 
					 | 
				
			||||||
public:
 | 
					 | 
				
			||||||
    IApplicationFunctions() : ServiceFramework("IApplicationFunctions") {
 | 
					 | 
				
			||||||
        static const FunctionInfo functions[] = {
 | 
					 | 
				
			||||||
            {1, &IApplicationFunctions::PopLaunchParameter, "PopLaunchParameter"},
 | 
					 | 
				
			||||||
            {21, &IApplicationFunctions::GetDesiredLanguage, "GetDesiredLanguage"},
 | 
					 | 
				
			||||||
            {22, &IApplicationFunctions::SetTerminateResult, "SetTerminateResult"},
 | 
					 | 
				
			||||||
            {66, &IApplicationFunctions::InitializeGamePlayRecording,
 | 
					 | 
				
			||||||
             "InitializeGamePlayRecording"},
 | 
					 | 
				
			||||||
            {67, &IApplicationFunctions::SetGamePlayRecordingState, "SetGamePlayRecordingState"},
 | 
					 | 
				
			||||||
            {40, &IApplicationFunctions::NotifyRunning, "NotifyRunning"},
 | 
					 | 
				
			||||||
        };
 | 
					 | 
				
			||||||
        RegisterHandlers(functions);
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
private:
 | 
					 | 
				
			||||||
    void PopLaunchParameter(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        constexpr u8 data[0x88] = {
 | 
					 | 
				
			||||||
            0xca, 0x97, 0x94, 0xc7, // Magic
 | 
					 | 
				
			||||||
            1,    0,    0,    0,    // IsAccountSelected (bool)
 | 
					 | 
				
			||||||
            1,    0,    0,    0,    // User Id (word 0)
 | 
					 | 
				
			||||||
            0,    0,    0,    0,    // User Id (word 1)
 | 
					 | 
				
			||||||
            0,    0,    0,    0,    // User Id (word 2)
 | 
					 | 
				
			||||||
            0,    0,    0,    0     // User Id (word 3)
 | 
					 | 
				
			||||||
        };
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        std::vector<u8> buffer(data, data + sizeof(data));
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 2, 0, 1};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
        rb.PushIpcInterface<AM::IStorage>(buffer);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_DEBUG(Service, "called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void SetTerminateResult(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        // Takes an input u32 Result, no output.
 | 
					 | 
				
			||||||
        // For example, in some cases official apps use this with error 0x2A2 then uses svcBreak.
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        IPC::RequestParser rp{ctx};
 | 
					 | 
				
			||||||
        u32 result = rp.Pop<u32>();
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 2};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called, result=0x%08X", result);
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void GetDesiredLanguage(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 4};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
        rb.Push<u64>(SystemLanguage::English);
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void InitializeGamePlayRecording(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 2};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void SetGamePlayRecordingState(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 2};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
    void NotifyRunning(Kernel::HLERequestContext& ctx) {
 | 
					 | 
				
			||||||
        IPC::ResponseBuilder rb{ctx, 3};
 | 
					 | 
				
			||||||
        rb.Push(RESULT_SUCCESS);
 | 
					 | 
				
			||||||
        rb.Push<u8>(0); // Unknown, seems to be ignored by official processes
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
        LOG_WARNING(Service, "(STUBBED) called");
 | 
					 | 
				
			||||||
    }
 | 
					 | 
				
			||||||
};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
class ILibraryAppletCreator final : public ServiceFramework<ILibraryAppletCreator> {
 | 
					 | 
				
			||||||
public:
 | 
					 | 
				
			||||||
    ILibraryAppletCreator() : ServiceFramework("ILibraryAppletCreator") {}
 | 
					 | 
				
			||||||
};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
class IApplicationProxy final : public ServiceFramework<IApplicationProxy> {
 | 
					class IApplicationProxy final : public ServiceFramework<IApplicationProxy> {
 | 
				
			||||||
public:
 | 
					public:
 | 
				
			||||||
    IApplicationProxy(std::shared_ptr<NVFlinger::NVFlinger> nvflinger)
 | 
					    IApplicationProxy(std::shared_ptr<NVFlinger::NVFlinger> nvflinger)
 | 
				
			||||||
 | 
				
			|||||||
@ -15,12 +15,6 @@ class NVFlinger;
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
namespace AM {
 | 
					namespace AM {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
// TODO: Add more languages
 | 
					 | 
				
			||||||
enum SystemLanguage {
 | 
					 | 
				
			||||||
    Japanese = 0,
 | 
					 | 
				
			||||||
    English = 1,
 | 
					 | 
				
			||||||
};
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
class AppletOE final : public ServiceFramework<AppletOE> {
 | 
					class AppletOE final : public ServiceFramework<AppletOE> {
 | 
				
			||||||
public:
 | 
					public:
 | 
				
			||||||
    AppletOE(std::shared_ptr<NVFlinger::NVFlinger> nvflinger);
 | 
					    AppletOE(std::shared_ptr<NVFlinger::NVFlinger> nvflinger);
 | 
				
			||||||
 | 
				
			|||||||
		Loading…
	
		Reference in New Issue
	
	Block a user