service: hid: Introduce proper AppletResource emulation
This commit is contained in:
parent
167efb2d2b
commit
e445ef9d60
|
@ -541,6 +541,8 @@ add_library(core STATIC
|
|||
hle/service/hid/xcd.cpp
|
||||
hle/service/hid/xcd.h
|
||||
hle/service/hid/errors.h
|
||||
hle/service/hid/controllers/applet_resource.cpp
|
||||
hle/service/hid/controllers/applet_resource.h
|
||||
hle/service/hid/controllers/console_six_axis.cpp
|
||||
hle/service/hid/controllers/console_six_axis.h
|
||||
hle/service/hid/controllers/controller_base.cpp
|
||||
|
|
|
@ -0,0 +1,199 @@
|
|||
// SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project
|
||||
// SPDX-License-Identifier: GPL-3.0-or-later
|
||||
|
||||
#include "core/core.h"
|
||||
#include "core/hle/kernel/k_shared_memory.h"
|
||||
#include "core/hle/service/hid/controllers/applet_resource.h"
|
||||
#include "core/hle/service/hid/errors.h"
|
||||
|
||||
namespace Service::HID {
|
||||
|
||||
AppletResource::AppletResource(Core::System& system_) : system{system_} {}
|
||||
|
||||
AppletResource::~AppletResource() = default;
|
||||
|
||||
Result AppletResource::CreateAppletResource(u64 aruid) {
|
||||
const u64 index = GetIndexFromAruid(aruid);
|
||||
|
||||
if (index >= AruidIndexMax) {
|
||||
return ResultAruidNotRegistered;
|
||||
}
|
||||
|
||||
if (data[index].flag.is_assigned) {
|
||||
return ResultAruidAlreadyRegistered;
|
||||
}
|
||||
|
||||
// TODO: Here shared memory is created for the process we don't quite emulate this part so
|
||||
// obtain this pointer from system
|
||||
auto& shared_memory = system.Kernel().GetHidSharedMem();
|
||||
|
||||
data[index].shared_memory_handle = &shared_memory;
|
||||
data[index].flag.is_assigned.Assign(true);
|
||||
// TODO: InitializeSixAxisControllerConfig(false);
|
||||
active_aruid = aruid;
|
||||
return ResultSuccess;
|
||||
}
|
||||
|
||||
Result AppletResource::RegisterAppletResourceUserId(u64 aruid, bool enable_input) {
|
||||
const u64 index = GetIndexFromAruid(aruid);
|
||||
|
||||
if (index < AruidIndexMax) {
|
||||
return ResultAruidAlreadyRegistered;
|
||||
}
|
||||
|
||||
std::size_t data_index = AruidIndexMax;
|
||||
for (std::size_t i = 0; i < AruidIndexMax; i++) {
|
||||
if (!data[i].flag.is_initialized) {
|
||||
data_index = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (data_index == AruidIndexMax) {
|
||||
return ResultAruidNoAvailableEntries;
|
||||
}
|
||||
|
||||
AruidData& aruid_data = data[data_index];
|
||||
|
||||
aruid_data.aruid = aruid;
|
||||
aruid_data.flag.is_initialized.Assign(true);
|
||||
if (enable_input) {
|
||||
aruid_data.flag.enable_pad_input.Assign(true);
|
||||
aruid_data.flag.enable_six_axis_sensor.Assign(true);
|
||||
aruid_data.flag.bit_18.Assign(true);
|
||||
aruid_data.flag.enable_touchscreen.Assign(true);
|
||||
}
|
||||
|
||||
data_index = AruidIndexMax;
|
||||
for (std::size_t i = 0; i < AruidIndexMax; i++) {
|
||||
if (registration_list.flag[i] == RegistrationStatus::Initialized) {
|
||||
if (registration_list.aruid[i] != aruid) {
|
||||
continue;
|
||||
}
|
||||
data_index = i;
|
||||
break;
|
||||
}
|
||||
if (registration_list.flag[i] == RegistrationStatus::None) {
|
||||
data_index = i;
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
if (data_index == AruidIndexMax) {
|
||||
return ResultSuccess;
|
||||
}
|
||||
|
||||
registration_list.flag[data_index] = RegistrationStatus::Initialized;
|
||||
registration_list.aruid[data_index] = aruid;
|
||||
|
||||
return ResultSuccess;
|
||||
}
|
||||
|
||||
void AppletResource::UnregisterAppletResourceUserId(u64 aruid) {
|
||||
u64 index = GetIndexFromAruid(aruid);
|
||||
|
||||
if (index < AruidIndexMax) {
|
||||
if (data[index].flag.is_assigned) {
|
||||
data[index].shared_memory_handle = nullptr;
|
||||
data[index].flag.is_assigned.Assign(false);
|
||||
}
|
||||
}
|
||||
|
||||
index = GetIndexFromAruid(aruid);
|
||||
if (index < AruidIndexMax) {
|
||||
DestroySevenSixAxisTransferMemory();
|
||||
data[index].flag.raw = 0;
|
||||
data[index].aruid = 0;
|
||||
|
||||
index = GetIndexFromAruid(aruid);
|
||||
if (index < AruidIndexMax) {
|
||||
registration_list.flag[index] = RegistrationStatus::PendingDelete;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
u64 AppletResource::GetActiveAruid() {
|
||||
return active_aruid;
|
||||
}
|
||||
|
||||
Result AppletResource::GetSharedMemoryHandle(Kernel::KSharedMemory** out_handle, u64 aruid) {
|
||||
u64 index = GetIndexFromAruid(aruid);
|
||||
if (index >= AruidIndexMax) {
|
||||
return ResultAruidNotRegistered;
|
||||
}
|
||||
|
||||
*out_handle = data[index].shared_memory_handle;
|
||||
return ResultSuccess;
|
||||
}
|
||||
|
||||
u64 AppletResource::GetIndexFromAruid(u64 aruid) {
|
||||
for (std::size_t i = 0; i < AruidIndexMax; i++) {
|
||||
if (registration_list.flag[i] == RegistrationStatus::Initialized &&
|
||||
registration_list.aruid[i] == aruid) {
|
||||
return i;
|
||||
}
|
||||
}
|
||||
return AruidIndexMax;
|
||||
}
|
||||
|
||||
Result AppletResource::DestroySevenSixAxisTransferMemory() {
|
||||
// TODO
|
||||
return ResultSuccess;
|
||||
}
|
||||
|
||||
void AppletResource::EnableInput(u64 aruid, bool is_enabled) {
|
||||
const u64 index = GetIndexFromAruid(aruid);
|
||||
if (index >= AruidIndexMax) {
|
||||
return;
|
||||
}
|
||||
|
||||
data[index].flag.enable_pad_input.Assign(is_enabled);
|
||||
data[index].flag.enable_touchscreen.Assign(is_enabled);
|
||||
}
|
||||
|
||||
void AppletResource::EnableSixAxisSensor(u64 aruid, bool is_enabled) {
|
||||
const u64 index = GetIndexFromAruid(aruid);
|
||||
if (index >= AruidIndexMax) {
|
||||
return;
|
||||
}
|
||||
|
||||
data[index].flag.enable_six_axis_sensor.Assign(is_enabled);
|
||||
}
|
||||
|
||||
void AppletResource::EnablePadInput(u64 aruid, bool is_enabled) {
|
||||
const u64 index = GetIndexFromAruid(aruid);
|
||||
if (index >= AruidIndexMax) {
|
||||
return;
|
||||
}
|
||||
|
||||
data[index].flag.enable_pad_input.Assign(is_enabled);
|
||||
}
|
||||
|
||||
void AppletResource::EnableTouchScreen(u64 aruid, bool is_enabled) {
|
||||
const u64 index = GetIndexFromAruid(aruid);
|
||||
if (index >= AruidIndexMax) {
|
||||
return;
|
||||
}
|
||||
|
||||
data[index].flag.enable_touchscreen.Assign(is_enabled);
|
||||
}
|
||||
|
||||
void AppletResource::SetIsPalmaConnectable(u64 aruid, bool is_connectable) {
|
||||
const u64 index = GetIndexFromAruid(aruid);
|
||||
if (index >= AruidIndexMax) {
|
||||
return;
|
||||
}
|
||||
|
||||
data[index].flag.is_palma_connectable.Assign(is_connectable);
|
||||
}
|
||||
|
||||
void AppletResource::EnablePalmaBoostMode(u64 aruid, bool is_enabled) {
|
||||
const u64 index = GetIndexFromAruid(aruid);
|
||||
if (index >= AruidIndexMax) {
|
||||
return;
|
||||
}
|
||||
|
||||
data[index].flag.enable_palma_boost_mode.Assign(is_enabled);
|
||||
}
|
||||
|
||||
} // namespace Service::HID
|
|
@ -0,0 +1,87 @@
|
|||
// SPDX-FileCopyrightText: Copyright 2023 yuzu Emulator Project
|
||||
// SPDX-License-Identifier: GPL-3.0-or-later
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <array>
|
||||
|
||||
#include "common/bit_field.h"
|
||||
#include "common/common_types.h"
|
||||
#include "core/hle/result.h"
|
||||
|
||||
namespace Core {
|
||||
class System;
|
||||
}
|
||||
|
||||
namespace Kernel {
|
||||
class KSharedMemory;
|
||||
}
|
||||
|
||||
namespace Service::HID {
|
||||
class AppletResource {
|
||||
public:
|
||||
explicit AppletResource(Core::System& system_);
|
||||
~AppletResource();
|
||||
|
||||
Result CreateAppletResource(u64 aruid);
|
||||
|
||||
Result RegisterAppletResourceUserId(u64 aruid, bool enable_input);
|
||||
void UnregisterAppletResourceUserId(u64 aruid);
|
||||
|
||||
u64 GetActiveAruid();
|
||||
Result GetSharedMemoryHandle(Kernel::KSharedMemory** out_handle, u64 aruid);
|
||||
|
||||
u64 GetIndexFromAruid(u64 aruid);
|
||||
|
||||
Result DestroySevenSixAxisTransferMemory();
|
||||
|
||||
void EnableInput(u64 aruid, bool is_enabled);
|
||||
void EnableSixAxisSensor(u64 aruid, bool is_enabled);
|
||||
void EnablePadInput(u64 aruid, bool is_enabled);
|
||||
void EnableTouchScreen(u64 aruid, bool is_enabled);
|
||||
void SetIsPalmaConnectable(u64 aruid, bool is_connectable);
|
||||
void EnablePalmaBoostMode(u64 aruid, bool is_enabled);
|
||||
|
||||
private:
|
||||
static constexpr std::size_t AruidIndexMax = 0x20;
|
||||
|
||||
enum RegistrationStatus : u32 {
|
||||
None,
|
||||
Initialized,
|
||||
PendingDelete,
|
||||
};
|
||||
|
||||
struct DataStatusFlag {
|
||||
union {
|
||||
u32 raw{};
|
||||
|
||||
BitField<0, 1, u32> is_initialized;
|
||||
BitField<1, 1, u32> is_assigned;
|
||||
BitField<16, 1, u32> enable_pad_input;
|
||||
BitField<17, 1, u32> enable_six_axis_sensor;
|
||||
BitField<18, 1, u32> bit_18;
|
||||
BitField<19, 1, u32> is_palma_connectable;
|
||||
BitField<20, 1, u32> enable_palma_boost_mode;
|
||||
BitField<21, 1, u32> enable_touchscreen;
|
||||
};
|
||||
};
|
||||
|
||||
struct AruidRegisterList {
|
||||
std::array<RegistrationStatus, AruidIndexMax> flag{};
|
||||
std::array<u64, AruidIndexMax> aruid{};
|
||||
};
|
||||
static_assert(sizeof(AruidRegisterList) == 0x180, "AruidRegisterList is an invalid size");
|
||||
|
||||
struct AruidData {
|
||||
DataStatusFlag flag{};
|
||||
u64 aruid{};
|
||||
Kernel::KSharedMemory* shared_memory_handle{nullptr};
|
||||
};
|
||||
|
||||
u64 active_aruid{};
|
||||
AruidRegisterList registration_list{};
|
||||
std::array<AruidData, AruidIndexMax> data{};
|
||||
|
||||
Core::System& system;
|
||||
};
|
||||
} // namespace Service::HID
|
|
@ -19,6 +19,11 @@ constexpr Result NpadIsSameType{ErrorModule::HID, 602};
|
|||
constexpr Result InvalidNpadId{ErrorModule::HID, 709};
|
||||
constexpr Result NpadNotConnected{ErrorModule::HID, 710};
|
||||
constexpr Result InvalidArraySize{ErrorModule::HID, 715};
|
||||
|
||||
constexpr Result ResultAruidNoAvailableEntries{ErrorModule::HID, 1044};
|
||||
constexpr Result ResultAruidAlreadyRegistered{ErrorModule::HID, 1046};
|
||||
constexpr Result ResultAruidNotRegistered{ErrorModule::HID, 1047};
|
||||
|
||||
constexpr Result InvalidPalmaHandle{ErrorModule::HID, 3302};
|
||||
|
||||
} // namespace Service::HID
|
||||
|
|
|
@ -1,6 +1,8 @@
|
|||
// SPDX-FileCopyrightText: Copyright 2018 yuzu Emulator Project
|
||||
// SPDX-License-Identifier: GPL-2.0-or-later
|
||||
|
||||
#include "core/hle/kernel/k_process.h"
|
||||
#include "core/hle/kernel/kernel.h"
|
||||
#include "core/hle/service/hid/hid.h"
|
||||
#include "core/hle/service/hid/hid_debug_server.h"
|
||||
#include "core/hle/service/hid/hid_firmware_settings.h"
|
||||
|
@ -20,6 +22,12 @@ void LoopProcess(Core::System& system) {
|
|||
std::shared_ptr<HidFirmwareSettings> firmware_settings =
|
||||
std::make_shared<HidFirmwareSettings>();
|
||||
|
||||
// TODO: Remove this hack until this service is emulated properly.
|
||||
const auto process_list = system.Kernel().GetProcessList();
|
||||
if (!process_list.empty()) {
|
||||
resouce_manager->RegisterAppletResourceUserId(process_list[0]->GetId(), true);
|
||||
}
|
||||
|
||||
server_manager->RegisterNamedService(
|
||||
"hid", std::make_shared<IHidServer>(system, resouce_manager, firmware_settings));
|
||||
server_manager->RegisterNamedService(
|
||||
|
|
|
@ -224,8 +224,13 @@ void IHidServer::CreateAppletResource(HLERequestContext& ctx) {
|
|||
|
||||
LOG_DEBUG(Service_HID, "called, applet_resource_user_id={}", applet_resource_user_id);
|
||||
|
||||
Result result = GetResourceManager()->CreateAppletResource(applet_resource_user_id);
|
||||
if (result.IsSuccess()) {
|
||||
result = GetResourceManager()->GetNpad()->Activate(applet_resource_user_id);
|
||||
}
|
||||
|
||||
IPC::ResponseBuilder rb{ctx, 2, 0, 1};
|
||||
rb.Push(ResultSuccess);
|
||||
rb.Push(result);
|
||||
rb.PushIpcInterface<IAppletResource>(system, resource_manager);
|
||||
}
|
||||
|
||||
|
|
|
@ -3,6 +3,7 @@
|
|||
|
||||
#include "core/hid/hid_core.h"
|
||||
#include "core/hle/service/hid/controllers/npad.h"
|
||||
#include "core/hle/service/hid/controllers/palma.h"
|
||||
#include "core/hle/service/hid/controllers/touchscreen.h"
|
||||
#include "core/hle/service/hid/errors.h"
|
||||
#include "core/hle/service/hid/hid_system_server.h"
|
||||
|
@ -63,13 +64,13 @@ IHidSystemServer::IHidSystemServer(Core::System& system_, std::shared_ptr<Resour
|
|||
{329, nullptr, "DetachAbstractedPadAll"},
|
||||
{330, nullptr, "CheckAbstractedPadConnection"},
|
||||
{500, nullptr, "SetAppletResourceUserId"},
|
||||
{501, nullptr, "RegisterAppletResourceUserId"},
|
||||
{502, nullptr, "UnregisterAppletResourceUserId"},
|
||||
{503, nullptr, "EnableAppletToGetInput"},
|
||||
{501, &IHidSystemServer::RegisterAppletResourceUserId, "RegisterAppletResourceUserId"},
|
||||
{502, &IHidSystemServer::UnregisterAppletResourceUserId, "UnregisterAppletResourceUserId"},
|
||||
{503, &IHidSystemServer::EnableAppletToGetInput, "EnableAppletToGetInput"},
|
||||
{504, nullptr, "SetAruidValidForVibration"},
|
||||
{505, nullptr, "EnableAppletToGetSixAxisSensor"},
|
||||
{506, nullptr, "EnableAppletToGetPadInput"},
|
||||
{507, nullptr, "EnableAppletToGetTouchScreen"},
|
||||
{505, &IHidSystemServer::EnableAppletToGetSixAxisSensor, "EnableAppletToGetSixAxisSensor"},
|
||||
{506, &IHidSystemServer::EnableAppletToGetPadInput, "EnableAppletToGetPadInput"},
|
||||
{507, &IHidSystemServer::EnableAppletToGetTouchScreen, "EnableAppletToGetTouchScreen"},
|
||||
{510, nullptr, "SetVibrationMasterVolume"},
|
||||
{511, nullptr, "GetVibrationMasterVolume"},
|
||||
{512, nullptr, "BeginPermitVibrationSession"},
|
||||
|
@ -420,6 +421,129 @@ void IHidSystemServer::GetIrSensorState(HLERequestContext& ctx) {
|
|||
IPC::ResponseBuilder rb{ctx, 2};
|
||||
rb.Push(ResultSuccess);
|
||||
}
|
||||
void IHidSystemServer::RegisterAppletResourceUserId(HLERequestContext& ctx) {
|
||||
IPC::RequestParser rp{ctx};
|
||||
struct Parameters {
|
||||
bool enable_input;
|
||||
INSERT_PADDING_WORDS_NOINIT(1);
|
||||
u64 applet_resource_user_id;
|
||||
};
|
||||
static_assert(sizeof(Parameters) == 0x10, "Parameters has incorrect size.");
|
||||
|
||||
const auto parameters{rp.PopRaw<Parameters>()};
|
||||
|
||||
LOG_INFO(Service_HID, "called, enable_input={}, applet_resource_user_id={}",
|
||||
parameters.enable_input, parameters.applet_resource_user_id);
|
||||
|
||||
Result result = GetResourceManager()->RegisterAppletResourceUserId(
|
||||
parameters.applet_resource_user_id, parameters.enable_input);
|
||||
|
||||
if (result.IsSuccess()) {
|
||||
// result = GetResourceManager()->GetNpad()->RegisterAppletResourceUserId(
|
||||
// parameters.applet_resource_user_id);
|
||||
}
|
||||
|
||||
IPC::ResponseBuilder rb{ctx, 2};
|
||||
rb.Push(ResultSuccess);
|
||||
}
|
||||
|
||||
void IHidSystemServer::UnregisterAppletResourceUserId(HLERequestContext& ctx) {
|
||||
IPC::RequestParser rp{ctx};
|
||||
u64 applet_resource_user_id{rp.Pop<u64>()};
|
||||
|
||||
LOG_INFO(Service_HID, "called, applet_resource_user_id={}", applet_resource_user_id);
|
||||
|
||||
GetResourceManager()->UnregisterAppletResourceUserId(applet_resource_user_id);
|
||||
// GetResourceManager()->GetNpad()->UnregisterAppletResourceUserId(applet_resource_user_id);
|
||||
// GetResourceManager()->GetPalma()->UnregisterAppletResourceUserId(applet_resource_user_id);
|
||||
|
||||
IPC::ResponseBuilder rb{ctx, 2};
|
||||
rb.Push(ResultSuccess);
|
||||
}
|
||||
|
||||
void IHidSystemServer::EnableAppletToGetInput(HLERequestContext& ctx) {
|
||||
IPC::RequestParser rp{ctx};
|
||||
struct Parameters {
|
||||
bool is_enabled;
|
||||
INSERT_PADDING_WORDS_NOINIT(1);
|
||||
u64 applet_resource_user_id;
|
||||
};
|
||||
static_assert(sizeof(Parameters) == 0x10, "Parameters has incorrect size.");
|
||||
|
||||
const auto parameters{rp.PopRaw<Parameters>()};
|
||||
|
||||
LOG_INFO(Service_HID, "called, is_enabled={}, applet_resource_user_id={}",
|
||||
parameters.is_enabled, parameters.applet_resource_user_id);
|
||||
|
||||
GetResourceManager()->EnableInput(parameters.applet_resource_user_id, parameters.is_enabled);
|
||||
// GetResourceManager()->GetNpad()->EnableInput(parameters.applet_resource_user_id);
|
||||
|
||||
IPC::ResponseBuilder rb{ctx, 2};
|
||||
rb.Push(ResultSuccess);
|
||||
}
|
||||
|
||||
void IHidSystemServer::EnableAppletToGetSixAxisSensor(HLERequestContext& ctx) {
|
||||
IPC::RequestParser rp{ctx};
|
||||
struct Parameters {
|
||||
bool is_enabled;
|
||||
INSERT_PADDING_WORDS_NOINIT(1);
|
||||
u64 applet_resource_user_id;
|
||||
};
|
||||
static_assert(sizeof(Parameters) == 0x10, "Parameters has incorrect size.");
|
||||
|
||||
const auto parameters{rp.PopRaw<Parameters>()};
|
||||
|
||||
LOG_INFO(Service_HID, "called, is_enabled={}, applet_resource_user_id={}",
|
||||
parameters.is_enabled, parameters.applet_resource_user_id);
|
||||
|
||||
GetResourceManager()->EnableTouchScreen(parameters.applet_resource_user_id,
|
||||
parameters.is_enabled);
|
||||
|
||||
IPC::ResponseBuilder rb{ctx, 2};
|
||||
rb.Push(ResultSuccess);
|
||||
}
|
||||
|
||||
void IHidSystemServer::EnableAppletToGetPadInput(HLERequestContext& ctx) {
|
||||
IPC::RequestParser rp{ctx};
|
||||
struct Parameters {
|
||||
bool is_enabled;
|
||||
INSERT_PADDING_WORDS_NOINIT(1);
|
||||
u64 applet_resource_user_id;
|
||||
};
|
||||
static_assert(sizeof(Parameters) == 0x10, "Parameters has incorrect size.");
|
||||
|
||||
const auto parameters{rp.PopRaw<Parameters>()};
|
||||
|
||||
LOG_INFO(Service_HID, "called, is_enabled={}, applet_resource_user_id={}",
|
||||
parameters.is_enabled, parameters.applet_resource_user_id);
|
||||
|
||||
GetResourceManager()->EnablePadInput(parameters.applet_resource_user_id, parameters.is_enabled);
|
||||
// GetResourceManager()->GetNpad()->EnableInput(parameters.applet_resource_user_id);
|
||||
|
||||
IPC::ResponseBuilder rb{ctx, 2};
|
||||
rb.Push(ResultSuccess);
|
||||
}
|
||||
|
||||
void IHidSystemServer::EnableAppletToGetTouchScreen(HLERequestContext& ctx) {
|
||||
IPC::RequestParser rp{ctx};
|
||||
struct Parameters {
|
||||
bool is_enabled;
|
||||
INSERT_PADDING_WORDS_NOINIT(1);
|
||||
u64 applet_resource_user_id;
|
||||
};
|
||||
static_assert(sizeof(Parameters) == 0x10, "Parameters has incorrect size.");
|
||||
|
||||
const auto parameters{rp.PopRaw<Parameters>()};
|
||||
|
||||
LOG_INFO(Service_HID, "called, is_enabled={}, applet_resource_user_id={}",
|
||||
parameters.is_enabled, parameters.applet_resource_user_id);
|
||||
|
||||
GetResourceManager()->EnableTouchScreen(parameters.applet_resource_user_id,
|
||||
parameters.is_enabled);
|
||||
|
||||
IPC::ResponseBuilder rb{ctx, 2};
|
||||
rb.Push(ResultSuccess);
|
||||
}
|
||||
|
||||
void IHidSystemServer::AcquireConnectionTriggerTimeoutEvent(HLERequestContext& ctx) {
|
||||
LOG_INFO(Service_AM, "(STUBBED) called");
|
||||
|
|
|
@ -38,6 +38,12 @@ private:
|
|||
void HasLeftRightBattery(HLERequestContext& ctx);
|
||||
void GetUniquePadsFromNpad(HLERequestContext& ctx);
|
||||
void GetIrSensorState(HLERequestContext& ctx);
|
||||
void RegisterAppletResourceUserId(HLERequestContext& ctx);
|
||||
void UnregisterAppletResourceUserId(HLERequestContext& ctx);
|
||||
void EnableAppletToGetInput(HLERequestContext& ctx);
|
||||
void EnableAppletToGetSixAxisSensor(HLERequestContext& ctx);
|
||||
void EnableAppletToGetPadInput(HLERequestContext& ctx);
|
||||
void EnableAppletToGetTouchScreen(HLERequestContext& ctx);
|
||||
void AcquireConnectionTriggerTimeoutEvent(HLERequestContext& ctx);
|
||||
void AcquireDeviceRegisteredEventForControllerSupport(HLERequestContext& ctx);
|
||||
void GetRegisteredDevices(HLERequestContext& ctx);
|
||||
|
|
|
@ -9,6 +9,7 @@
|
|||
#include "core/hle/service/hid/resource_manager.h"
|
||||
#include "core/hle/service/ipc_helpers.h"
|
||||
|
||||
#include "core/hle/service/hid/controllers/applet_resource.h"
|
||||
#include "core/hle/service/hid/controllers/console_six_axis.h"
|
||||
#include "core/hle/service/hid/controllers/debug_pad.h"
|
||||
#include "core/hle/service/hid/controllers/gesture.h"
|
||||
|
@ -33,7 +34,9 @@ constexpr auto mouse_keyboard_update_ns = std::chrono::nanoseconds{8 * 1000 * 10
|
|||
constexpr auto motion_update_ns = std::chrono::nanoseconds{5 * 1000 * 1000}; // (5ms, 200Hz)
|
||||
|
||||
ResourceManager::ResourceManager(Core::System& system_)
|
||||
: system{system_}, service_context{system_, "hid"} {}
|
||||
: system{system_}, service_context{system_, "hid"} {
|
||||
applet_resource = std::make_shared<AppletResource>(system);
|
||||
}
|
||||
|
||||
ResourceManager::~ResourceManager() = default;
|
||||
|
||||
|
@ -77,6 +80,11 @@ void ResourceManager::Initialize() {
|
|||
system.HIDCore().ReloadInputDevices();
|
||||
is_initialized = true;
|
||||
}
|
||||
|
||||
std::shared_ptr<AppletResource> ResourceManager::GetAppletResource() const {
|
||||
return applet_resource;
|
||||
}
|
||||
|
||||
std::shared_ptr<CaptureButton> ResourceManager::GetCaptureButton() const {
|
||||
return capture_button;
|
||||
}
|
||||
|
@ -137,6 +145,46 @@ std::shared_ptr<UniquePad> ResourceManager::GetUniquePad() const {
|
|||
return unique_pad;
|
||||
}
|
||||
|
||||
Result ResourceManager::CreateAppletResource(u64 aruid) {
|
||||
std::scoped_lock lock{shared_mutex};
|
||||
return applet_resource->CreateAppletResource(aruid);
|
||||
}
|
||||
|
||||
Result ResourceManager::RegisterAppletResourceUserId(u64 aruid, bool bool_value) {
|
||||
std::scoped_lock lock{shared_mutex};
|
||||
return applet_resource->RegisterAppletResourceUserId(aruid, bool_value);
|
||||
}
|
||||
|
||||
void ResourceManager::UnregisterAppletResourceUserId(u64 aruid) {
|
||||
std::scoped_lock lock{shared_mutex};
|
||||
applet_resource->UnregisterAppletResourceUserId(aruid);
|
||||
}
|
||||
|
||||
Result ResourceManager::GetSharedMemoryHandle(Kernel::KSharedMemory** out_handle, u64 aruid) {
|
||||
std::scoped_lock lock{shared_mutex};
|
||||
return applet_resource->GetSharedMemoryHandle(out_handle, aruid);
|
||||
}
|
||||
|
||||
void ResourceManager::EnableInput(u64 aruid, bool is_enabled) {
|
||||
std::scoped_lock lock{shared_mutex};
|
||||
applet_resource->EnableInput(aruid, is_enabled);
|
||||
}
|
||||
|
||||
void ResourceManager::EnableSixAxisSensor(u64 aruid, bool is_enabled) {
|
||||
std::scoped_lock lock{shared_mutex};
|
||||
applet_resource->EnableSixAxisSensor(aruid, is_enabled);
|
||||
}
|
||||
|
||||
void ResourceManager::EnablePadInput(u64 aruid, bool is_enabled) {
|
||||
std::scoped_lock lock{shared_mutex};
|
||||
applet_resource->EnablePadInput(aruid, is_enabled);
|
||||
}
|
||||
|
||||
void ResourceManager::EnableTouchScreen(u64 aruid, bool is_enabled) {
|
||||
std::scoped_lock lock{shared_mutex};
|
||||
applet_resource->EnableTouchScreen(aruid, is_enabled);
|
||||
}
|
||||
|
||||
void ResourceManager::UpdateControllers(std::uintptr_t user_data,
|
||||
std::chrono::nanoseconds ns_late) {
|
||||
auto& core_timing = system.CoreTiming();
|
||||
|
@ -172,14 +220,12 @@ void ResourceManager::UpdateMotion(std::uintptr_t user_data, std::chrono::nanose
|
|||
}
|
||||
|
||||
IAppletResource::IAppletResource(Core::System& system_, std::shared_ptr<ResourceManager> resource)
|
||||
: ServiceFramework{system_, "IAppletResource"} {
|
||||
: ServiceFramework{system_, "IAppletResource"}, resource_manager{resource} {
|
||||
static const FunctionInfo functions[] = {
|
||||
{0, &IAppletResource::GetSharedMemoryHandle, "GetSharedMemoryHandle"},
|
||||
};
|
||||
RegisterHandlers(functions);
|
||||
|
||||
resource->Initialize();
|
||||
|
||||
// Register update callbacks
|
||||
npad_update_event = Core::Timing::CreateEvent(
|
||||
"HID::UpdatePadCallback",
|
||||
|
@ -233,9 +279,13 @@ IAppletResource::~IAppletResource() {
|
|||
void IAppletResource::GetSharedMemoryHandle(HLERequestContext& ctx) {
|
||||
LOG_DEBUG(Service_HID, "called");
|
||||
|
||||
Kernel::KSharedMemory* handle;
|
||||
const u64 applet_resource_user_id = resource_manager->GetAppletResource()->GetActiveAruid();
|
||||
const auto result = resource_manager->GetSharedMemoryHandle(&handle, applet_resource_user_id);
|
||||
|
||||
IPC::ResponseBuilder rb{ctx, 2, 1};
|
||||
rb.Push(ResultSuccess);
|
||||
rb.PushCopyObjects(&system.Kernel().GetHidSharedMem());
|
||||
rb.Push(result);
|
||||
rb.PushCopyObjects(handle);
|
||||
}
|
||||
|
||||
} // namespace Service::HID
|
||||
|
|
|
@ -6,11 +6,20 @@
|
|||
#include "core/hle/service/kernel_helpers.h"
|
||||
#include "core/hle/service/service.h"
|
||||
|
||||
namespace Core {
|
||||
class System;
|
||||
}
|
||||
|
||||
namespace Core::Timing {
|
||||
struct EventType;
|
||||
}
|
||||
|
||||
namespace Kernel {
|
||||
class KSharedMemory;
|
||||
}
|
||||
|
||||
namespace Service::HID {
|
||||
class AppletResource;
|
||||
class Controller_Stubbed;
|
||||
class ConsoleSixAxis;
|
||||
class DebugPad;
|
||||
|
@ -38,6 +47,7 @@ public:
|
|||
|
||||
void Initialize();
|
||||
|
||||
std::shared_ptr<AppletResource> GetAppletResource() const;
|
||||
std::shared_ptr<CaptureButton> GetCaptureButton() const;
|
||||
std::shared_ptr<ConsoleSixAxis> GetConsoleSixAxis() const;
|
||||
std::shared_ptr<DebugMouse> GetDebugMouse() const;
|
||||
|
@ -54,6 +64,18 @@ public:
|
|||
std::shared_ptr<TouchScreen> GetTouchScreen() const;
|
||||
std::shared_ptr<UniquePad> GetUniquePad() const;
|
||||
|
||||
Result CreateAppletResource(u64 aruid);
|
||||
|
||||
Result RegisterAppletResourceUserId(u64 aruid, bool bool_value);
|
||||
void UnregisterAppletResourceUserId(u64 aruid);
|
||||
|
||||
Result GetSharedMemoryHandle(Kernel::KSharedMemory** out_handle, u64 aruid);
|
||||
|
||||
void EnableInput(u64 aruid, bool is_enabled);
|
||||
void EnableSixAxisSensor(u64 aruid, bool is_enabled);
|
||||
void EnablePadInput(u64 aruid, bool is_enabled);
|
||||
void EnableTouchScreen(u64 aruid, bool is_enabled);
|
||||
|
||||
void UpdateControllers(std::uintptr_t user_data, std::chrono::nanoseconds ns_late);
|
||||
void UpdateNpad(std::uintptr_t user_data, std::chrono::nanoseconds ns_late);
|
||||
void UpdateMouseKeyboard(std::uintptr_t user_data, std::chrono::nanoseconds ns_late);
|
||||
|
@ -62,6 +84,9 @@ public:
|
|||
private:
|
||||
bool is_initialized{false};
|
||||
|
||||
mutable std::mutex shared_mutex;
|
||||
std::shared_ptr<AppletResource> applet_resource = nullptr;
|
||||
|
||||
std::shared_ptr<CaptureButton> capture_button = nullptr;
|
||||
std::shared_ptr<ConsoleSixAxis> console_six_axis = nullptr;
|
||||
std::shared_ptr<DebugMouse> debug_mouse = nullptr;
|
||||
|
@ -106,6 +131,8 @@ private:
|
|||
std::shared_ptr<Core::Timing::EventType> default_update_event;
|
||||
std::shared_ptr<Core::Timing::EventType> mouse_keyboard_update_event;
|
||||
std::shared_ptr<Core::Timing::EventType> motion_update_event;
|
||||
|
||||
std::shared_ptr<ResourceManager> resource_manager;
|
||||
};
|
||||
|
||||
} // namespace Service::HID
|
||||
|
|
Reference in New Issue