mirror of
https://github.com/Atmosphere-NX/Atmosphere.git
synced 2025-04-22 04:24:48 +00:00
sf: update ams.mitm for new format
This commit is contained in:
parent
4485a46e53
commit
e5a233efa2
27 changed files with 285 additions and 292 deletions
|
@ -55,6 +55,7 @@
|
|||
#include <stratosphere/map.hpp>
|
||||
#include <stratosphere/ncm.hpp>
|
||||
#include <stratosphere/nim.hpp>
|
||||
#include <stratosphere/ns.hpp>
|
||||
#include <stratosphere/patcher.hpp>
|
||||
#include <stratosphere/pgl.hpp>
|
||||
#include <stratosphere/psc.hpp>
|
||||
|
|
19
libraries/libstratosphere/include/stratosphere/ns.hpp
Normal file
19
libraries/libstratosphere/include/stratosphere/ns.hpp
Normal file
|
@ -0,0 +1,19 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020 Atmosphère-NX
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify it
|
||||
* under the terms and conditions of the GNU General Public License,
|
||||
* version 2, as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
|
||||
* more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
|
||||
#include <stratosphere/ns/impl/ns_i_async.hpp>
|
|
@ -0,0 +1,31 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020 Atmosphère-NX
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify it
|
||||
* under the terms and conditions of the GNU General Public License,
|
||||
* version 2, as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
|
||||
* more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
#pragma once
|
||||
#include <vapours.hpp>
|
||||
#include <stratosphere/err/err_error_context.hpp>
|
||||
#include <stratosphere/sf.hpp>
|
||||
|
||||
namespace ams::ns::impl {
|
||||
|
||||
#define AMS_NS_I_ASYNC_RESULT_INTERFACE_INFO(C, H) \
|
||||
AMS_SF_METHOD_INFO(C, H, 0, Result, Get, ()) \
|
||||
AMS_SF_METHOD_INFO(C, H, 1, Result, Cancel, ()) \
|
||||
AMS_SF_METHOD_INFO(C, H, 2, Result, GetErrorContext, (::ams::sf::Out<::ams::err::ErrorContext> out))
|
||||
|
||||
AMS_SF_DEFINE_INTERFACE(IAsyncResult, AMS_NS_I_ASYNC_RESULT_INTERFACE_INFO)
|
||||
|
||||
}
|
|
@ -164,7 +164,7 @@ namespace ams::sf::hipc {
|
|||
}
|
||||
|
||||
template<typename Interface, typename ServiceImpl>
|
||||
static constexpr inline std::shared_ptr<Service> MakeSharedMitm(std::shared_ptr<::Service> &&s, const sm::MitmProcessInfo &client_info) {
|
||||
static constexpr inline std::shared_ptr<Interface> MakeSharedMitm(std::shared_ptr<::Service> &&s, const sm::MitmProcessInfo &client_info) {
|
||||
return sf::MakeShared<Interface, ServiceImpl>(std::forward<std::shared_ptr<::Service>>(s), client_info);
|
||||
}
|
||||
|
||||
|
@ -212,7 +212,8 @@ namespace ams::sf::hipc {
|
|||
return ResultSuccess();
|
||||
}
|
||||
|
||||
template<typename Interface, typename ServiceImpl, auto MakeShared = MakeSharedMitm<Interface, ServiceImpl>> requires (sf::IsMitmServiceObject<Interface>)
|
||||
template<typename Interface, typename ServiceImpl, auto MakeShared = MakeSharedMitm<Interface, ServiceImpl>>
|
||||
requires (sf::IsMitmServiceObject<Interface> && sf::IsMitmServiceImpl<ServiceImpl>)
|
||||
Result RegisterMitmServer(sm::ServiceName service_name) {
|
||||
/* Install mitm service. */
|
||||
Handle port_handle;
|
||||
|
|
|
@ -180,7 +180,9 @@ namespace ams::sf::impl {
|
|||
public: \
|
||||
CMD_MACRO(CLASSNAME, AMS_SF_IMPL_DECLARE_INTERFACE_FUNCTION) \
|
||||
private: \
|
||||
template<typename S, typename T> requires (std::same_as<CLASSNAME, S> && !std::same_as<CLASSNAME, T>&& Is##CLASSNAME<T>) \
|
||||
template<typename S, typename T> \
|
||||
requires ((std::same_as<CLASSNAME, S> && !std::same_as<CLASSNAME, T>&& Is##CLASSNAME<T>) && \
|
||||
(::ams::sf::IsMitmServiceObject<S> == ::ams::sf::IsMitmServiceImpl<T>)) \
|
||||
struct ImplGenerator { \
|
||||
public: \
|
||||
class ImplHolder : public S { \
|
||||
|
@ -195,6 +197,9 @@ namespace ams::sf::impl {
|
|||
} \
|
||||
ALWAYS_INLINE T &GetImpl() { return this->impl; } \
|
||||
ALWAYS_INLINE const T &GetImpl() const { return this->impl; } \
|
||||
\
|
||||
template<typename U = S> requires ::ams::sf::IsMitmServiceObject<S> && std::same_as<U, S> \
|
||||
static ALWAYS_INLINE bool ShouldMitm(os::ProcessId p, ncm::ProgramId r) { return T::ShouldMitm(p, r); } \
|
||||
private: \
|
||||
CMD_MACRO(CLASSNAME, AMS_SF_IMPL_DECLARE_INTERFACE_FUNCTION_INVOKER) \
|
||||
public: \
|
||||
|
|
|
@ -29,22 +29,26 @@ namespace ams::sf {
|
|||
concept IsServiceObject = std::derived_from<T, IServiceObject>;
|
||||
|
||||
class IMitmServiceObject : public IServiceObject {
|
||||
public:
|
||||
virtual ~IMitmServiceObject() { /* ... */ }
|
||||
};
|
||||
|
||||
class MitmServiceImplBase {
|
||||
protected:
|
||||
std::shared_ptr<::Service> forward_service;
|
||||
sm::MitmProcessInfo client_info;
|
||||
public:
|
||||
IMitmServiceObject(std::shared_ptr<::Service> &&s, const sm::MitmProcessInfo &c) : forward_service(std::move(s)), client_info(c) { /* ... */ }
|
||||
|
||||
virtual ~IMitmServiceObject() { /* ... */ }
|
||||
|
||||
static bool ShouldMitm(os::ProcessId process_id, ncm::ProgramId program_id);
|
||||
MitmServiceImplBase(std::shared_ptr<::Service> &&s, const sm::MitmProcessInfo &c) : forward_service(std::move(s)), client_info(c) { /* ... */ }
|
||||
};
|
||||
|
||||
template<typename T>
|
||||
concept IsMitmServiceObject = IsServiceObject<T> && std::derived_from<T, IMitmServiceObject>;
|
||||
|
||||
/* Utility. */
|
||||
#define AMS_SF_MITM_SERVICE_OBJECT_CTOR(cls) cls(std::shared_ptr<::Service> &&s, const sm::MitmProcessInfo &c) : ::ams::sf::IMitmServiceObject(std::forward<std::shared_ptr<::Service>>(s), c)
|
||||
template<typename T>
|
||||
concept IsMitmServiceImpl = requires (std::shared_ptr<::Service> &&s, const sm::MitmProcessInfo &c) {
|
||||
{ T(std::forward<std::shared_ptr<::Service>>(s), c) };
|
||||
{ T::ShouldMitm(c) } -> std::same_as<bool>;
|
||||
};
|
||||
|
||||
template<typename Interface, typename Impl, typename... Arguments> requires std::constructible_from<Impl, Arguments...>
|
||||
constexpr ALWAYS_INLINE std::shared_ptr<typename Interface::ImplHolder<Impl>> MakeShared(Arguments &&... args) {
|
||||
|
|
|
@ -37,7 +37,7 @@ namespace ams::mitm::bpc_ams {
|
|||
{
|
||||
Handle bpcams_h;
|
||||
R_ABORT_UNLESS(svcManageNamedPort(&bpcams_h, AtmosphereServiceName.name, AtmosphereMaxSessions));
|
||||
g_server_manager.RegisterServer<bpc::AtmosphereService>(bpcams_h);
|
||||
g_server_manager.RegisterServer<bpc::impl::IAtmosphereInterface, bpc::AtmosphereService>(bpcams_h);
|
||||
}
|
||||
|
||||
/* Loop forever, servicing our services. */
|
||||
|
|
|
@ -18,20 +18,21 @@
|
|||
|
||||
namespace ams::mitm::bpc {
|
||||
|
||||
class AtmosphereService final : public sf::IServiceObject {
|
||||
private:
|
||||
enum class CommandId {
|
||||
RebootToFatalError = 65000,
|
||||
SetRebootPayload = 65001,
|
||||
};
|
||||
private:
|
||||
namespace impl {
|
||||
|
||||
#define AMS_BPC_MITM_ATMOSPHERE_INTERFACE_INTERFACE_INFO(C, H) \
|
||||
AMS_SF_METHOD_INFO(C, H, 65000, void, RebootToFatalError, (const ams::FatalErrorContext &ctx)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 65001, void, SetRebootPayload, (const ams::sf::InBuffer &payload))
|
||||
|
||||
AMS_SF_DEFINE_INTERFACE(IAtmosphereInterface, AMS_BPC_MITM_ATMOSPHERE_INTERFACE_INTERFACE_INFO)
|
||||
|
||||
}
|
||||
|
||||
class AtmosphereService final {
|
||||
public:
|
||||
void RebootToFatalError(const ams::FatalErrorContext &ctx);
|
||||
void SetRebootPayload(const ams::sf::InBuffer &payload);
|
||||
public:
|
||||
DEFINE_SERVICE_DISPATCH_TABLE {
|
||||
MAKE_SERVICE_COMMAND_META(RebootToFatalError),
|
||||
MAKE_SERVICE_COMMAND_META(SetRebootPayload),
|
||||
};
|
||||
};
|
||||
static_assert(impl::IsIAtmosphereInterface<AtmosphereService>);
|
||||
|
||||
}
|
||||
|
|
|
@ -18,12 +18,19 @@
|
|||
|
||||
namespace ams::mitm::bpc {
|
||||
|
||||
class BpcMitmService : public sf::IMitmServiceObject {
|
||||
private:
|
||||
enum class CommandId {
|
||||
ShutdownSystem = 0,
|
||||
RebootSystem = 1,
|
||||
};
|
||||
namespace impl {
|
||||
|
||||
#define AMS_BPC_MITM_INTERFACE_INFO(C, H) \
|
||||
AMS_SF_METHOD_INFO(C, H, 0, Result, ShutdownSystem, ()) \
|
||||
AMS_SF_METHOD_INFO(C, H, 1, Result, RebootSystem, ())
|
||||
|
||||
AMS_SF_DEFINE_MITM_INTERFACE(IBpcMitmInterface, AMS_BPC_MITM_INTERFACE_INFO)
|
||||
|
||||
}
|
||||
|
||||
class BpcMitmService : public sf::MitmServiceImplBase {
|
||||
public:
|
||||
using MitmServiceImplBase::MitmServiceImplBase;
|
||||
public:
|
||||
static bool ShouldMitm(const sm::MitmProcessInfo &client_info) {
|
||||
/* We will mitm:
|
||||
|
@ -36,16 +43,10 @@ namespace ams::mitm::bpc {
|
|||
client_info.override_status.IsHbl();
|
||||
}
|
||||
public:
|
||||
SF_MITM_SERVICE_OBJECT_CTOR(BpcMitmService) { /* ... */ }
|
||||
protected:
|
||||
/* Overridden commands. */
|
||||
Result ShutdownSystem();
|
||||
Result RebootSystem();
|
||||
public:
|
||||
DEFINE_SERVICE_DISPATCH_TABLE {
|
||||
MAKE_SERVICE_COMMAND_META(ShutdownSystem),
|
||||
MAKE_SERVICE_COMMAND_META(RebootSystem),
|
||||
};
|
||||
};
|
||||
static_assert(impl::IsIBpcMitmInterface<BpcMitmService>);
|
||||
|
||||
}
|
||||
|
|
|
@ -39,7 +39,7 @@ namespace ams::mitm::bpc {
|
|||
|
||||
/* Create bpc mitm. */
|
||||
const sm::ServiceName service_name = (hos::GetVersion() >= hos::Version_2_0_0) ? MitmServiceName : DeprecatedMitmServiceName;
|
||||
R_ABORT_UNLESS(g_server_manager.RegisterMitmServer<BpcMitmService>(service_name));
|
||||
R_ABORT_UNLESS((g_server_manager.RegisterMitmServer<impl::IBpcMitmInterface, BpcMitmService>(service_name)));
|
||||
|
||||
/* Loop forever, servicing our services. */
|
||||
g_server_manager.LoopProcess();
|
||||
|
|
|
@ -35,9 +35,9 @@ namespace ams::mitm::fs {
|
|||
|
||||
os::Mutex g_data_storage_lock(false);
|
||||
os::Mutex g_storage_cache_lock(false);
|
||||
std::unordered_map<u64, std::weak_ptr<IStorageInterface>> g_storage_cache;
|
||||
std::unordered_map<u64, std::weak_ptr<ams::fssrv::sf::IStorage>> g_storage_cache;
|
||||
|
||||
std::shared_ptr<IStorageInterface> GetStorageCacheEntry(ncm::ProgramId program_id) {
|
||||
std::shared_ptr<ams::fssrv::sf::IStorage> GetStorageCacheEntry(ncm::ProgramId program_id) {
|
||||
std::scoped_lock lk(g_storage_cache_lock);
|
||||
|
||||
auto it = g_storage_cache.find(static_cast<u64>(program_id));
|
||||
|
@ -48,7 +48,7 @@ namespace ams::mitm::fs {
|
|||
return it->second.lock();
|
||||
}
|
||||
|
||||
void SetStorageCacheEntry(ncm::ProgramId program_id, std::shared_ptr<IStorageInterface> *new_intf) {
|
||||
void SetStorageCacheEntry(ncm::ProgramId program_id, std::shared_ptr<ams::fssrv::sf::IStorage> *new_intf) {
|
||||
std::scoped_lock lk(g_storage_cache_lock);
|
||||
|
||||
auto it = g_storage_cache.find(static_cast<u64>(program_id));
|
||||
|
@ -69,7 +69,17 @@ namespace ams::mitm::fs {
|
|||
return (tmp != 0);
|
||||
}
|
||||
|
||||
Result OpenHblWebContentFileSystem(sf::Out<std::shared_ptr<IFileSystemInterface>> &out, ncm::ProgramId client_program_id, ncm::ProgramId program_id, FsFileSystemType filesystem_type) {
|
||||
template<typename... Arguments>
|
||||
constexpr ALWAYS_INLINE auto MakeSharedFileSystem(Arguments &&... args) {
|
||||
return sf::MakeShared<ams::fssrv::sf::IFileSystem, ams::fssrv::impl::FileSystemInterfaceAdapter>(std::forward<Arguments>(args)...);
|
||||
}
|
||||
|
||||
template<typename... Arguments>
|
||||
constexpr ALWAYS_INLINE auto MakeSharedStorage(Arguments &&... args) {
|
||||
return sf::MakeShared<ams::fssrv::sf::IStorage, ams::fssrv::impl::StorageInterfaceAdapter>(std::forward<Arguments>(args)...);
|
||||
}
|
||||
|
||||
Result OpenHblWebContentFileSystem(sf::Out<std::shared_ptr<ams::fssrv::sf::IFileSystem>> &out, ncm::ProgramId client_program_id, ncm::ProgramId program_id, FsFileSystemType filesystem_type) {
|
||||
/* Verify eligibility. */
|
||||
bool is_hbl;
|
||||
R_UNLESS(R_SUCCEEDED(pm::info::IsHblProgramId(&is_hbl, program_id)), sm::mitm::ResultShouldForwardToSession());
|
||||
|
@ -88,11 +98,11 @@ namespace ams::mitm::fs {
|
|||
const sf::cmif::DomainObjectId target_object_id{serviceGetObjectId(&sd_fs.s)};
|
||||
std::unique_ptr<fs::fsa::IFileSystem> sd_ifs = std::make_unique<fs::RemoteFileSystem>(sd_fs);
|
||||
|
||||
out.SetValue(std::make_shared<IFileSystemInterface>(std::make_shared<fs::ReadOnlyFileSystem>(std::make_unique<fssystem::SubDirectoryFileSystem>(std::move(sd_ifs), AtmosphereHblWebContentDir)), false), target_object_id);
|
||||
out.SetValue(MakeSharedFileSystem(std::make_shared<fs::ReadOnlyFileSystem>(std::make_unique<fssystem::SubDirectoryFileSystem>(std::move(sd_ifs), AtmosphereHblWebContentDir)), false), target_object_id);
|
||||
return ResultSuccess();
|
||||
}
|
||||
|
||||
Result OpenProgramSpecificWebContentFileSystem(sf::Out<std::shared_ptr<IFileSystemInterface>> &out, ncm::ProgramId client_program_id, ncm::ProgramId program_id, FsFileSystemType filesystem_type, Service *fwd, const fssrv::sf::Path *path, bool with_id) {
|
||||
Result OpenProgramSpecificWebContentFileSystem(sf::Out<std::shared_ptr<ams::fssrv::sf::IFileSystem>> &out, ncm::ProgramId client_program_id, ncm::ProgramId program_id, FsFileSystemType filesystem_type, Service *fwd, const fssrv::sf::Path *path, bool with_id) {
|
||||
/* Directory must exist. */
|
||||
{
|
||||
FsDir d;
|
||||
|
@ -132,13 +142,13 @@ namespace ams::mitm::fs {
|
|||
new_fs = std::make_shared<fs::ReadOnlyFileSystem>(std::move(subdir_fs));
|
||||
}
|
||||
|
||||
out.SetValue(std::make_shared<IFileSystemInterface>(std::move(new_fs), false), target_object_id);
|
||||
out.SetValue(MakeSharedFileSystem(std::move(new_fs), false), target_object_id);
|
||||
}
|
||||
|
||||
return ResultSuccess();
|
||||
}
|
||||
|
||||
Result OpenWebContentFileSystem(sf::Out<std::shared_ptr<IFileSystemInterface>> &out, ncm::ProgramId client_program_id, ncm::ProgramId program_id, FsFileSystemType filesystem_type, Service *fwd, const fssrv::sf::Path *path, bool with_id, bool try_program_specific) {
|
||||
Result OpenWebContentFileSystem(sf::Out<std::shared_ptr<ams::fssrv::sf::IFileSystem>> &out, ncm::ProgramId client_program_id, ncm::ProgramId program_id, FsFileSystemType filesystem_type, Service *fwd, const fssrv::sf::Path *path, bool with_id, bool try_program_specific) {
|
||||
/* Check first that we're a web applet opening web content. */
|
||||
R_UNLESS(ncm::IsWebAppletId(client_program_id), sm::mitm::ResultShouldForwardToSession());
|
||||
R_UNLESS(filesystem_type == FsFileSystemType_ContentManual, sm::mitm::ResultShouldForwardToSession());
|
||||
|
@ -155,15 +165,15 @@ namespace ams::mitm::fs {
|
|||
|
||||
}
|
||||
|
||||
Result FsMitmService::OpenFileSystemWithPatch(sf::Out<std::shared_ptr<IFileSystemInterface>> out, ncm::ProgramId program_id, u32 _filesystem_type) {
|
||||
Result FsMitmService::OpenFileSystemWithPatch(sf::Out<std::shared_ptr<ams::fssrv::sf::IFileSystem>> out, ncm::ProgramId program_id, u32 _filesystem_type) {
|
||||
return OpenWebContentFileSystem(out, this->client_info.program_id, program_id, static_cast<FsFileSystemType>(_filesystem_type), this->forward_service.get(), nullptr, false, this->client_info.override_status.IsProgramSpecific());
|
||||
}
|
||||
|
||||
Result FsMitmService::OpenFileSystemWithId(sf::Out<std::shared_ptr<IFileSystemInterface>> out, const fssrv::sf::Path &path, ncm::ProgramId program_id, u32 _filesystem_type) {
|
||||
Result FsMitmService::OpenFileSystemWithId(sf::Out<std::shared_ptr<ams::fssrv::sf::IFileSystem>> out, const fssrv::sf::Path &path, ncm::ProgramId program_id, u32 _filesystem_type) {
|
||||
return OpenWebContentFileSystem(out, this->client_info.program_id, program_id, static_cast<FsFileSystemType>(_filesystem_type), this->forward_service.get(), std::addressof(path), true, this->client_info.override_status.IsProgramSpecific());
|
||||
}
|
||||
|
||||
Result FsMitmService::OpenSdCardFileSystem(sf::Out<std::shared_ptr<IFileSystemInterface>> out) {
|
||||
Result FsMitmService::OpenSdCardFileSystem(sf::Out<std::shared_ptr<ams::fssrv::sf::IFileSystem>> out) {
|
||||
/* We only care about redirecting this for NS/emummc. */
|
||||
R_UNLESS(this->client_info.program_id == ncm::SystemProgramId::Ns, sm::mitm::ResultShouldForwardToSession());
|
||||
R_UNLESS(emummc::IsActive(), sm::mitm::ResultShouldForwardToSession());
|
||||
|
@ -175,11 +185,11 @@ namespace ams::mitm::fs {
|
|||
|
||||
/* Return output filesystem. */
|
||||
std::shared_ptr<fs::fsa::IFileSystem> redir_fs = std::make_shared<fssystem::DirectoryRedirectionFileSystem>(std::make_shared<RemoteFileSystem>(sd_fs), "/Nintendo", emummc::GetNintendoDirPath());
|
||||
out.SetValue(std::make_shared<IFileSystemInterface>(std::move(redir_fs), false), target_object_id);
|
||||
out.SetValue(MakeSharedFileSystem(std::move(redir_fs), false), target_object_id);
|
||||
return ResultSuccess();
|
||||
}
|
||||
|
||||
Result FsMitmService::OpenSaveDataFileSystem(sf::Out<std::shared_ptr<IFileSystemInterface>> out, u8 _space_id, const fs::SaveDataAttribute &attribute) {
|
||||
Result FsMitmService::OpenSaveDataFileSystem(sf::Out<std::shared_ptr<ams::fssrv::sf::IFileSystem>> out, u8 _space_id, const fs::SaveDataAttribute &attribute) {
|
||||
/* We only want to intercept saves for games, right now. */
|
||||
const bool is_game_or_hbl = this->client_info.override_status.IsHbl() || ncm::IsApplicationId(this->client_info.program_id);
|
||||
R_UNLESS(is_game_or_hbl, sm::mitm::ResultShouldForwardToSession());
|
||||
|
@ -240,11 +250,11 @@ namespace ams::mitm::fs {
|
|||
}
|
||||
|
||||
/* Set output. */
|
||||
out.SetValue(std::make_shared<IFileSystemInterface>(std::move(dirsave_ifs), false), target_object_id);
|
||||
out.SetValue(MakeSharedFileSystem(std::move(dirsave_ifs), false), target_object_id);
|
||||
return ResultSuccess();
|
||||
}
|
||||
|
||||
Result FsMitmService::OpenBisStorage(sf::Out<std::shared_ptr<IStorageInterface>> out, u32 _bis_partition_id) {
|
||||
Result FsMitmService::OpenBisStorage(sf::Out<std::shared_ptr<ams::fssrv::sf::IStorage>> out, u32 _bis_partition_id) {
|
||||
const ::FsBisPartitionId bis_partition_id = static_cast<::FsBisPartitionId>(_bis_partition_id);
|
||||
|
||||
/* Try to open a storage for the partition. */
|
||||
|
@ -265,23 +275,23 @@ namespace ams::mitm::fs {
|
|||
|
||||
/* Set output storage. */
|
||||
if (bis_partition_id == FsBisPartitionId_BootPartition1Root) {
|
||||
out.SetValue(std::make_shared<IStorageInterface>(new Boot0Storage(bis_storage, this->client_info)), target_object_id);
|
||||
out.SetValue(MakeSharedStorage(new Boot0Storage(bis_storage, this->client_info)), target_object_id);
|
||||
} else if (bis_partition_id == FsBisPartitionId_CalibrationBinary) {
|
||||
out.SetValue(std::make_shared<IStorageInterface>(new CalibrationBinaryStorage(bis_storage, this->client_info)), target_object_id);
|
||||
out.SetValue(MakeSharedStorage(new CalibrationBinaryStorage(bis_storage, this->client_info)), target_object_id);
|
||||
} else {
|
||||
if (can_write_bis || can_write_bis_for_choi_support) {
|
||||
/* We can write, so create a writable storage. */
|
||||
out.SetValue(std::make_shared<IStorageInterface>(new RemoteStorage(bis_storage)), target_object_id);
|
||||
out.SetValue(MakeSharedStorage(new RemoteStorage(bis_storage)), target_object_id);
|
||||
} else {
|
||||
/* We can only read, so create a readable storage. */
|
||||
out.SetValue(std::make_shared<IStorageInterface>(new ReadOnlyStorageAdapter(new RemoteStorage(bis_storage))), target_object_id);
|
||||
out.SetValue(MakeSharedStorage(new ReadOnlyStorageAdapter(new RemoteStorage(bis_storage))), target_object_id);
|
||||
}
|
||||
}
|
||||
|
||||
return ResultSuccess();
|
||||
}
|
||||
|
||||
Result FsMitmService::OpenDataStorageByCurrentProcess(sf::Out<std::shared_ptr<IStorageInterface>> out) {
|
||||
Result FsMitmService::OpenDataStorageByCurrentProcess(sf::Out<std::shared_ptr<ams::fssrv::sf::IStorage>> out) {
|
||||
/* Only mitm if we should override contents for the current process. */
|
||||
R_UNLESS(this->client_info.override_status.IsProgramSpecific(), sm::mitm::ResultShouldForwardToSession());
|
||||
|
||||
|
@ -298,7 +308,7 @@ namespace ams::mitm::fs {
|
|||
|
||||
/* Try to get a storage from the cache. */
|
||||
{
|
||||
std::shared_ptr<IStorageInterface> cached_storage = GetStorageCacheEntry(this->client_info.program_id);
|
||||
std::shared_ptr<ams::fssrv::sf::IStorage> cached_storage = GetStorageCacheEntry(this->client_info.program_id);
|
||||
if (cached_storage != nullptr) {
|
||||
out.SetValue(std::move(cached_storage), target_object_id);
|
||||
return ResultSuccess();
|
||||
|
@ -307,18 +317,18 @@ namespace ams::mitm::fs {
|
|||
|
||||
/* Make a new layered romfs, and cache to storage. */
|
||||
{
|
||||
std::shared_ptr<IStorageInterface> new_storage_intf = nullptr;
|
||||
std::shared_ptr<ams::fssrv::sf::IStorage> new_storage_intf = nullptr;
|
||||
|
||||
/* Create the layered storage. */
|
||||
FsFile data_file;
|
||||
if (R_SUCCEEDED(OpenAtmosphereSdFile(&data_file, this->client_info.program_id, "romfs.bin", OpenMode_Read))) {
|
||||
auto layered_storage = std::make_shared<LayeredRomfsStorage>(std::make_unique<ReadOnlyStorageAdapter>(new RemoteStorage(data_storage)), std::make_unique<ReadOnlyStorageAdapter>(new FileStorage(new RemoteFile(data_file))), this->client_info.program_id);
|
||||
layered_storage->BeginInitialize();
|
||||
new_storage_intf = std::make_shared<IStorageInterface>(layered_storage);
|
||||
new_storage_intf = MakeSharedStorage(layered_storage);
|
||||
} else {
|
||||
auto layered_storage = std::make_shared<LayeredRomfsStorage>(std::make_unique<ReadOnlyStorageAdapter>(new RemoteStorage(data_storage)), nullptr, this->client_info.program_id);
|
||||
layered_storage->BeginInitialize();
|
||||
new_storage_intf = std::make_shared<IStorageInterface>(layered_storage);
|
||||
new_storage_intf = MakeSharedStorage(layered_storage);
|
||||
}
|
||||
|
||||
SetStorageCacheEntry(this->client_info.program_id, &new_storage_intf);
|
||||
|
@ -328,7 +338,7 @@ namespace ams::mitm::fs {
|
|||
return ResultSuccess();
|
||||
}
|
||||
|
||||
Result FsMitmService::OpenDataStorageByDataId(sf::Out<std::shared_ptr<IStorageInterface>> out, ncm::DataId _data_id, u8 storage_id) {
|
||||
Result FsMitmService::OpenDataStorageByDataId(sf::Out<std::shared_ptr<ams::fssrv::sf::IStorage>> out, ncm::DataId _data_id, u8 storage_id) {
|
||||
/* Only mitm if we should override contents for the current process. */
|
||||
R_UNLESS(this->client_info.override_status.IsProgramSpecific(), sm::mitm::ResultShouldForwardToSession());
|
||||
|
||||
|
@ -348,7 +358,7 @@ namespace ams::mitm::fs {
|
|||
|
||||
/* Try to get a storage from the cache. */
|
||||
{
|
||||
std::shared_ptr<IStorageInterface> cached_storage = GetStorageCacheEntry(data_id);
|
||||
std::shared_ptr<ams::fssrv::sf::IStorage> cached_storage = GetStorageCacheEntry(data_id);
|
||||
if (cached_storage != nullptr) {
|
||||
out.SetValue(std::move(cached_storage), target_object_id);
|
||||
return ResultSuccess();
|
||||
|
@ -357,18 +367,18 @@ namespace ams::mitm::fs {
|
|||
|
||||
/* Make a new layered romfs, and cache to storage. */
|
||||
{
|
||||
std::shared_ptr<IStorageInterface> new_storage_intf = nullptr;
|
||||
std::shared_ptr<ams::fssrv::sf::IStorage> new_storage_intf = nullptr;
|
||||
|
||||
/* Create the layered storage. */
|
||||
FsFile data_file;
|
||||
if (R_SUCCEEDED(OpenAtmosphereSdFile(&data_file, data_id, "romfs.bin", OpenMode_Read))) {
|
||||
auto layered_storage = std::make_shared<LayeredRomfsStorage>(std::make_unique<ReadOnlyStorageAdapter>(new RemoteStorage(data_storage)), std::make_unique<ReadOnlyStorageAdapter>(new FileStorage(new RemoteFile(data_file))), data_id);
|
||||
layered_storage->BeginInitialize();
|
||||
new_storage_intf = std::make_shared<IStorageInterface>(layered_storage);
|
||||
new_storage_intf = MakeSharedStorage(layered_storage);
|
||||
} else {
|
||||
auto layered_storage = std::make_shared<LayeredRomfsStorage>(std::make_unique<ReadOnlyStorageAdapter>(new RemoteStorage(data_storage)), nullptr, data_id);
|
||||
layered_storage->BeginInitialize();
|
||||
new_storage_intf = std::make_shared<IStorageInterface>(layered_storage);
|
||||
new_storage_intf = MakeSharedStorage(layered_storage);
|
||||
}
|
||||
|
||||
SetStorageCacheEntry(data_id, &new_storage_intf);
|
||||
|
|
|
@ -20,30 +20,26 @@
|
|||
|
||||
namespace ams::mitm::fs {
|
||||
|
||||
using IStorageInterface = ams::fssrv::impl::StorageInterfaceAdapter;
|
||||
using IFileSystemInterface = ams::fssrv::impl::FileSystemInterfaceAdapter;
|
||||
namespace {
|
||||
|
||||
/* TODO: Consider re-enabling the mitm flag logic. */
|
||||
#define AMS_FS_MITM_INTERFACE_INFO(C, H) \
|
||||
AMS_SF_METHOD_INFO(C, H, 7, Result, OpenFileSystemWithPatch, (sf::Out<std::shared_ptr<ams::fssrv::sf::IFileSystem>> out, ncm::ProgramId program_id, u32 _filesystem_type), hos::Version_2_0_0) \
|
||||
AMS_SF_METHOD_INFO(C, H, 8, Result, OpenFileSystemWithId, (sf::Out<std::shared_ptr<ams::fssrv::sf::IFileSystem>> out, const fssrv::sf::Path &path, ncm::ProgramId program_id, u32 _filesystem_type), hos::Version_2_0_0) \
|
||||
AMS_SF_METHOD_INFO(C, H, 18, Result, OpenSdCardFileSystem, (sf::Out<std::shared_ptr<ams::fssrv::sf::IFileSystem>> out)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 51, Result, OpenSaveDataFileSystem, (sf::Out<std::shared_ptr<ams::fssrv::sf::IFileSystem>> out, u8 space_id, const ams::fs::SaveDataAttribute &attribute)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 12, Result, OpenBisStorage, (sf::Out<std::shared_ptr<ams::fssrv::sf::IStorage>> out, u32 bis_partition_id)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 200, Result, OpenDataStorageByCurrentProcess, (sf::Out<std::shared_ptr<ams::fssrv::sf::IStorage>> out)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 202, Result, OpenDataStorageByDataId, (sf::Out<std::shared_ptr<ams::fssrv::sf::IStorage>> out, ncm::DataId data_id, u8 storage_id))
|
||||
|
||||
class FsMitmService : public sf::IMitmServiceObject {
|
||||
private:
|
||||
enum class CommandId {
|
||||
OpenFileSystemDeprecated = 0,
|
||||
AMS_SF_DEFINE_MITM_INTERFACE(IFsMitmInterface, AMS_FS_MITM_INTERFACE_INFO)
|
||||
|
||||
SetCurrentProcess = 1,
|
||||
OpenFileSystemWithPatch = 7,
|
||||
OpenFileSystemWithId = 8,
|
||||
}
|
||||
|
||||
OpenSdCardFileSystem = 18,
|
||||
|
||||
OpenSaveDataFileSystem = 51,
|
||||
|
||||
OpenBisStorage = 12,
|
||||
OpenDataStorageByCurrentProcess = 200,
|
||||
OpenDataStorageByDataId = 202,
|
||||
};
|
||||
class FsMitmService : public sf::MitmServiceImplBase {
|
||||
public:
|
||||
NX_CONSTEXPR bool ShouldMitmProgramId(const ncm::ProgramId program_id) {
|
||||
using MitmServiceImplBase::MitmServiceImplBase;
|
||||
public:
|
||||
static constexpr ALWAYS_INLINE bool ShouldMitmProgramId(const ncm::ProgramId program_id) {
|
||||
/* We want to mitm everything that isn't a system-module. */
|
||||
if (!ncm::IsSystemProgramId(program_id)) {
|
||||
return true;
|
||||
|
@ -81,26 +77,14 @@ namespace ams::mitm::fs {
|
|||
return has_launched_qlaunch || ShouldMitmProgramId(client_info.program_id);
|
||||
}
|
||||
public:
|
||||
SF_MITM_SERVICE_OBJECT_CTOR(FsMitmService) { /* ... */ }
|
||||
protected:
|
||||
/* Overridden commands. */
|
||||
Result OpenFileSystemWithPatch(sf::Out<std::shared_ptr<IFileSystemInterface>> out, ncm::ProgramId program_id, u32 _filesystem_type);
|
||||
Result OpenFileSystemWithId(sf::Out<std::shared_ptr<IFileSystemInterface>> out, const fssrv::sf::Path &path, ncm::ProgramId program_id, u32 _filesystem_type);
|
||||
Result OpenSdCardFileSystem(sf::Out<std::shared_ptr<IFileSystemInterface>> out);
|
||||
Result OpenSaveDataFileSystem(sf::Out<std::shared_ptr<IFileSystemInterface>> out, u8 space_id, const ams::fs::SaveDataAttribute &attribute);
|
||||
Result OpenBisStorage(sf::Out<std::shared_ptr<IStorageInterface>> out, u32 bis_partition_id);
|
||||
Result OpenDataStorageByCurrentProcess(sf::Out<std::shared_ptr<IStorageInterface>> out);
|
||||
Result OpenDataStorageByDataId(sf::Out<std::shared_ptr<IStorageInterface>> out, ncm::DataId data_id, u8 storage_id);
|
||||
public:
|
||||
DEFINE_SERVICE_DISPATCH_TABLE {
|
||||
MAKE_SERVICE_COMMAND_META(OpenFileSystemWithPatch, hos::Version_2_0_0),
|
||||
MAKE_SERVICE_COMMAND_META(OpenFileSystemWithId, hos::Version_2_0_0),
|
||||
MAKE_SERVICE_COMMAND_META(OpenSdCardFileSystem),
|
||||
MAKE_SERVICE_COMMAND_META(OpenSaveDataFileSystem),
|
||||
MAKE_SERVICE_COMMAND_META(OpenBisStorage),
|
||||
MAKE_SERVICE_COMMAND_META(OpenDataStorageByCurrentProcess),
|
||||
MAKE_SERVICE_COMMAND_META(OpenDataStorageByDataId),
|
||||
};
|
||||
Result OpenFileSystemWithPatch(sf::Out<std::shared_ptr<ams::fssrv::sf::IFileSystem>> out, ncm::ProgramId program_id, u32 _filesystem_type);
|
||||
Result OpenFileSystemWithId(sf::Out<std::shared_ptr<ams::fssrv::sf::IFileSystem>> out, const fssrv::sf::Path &path, ncm::ProgramId program_id, u32 _filesystem_type);
|
||||
Result OpenSdCardFileSystem(sf::Out<std::shared_ptr<ams::fssrv::sf::IFileSystem>> out);
|
||||
Result OpenSaveDataFileSystem(sf::Out<std::shared_ptr<ams::fssrv::sf::IFileSystem>> out, u8 space_id, const ams::fs::SaveDataAttribute &attribute);
|
||||
Result OpenBisStorage(sf::Out<std::shared_ptr<ams::fssrv::sf::IStorage>> out, u32 bis_partition_id);
|
||||
Result OpenDataStorageByCurrentProcess(sf::Out<std::shared_ptr<ams::fssrv::sf::IStorage>> out);
|
||||
Result OpenDataStorageByDataId(sf::Out<std::shared_ptr<ams::fssrv::sf::IStorage>> out, ncm::DataId data_id, u8 storage_id);
|
||||
};
|
||||
|
||||
}
|
||||
|
|
|
@ -78,7 +78,7 @@ namespace ams::mitm::fs {
|
|||
|
||||
void MitmModule::ThreadFunction(void *arg) {
|
||||
/* Create fs mitm. */
|
||||
R_ABORT_UNLESS(g_server_manager.RegisterMitmServer<FsMitmService>(MitmServiceName));
|
||||
R_ABORT_UNLESS((g_server_manager.RegisterMitmServer<IFsMitmInterface, FsMitmService>(MitmServiceName)));
|
||||
|
||||
/* Process for the server. */
|
||||
ProcessForServerOnAllThreads();
|
||||
|
|
|
@ -19,11 +19,18 @@
|
|||
|
||||
namespace ams::mitm::hid {
|
||||
|
||||
class HidMitmService : public sf::IMitmServiceObject {
|
||||
private:
|
||||
enum class CommandId {
|
||||
SetSupportedNpadStyleSet = 100,
|
||||
};
|
||||
namespace {
|
||||
|
||||
#define AMS_HID_MITM_INTERFACE_INFO(C, H) \
|
||||
AMS_SF_METHOD_INFO(C, H, 100, Result, SetSupportedNpadStyleSet, (const sf::ClientAppletResourceUserId &client_aruid, u32 style_set))
|
||||
|
||||
AMS_SF_DEFINE_MITM_INTERFACE(IHidMitmInterface, AMS_HID_MITM_INTERFACE_INFO)
|
||||
|
||||
}
|
||||
|
||||
class HidMitmService : public sf::MitmServiceImplBase {
|
||||
public:
|
||||
using MitmServiceImplBase::MitmServiceImplBase;
|
||||
public:
|
||||
static bool ShouldMitm(const sm::MitmProcessInfo &client_info) {
|
||||
/* TODO: Remove in Atmosphere 0.10.2. */
|
||||
|
@ -33,14 +40,9 @@ namespace ams::mitm::hid {
|
|||
return client_info.override_status.IsHbl();
|
||||
}
|
||||
public:
|
||||
SF_MITM_SERVICE_OBJECT_CTOR(HidMitmService) { /* ... */ }
|
||||
protected:
|
||||
/* Overridden commands. */
|
||||
Result SetSupportedNpadStyleSet(const sf::ClientAppletResourceUserId &client_aruid, u32 style_set);
|
||||
public:
|
||||
DEFINE_SERVICE_DISPATCH_TABLE {
|
||||
MAKE_SERVICE_COMMAND_META(SetSupportedNpadStyleSet),
|
||||
};
|
||||
};
|
||||
static_assert(IsIHidMitmInterface<HidMitmService>);
|
||||
|
||||
}
|
||||
|
|
|
@ -59,7 +59,7 @@ namespace ams::mitm::hid {
|
|||
}
|
||||
|
||||
/* Create hid mitm. */
|
||||
R_ABORT_UNLESS(g_server_manager.RegisterMitmServer<HidMitmService>(MitmServiceName));
|
||||
R_ABORT_UNLESS((g_server_manager.RegisterMitmServer<IHidMitmInterface, HidMitmService>(MitmServiceName)));
|
||||
|
||||
/* Loop forever, servicing our services. */
|
||||
g_server_manager.LoopProcess();
|
||||
|
|
|
@ -18,13 +18,20 @@
|
|||
|
||||
namespace ams::mitm::ns {
|
||||
|
||||
class NsAmMitmService : public sf::IMitmServiceObject {
|
||||
private:
|
||||
enum class CommandId {
|
||||
GetApplicationContentPath = 21,
|
||||
ResolveApplicationContentPath = 23,
|
||||
GetRunningApplicationProgramId = 92,
|
||||
};
|
||||
namespace impl {
|
||||
|
||||
#define AMS_NS_AM_MITM_INTERFACE_INFO(C, H) \
|
||||
AMS_SF_METHOD_INFO(C, H, 21, Result, GetApplicationContentPath, (const sf::OutBuffer &out_path, ncm::ProgramId application_id, u8 content_type)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 23, Result, ResolveApplicationContentPath, (ncm::ProgramId application_id, u8 content_type)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 92, Result, GetRunningApplicationProgramId, (sf::Out<ncm::ProgramId> out, ncm::ProgramId application_id), hos::Version_6_0_0)
|
||||
|
||||
AMS_SF_DEFINE_MITM_INTERFACE(IAmMitmInterface, AMS_NS_AM_MITM_INTERFACE_INFO)
|
||||
|
||||
}
|
||||
|
||||
class NsAmMitmService : public sf::MitmServiceImplBase {
|
||||
public:
|
||||
using MitmServiceImplBase::MitmServiceImplBase;
|
||||
public:
|
||||
static bool ShouldMitm(const sm::MitmProcessInfo &client_info) {
|
||||
/* We will mitm:
|
||||
|
@ -33,18 +40,11 @@ namespace ams::mitm::ns {
|
|||
return ncm::IsWebAppletId(client_info.program_id);
|
||||
}
|
||||
public:
|
||||
SF_MITM_SERVICE_OBJECT_CTOR(NsAmMitmService) { /* ... */ }
|
||||
protected:
|
||||
/* Actual command API. */
|
||||
Result GetApplicationContentPath(const sf::OutBuffer &out_path, ncm::ProgramId application_id, u8 content_type);
|
||||
Result ResolveApplicationContentPath(ncm::ProgramId application_id, u8 content_type);
|
||||
Result GetRunningApplicationProgramId(sf::Out<ncm::ProgramId> out, ncm::ProgramId application_id);
|
||||
public:
|
||||
DEFINE_SERVICE_DISPATCH_TABLE {
|
||||
MAKE_SERVICE_COMMAND_META(GetApplicationContentPath),
|
||||
MAKE_SERVICE_COMMAND_META(ResolveApplicationContentPath),
|
||||
MAKE_SERVICE_COMMAND_META(GetRunningApplicationProgramId, hos::Version_6_0_0),
|
||||
};
|
||||
};
|
||||
static_assert(impl::IsIAmMitmInterface<NsAmMitmService>);
|
||||
|
||||
}
|
||||
|
|
|
@ -37,13 +37,13 @@ namespace ams::mitm::ns {
|
|||
return nswebGetRunningApplicationProgramId(this->srv.get(), reinterpret_cast<u64 *>(out.GetPointer()), static_cast<u64>(application_id));
|
||||
}
|
||||
|
||||
Result NsWebMitmService::GetDocumentInterface(sf::Out<std::shared_ptr<NsDocumentService>> out) {
|
||||
Result NsWebMitmService::GetDocumentInterface(sf::Out<std::shared_ptr<impl::IDocumentInterface>> out) {
|
||||
/* Open a document interface. */
|
||||
NsDocumentInterface doc;
|
||||
R_TRY(nsGetDocumentInterfaceFwd(this->forward_service.get(), &doc));
|
||||
const sf::cmif::DomainObjectId target_object_id{serviceGetObjectId(&doc.s)};
|
||||
|
||||
out.SetValue(std::make_shared<NsDocumentService>(this->client_info, std::make_unique<NsDocumentInterface>(doc)), target_object_id);
|
||||
out.SetValue(sf::MakeShared<impl::IDocumentInterface, NsDocumentService>(this->client_info, std::make_unique<NsDocumentInterface>(doc)), target_object_id);
|
||||
return ResultSuccess();
|
||||
}
|
||||
|
||||
|
|
|
@ -20,13 +20,23 @@
|
|||
|
||||
namespace ams::mitm::ns {
|
||||
|
||||
class NsDocumentService : public sf::IServiceObject {
|
||||
private:
|
||||
enum class CommandId {
|
||||
GetApplicationContentPath = 21,
|
||||
ResolveApplicationContentPath = 23,
|
||||
GetRunningApplicationProgramId = 92,
|
||||
};
|
||||
namespace impl {
|
||||
|
||||
#define AMS_NS_DOCUMENT_MITM_INTERFACE_INFO(C, H) \
|
||||
AMS_SF_METHOD_INFO(C, H, 21, Result, GetApplicationContentPath, (const sf::OutBuffer &out_path, ncm::ProgramId application_id, u8 content_type)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 23, Result, ResolveApplicationContentPath, (ncm::ProgramId application_id, u8 content_type)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 92, Result, GetRunningApplicationProgramId, (sf::Out<ncm::ProgramId> out, ncm::ProgramId application_id), hos::Version_6_0_0)
|
||||
|
||||
AMS_SF_DEFINE_INTERFACE(IDocumentInterface, AMS_NS_DOCUMENT_MITM_INTERFACE_INFO)
|
||||
|
||||
#define AMS_NS_WEB_MITM_INTERFACE_INFO(C, H) \
|
||||
AMS_SF_METHOD_INFO(C, H, 7999, Result, GetDocumentInterface, (sf::Out<std::shared_ptr<IDocumentInterface>> out))
|
||||
|
||||
AMS_SF_DEFINE_MITM_INTERFACE(IWebMitmInterface, AMS_NS_WEB_MITM_INTERFACE_INFO)
|
||||
|
||||
}
|
||||
|
||||
class NsDocumentService {
|
||||
private:
|
||||
sm::MitmProcessInfo client_info;
|
||||
std::unique_ptr<::NsDocumentInterface> srv;
|
||||
|
@ -36,24 +46,17 @@ namespace ams::mitm::ns {
|
|||
virtual ~NsDocumentService() {
|
||||
nsDocumentInterfaceClose(this->srv.get());
|
||||
}
|
||||
protected:
|
||||
public:
|
||||
/* Actual command API. */
|
||||
Result GetApplicationContentPath(const sf::OutBuffer &out_path, ncm::ProgramId application_id, u8 content_type);
|
||||
Result ResolveApplicationContentPath(ncm::ProgramId application_id, u8 content_type);
|
||||
Result GetRunningApplicationProgramId(sf::Out<ncm::ProgramId> out, ncm::ProgramId application_id);
|
||||
public:
|
||||
DEFINE_SERVICE_DISPATCH_TABLE {
|
||||
MAKE_SERVICE_COMMAND_META(GetApplicationContentPath),
|
||||
MAKE_SERVICE_COMMAND_META(ResolveApplicationContentPath),
|
||||
MAKE_SERVICE_COMMAND_META(GetRunningApplicationProgramId, hos::Version_6_0_0),
|
||||
};
|
||||
};
|
||||
static_assert(impl::IsIDocumentInterface<NsDocumentService>);
|
||||
|
||||
class NsWebMitmService : public sf::IMitmServiceObject {
|
||||
private:
|
||||
enum class CommandId {
|
||||
GetDocumentInterface = 7999,
|
||||
};
|
||||
class NsWebMitmService : public sf::MitmServiceImplBase {
|
||||
public:
|
||||
using MitmServiceImplBase::MitmServiceImplBase;
|
||||
public:
|
||||
static bool ShouldMitm(const sm::MitmProcessInfo &client_info) {
|
||||
/* We will mitm:
|
||||
|
@ -62,13 +65,8 @@ namespace ams::mitm::ns {
|
|||
return ncm::IsWebAppletId(client_info.program_id);
|
||||
}
|
||||
public:
|
||||
SF_MITM_SERVICE_OBJECT_CTOR(NsWebMitmService) { /* ... */ }
|
||||
protected:
|
||||
Result GetDocumentInterface(sf::Out<std::shared_ptr<NsDocumentService>> out);
|
||||
public:
|
||||
DEFINE_SERVICE_DISPATCH_TABLE {
|
||||
MAKE_SERVICE_COMMAND_META(GetDocumentInterface),
|
||||
};
|
||||
Result GetDocumentInterface(sf::Out<std::shared_ptr<impl::IDocumentInterface>> out);
|
||||
};
|
||||
static_assert(impl::IsIWebMitmInterface<NsWebMitmService>);
|
||||
|
||||
}
|
||||
|
|
|
@ -39,9 +39,9 @@ namespace ams::mitm::ns {
|
|||
|
||||
/* Create mitm servers. */
|
||||
if (hos::GetVersion() < hos::Version_3_0_0) {
|
||||
R_ABORT_UNLESS(g_server_manager.RegisterMitmServer<NsAmMitmService>(NsAmMitmServiceName));
|
||||
R_ABORT_UNLESS((g_server_manager.RegisterMitmServer<impl::IAmMitmInterface, NsAmMitmService>(NsAmMitmServiceName)));
|
||||
} else {
|
||||
R_ABORT_UNLESS(g_server_manager.RegisterMitmServer<NsWebMitmService>(NsWebMitmServiceName));
|
||||
R_ABORT_UNLESS((g_server_manager.RegisterMitmServer<impl::IWebMitmInterface, NsWebMitmService>(NsWebMitmServiceName)));
|
||||
}
|
||||
|
||||
/* Loop forever, servicing our services. */
|
||||
|
|
|
@ -18,16 +18,23 @@
|
|||
|
||||
namespace ams::mitm::settings {
|
||||
|
||||
class SetMitmService : public sf::IMitmServiceObject {
|
||||
private:
|
||||
enum class CommandId {
|
||||
GetLanguageCode = 0,
|
||||
GetRegionCode = 4,
|
||||
};
|
||||
namespace {
|
||||
|
||||
#define AMS_SETTINGS_MITM_INTERFACE_INFO(C, H) \
|
||||
AMS_SF_METHOD_INFO(C, H, 0, Result, GetLanguageCode, (sf::Out<ams::settings::LanguageCode> out)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 4, Result, GetRegionCode, (sf::Out<ams::settings::RegionCode> out))
|
||||
|
||||
AMS_SF_DEFINE_MITM_INTERFACE(ISetMitmInterface, AMS_SETTINGS_MITM_INTERFACE_INFO)
|
||||
|
||||
}
|
||||
|
||||
class SetMitmService : public sf::MitmServiceImplBase {
|
||||
private:
|
||||
os::Mutex lock{false};
|
||||
cfg::OverrideLocale locale;
|
||||
bool got_locale;
|
||||
bool got_locale = false;
|
||||
public:
|
||||
using MitmServiceImplBase::MitmServiceImplBase;
|
||||
public:
|
||||
static bool ShouldMitm(const sm::MitmProcessInfo &client_info) {
|
||||
/* We will mitm:
|
||||
|
@ -36,20 +43,12 @@ namespace ams::mitm::settings {
|
|||
const bool is_game = (ncm::IsApplicationId(client_info.program_id) && !client_info.override_status.IsHbl());
|
||||
return client_info.program_id == ncm::SystemProgramId::Ns || is_game;
|
||||
}
|
||||
public:
|
||||
SF_MITM_SERVICE_OBJECT_CTOR(SetMitmService) {
|
||||
this->got_locale = false;
|
||||
}
|
||||
private:
|
||||
Result EnsureLocale();
|
||||
protected:
|
||||
public:
|
||||
Result GetLanguageCode(sf::Out<ams::settings::LanguageCode> out);
|
||||
Result GetRegionCode(sf::Out<ams::settings::RegionCode> out);
|
||||
public:
|
||||
DEFINE_SERVICE_DISPATCH_TABLE {
|
||||
MAKE_SERVICE_COMMAND_META(GetLanguageCode),
|
||||
MAKE_SERVICE_COMMAND_META(GetRegionCode),
|
||||
};
|
||||
};
|
||||
static_assert(IsISetMitmInterface<SetMitmService>);
|
||||
|
||||
}
|
||||
|
|
|
@ -43,8 +43,8 @@ namespace ams::mitm::settings {
|
|||
mitm::WaitInitialized();
|
||||
|
||||
/* Create mitm servers. */
|
||||
R_ABORT_UNLESS(g_server_manager.RegisterMitmServer<SetMitmService>(SetMitmServiceName));
|
||||
R_ABORT_UNLESS(g_server_manager.RegisterMitmServer<SetSysMitmService>(SetSysMitmServiceName));
|
||||
R_ABORT_UNLESS((g_server_manager.RegisterMitmServer<ISetMitmInterface, SetMitmService>(SetMitmServiceName)));
|
||||
R_ABORT_UNLESS((g_server_manager.RegisterMitmServer<ISetSysMitmInterface, SetSysMitmService>(SetSysMitmServiceName)));
|
||||
|
||||
/* Loop forever, servicing our services. */
|
||||
g_server_manager.LoopProcess();
|
||||
|
|
|
@ -18,15 +18,21 @@
|
|||
|
||||
namespace ams::mitm::settings {
|
||||
|
||||
class SetSysMitmService : public sf::IMitmServiceObject {
|
||||
private:
|
||||
enum class CommandId {
|
||||
GetFirmwareVersion = 3,
|
||||
GetFirmwareVersion2 = 4,
|
||||
namespace {
|
||||
|
||||
GetSettingsItemValueSize = 37,
|
||||
GetSettingsItemValue = 38,
|
||||
};
|
||||
#define AMS_SETTINGS_SYSTEM_MITM_INTERFACE_INFO(C, H) \
|
||||
AMS_SF_METHOD_INFO(C, H, 3, Result, GetFirmwareVersion, (sf::Out<ams::settings::FirmwareVersion> out)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 4, Result, GetFirmwareVersion2, (sf::Out<ams::settings::FirmwareVersion> out)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 37, Result, GetSettingsItemValueSize, (sf::Out<u64> out_size, const ams::settings::fwdbg::SettingsName &name, const ams::settings::fwdbg::SettingsItemKey &key)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 38, Result, GetSettingsItemValue, (sf::Out<u64> out_size, const sf::OutBuffer &out, const ams::settings::fwdbg::SettingsName &name, const ams::settings::fwdbg::SettingsItemKey &key))
|
||||
|
||||
AMS_SF_DEFINE_MITM_INTERFACE(ISetSysMitmInterface, AMS_SETTINGS_SYSTEM_MITM_INTERFACE_INFO)
|
||||
|
||||
}
|
||||
|
||||
class SetSysMitmService : public sf::MitmServiceImplBase {
|
||||
public:
|
||||
using MitmServiceImplBase::MitmServiceImplBase;
|
||||
public:
|
||||
static bool ShouldMitm(const sm::MitmProcessInfo &client_info) {
|
||||
/* We will mitm:
|
||||
|
@ -35,19 +41,11 @@ namespace ams::mitm::settings {
|
|||
return true;
|
||||
}
|
||||
public:
|
||||
SF_MITM_SERVICE_OBJECT_CTOR(SetSysMitmService) { /* ... */ }
|
||||
protected:
|
||||
Result GetFirmwareVersion(sf::Out<ams::settings::FirmwareVersion> out);
|
||||
Result GetFirmwareVersion2(sf::Out<ams::settings::FirmwareVersion> out);
|
||||
Result GetSettingsItemValueSize(sf::Out<u64> out_size, const ams::settings::fwdbg::SettingsName &name, const ams::settings::fwdbg::SettingsItemKey &key);
|
||||
Result GetSettingsItemValue(sf::Out<u64> out_size, const sf::OutBuffer &out, const ams::settings::fwdbg::SettingsName &name, const ams::settings::fwdbg::SettingsItemKey &key);
|
||||
public:
|
||||
DEFINE_SERVICE_DISPATCH_TABLE {
|
||||
MAKE_SERVICE_COMMAND_META(GetFirmwareVersion),
|
||||
MAKE_SERVICE_COMMAND_META(GetFirmwareVersion2),
|
||||
MAKE_SERVICE_COMMAND_META(GetSettingsItemValueSize),
|
||||
MAKE_SERVICE_COMMAND_META(GetSettingsItemValue),
|
||||
};
|
||||
};
|
||||
static_assert(IsISetSysMitmInterface<SetSysMitmService>);
|
||||
|
||||
}
|
||||
|
|
|
@ -15,7 +15,6 @@
|
|||
*/
|
||||
#pragma once
|
||||
#include <stratosphere.hpp>
|
||||
#include "sysupdater_i_async_result.hpp"
|
||||
#include "sysupdater_thread_allocator.hpp"
|
||||
|
||||
namespace ams::mitm::sysupdater {
|
||||
|
@ -59,18 +58,18 @@ namespace ams::mitm::sysupdater {
|
|||
}
|
||||
};
|
||||
|
||||
class AsyncBase : public IAsyncBase {
|
||||
class AsyncBase {
|
||||
public:
|
||||
virtual ~AsyncBase() { /* ... */ }
|
||||
|
||||
static Result ToAsyncResult(Result result);
|
||||
|
||||
virtual Result Cancel() override final {
|
||||
Result Cancel() {
|
||||
this->CancelImpl();
|
||||
return ResultSuccess();
|
||||
}
|
||||
|
||||
virtual Result GetErrorContext(sf::Out<err::ErrorContext> out) override {
|
||||
virtual Result GetErrorContext(sf::Out<err::ErrorContext> out) {
|
||||
*out = {};
|
||||
return ResultSuccess();
|
||||
}
|
||||
|
@ -78,29 +77,17 @@ namespace ams::mitm::sysupdater {
|
|||
virtual void CancelImpl() = 0;
|
||||
};
|
||||
|
||||
class AsyncResultBase : public IAsyncResult {
|
||||
class AsyncResultBase : public AsyncBase {
|
||||
public:
|
||||
virtual ~AsyncResultBase() { /* ... */ }
|
||||
|
||||
static Result ToAsyncResult(Result result) { return AsyncBase::ToAsyncResult(result); }
|
||||
|
||||
virtual Result Cancel() override final {
|
||||
this->CancelImpl();
|
||||
return ResultSuccess();
|
||||
}
|
||||
|
||||
virtual Result Get() override final {
|
||||
Result Get() {
|
||||
return ToAsyncResult(this->GetImpl());
|
||||
}
|
||||
|
||||
virtual Result GetErrorContext(sf::Out<err::ErrorContext> out) override {
|
||||
*out = {};
|
||||
return ResultSuccess();
|
||||
}
|
||||
private:
|
||||
virtual void CancelImpl() = 0;
|
||||
virtual Result GetImpl() = 0;
|
||||
};
|
||||
static_assert(ns::impl::IsIAsyncResult<AsyncResultBase>);
|
||||
|
||||
/* NOTE: Based off of ns AsyncPrepareCardUpdateImpl. */
|
||||
/* We don't implement the RequestServer::ManagedStop details, as we don't implement stoppable request list. */
|
||||
|
|
|
@ -1,44 +0,0 @@
|
|||
/*
|
||||
* Copyright (c) 2018-2020 Atmosphère-NX
|
||||
*
|
||||
* This program is free software; you can redistribute it and/or modify it
|
||||
* under the terms and conditions of the GNU General Public License,
|
||||
* version 2, as published by the Free Software Foundation.
|
||||
*
|
||||
* This program is distributed in the hope it will be useful, but WITHOUT
|
||||
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
|
||||
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
|
||||
* more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
#pragma once
|
||||
#include <stratosphere.hpp>
|
||||
|
||||
namespace ams::mitm::sysupdater {
|
||||
|
||||
class IAsyncBase : public sf::IServiceObject {
|
||||
public:
|
||||
virtual Result Cancel() = 0;
|
||||
virtual Result GetErrorContext(sf::Out<err::ErrorContext> out) = 0;
|
||||
};
|
||||
|
||||
class IAsyncResult : public IAsyncBase {
|
||||
private:
|
||||
enum class CommandId {
|
||||
Get = 0,
|
||||
Cancel = 1,
|
||||
GetErrorContext = 2,
|
||||
};
|
||||
public:
|
||||
virtual Result Get() = 0;
|
||||
public:
|
||||
DEFINE_SERVICE_DISPATCH_TABLE {
|
||||
MAKE_SERVICE_COMMAND_META(Get),
|
||||
MAKE_SERVICE_COMMAND_META(Cancel),
|
||||
MAKE_SERVICE_COMMAND_META(GetErrorContext),
|
||||
};
|
||||
};
|
||||
|
||||
}
|
|
@ -50,7 +50,7 @@ namespace ams::mitm::sysupdater {
|
|||
ON_SCOPE_EXIT { nim::FinalizeForNetworkInstallManager(); };
|
||||
|
||||
/* Register ams:su. */
|
||||
R_ABORT_UNLESS((g_server_manager.RegisterServer<sysupdater::SystemUpdateService>(SystemUpdateServiceName, SystemUpdateMaxSessions, sf::ServiceObjectTraits<sysupdater::SystemUpdateService>::SharedPointerHelper::GetEmptyDeleteSharedPointer(std::addressof(g_system_update_service_object)))));
|
||||
R_ABORT_UNLESS((g_server_manager.RegisterServer<sysupdater::impl::ISystemUpdateInterface, sysupdater::SystemUpdateService>(SystemUpdateServiceName, SystemUpdateMaxSessions, sf::GetSharedPointerTo<sysupdater::impl::ISystemUpdateInterface>(g_system_update_service_object))));
|
||||
|
||||
/* Loop forever, servicing our services. */
|
||||
g_server_manager.LoopProcess();
|
||||
|
|
|
@ -411,21 +411,21 @@ namespace ams::mitm::sysupdater {
|
|||
return this->SetupUpdateImpl(transfer_memory.GetValue(), transfer_memory_size, path, exfat, firmware_variation_id);
|
||||
}
|
||||
|
||||
Result SystemUpdateService::RequestPrepareUpdate(sf::OutCopyHandle out_event_handle, sf::Out<std::shared_ptr<IAsyncResult>> out_async) {
|
||||
Result SystemUpdateService::RequestPrepareUpdate(sf::OutCopyHandle out_event_handle, sf::Out<std::shared_ptr<ns::impl::IAsyncResult>> out_async) {
|
||||
/* Ensure the update is setup but not prepared. */
|
||||
R_UNLESS(this->setup_update, ns::ResultCardUpdateNotSetup());
|
||||
R_UNLESS(!this->requested_update, ns::ResultPrepareCardUpdateAlreadyRequested());
|
||||
|
||||
/* Create the async result. */
|
||||
auto async_result = std::make_shared<AsyncPrepareSdCardUpdateImpl>(std::addressof(*this->update_task));
|
||||
auto async_result = sf::MakeShared<ns::impl::IAsyncResult, AsyncPrepareSdCardUpdateImpl>(std::addressof(*this->update_task));
|
||||
R_UNLESS(async_result != nullptr, ns::ResultOutOfMaxRunningTask());
|
||||
|
||||
/* Run the task. */
|
||||
R_TRY(async_result->Run());
|
||||
R_TRY(async_result->GetImpl().Run());
|
||||
|
||||
/* We prepared the task! */
|
||||
this->requested_update = true;
|
||||
out_event_handle.SetValue(async_result->GetEvent().GetReadableHandle());
|
||||
out_event_handle.SetValue(async_result->GetImpl().GetEvent().GetReadableHandle());
|
||||
out_async.SetValue(std::move(async_result));
|
||||
|
||||
return ResultSuccess();
|
||||
|
|
|
@ -15,7 +15,6 @@
|
|||
*/
|
||||
#pragma once
|
||||
#include <stratosphere.hpp>
|
||||
#include "sysupdater_i_async_result.hpp"
|
||||
#include "sysupdater_apply_manager.hpp"
|
||||
|
||||
namespace ams::mitm::sysupdater {
|
||||
|
@ -39,18 +38,25 @@ namespace ams::mitm::sysupdater {
|
|||
s64 total_size;
|
||||
};
|
||||
|
||||
class SystemUpdateService final : public sf::IServiceObject {
|
||||
private:
|
||||
enum class CommandId {
|
||||
GetUpdateInformation = 0,
|
||||
ValidateUpdate = 1,
|
||||
SetupUpdate = 2,
|
||||
SetupUpdateWithVariation = 3,
|
||||
RequestPrepareUpdate = 4,
|
||||
GetPrepareUpdateProgress = 5,
|
||||
HasPreparedUpdate = 6,
|
||||
ApplyPreparedUpdate = 7,
|
||||
};
|
||||
namespace impl {
|
||||
|
||||
#define AMS_SYSUPDATER_SYSTEM_UPDATE_INTERFACE_INFO(C, H) \
|
||||
AMS_SF_METHOD_INFO(C, H, 0, Result, GetUpdateInformation, (sf::Out<UpdateInformation> out, const ncm::Path &path)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 1, Result, ValidateUpdate, (sf::Out<Result> out_validate_result, sf::Out<UpdateValidationInfo> out_validate_info, const ncm::Path &path)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 2, Result, SetupUpdate, (sf::CopyHandle transfer_memory, u64 transfer_memory_size, const ncm::Path &path, bool exfat)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 3, Result, SetupUpdateWithVariation, (sf::CopyHandle transfer_memory, u64 transfer_memory_size, const ncm::Path &path, bool exfat, ncm::FirmwareVariationId firmware_variation_id)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 4, Result, RequestPrepareUpdate, (sf::OutCopyHandle out_event_handle, sf::Out<std::shared_ptr<ns::impl::IAsyncResult>> out_async)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 5, Result, GetPrepareUpdateProgress, (sf::Out<SystemUpdateProgress> out)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 6, Result, HasPreparedUpdate, (sf::Out<bool> out)) \
|
||||
AMS_SF_METHOD_INFO(C, H, 7, Result, ApplyPreparedUpdate, ())
|
||||
|
||||
AMS_SF_DEFINE_INTERFACE(ISystemUpdateInterface, AMS_SYSUPDATER_SYSTEM_UPDATE_INTERFACE_INFO)
|
||||
|
||||
|
||||
|
||||
}
|
||||
|
||||
class SystemUpdateService final {
|
||||
private:
|
||||
SystemUpdateApplyManager apply_manager;
|
||||
std::optional<ncm::PackageSystemDowngradeTask> update_task;
|
||||
|
@ -62,26 +68,16 @@ namespace ams::mitm::sysupdater {
|
|||
private:
|
||||
Result SetupUpdateImpl(os::ManagedHandle transfer_memory, u64 transfer_memory_size, const ncm::Path &path, bool exfat, ncm::FirmwareVariationId firmware_variation_id);
|
||||
Result InitializeUpdateTask(os::ManagedHandle &transfer_memory, u64 transfer_memory_size, const ncm::Path &path, bool exfat, ncm::FirmwareVariationId firmware_variation_id);
|
||||
private:
|
||||
public:
|
||||
Result GetUpdateInformation(sf::Out<UpdateInformation> out, const ncm::Path &path);
|
||||
Result ValidateUpdate(sf::Out<Result> out_validate_result, sf::Out<UpdateValidationInfo> out_validate_info, const ncm::Path &path);
|
||||
Result SetupUpdate(sf::CopyHandle transfer_memory, u64 transfer_memory_size, const ncm::Path &path, bool exfat);
|
||||
Result SetupUpdateWithVariation(sf::CopyHandle transfer_memory, u64 transfer_memory_size, const ncm::Path &path, bool exfat, ncm::FirmwareVariationId firmware_variation_id);
|
||||
Result RequestPrepareUpdate(sf::OutCopyHandle out_event_handle, sf::Out<std::shared_ptr<IAsyncResult>> out_async);
|
||||
Result RequestPrepareUpdate(sf::OutCopyHandle out_event_handle, sf::Out<std::shared_ptr<ns::impl::IAsyncResult>> out_async);
|
||||
Result GetPrepareUpdateProgress(sf::Out<SystemUpdateProgress> out);
|
||||
Result HasPreparedUpdate(sf::Out<bool> out);
|
||||
Result ApplyPreparedUpdate();
|
||||
public:
|
||||
DEFINE_SERVICE_DISPATCH_TABLE {
|
||||
MAKE_SERVICE_COMMAND_META(GetUpdateInformation),
|
||||
MAKE_SERVICE_COMMAND_META(ValidateUpdate),
|
||||
MAKE_SERVICE_COMMAND_META(SetupUpdate),
|
||||
MAKE_SERVICE_COMMAND_META(SetupUpdateWithVariation),
|
||||
MAKE_SERVICE_COMMAND_META(RequestPrepareUpdate),
|
||||
MAKE_SERVICE_COMMAND_META(GetPrepareUpdateProgress),
|
||||
MAKE_SERVICE_COMMAND_META(HasPreparedUpdate),
|
||||
MAKE_SERVICE_COMMAND_META(ApplyPreparedUpdate),
|
||||
};
|
||||
};
|
||||
static_assert(impl::IsISystemUpdateInterface<SystemUpdateService>);
|
||||
|
||||
}
|
||||
|
|
Loading…
Add table
Reference in a new issue