mirror of
https://git.eden-emu.dev/eden-emu/eden.git
synced 2026-09-26 19:11:00 +00:00
+105
-109
@@ -75,41 +75,6 @@ class IManagerForSystemService final : public ServiceFramework<IManagerForSystem
|
||||
public:
|
||||
explicit IManagerForSystemService(Core::System& system_, Common::UUID uuid)
|
||||
: ServiceFramework{system_, "IManagerForSystemService"}, account_id{uuid} {
|
||||
// clang-format off
|
||||
static const FunctionInfo functions[] = {
|
||||
{0, D<&IManagerForSystemService::CheckAvailability>, "CheckAvailability"},
|
||||
{1, D<&IManagerForSystemService::GetAccountId>, "GetAccountId"},
|
||||
{2, nullptr, "EnsureIdTokenCacheAsync"},
|
||||
{3, D<&IManagerForSystemService::LoadIdTokenCacheDeprecated>, "LoadIdTokenCacheDeprecated"}, // 19.0.0+
|
||||
{4, D<&IManagerForSystemService::LoadIdTokenCache>, "LoadIdTokenCache"}, // 19.0.0+
|
||||
{100, nullptr, "SetSystemProgramIdentification"},
|
||||
{101, nullptr, "RefreshNotificationTokenAsync"}, // 7.0.0+
|
||||
{110, nullptr, "GetServiceEntryRequirementCache"}, // 4.0.0+
|
||||
{111, nullptr, "InvalidateServiceEntryRequirementCache"}, // 4.0.0+
|
||||
{112, nullptr, "InvalidateTokenCache"}, // 4.0.0 - 6.2.0
|
||||
{113, nullptr, "GetServiceEntryRequirementCacheForOnlinePlay"}, // 6.1.0+
|
||||
{120, nullptr, "GetNintendoAccountId"},
|
||||
{121, nullptr, "CalculateNintendoAccountAuthenticationFingerprint"}, // 9.0.0+
|
||||
{130, nullptr, "GetNintendoAccountUserResourceCache"},
|
||||
{131, nullptr, "RefreshNintendoAccountUserResourceCacheAsync"},
|
||||
{132, nullptr, "RefreshNintendoAccountUserResourceCacheAsyncIfSecondsElapsed"},
|
||||
{133, nullptr, "GetNintendoAccountVerificationUrlCache"}, // 9.0.0+
|
||||
{134, nullptr, "RefreshNintendoAccountVerificationUrlCache"}, // 9.0.0+
|
||||
{135, nullptr, "RefreshNintendoAccountVerificationUrlCacheAsyncIfSecondsElapsed"}, // 9.0.0+
|
||||
{136, nullptr, "GetNintendoAccountUserResourceCache"}, // 19.0.0+
|
||||
{140, nullptr, "GetNetworkServiceLicenseCache"}, // 5.0.0+
|
||||
{141, nullptr, "RefreshNetworkServiceLicenseCacheAsync"}, // 5.0.0+
|
||||
{142, nullptr, "RefreshNetworkServiceLicenseCacheAsyncIfSecondsElapsed"}, // 5.0.0+
|
||||
{143, D<&IManagerForSystemService::GetNetworkServiceLicenseCacheEx>, "GetNetworkServiceLicenseCacheEx"}, // 15.0.0+
|
||||
{150, nullptr, "CreateAuthorizationRequest"},
|
||||
{160, nullptr, "RequiresUpdateNetworkServiceAccountIdTokenCache"},
|
||||
{161, nullptr, "RequireReauthenticationOfNetworkServiceAccount"},
|
||||
{170, nullptr, "CreateDeviceHistoryRequest"}, // 17.0.0+
|
||||
{180, nullptr, "GetRequestForNintendoAccountReauthentication"} // 18.0.0+
|
||||
};
|
||||
// clang-format on
|
||||
|
||||
RegisterHandlers(functions);
|
||||
}
|
||||
|
||||
private:
|
||||
@@ -143,6 +108,39 @@ private:
|
||||
R_SUCCEED();
|
||||
}
|
||||
|
||||
FunctionInfoBase const* FindRequest(u32 key) override {
|
||||
return HandlerTableGenerateWithFind(key,
|
||||
FunctionInfo{0, D<&IManagerForSystemService::CheckAvailability>, "CheckAvailability"},
|
||||
FunctionInfo{1, D<&IManagerForSystemService::GetAccountId>, "GetAccountId"},
|
||||
FunctionInfo{2, nullptr, "EnsureIdTokenCacheAsync"},
|
||||
FunctionInfo{3, D<&IManagerForSystemService::LoadIdTokenCacheDeprecated>, "LoadIdTokenCacheDeprecated"}, // 19.0.0+
|
||||
FunctionInfo{4, D<&IManagerForSystemService::LoadIdTokenCache>, "LoadIdTokenCache"}, // 19.0.0+
|
||||
FunctionInfo{100, nullptr, "SetSystemProgramIdentification"},
|
||||
FunctionInfo{101, nullptr, "RefreshNotificationTokenAsync"}, // 7.0.0+
|
||||
FunctionInfo{110, nullptr, "GetServiceEntryRequirementCache"}, // 4.0.0+
|
||||
FunctionInfo{111, nullptr, "InvalidateServiceEntryRequirementCache"}, // 4.0.0+
|
||||
FunctionInfo{112, nullptr, "InvalidateTokenCache"}, // 4.0.0 - 6.2.0
|
||||
FunctionInfo{113, nullptr, "GetServiceEntryRequirementCacheForOnlinePlay"}, // 6.1.0+
|
||||
FunctionInfo{120, nullptr, "GetNintendoAccountId"},
|
||||
FunctionInfo{121, nullptr, "CalculateNintendoAccountAuthenticationFingerprint"}, // 9.0.0+
|
||||
FunctionInfo{130, nullptr, "GetNintendoAccountUserResourceCache"},
|
||||
FunctionInfo{131, nullptr, "RefreshNintendoAccountUserResourceCacheAsync"},
|
||||
FunctionInfo{132, nullptr, "RefreshNintendoAccountUserResourceCacheAsyncIfSecondsElapsed"},
|
||||
FunctionInfo{133, nullptr, "GetNintendoAccountVerificationUrlCache"}, // 9.0.0+
|
||||
FunctionInfo{134, nullptr, "RefreshNintendoAccountVerificationUrlCache"}, // 9.0.0+
|
||||
FunctionInfo{135, nullptr, "RefreshNintendoAccountVerificationUrlCacheAsyncIfSecondsElapsed"}, // 9.0.0+
|
||||
FunctionInfo{136, nullptr, "GetNintendoAccountUserResourceCache"}, // 19.0.0+
|
||||
FunctionInfo{140, nullptr, "GetNetworkServiceLicenseCache"}, // 5.0.0+
|
||||
FunctionInfo{141, nullptr, "RefreshNetworkServiceLicenseCacheAsync"}, // 5.0.0+
|
||||
FunctionInfo{142, nullptr, "RefreshNetworkServiceLicenseCacheAsyncIfSecondsElapsed"}, // 5.0.0+
|
||||
FunctionInfo{143, D<&IManagerForSystemService::GetNetworkServiceLicenseCacheEx>, "GetNetworkServiceLicenseCacheEx"}, // 15.0.0+
|
||||
FunctionInfo{150, nullptr, "CreateAuthorizationRequest"},
|
||||
FunctionInfo{160, nullptr, "RequiresUpdateNetworkServiceAccountIdTokenCache"},
|
||||
FunctionInfo{161, nullptr, "RequireReauthenticationOfNetworkServiceAccount"},
|
||||
FunctionInfo{170, nullptr, "CreateDeviceHistoryRequest"}, // 17.0.0+
|
||||
FunctionInfo{180, nullptr, "GetRequestForNintendoAccountReauthentication"} // 18.0.0+
|
||||
);
|
||||
}
|
||||
Common::UUID account_id;
|
||||
};
|
||||
|
||||
@@ -151,25 +149,24 @@ class IFloatingRegistrationRequest final : public ServiceFramework<IFloatingRegi
|
||||
public:
|
||||
explicit IFloatingRegistrationRequest(Core::System& system_, Common::UUID)
|
||||
: ServiceFramework{system_, "IFloatingRegistrationRequest"} {
|
||||
// clang-format off
|
||||
static const FunctionInfo functions[] = {
|
||||
{0, nullptr, "GetSessionId"},
|
||||
{12, nullptr, "GetAccountId"},
|
||||
{13, nullptr, "GetLinkedNintendoAccountId"},
|
||||
{14, nullptr, "GetNickname"},
|
||||
{15, nullptr, "GetProfileImage"},
|
||||
{16, nullptr, "GetProfileLargeImage"}, // 18.0.0+
|
||||
{21, nullptr, "LoadIdTokenCache"},
|
||||
{100, nullptr, "RegisterUser"}, // [1.0.0-3.0.2] RegisterAsync
|
||||
{101, nullptr, "RegisterUserWithUid"}, // [1.0.0-3.0.2] RegisterWithUidAsync
|
||||
{102, nullptr, "RegisterNetworkServiceAccountAsync"}, // 4.0.0+
|
||||
{103, nullptr, "RegisterNetworkServiceAccountWithUidAsync"}, // 4.0.0+
|
||||
{110, nullptr, "SetSystemProgramIdentification"},
|
||||
{111, nullptr, "EnsureIdTokenCacheAsync"},
|
||||
};
|
||||
// clang-format on
|
||||
}
|
||||
|
||||
RegisterHandlers(functions);
|
||||
FunctionInfoBase const* FindRequest(u32 key) override {
|
||||
return HandlerTableGenerateWithFind(key,
|
||||
FunctionInfo{0, nullptr, "GetSessionId"},
|
||||
FunctionInfo{12, nullptr, "GetAccountId"},
|
||||
FunctionInfo{13, nullptr, "GetLinkedNintendoAccountId"},
|
||||
FunctionInfo{14, nullptr, "GetNickname"},
|
||||
FunctionInfo{15, nullptr, "GetProfileImage"},
|
||||
FunctionInfo{16, nullptr, "GetProfileLargeImage", MakeVersionGate({18,0,0})},
|
||||
FunctionInfo{21, nullptr, "LoadIdTokenCache"},
|
||||
FunctionInfo{100, nullptr, "RegisterUser"}, // [1.0.0-3.0.2] RegisterAsync
|
||||
FunctionInfo{101, nullptr, "RegisterUserWithUid"}, // [1.0.0-3.0.2] RegisterWithUidAsync
|
||||
FunctionInfo{102, nullptr, "RegisterNetworkServiceAccountAsync", MakeVersionGate({4,0,0})},
|
||||
FunctionInfo{103, nullptr, "RegisterNetworkServiceAccountWithUidAsync", MakeVersionGate({4,0,0})},
|
||||
FunctionInfo{110, nullptr, "SetSystemProgramIdentification"},
|
||||
FunctionInfo{111, nullptr, "EnsureIdTokenCacheAsync"}
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -177,62 +174,6 @@ class IAdministrator final : public ServiceFramework<IAdministrator> {
|
||||
public:
|
||||
explicit IAdministrator(Core::System& system_, Common::UUID)
|
||||
: ServiceFramework{system_, "IAdministrator"} {
|
||||
// clang-format off
|
||||
static const FunctionInfo functions[] = {
|
||||
{0, nullptr, "CheckAvailability"},
|
||||
{1, nullptr, "GetAccountId"},
|
||||
{2, nullptr, "EnsureIdTokenCacheAsync"},
|
||||
{3, nullptr, "LoadIdTokenCache"},
|
||||
{100, nullptr, "SetSystemProgramIdentification"},
|
||||
{101, nullptr, "RefreshNotificationTokenAsync"}, // 7.0.0+
|
||||
{110, nullptr, "GetServiceEntryRequirementCache"}, // 4.0.0+
|
||||
{111, nullptr, "InvalidateServiceEntryRequirementCache"}, // 4.0.0+
|
||||
{112, nullptr, "InvalidateTokenCache"}, // 4.0.0 - 6.2.0
|
||||
{113, nullptr, "GetServiceEntryRequirementCacheForOnlinePlay"}, // 6.1.0+
|
||||
{120, nullptr, "GetNintendoAccountId"},
|
||||
{121, nullptr, "CalculateNintendoAccountAuthenticationFingerprint"}, // 9.0.0+
|
||||
{130, nullptr, "GetNintendoAccountUserResourceCache"},
|
||||
{131, nullptr, "RefreshNintendoAccountUserResourceCacheAsync"},
|
||||
{132, nullptr, "RefreshNintendoAccountUserResourceCacheAsyncIfSecondsElapsed"},
|
||||
{133, nullptr, "GetNintendoAccountVerificationUrlCache"}, // 9.0.0+
|
||||
{134, nullptr, "RefreshNintendoAccountVerificationUrlCacheAsync"}, // 9.0.0+
|
||||
{135, nullptr, "RefreshNintendoAccountVerificationUrlCacheAsyncIfSecondsElapsed"}, // 9.0.0+
|
||||
{140, nullptr, "GetNetworkServiceLicenseCache"}, // 5.0.0+
|
||||
{141, nullptr, "RefreshNetworkServiceLicenseCacheAsync"}, // 5.0.0+
|
||||
{142, nullptr, "RefreshNetworkServiceLicenseCacheAsyncIfSecondsElapsed"}, // 5.0.0+
|
||||
{143, nullptr, "GetNetworkServiceLicenseCacheEx"},
|
||||
{150, nullptr, "CreateAuthorizationRequest"},
|
||||
{160, nullptr, "RequiresUpdateNetworkServiceAccountIdTokenCache"},
|
||||
{161, nullptr, "RequireReauthenticationOfNetworkServiceAccount"},
|
||||
{170, nullptr, "CreateDeviceHistoryRequest"}, // 17.0.0+
|
||||
{180, nullptr, "GetRequestForNintendoAccountReauthentication"}, // 18.0.0+
|
||||
{200, nullptr, "IsRegistered"},
|
||||
{201, nullptr, "RegisterAsync"},
|
||||
{202, nullptr, "UnregisterAsync"},
|
||||
{203, nullptr, "DeleteRegistrationInfoLocally"},
|
||||
{220, nullptr, "SynchronizeProfileAsync"},
|
||||
{221, nullptr, "UploadProfileAsync"},
|
||||
{222, nullptr, "SynchronizaProfileAsyncIfSecondsElapsed"},
|
||||
{250, &IAdministrator::IsLinkedWithNintendoAccount, "IsLinkedWithNintendoAccount"},
|
||||
{251, nullptr, "CreateProcedureToLinkWithNintendoAccount"},
|
||||
{252, nullptr, "ResumeProcedureToLinkWithNintendoAccount"},
|
||||
{255, nullptr, "CreateProcedureToUpdateLinkageStateOfNintendoAccount"},
|
||||
{256, nullptr, "ResumeProcedureToUpdateLinkageStateOfNintendoAccount"},
|
||||
{260, nullptr, "CreateProcedureToLinkNnidWithNintendoAccount"}, // 3.0.0+
|
||||
{261, nullptr, "ResumeProcedureToLinkNnidWithNintendoAccount"}, // 3.0.0+
|
||||
{280, nullptr, "ProxyProcedureToAcquireApplicationAuthorizationForNintendoAccount"},
|
||||
{290, nullptr, "GetRequestForNintendoAccountUserResourceView"}, // 8.0.0+
|
||||
{300, nullptr, "TryRecoverNintendoAccountUserStateAsync"}, // 6.0.0+
|
||||
{400, nullptr, "IsServiceEntryRequirementCacheRefreshRequiredForOnlinePlay"}, // 6.1.0+
|
||||
{401, nullptr, "RefreshServiceEntryRequirementCacheForOnlinePlayAsync"}, // 6.1.0+
|
||||
{900, nullptr, "GetAuthenticationInfoForWin"}, // 9.0.0+
|
||||
{901, nullptr, "ImportAsyncForWin"}, // 9.0.0+
|
||||
{997, nullptr, "DebugUnlinkNintendoAccountAsync"},
|
||||
{998, nullptr, "DebugSetAvailabilityErrorDetail"},
|
||||
};
|
||||
// clang-format on
|
||||
|
||||
RegisterHandlers(functions);
|
||||
}
|
||||
|
||||
private:
|
||||
@@ -241,6 +182,61 @@ private:
|
||||
rb.Push(ResultSuccess);
|
||||
rb.Push(false);
|
||||
}
|
||||
|
||||
FunctionInfoBase const* FindRequest(u32 key) override {
|
||||
return HandlerTableGenerateWithFind(key,
|
||||
FunctionInfo{0, nullptr, "CheckAvailability"},
|
||||
FunctionInfo{1, nullptr, "GetAccountId"},
|
||||
FunctionInfo{2, nullptr, "EnsureIdTokenCacheAsync"},
|
||||
FunctionInfo{3, nullptr, "LoadIdTokenCache"},
|
||||
FunctionInfo{100, nullptr, "SetSystemProgramIdentification"},
|
||||
FunctionInfo{101, nullptr, "RefreshNotificationTokenAsync", MakeVersionGate({7,0,0})},
|
||||
FunctionInfo{110, nullptr, "GetServiceEntryRequirementCache"}, // 4.0.0+
|
||||
FunctionInfo{111, nullptr, "InvalidateServiceEntryRequirementCache"}, // 4.0.0+
|
||||
FunctionInfo{112, nullptr, "InvalidateTokenCache"}, // 4.0.0 - 6.2.0
|
||||
FunctionInfo{113, nullptr, "GetServiceEntryRequirementCacheForOnlinePlay"}, // 6.1.0+
|
||||
FunctionInfo{120, nullptr, "GetNintendoAccountId"},
|
||||
FunctionInfo{121, nullptr, "CalculateNintendoAccountAuthenticationFingerprint"}, // 9.0.0+
|
||||
FunctionInfo{130, nullptr, "GetNintendoAccountUserResourceCache"},
|
||||
FunctionInfo{131, nullptr, "RefreshNintendoAccountUserResourceCacheAsync"},
|
||||
FunctionInfo{132, nullptr, "RefreshNintendoAccountUserResourceCacheAsyncIfSecondsElapsed"},
|
||||
FunctionInfo{133, nullptr, "GetNintendoAccountVerificationUrlCache"}, // 9.0.0+
|
||||
FunctionInfo{134, nullptr, "RefreshNintendoAccountVerificationUrlCacheAsync"}, // 9.0.0+
|
||||
FunctionInfo{135, nullptr, "RefreshNintendoAccountVerificationUrlCacheAsyncIfSecondsElapsed"}, // 9.0.0+
|
||||
FunctionInfo{140, nullptr, "GetNetworkServiceLicenseCache"}, // 5.0.0+
|
||||
FunctionInfo{141, nullptr, "RefreshNetworkServiceLicenseCacheAsync"}, // 5.0.0+
|
||||
FunctionInfo{142, nullptr, "RefreshNetworkServiceLicenseCacheAsyncIfSecondsElapsed"}, // 5.0.0+
|
||||
FunctionInfo{143, nullptr, "GetNetworkServiceLicenseCacheEx"},
|
||||
FunctionInfo{150, nullptr, "CreateAuthorizationRequest"},
|
||||
FunctionInfo{160, nullptr, "RequiresUpdateNetworkServiceAccountIdTokenCache"},
|
||||
FunctionInfo{161, nullptr, "RequireReauthenticationOfNetworkServiceAccount"},
|
||||
FunctionInfo{170, nullptr, "CreateDeviceHistoryRequest"}, // 17.0.0+
|
||||
FunctionInfo{180, nullptr, "GetRequestForNintendoAccountReauthentication"}, // 18.0.0+
|
||||
FunctionInfo{200, nullptr, "IsRegistered"},
|
||||
FunctionInfo{201, nullptr, "RegisterAsync"},
|
||||
FunctionInfo{202, nullptr, "UnregisterAsync"},
|
||||
FunctionInfo{203, nullptr, "DeleteRegistrationInfoLocally"},
|
||||
FunctionInfo{220, nullptr, "SynchronizeProfileAsync"},
|
||||
FunctionInfo{221, nullptr, "UploadProfileAsync"},
|
||||
FunctionInfo{222, nullptr, "SynchronizaProfileAsyncIfSecondsElapsed"},
|
||||
FunctionInfo{250, &IAdministrator::IsLinkedWithNintendoAccount, "IsLinkedWithNintendoAccount"},
|
||||
FunctionInfo{251, nullptr, "CreateProcedureToLinkWithNintendoAccount"},
|
||||
FunctionInfo{252, nullptr, "ResumeProcedureToLinkWithNintendoAccount"},
|
||||
FunctionInfo{255, nullptr, "CreateProcedureToUpdateLinkageStateOfNintendoAccount"},
|
||||
FunctionInfo{256, nullptr, "ResumeProcedureToUpdateLinkageStateOfNintendoAccount"},
|
||||
FunctionInfo{260, nullptr, "CreateProcedureToLinkNnidWithNintendoAccount"}, // 3.0.0+
|
||||
FunctionInfo{261, nullptr, "ResumeProcedureToLinkNnidWithNintendoAccount"}, // 3.0.0+
|
||||
FunctionInfo{280, nullptr, "ProxyProcedureToAcquireApplicationAuthorizationForNintendoAccount"},
|
||||
FunctionInfo{290, nullptr, "GetRequestForNintendoAccountUserResourceView"}, // 8.0.0+
|
||||
FunctionInfo{300, nullptr, "TryRecoverNintendoAccountUserStateAsync"}, // 6.0.0+
|
||||
FunctionInfo{400, nullptr, "IsServiceEntryRequirementCacheRefreshRequiredForOnlinePlay"}, // 6.1.0+
|
||||
FunctionInfo{401, nullptr, "RefreshServiceEntryRequirementCacheForOnlinePlayAsync"}, // 6.1.0+
|
||||
FunctionInfo{900, nullptr, "GetAuthenticationInfoForWin"}, // 9.0.0+
|
||||
FunctionInfo{901, nullptr, "ImportAsyncForWin"}, // 9.0.0+
|
||||
FunctionInfo{997, nullptr, "DebugUnlinkNintendoAccountAsync"},
|
||||
FunctionInfo{998, nullptr, "DebugSetAvailabilityErrorDetail"}
|
||||
);
|
||||
}
|
||||
};
|
||||
|
||||
class IAuthorizationRequest final : public ServiceFramework<IAuthorizationRequest> {
|
||||
|
||||
@@ -47,22 +47,7 @@ ServiceFrameworkBase::~ServiceFrameworkBase() {
|
||||
const auto guard = ServiceFrameworkBase::LockService();
|
||||
}
|
||||
|
||||
void ServiceFrameworkBase::RegisterHandlersBase(const FunctionInfoBase* functions, std::size_t n) {
|
||||
// Usually this array is sorted by id already, so hint to insert at the end
|
||||
handlers.reserve(handlers.size() + n);
|
||||
for (std::size_t i = 0; i < n; ++i)
|
||||
handlers.emplace_hint(handlers.cend(), functions[i].expected_header, functions[i]);
|
||||
}
|
||||
|
||||
void ServiceFrameworkBase::RegisterHandlersBaseTipc(const FunctionInfoBase* functions, std::size_t n) {
|
||||
// Usually this array is sorted by id already, so hint to insert at the end
|
||||
handlers_tipc.reserve(handlers_tipc.size() + n);
|
||||
for (std::size_t i = 0; i < n; ++i)
|
||||
handlers_tipc.emplace_hint(handlers_tipc.cend(), functions[i].expected_header, functions[i]);
|
||||
}
|
||||
|
||||
void ServiceFrameworkBase::ReportUnimplementedFunction(HLERequestContext& ctx,
|
||||
const FunctionInfoBase* info) {
|
||||
void ServiceFrameworkBase::ReportUnimplementedFunction(HLERequestContext& ctx, const FunctionInfoBase* info) {
|
||||
auto cmd_buf = ctx.CommandBuffer();
|
||||
std::string function_name = info == nullptr ? "<unknown>" : info->name;
|
||||
|
||||
@@ -82,16 +67,10 @@ void ServiceFrameworkBase::ReportUnimplementedFunction(HLERequestContext& ctx,
|
||||
}
|
||||
|
||||
void ServiceFrameworkBase::InvokeRequest(HLERequestContext& ctx) {
|
||||
const auto command = ctx.GetCommand();
|
||||
auto it = handlers.find(command);
|
||||
const bool is_cmd_read = command == 0;
|
||||
FunctionInfoBase const* info = it == handlers.end() ? nullptr : &it->second;
|
||||
if (info == nullptr || info->handler_callback == nullptr)
|
||||
return ReportUnimplementedFunction(ctx, info);
|
||||
|
||||
const bool is_cmd_read = ctx.GetCommand() == 0;
|
||||
auto const info = FindRequest(ctx.GetCommand());
|
||||
LOG_TRACE(Service, "{}", MakeFunctionString(info->name, GetServiceName(), ctx.CommandBuffer()));
|
||||
handler_invoker(this, info->handler_callback, ctx);
|
||||
|
||||
if (is_i_storage && is_cmd_read) {
|
||||
const auto* const process = ctx.GetThread().GetOwnerProcess();
|
||||
if (process != nullptr && system.IsNVDECActiveForProcess(process->GetId())) {
|
||||
@@ -101,11 +80,7 @@ void ServiceFrameworkBase::InvokeRequest(HLERequestContext& ctx) {
|
||||
}
|
||||
|
||||
void ServiceFrameworkBase::InvokeRequestTipc(HLERequestContext& ctx) {
|
||||
auto it = handlers_tipc.find(ctx.GetCommand());
|
||||
FunctionInfoBase const* info = it == handlers_tipc.end() ? nullptr : &it->second;
|
||||
if (info == nullptr || info->handler_callback == nullptr)
|
||||
return ReportUnimplementedFunction(ctx, info);
|
||||
|
||||
auto const info = FindRequestTipc(ctx.GetCommand());
|
||||
LOG_TRACE(Service, "{}", MakeFunctionString(info->name, GetServiceName(), ctx.CommandBuffer()));
|
||||
handler_invoker(this, info->handler_callback, ctx);
|
||||
}
|
||||
|
||||
@@ -7,7 +7,10 @@
|
||||
#pragma once
|
||||
|
||||
#include <cstddef>
|
||||
#include <memory>
|
||||
#include <mutex>
|
||||
#include <tuple>
|
||||
#include "frozen/map.h"
|
||||
#include "common/container/unordered_map.h"
|
||||
#include "common/common_types.h"
|
||||
#include "core/hle/service/hle_ipc.h"
|
||||
@@ -77,30 +80,37 @@ protected:
|
||||
[[nodiscard]] virtual std::unique_lock<std::mutex> LockService() noexcept {
|
||||
return std::unique_lock{lock_service};
|
||||
}
|
||||
private:
|
||||
template <typename T>
|
||||
friend class ServiceFramework;
|
||||
|
||||
static constexpr u32 MakeVersionGate(std::tuple<u32, u32, u32> since, std::tuple<u32, u32, u32> until = {0, 0, 0}) {
|
||||
auto const [s_maj, s_min, s_pat] = since;
|
||||
auto const [u_maj, u_min, u_pat] = until;
|
||||
return (u_pat << 0) | (u_min << 4) | (u_maj << 8)
|
||||
| (s_pat << 12) | (s_min << 16) | (s_maj << 20);
|
||||
}
|
||||
|
||||
struct FunctionInfoBase {
|
||||
u32 expected_header;
|
||||
HandlerFnP<ServiceFrameworkBase> handler_callback;
|
||||
const char* name;
|
||||
u32 version_gating;
|
||||
};
|
||||
private:
|
||||
template <typename T>
|
||||
friend class ServiceFramework;
|
||||
|
||||
using InvokerFn = void(ServiceFrameworkBase* object, HandlerFnP<ServiceFrameworkBase> member,
|
||||
HLERequestContext& ctx);
|
||||
using InvokerFn = void(ServiceFrameworkBase* object, HandlerFnP<ServiceFrameworkBase> member, HLERequestContext& ctx);
|
||||
|
||||
explicit ServiceFrameworkBase(Core::System& system_, const char* service_name_,
|
||||
u32 max_sessions_, InvokerFn* handler_invoker_);
|
||||
explicit ServiceFrameworkBase(Core::System& system_, const char* service_name_, u32 max_sessions_, InvokerFn* handler_invoker_);
|
||||
~ServiceFrameworkBase() override;
|
||||
|
||||
virtual FunctionInfoBase const* FindRequest(u32 key) = 0;
|
||||
virtual FunctionInfoBase const* FindRequestTipc(u32 key) = 0;
|
||||
|
||||
void RegisterHandlersBase(const FunctionInfoBase* functions, std::size_t n);
|
||||
void RegisterHandlersBaseTipc(const FunctionInfoBase* functions, std::size_t n);
|
||||
void ReportUnimplementedFunction(HLERequestContext& ctx, const FunctionInfoBase* info);
|
||||
|
||||
protected:
|
||||
::Common::unordered_map<u32, FunctionInfoBase> handlers;
|
||||
::Common::unordered_map<u32, FunctionInfoBase> handlers_tipc;
|
||||
/// Used to gain exclusive access to the service members, e.g. from CoreTiming thread.
|
||||
std::mutex lock_service;
|
||||
/// System context that the service operates under.
|
||||
@@ -143,25 +153,60 @@ protected:
|
||||
/// @param expected_header_ request header in the command buffer which will trigger dispatch to this handler
|
||||
/// @param handler_callback_ member function in this service which will be called to handle the request
|
||||
/// @param name_ human-friendly name for the request. Used mostly for logging purposes.
|
||||
FunctionInfoTyped(u32 expected_header_, HandlerFnP<T> handler_callback_, const char* name_)
|
||||
: FunctionInfoBase{expected_header_, HandlerFnP<ServiceFrameworkBase>(handler_callback_), name_} {}
|
||||
FunctionInfoTyped(u32 expected_header_, HandlerFnP<T> handler_callback_, const char* name_, u32 version_gating_ = 0)
|
||||
: FunctionInfoBase{expected_header_, HandlerFnP<ServiceFrameworkBase>(handler_callback_), name_, version_gating_}
|
||||
{}
|
||||
};
|
||||
using FunctionInfo = FunctionInfoTyped<Self>;
|
||||
|
||||
/**
|
||||
* Initializes the handler with no functions installed.
|
||||
*
|
||||
* @param system_ The system context to construct this service under.
|
||||
* @param service_name_ Name of the service.
|
||||
* @param max_sessions_ Maximum number of sessions that can be connected to this service at the
|
||||
* same time.
|
||||
*/
|
||||
template<typename ...Ts>
|
||||
requires (std::same_as<Ts, FunctionInfo> && ...)
|
||||
static FunctionInfoBase const* HandlerTableGenerateWithFind(u32 key, Ts... args) {
|
||||
static auto const map = frozen::map<u32, FunctionInfo, sizeof...(args)>{
|
||||
{args.expected_header, FunctionInfo(args)}...
|
||||
};
|
||||
auto const it = map.find(key);
|
||||
return it != map.end() ? std::addressof(it->second) : nullptr;
|
||||
}
|
||||
|
||||
/// @brief Initializes the handler with no functions installed.
|
||||
/// @param system_ The system context to construct this service under.
|
||||
/// @param service_name_ Name of the service.
|
||||
/// @param max_sessions_ Maximum number of sessions that can be connected to this service at the
|
||||
/// same time.
|
||||
explicit ServiceFramework(Core::System& system_, const char* service_name_, u32 max_sessions_ = ServerSessionCountMax)
|
||||
: ServiceFrameworkBase(system_, service_name_, max_sessions_, Invoker) {}
|
||||
: ServiceFrameworkBase(system_, service_name_, max_sessions_, Invoker)
|
||||
{}
|
||||
|
||||
FunctionInfoBase const* FindRequest(u32 key) override {
|
||||
auto it = handlers.find(key);
|
||||
FunctionInfoBase const* info = it == handlers.end() ? nullptr : &it->second;
|
||||
return !(info == nullptr || info->handler_callback == nullptr) ? info : nullptr;
|
||||
}
|
||||
|
||||
FunctionInfoBase const* FindRequestTipc(u32 key) override {
|
||||
auto it = handlers_tipc.find(key);
|
||||
FunctionInfoBase const* info = it == handlers_tipc.end() ? nullptr : &it->second;
|
||||
return !(info == nullptr || info->handler_callback == nullptr) ? info : nullptr;
|
||||
}
|
||||
|
||||
constexpr void RegisterHandlersBase(const FunctionInfoBase* functions, std::size_t n) {
|
||||
// Usually this array is sorted by id already, so hint to insert at the end
|
||||
handlers.reserve(handlers.size() + n);
|
||||
for (std::size_t i = 0; i < n; ++i)
|
||||
handlers.emplace_hint(handlers.cend(), functions[i].expected_header, functions[i]);
|
||||
}
|
||||
|
||||
constexpr void RegisterHandlersBaseTipc(const FunctionInfoBase* functions, std::size_t n) {
|
||||
// Usually this array is sorted by id already, so hint to insert at the end
|
||||
handlers_tipc.reserve(handlers_tipc.size() + n);
|
||||
for (std::size_t i = 0; i < n; ++i)
|
||||
handlers_tipc.emplace_hint(handlers_tipc.cend(), functions[i].expected_header, functions[i]);
|
||||
}
|
||||
|
||||
/// Registers handlers in the service.
|
||||
template <typename T = Self, std::size_t N>
|
||||
void RegisterHandlers(const FunctionInfoTyped<T> (&functions)[N]) {
|
||||
constexpr void RegisterHandlers(const FunctionInfoTyped<T> (&functions)[N]) {
|
||||
RegisterHandlers(functions, N);
|
||||
}
|
||||
|
||||
@@ -170,13 +215,13 @@ protected:
|
||||
* overload in order to avoid needing to specify the array size.
|
||||
*/
|
||||
template <typename T = Self>
|
||||
void RegisterHandlers(const FunctionInfoTyped<T>* functions, std::size_t n) {
|
||||
constexpr void RegisterHandlers(const FunctionInfoTyped<T>* functions, std::size_t n) {
|
||||
RegisterHandlersBase(functions, n);
|
||||
}
|
||||
|
||||
/// Registers handlers in the service.
|
||||
template <typename T = Self, std::size_t N>
|
||||
void RegisterHandlersTipc(const FunctionInfoTyped<T> (&functions)[N]) {
|
||||
constexpr void RegisterHandlersTipc(const FunctionInfoTyped<T> (&functions)[N]) {
|
||||
RegisterHandlersTipc(functions, N);
|
||||
}
|
||||
|
||||
@@ -185,7 +230,7 @@ protected:
|
||||
* overload in order to avoid needing to specify the array size.
|
||||
*/
|
||||
template <typename T = Self>
|
||||
void RegisterHandlersTipc(const FunctionInfoTyped<T>* functions, std::size_t n) {
|
||||
constexpr void RegisterHandlersTipc(const FunctionInfoTyped<T>* functions, std::size_t n) {
|
||||
RegisterHandlersBaseTipc(functions, n);
|
||||
}
|
||||
|
||||
@@ -217,6 +262,9 @@ private:
|
||||
// Cast back up to our original types and call the member function
|
||||
(static_cast<Self*>(object)->*HandlerFnP<Self>(member))(ctx);
|
||||
}
|
||||
|
||||
::Common::unordered_map<u32, FunctionInfoBase> handlers;
|
||||
::Common::unordered_map<u32, FunctionInfoBase> handlers_tipc;
|
||||
};
|
||||
|
||||
} // namespace Service
|
||||
|
||||
Reference in New Issue
Block a user