ams: support building unit test programs on windows/linux/macos

This commit is contained in:
Michael Scire 2022-03-06 12:08:20 -08:00 committed by SciresM
parent 9a38be201a
commit 64a97576d0
756 changed files with 33359 additions and 9372 deletions

View file

@ -21,9 +21,11 @@ namespace ams::sf::cmif {
return this->ProcessMessageImpl(ctx, static_cast<DomainServiceObject *>(ctx.srv_obj)->GetServerDomain(), in_raw_data);
}
#if AMS_SF_MITM_SUPPORTED
Result DomainServiceObjectDispatchTable::ProcessMessageForMitm(ServiceDispatchContext &ctx, const cmif::PointerAndSize &in_raw_data) const {
return this->ProcessMessageForMitmImpl(ctx, static_cast<DomainServiceObject *>(ctx.srv_obj)->GetServerDomain(), in_raw_data);
}
#endif
Result DomainServiceObjectDispatchTable::ProcessMessageImpl(ServiceDispatchContext &ctx, ServerDomainBase *domain, const cmif::PointerAndSize &in_raw_data) const {
const CmifDomainInHeader *in_header = reinterpret_cast<const CmifDomainInHeader *>(in_raw_data.GetPointer());
@ -59,6 +61,7 @@ namespace ams::sf::cmif {
}
}
#if AMS_SF_MITM_SUPPORTED
Result DomainServiceObjectDispatchTable::ProcessMessageForMitmImpl(ServiceDispatchContext &ctx, ServerDomainBase *domain, const cmif::PointerAndSize &in_raw_data) const {
const CmifDomainInHeader *in_header = reinterpret_cast<const CmifDomainInHeader *>(in_raw_data.GetPointer());
R_UNLESS(in_raw_data.GetSize() >= sizeof(*in_header), sf::cmif::ResultInvalidHeaderSize());
@ -106,6 +109,7 @@ namespace ams::sf::cmif {
return sf::cmif::ResultInvalidInHeader();
}
}
#endif
Result DomainServiceObjectProcessor::PrepareForProcess(const ServiceDispatchContext &ctx, const ServerMessageRuntimeMetadata runtime_metadata) const {
/* Validate in object count. */

View file

@ -21,25 +21,36 @@ namespace ams::sf {
namespace {
ALWAYS_INLINE std::atomic<uintptr_t> *GetAtomicSfInlineContext(os::ThreadType *thread) {
static_assert(sizeof(thread->atomic_sf_inline_context) >= sizeof(std::atomic<uintptr_t>));
return reinterpret_cast<std::atomic<uintptr_t> *>(std::addressof(thread->atomic_sf_inline_context));
}
#if !defined(ATMOSPHERE_COMPILER_CLANG)
ALWAYS_INLINE util::AtomicRef<uintptr_t> GetAtomicSfInlineContext(os::ThreadType *thread = os::GetCurrentThread()) {
uintptr_t * const p = std::addressof(os::GetSdkInternalTlsArray(thread)->sf_inline_context);
ALWAYS_INLINE std::atomic<uintptr_t> *GetAtomicSfInlineContext() {
return GetAtomicSfInlineContext(os::GetCurrentThread());
return util::AtomicRef<uintptr_t>(*p);
}
#else
ALWAYS_INLINE util::Atomic<uintptr_t> &GetAtomicSfInlineContext(os::ThreadType *thread = os::GetCurrentThread()) {
uintptr_t * const p = std::addressof(os::GetSdkInternalTlsArray(thread)->sf_inline_context);
static_assert(sizeof(std::atomic<uintptr_t>) == sizeof(uintptr_t));
static_assert(sizeof(util::Atomic<uintptr_t>) == sizeof(std::atomic<uintptr_t>));
return *reinterpret_cast<util::Atomic<uintptr_t> *>(p);
}
#endif
ALWAYS_INLINE void OnSetInlineContext(os::ThreadType *thread) {
#if defined(ATMOSPHERE_OS_HORIZON)
/* Ensure that libnx receives the priority value. */
::fsSetPriority(static_cast<::FsPriority>(::ams::sf::GetFsInlineContext(thread)));
#else
AMS_UNUSED(thread);
#endif
}
}
InlineContext GetInlineContext() {
/* Get the context. */
uintptr_t thread_context = GetAtomicSfInlineContext()->load();
uintptr_t thread_context = GetAtomicSfInlineContext().Load();
/* Copy it out. */
InlineContext ctx;
@ -59,7 +70,7 @@ namespace ams::sf {
std::memcpy(std::addressof(new_context_value), std::addressof(ctx), sizeof(ctx));
/* Get the old context. */
uintptr_t old_context_value = GetAtomicSfInlineContext(cur_thread)->exchange(new_context_value);
uintptr_t old_context_value = GetAtomicSfInlineContext(cur_thread).Exchange(new_context_value);
/* Convert and copy it out. */
InlineContext old_ctx;
@ -71,21 +82,32 @@ namespace ams::sf {
namespace {
ALWAYS_INLINE std::atomic<u8> *GetAtomicFsInlineContext(os::ThreadType *thread) {
static_assert(sizeof(thread->atomic_sf_inline_context) >= sizeof(std::atomic<u8>));
return reinterpret_cast<std::atomic<u8> *>(std::addressof(thread->atomic_sf_inline_context));
#if !defined(ATMOSPHERE_COMPILER_CLANG)
ALWAYS_INLINE util::AtomicRef<u8> GetAtomicFsInlineContext(os::ThreadType *thread) {
uintptr_t * const p = std::addressof(os::GetSdkInternalTlsArray(thread)->sf_inline_context);
return util::AtomicRef<u8>(*reinterpret_cast<u8 *>(p));
}
#else
ALWAYS_INLINE util::Atomic<u8> &GetAtomicFsInlineContext(os::ThreadType *thread) {
uintptr_t * const p = std::addressof(os::GetSdkInternalTlsArray(thread)->sf_inline_context);
static_assert(sizeof(std::atomic<u8>) == sizeof(u8));
static_assert(sizeof(util::Atomic<u8>) == sizeof(std::atomic<u8>));
return *reinterpret_cast<util::Atomic<u8> *>(reinterpret_cast<u8 *>(p));
}
#endif
}
u8 GetFsInlineContext(os::ThreadType *thread) {
return GetAtomicFsInlineContext(thread)->load();
return GetAtomicFsInlineContext(thread).Load();
}
u8 SetFsInlineContext(os::ThreadType *thread, u8 ctx) {
ON_SCOPE_EXIT { cmif::OnSetInlineContext(thread); };
return GetAtomicFsInlineContext(thread)->exchange(ctx);
return GetAtomicFsInlineContext(thread).Exchange(ctx);
}
}

View file

@ -19,6 +19,13 @@ namespace ams::sf::cmif {
namespace {
constexpr inline u32 InHeaderMagic = util::FourCC<'S','F','C','I'>::Code;
constexpr inline u32 OutHeaderMagic = util::FourCC<'S','F','C','O'>::Code;
#if defined(ATMOSPHERE_OS_HORIZON)
static_assert(InHeaderMagic == CMIF_IN_HEADER_MAGIC);
static_assert(OutHeaderMagic == CMIF_OUT_HEADER_MAGIC);
#endif
ALWAYS_INLINE decltype(ServiceCommandMeta::handler) FindCommandHandlerByBinarySearch(const ServiceCommandMeta *entries, const size_t entry_count, const u32 cmd_id, const hos::Version hos_version) {
/* Binary search for the handler. */
ssize_t lo = 0;
@ -84,7 +91,7 @@ namespace ams::sf::cmif {
/* Parse the CMIF in header. */
const CmifInHeader *in_header = reinterpret_cast<const CmifInHeader *>(in_raw_data.GetPointer());
R_UNLESS(in_raw_data.GetSize() >= sizeof(*in_header), sf::cmif::ResultInvalidHeaderSize());
R_UNLESS(in_header->magic == CMIF_IN_HEADER_MAGIC && in_header->version <= max_cmif_version, sf::cmif::ResultInvalidInHeader());
R_UNLESS(in_header->magic == InHeaderMagic && in_header->version <= max_cmif_version, sf::cmif::ResultInvalidInHeader());
const cmif::PointerAndSize in_message_raw_data = cmif::PointerAndSize(in_raw_data.GetAddress() + sizeof(*in_header), in_raw_data.GetSize() - sizeof(*in_header));
const u32 cmd_id = in_header->command_id;
@ -108,11 +115,12 @@ namespace ams::sf::cmif {
}
/* Write output header to raw data. */
*out_header = CmifOutHeader{CMIF_OUT_HEADER_MAGIC, 0, command_result.GetValue(), 0};
*out_header = CmifOutHeader{OutHeaderMagic, 0, command_result.GetValue(), 0};
return ResultSuccess();
}
#if AMS_SF_MITM_SUPPORTED
Result impl::ServiceDispatchTableBase::ProcessMessageForMitmImpl(ServiceDispatchContext &ctx, const cmif::PointerAndSize &in_raw_data, const ServiceCommandMeta *entries, const size_t entry_count) const {
/* Get versioning info. */
const auto hos_version = hos::GetVersion();
@ -121,7 +129,7 @@ namespace ams::sf::cmif {
/* Parse the CMIF in header. */
const CmifInHeader *in_header = reinterpret_cast<const CmifInHeader *>(in_raw_data.GetPointer());
R_UNLESS(in_raw_data.GetSize() >= sizeof(*in_header), sf::cmif::ResultInvalidHeaderSize());
R_UNLESS(in_header->magic == CMIF_IN_HEADER_MAGIC && in_header->version <= max_cmif_version, sf::cmif::ResultInvalidInHeader());
R_UNLESS(in_header->magic == InHeaderMagic && in_header->version <= max_cmif_version, sf::cmif::ResultInvalidInHeader());
const cmif::PointerAndSize in_message_raw_data = cmif::PointerAndSize(in_raw_data.GetAddress() + sizeof(*in_header), in_raw_data.GetSize() - sizeof(*in_header));
const u32 cmd_id = in_header->command_id;
@ -154,9 +162,10 @@ namespace ams::sf::cmif {
}
/* Write output header to raw data. */
*out_header = CmifOutHeader{CMIF_OUT_HEADER_MAGIC, 0, command_result.GetValue(), 0};
*out_header = CmifOutHeader{OutHeaderMagic, 0, command_result.GetValue(), 0};
return ResultSuccess();
}
#endif
}

View file

@ -21,7 +21,7 @@ namespace ams::sf::hipc {
ALWAYS_INLINE Result ReceiveImpl(os::NativeHandle session_handle, void *message_buf, size_t message_buf_size) {
s32 unused_index;
if (message_buf == svc::GetThreadLocalRegion()->message_buffer) {
if (message_buf == hipc::GetMessageBufferOnTls()) {
/* Consider: AMS_ABORT_UNLESS(message_buf_size == TlsMessageBufferSize); */
return svc::ReplyAndReceive(&unused_index, &session_handle, 1, svc::InvalidHandle, std::numeric_limits<u64>::max());
} else {
@ -31,7 +31,7 @@ namespace ams::sf::hipc {
ALWAYS_INLINE Result ReplyImpl(os::NativeHandle session_handle, void *message_buf, size_t message_buf_size) {
s32 unused_index;
if (message_buf == svc::GetThreadLocalRegion()->message_buffer) {
if (message_buf == hipc::GetMessageBufferOnTls()) {
/* Consider: AMS_ABORT_UNLESS(message_buf_size == TlsMessageBufferSize); */
return svc::ReplyAndReceive(&unused_index, &session_handle, 0, session_handle, 0);
} else {

View file

@ -16,6 +16,8 @@
#include <stratosphere.hpp>
#include "sf_hipc_mitm_query_api.hpp"
#if AMS_SF_MITM_SUPPORTED
#define AMS_SF_HIPC_IMPL_I_MITM_QUERY_SERVICE_INTERFACE_INFO(C, H) \
AMS_SF_METHOD_INFO(C, H, 65000, void, ShouldMitm, (sf::Out<bool> out, const sm::MitmProcessInfo &client_info), (out, client_info))
@ -74,3 +76,5 @@ namespace ams::sf::hipc::impl {
}
}
#endif

View file

@ -18,6 +18,8 @@
namespace ams::sf::hipc::impl {
#if AMS_SF_MITM_SUPPORTED
void RegisterMitmQueryHandle(os::NativeHandle query_handle, ServerManagerBase::MitmQueryFunction query_func);
#endif
}

View file

@ -32,7 +32,9 @@ namespace ams::sf::hipc {
private:
ServerDomainSessionManager *m_manager;
ServerSession *m_session;
#if AMS_SF_MITM_SUPPORTED
const bool m_is_mitm_session;
#endif
private:
Result CloneCurrentObjectImpl(sf::OutMoveHandle &out_client_handle, ServerSessionManager *tagged_manager) {
/* Clone the object. */
@ -44,8 +46,11 @@ namespace ams::sf::hipc {
R_ABORT_UNLESS(hipc::CreateSession(std::addressof(server_handle), std::addressof(client_handle)));
/* Register with manager. */
#if AMS_SF_MITM_SUPPORTED
if (!m_is_mitm_session) {
#endif
R_ABORT_UNLESS(tagged_manager->RegisterSession(server_handle, std::move(clone)));
#if AMS_SF_MITM_SUPPORTED
} else {
/* Check that we can create a mitm session. */
AMS_ABORT_UNLESS(ServerManagerBase::CanAnyManageMitmServers());
@ -55,15 +60,18 @@ namespace ams::sf::hipc {
R_ABORT_UNLESS(serviceClone(util::GetReference(m_session->m_forward_service).get(), new_forward_service.get()));
R_ABORT_UNLESS(tagged_manager->RegisterMitmSession(server_handle, std::move(clone), std::move(new_forward_service)));
}
#endif
/* Set output client handle. */
out_client_handle.SetValue(client_handle, false);
return ResultSuccess();
}
public:
explicit HipcManagerImpl(ServerDomainSessionManager *m, ServerSession *s) : m_manager(m), m_session(s), m_is_mitm_session(s->IsMitmSession()) {
/* ... */
}
#if AMS_SF_MITM_SUPPORTED
explicit HipcManagerImpl(ServerDomainSessionManager *m, ServerSession *s) : m_manager(m), m_session(s), m_is_mitm_session(s->IsMitmSession()) { /* ... */ }
#else
explicit HipcManagerImpl(ServerDomainSessionManager *m, ServerSession *s) : m_manager(m), m_session(s) { /* ... */ }
#endif
Result ConvertCurrentObjectToDomain(sf::Out<cmif::DomainObjectId> out) {
/* Allocate a domain. */
@ -72,6 +80,7 @@ namespace ams::sf::hipc {
/* Set up the new domain object. */
cmif::DomainObjectId object_id = cmif::InvalidDomainObjectId;
#if AMS_SF_MITM_SUPPORTED
if (m_is_mitm_session) {
/* Check that we can create a mitm session. */
AMS_ABORT_UNLESS(ServerManagerBase::CanAnyManageMitmServers());
@ -93,6 +102,9 @@ namespace ams::sf::hipc {
/* Set the new object holder. */
m_session->m_srv_obj_holder = cmif::ServiceObjectHolder(std::move(cmif_domain));
} else {
#else
{
#endif
/* Make a new shared pointer to manage the allocated domain. */
SharedPointer<cmif::DomainServiceObject> cmif_domain(domain, false);
@ -119,6 +131,7 @@ namespace ams::sf::hipc {
/* Get domain object. */
auto &&object = domain->GetObject(object_id);
#if AMS_SF_MITM_SUPPORTED
if (!object) {
R_UNLESS(m_is_mitm_session, sf::hipc::ResultDomainObjectNotFound());
@ -131,8 +144,15 @@ namespace ams::sf::hipc {
out.SetValue(handle, false);
return ResultSuccess();
}
#else
R_UNLESS(!!(object), sf::hipc::ResultDomainObjectNotFound());
#endif
#if AMS_SF_MITM_SUPPORTED
if (!m_is_mitm_session || (ServerManagerBase::CanAnyManageMitmServers() && object_id.value != serviceGetObjectId(util::GetReference(m_session->m_forward_service).get()))) {
#else
{
#endif
/* Create new session handles. */
os::NativeHandle server_handle, client_handle;
R_ABORT_UNLESS(hipc::CreateSession(std::addressof(server_handle), std::addressof(client_handle)));
@ -142,6 +162,7 @@ namespace ams::sf::hipc {
/* Set output client handle. */
out.SetValue(client_handle, false);
#if AMS_SF_MITM_SUPPORTED
} else {
/* Check that we can create a mitm session. */
AMS_ABORT_UNLESS(ServerManagerBase::CanAnyManageMitmServers());
@ -161,6 +182,7 @@ namespace ams::sf::hipc {
/* Set output client handle. */
out.SetValue(client_handle, false);
#endif
}
return ResultSuccess();

View file

@ -18,6 +18,7 @@
namespace ams::sf::hipc {
#if AMS_SF_MITM_SUPPORTED
Result ServerManagerBase::InstallMitmServerImpl(os::NativeHandle *out_port_handle, sm::ServiceName service_name, ServerManagerBase::MitmQueryFunction query_func) {
/* Install the Mitm. */
os::NativeHandle query_handle;
@ -31,6 +32,7 @@ namespace ams::sf::hipc {
return ResultSuccess();
}
#endif
void ServerManagerBase::RegisterServerSessionToWait(ServerSession *session) {
session->m_has_received = false;
@ -79,8 +81,10 @@ namespace ams::sf::hipc {
void ServerManagerBase::AddUserMultiWaitHolder(os::MultiWaitHolderType *holder) {
const auto user_data_tag = static_cast<UserDataTag>(os::GetMultiWaitHolderUserData(holder));
AMS_ABORT_UNLESS(user_data_tag != UserDataTag::Server);
AMS_ABORT_UNLESS(user_data_tag != UserDataTag::MitmServer);
AMS_ABORT_UNLESS(user_data_tag != UserDataTag::Session);
#if AMS_SF_MITM_SUPPORTED
AMS_ABORT_UNLESS(user_data_tag != UserDataTag::MitmServer);
#endif
this->LinkToDeferredList(holder);
}
@ -98,6 +102,7 @@ namespace ams::sf::hipc {
}
}
#if AMS_SF_MITM_SUPPORTED
Result ServerManagerBase::ProcessForMitmServer(os::MultiWaitHolderType *holder) {
AMS_ABORT_UNLESS(static_cast<UserDataTag>(os::GetMultiWaitHolderUserData(holder)) == UserDataTag::MitmServer);
@ -107,13 +112,14 @@ namespace ams::sf::hipc {
/* Create resources for new session. */
return this->OnNeedsToAccept(server->m_index, server);
}
#endif
Result ServerManagerBase::ProcessForSession(os::MultiWaitHolderType *holder) {
AMS_ABORT_UNLESS(static_cast<UserDataTag>(os::GetMultiWaitHolderUserData(holder)) == UserDataTag::Session);
ServerSession *session = static_cast<ServerSession *>(holder);
cmif::PointerAndSize tls_message(svc::GetThreadLocalRegion()->message_buffer, hipc::TlsMessageBufferSize);
cmif::PointerAndSize tls_message(hipc::GetMessageBufferOnTls(), hipc::TlsMessageBufferSize);
if (this->CanDeferInvokeRequest()) {
const cmif::PointerAndSize &saved_message = session->m_saved_message;
AMS_ABORT_UNLESS(tls_message.GetSize() == saved_message.GetSize());
@ -136,12 +142,14 @@ namespace ams::sf::hipc {
R_TRY(this->ReceiveRequest(session, tls_message));
session->m_has_received = true;
#if AMS_SF_MITM_SUPPORTED
if (this->CanManageMitmServers()) {
const cmif::PointerAndSize &saved_message = session->m_saved_message;
AMS_ABORT_UNLESS(tls_message.GetSize() == saved_message.GetSize());
std::memcpy(saved_message.GetPointer(), tls_message.GetPointer(), tls_message.GetSize());
}
#endif
}
R_TRY_CATCH(this->ProcessRequest(session, tls_message)) {
@ -157,11 +165,13 @@ namespace ams::sf::hipc {
switch (static_cast<UserDataTag>(os::GetMultiWaitHolderUserData(holder))) {
case UserDataTag::Server:
return this->ProcessForServer(holder);
case UserDataTag::Session:
return this->ProcessForSession(holder);
#if AMS_SF_MITM_SUPPORTED
case UserDataTag::MitmServer:
AMS_ABORT_UNLESS(this->CanManageMitmServers());
return this->ProcessForMitmServer(holder);
case UserDataTag::Session:
return this->ProcessForSession(holder);
#endif
AMS_UNREACHABLE_DEFAULT_CASE();
}
}

View file

@ -19,6 +19,7 @@ namespace ams::sf::hipc {
namespace {
#if AMS_SF_MITM_SUPPORTED
constexpr inline void PreProcessCommandBufferForMitm(const cmif::ServiceDispatchContext &ctx, const cmif::PointerAndSize &pointer_buffer, uintptr_t cmd_buffer) {
/* TODO: Less gross method of editing command buffer? */
if (ctx.request.meta.send_pid) {
@ -36,9 +37,11 @@ namespace ams::sf::hipc {
*reinterpret_cast<HipcRecvListEntry *>(cmd_buffer + old_recv_list_offset) = hipcMakeRecvStatic(pointer_buffer.GetPointer(), pointer_buffer.GetSize());
}
}
#endif
}
#if AMS_SF_MITM_SUPPORTED
Result ServerSession::ForwardRequest(const cmif::ServiceDispatchContext &ctx) const {
AMS_ABORT_UNLESS(ServerManagerBase::CanAnyManageMitmServers());
AMS_ABORT_UNLESS(this->IsMitmSession());
@ -48,7 +51,7 @@ namespace ams::sf::hipc {
AMS_ABORT_UNLESS(m_saved_message.GetSize() == TlsMessageBufferSize);
/* Get TLS message buffer. */
u32 * const message_buffer = svc::GetThreadLocalRegion()->message_buffer;
u32 * const message_buffer = static_cast<u32 *>(hipc::GetMessageBufferOnTls());
/* Copy saved TLS in. */
std::memcpy(message_buffer, m_saved_message.GetPointer(), m_saved_message.GetSize());
@ -72,6 +75,7 @@ namespace ams::sf::hipc {
return ResultSuccess();
}
#endif
void ServerSessionManager::DestroySession(ServerSession *session) {
/* Destroy object. */
@ -104,7 +108,12 @@ namespace ams::sf::hipc {
Result ServerSessionManager::AcceptSessionImpl(ServerSession *session_memory, os::NativeHandle port_handle, cmif::ServiceObjectHolder &&obj) {
/* Create session handle. */
os::NativeHandle session_handle;
#if defined(ATMOSPHERE_OS_HORIZON)
R_TRY(svc::AcceptSession(std::addressof(session_handle), port_handle));
#else
AMS_UNUSED(port_handle);
AMS_ABORT("TODO");
#endif
auto session_guard = SCOPE_GUARD { os::CloseNativeHandle(session_handle); };
@ -115,6 +124,7 @@ namespace ams::sf::hipc {
return ResultSuccess();
}
#if AMS_SF_MITM_SUPPORTED
Result ServerSessionManager::RegisterMitmSessionImpl(ServerSession *session_memory, os::NativeHandle mitm_session_handle, cmif::ServiceObjectHolder &&obj, std::shared_ptr<::Service> &&fsrv) {
AMS_ABORT_UNLESS(ServerManagerBase::CanAnyManageMitmServers());
@ -149,6 +159,7 @@ namespace ams::sf::hipc {
session_guard.Cancel();
return ResultSuccess();
}
#endif
Result ServerSessionManager::RegisterSession(os::NativeHandle session_handle, cmif::ServiceObjectHolder &&obj) {
/* We don't actually care about what happens to the session. It'll get linked. */
@ -162,6 +173,7 @@ namespace ams::sf::hipc {
return this->AcceptSession(std::addressof(session_ptr), port_handle, std::forward<cmif::ServiceObjectHolder>(obj));
}
#if AMS_SF_MITM_SUPPORTED
Result ServerSessionManager::RegisterMitmSession(os::NativeHandle mitm_session_handle, cmif::ServiceObjectHolder &&obj, std::shared_ptr<::Service> &&fsrv) {
/* We don't actually care about what happens to the session. It'll get linked. */
ServerSession *session_ptr = nullptr;
@ -173,6 +185,7 @@ namespace ams::sf::hipc {
ServerSession *session_ptr = nullptr;
return this->AcceptMitmSession(std::addressof(session_ptr), mitm_port_handle, std::forward<cmif::ServiceObjectHolder>(obj), std::forward<std::shared_ptr<::Service>>(fsrv));
}
#endif
Result ServerSessionManager::ReceiveRequestImpl(ServerSession *session, const cmif::PointerAndSize &message) {
const cmif::PointerAndSize &pointer_buffer = session->m_pointer_buffer;
@ -207,7 +220,7 @@ namespace ams::sf::hipc {
namespace {
constexpr ALWAYS_INLINE u32 GetCmifCommandType(const cmif::PointerAndSize &message) {
ALWAYS_INLINE u32 GetCmifCommandType(const cmif::PointerAndSize &message) {
HipcHeader hdr = {};
__builtin_memcpy(std::addressof(hdr), message.GetPointer(), sizeof(hdr));
return hdr.type;

View file

@ -89,7 +89,7 @@ namespace ams::sf {
return DefaultDeallocate(buffer, size, alignment);
}
virtual bool IsEqualImpl(const MemoryResource &resource) const {
virtual bool IsEqualImpl(const MemoryResource &resource) const override {
return this == std::addressof(resource);
}
};