mirror of
https://github.com/Atmosphere-NX/Atmosphere
synced 2024-12-22 20:31:14 +00:00
ams_mitm: implement ns.mitm
This commit is contained in:
parent
2bae1ad116
commit
66372e2b2e
10 changed files with 296 additions and 12 deletions
41
stratosphere/ams_mitm/source/ns_mitm/ns_am_mitm_service.cpp
Normal file
41
stratosphere/ams_mitm/source/ns_mitm/ns_am_mitm_service.cpp
Normal file
|
@ -0,0 +1,41 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2018-2019 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/>.
|
||||||
|
*/
|
||||||
|
#include <stratosphere.hpp>
|
||||||
|
#include "ns_am_mitm_service.hpp"
|
||||||
|
#include "ns_shim.h"
|
||||||
|
|
||||||
|
namespace ams::mitm::ns {
|
||||||
|
|
||||||
|
Result NsAmMitmService::GetApplicationContentPath(const sf::OutBuffer &out_path, ncm::ProgramId application_id, u8 content_type) {
|
||||||
|
return nsamGetApplicationContentPathFwd(this->forward_service.get(), out_path.GetPointer(), out_path.GetSize(), static_cast<u64>(application_id), static_cast<NcmContentType>(content_type));
|
||||||
|
}
|
||||||
|
|
||||||
|
Result NsAmMitmService::ResolveApplicationContentPath(ncm::ProgramId application_id, u8 content_type) {
|
||||||
|
/* Always succeed for web applets asking about HBL. */
|
||||||
|
/* This enables hbl html. */
|
||||||
|
bool is_hbl;
|
||||||
|
if (R_SUCCEEDED(pm::info::IsHblProgramId(&is_hbl, application_id)) && is_hbl) {
|
||||||
|
nsamResolveApplicationContentPathFwd(this->forward_service.get(), static_cast<u64>(application_id), static_cast<NcmContentType>(content_type));
|
||||||
|
return ResultSuccess();
|
||||||
|
}
|
||||||
|
return nsamResolveApplicationContentPathFwd(this->forward_service.get(), static_cast<u64>(application_id), static_cast<NcmContentType>(content_type));
|
||||||
|
}
|
||||||
|
|
||||||
|
Result NsAmMitmService::GetRunningApplicationProgramId(sf::Out<ncm::ProgramId> out, ncm::ProgramId application_id) {
|
||||||
|
return nsamGetRunningApplicationProgramIdFwd(this->forward_service.get(), reinterpret_cast<u64 *>(out.GetPointer()), static_cast<u64>(application_id));
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -21,20 +21,29 @@ namespace ams::mitm::ns {
|
||||||
class NsAmMitmService : public sf::IMitmServiceObject {
|
class NsAmMitmService : public sf::IMitmServiceObject {
|
||||||
private:
|
private:
|
||||||
enum class CommandId {
|
enum class CommandId {
|
||||||
/* TODO */
|
GetApplicationContentPath = 21,
|
||||||
|
ResolveApplicationContentPath = 23,
|
||||||
|
GetRunningApplicationProgramId = 92,
|
||||||
};
|
};
|
||||||
public:
|
public:
|
||||||
static bool ShouldMitm(const sm::MitmProcessInfo &client_info) {
|
static bool ShouldMitm(const sm::MitmProcessInfo &client_info) {
|
||||||
/* TODO */
|
/* We will mitm:
|
||||||
return false;
|
* - web applets, to facilitate hbl web browser launching.
|
||||||
|
*/
|
||||||
|
return ncm::IsWebAppletProgramId(client_info.program_id);
|
||||||
}
|
}
|
||||||
public:
|
public:
|
||||||
SF_MITM_SERVICE_OBJECT_CTOR(NsAmMitmService) { /* ... */ }
|
SF_MITM_SERVICE_OBJECT_CTOR(NsAmMitmService) { /* ... */ }
|
||||||
protected:
|
protected:
|
||||||
/* TODO */
|
/* 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:
|
public:
|
||||||
DEFINE_SERVICE_DISPATCH_TABLE {
|
DEFINE_SERVICE_DISPATCH_TABLE {
|
||||||
/* TODO */
|
MAKE_SERVICE_COMMAND_META(GetApplicationContentPath),
|
||||||
|
MAKE_SERVICE_COMMAND_META(ResolveApplicationContentPath),
|
||||||
|
MAKE_SERVICE_COMMAND_META(GetRunningApplicationProgramId, hos::Version_600),
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
85
stratosphere/ams_mitm/source/ns_mitm/ns_shim.c
Normal file
85
stratosphere/ams_mitm/source/ns_mitm/ns_shim.c
Normal file
|
@ -0,0 +1,85 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2018-2019 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/>.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include <string.h>
|
||||||
|
#include <switch.h>
|
||||||
|
#include "ns_shim.h"
|
||||||
|
|
||||||
|
/* Command forwarders. */
|
||||||
|
Result nsGetDocumentInterfaceFwd(Service* s, NsDocumentInterface* out) {
|
||||||
|
return serviceDispatch(s, 7999,
|
||||||
|
.out_num_objects = 1,
|
||||||
|
.out_objects = &out->s,
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
static Result _nsGetApplicationContentPath(Service *s, void* out, size_t out_size, u64 app_id, NcmContentType content_type) {
|
||||||
|
const struct {
|
||||||
|
u8 content_type;
|
||||||
|
u64 app_id;
|
||||||
|
} in = { content_type, app_id };
|
||||||
|
return serviceDispatchIn(s, 21, in,
|
||||||
|
.buffer_attrs = { SfBufferAttr_HipcMapAlias | SfBufferAttr_Out },
|
||||||
|
.buffers = { { out, out_size } },
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
static Result _nsResolveApplicationContentPath(Service* s, u64 app_id, NcmContentType content_type) {
|
||||||
|
const struct {
|
||||||
|
u8 content_type;
|
||||||
|
u64 app_id;
|
||||||
|
} in = { content_type, app_id };
|
||||||
|
return serviceDispatchIn(s, 23, in);
|
||||||
|
}
|
||||||
|
|
||||||
|
static Result _nsGetRunningApplicationProgramId(Service* s, u64* out_program_id, u64 app_id) {
|
||||||
|
if (hosversionBefore(6, 0, 0)) {
|
||||||
|
return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer);
|
||||||
|
}
|
||||||
|
return serviceDispatchInOut(s, 92, app_id, *out_program_id);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Application Manager forwarders. */
|
||||||
|
Result nsamGetApplicationContentPathFwd(Service* s, void* out, size_t out_size, u64 app_id, NcmContentType content_type) {
|
||||||
|
return _nsGetApplicationContentPath(s, out, out_size, app_id, content_type);
|
||||||
|
}
|
||||||
|
|
||||||
|
Result nsamResolveApplicationContentPathFwd(Service* s, u64 app_id, NcmContentType content_type) {
|
||||||
|
return _nsResolveApplicationContentPath(s, app_id, content_type);
|
||||||
|
}
|
||||||
|
|
||||||
|
Result nsamGetRunningApplicationProgramIdFwd(Service* s, u64* out_program_id, u64 app_id) {
|
||||||
|
return _nsGetRunningApplicationProgramId(s, out_program_id, app_id);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Web forwarders */
|
||||||
|
Result nswebGetApplicationContentPath(NsDocumentInterface* doc, void* out, size_t out_size, u64 app_id, NcmContentType content_type) {
|
||||||
|
return _nsGetApplicationContentPath(&doc->s, out, out_size, app_id, content_type);
|
||||||
|
}
|
||||||
|
|
||||||
|
Result nswebResolveApplicationContentPath(NsDocumentInterface* doc, u64 app_id, NcmContentType content_type) {
|
||||||
|
return _nsResolveApplicationContentPath(&doc->s, app_id, content_type);
|
||||||
|
}
|
||||||
|
|
||||||
|
Result nswebGetRunningApplicationProgramId(NsDocumentInterface* doc, u64* out_program_id, u64 app_id) {
|
||||||
|
return _nsGetRunningApplicationProgramId(&doc->s, out_program_id, app_id);
|
||||||
|
}
|
||||||
|
|
||||||
|
void nsDocumentInterfaceClose(NsDocumentInterface* doc) {
|
||||||
|
serviceClose(&doc->s);
|
||||||
|
}
|
||||||
|
|
33
stratosphere/ams_mitm/source/ns_mitm/ns_shim.h
Normal file
33
stratosphere/ams_mitm/source/ns_mitm/ns_shim.h
Normal file
|
@ -0,0 +1,33 @@
|
||||||
|
/**
|
||||||
|
* @file ns_shim.h
|
||||||
|
* @brief Nintendo Shell Services (ns) IPC wrapper.
|
||||||
|
* @author SciresM
|
||||||
|
* @copyright libnx Authors
|
||||||
|
*/
|
||||||
|
#pragma once
|
||||||
|
#include <switch.h>
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
extern "C" {
|
||||||
|
#endif
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
Service s;
|
||||||
|
} NsDocumentInterface;
|
||||||
|
|
||||||
|
/* Command forwarders. */
|
||||||
|
Result nsGetDocumentInterfaceFwd(Service* s, NsDocumentInterface* out);
|
||||||
|
|
||||||
|
Result nsamGetApplicationContentPathFwd(Service* s, void* out, size_t out_size, u64 app_id, NcmContentType content_type);
|
||||||
|
Result nsamResolveApplicationContentPathFwd(Service* s, u64 app_id, NcmContentType content_type);
|
||||||
|
Result nsamGetRunningApplicationProgramIdFwd(Service* s, u64* out_program_id, u64 app_id);
|
||||||
|
|
||||||
|
Result nswebGetApplicationContentPath(NsDocumentInterface* doc, void* out, size_t out_size, u64 app_id, NcmContentType content_type);
|
||||||
|
Result nswebResolveApplicationContentPath(NsDocumentInterface* doc, u64 app_id, NcmContentType content_type);
|
||||||
|
Result nswebGetRunningApplicationProgramId(NsDocumentInterface* doc, u64* out_program_id, u64 app_id);
|
||||||
|
|
||||||
|
void nsDocumentInterfaceClose(NsDocumentInterface* doc);
|
||||||
|
|
||||||
|
#ifdef __cplusplus
|
||||||
|
}
|
||||||
|
#endif
|
50
stratosphere/ams_mitm/source/ns_mitm/ns_web_mitm_service.cpp
Normal file
50
stratosphere/ams_mitm/source/ns_mitm/ns_web_mitm_service.cpp
Normal file
|
@ -0,0 +1,50 @@
|
||||||
|
/*
|
||||||
|
* Copyright (c) 2018-2019 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/>.
|
||||||
|
*/
|
||||||
|
#include <stratosphere.hpp>
|
||||||
|
#include "ns_web_mitm_service.hpp"
|
||||||
|
|
||||||
|
namespace ams::mitm::ns {
|
||||||
|
|
||||||
|
Result NsDocumentService::GetApplicationContentPath(const sf::OutBuffer &out_path, ncm::ProgramId application_id, u8 content_type) {
|
||||||
|
return nswebGetApplicationContentPath(this->srv.get(), out_path.GetPointer(), out_path.GetSize(), static_cast<u64>(application_id), static_cast<NcmContentType>(content_type));
|
||||||
|
}
|
||||||
|
|
||||||
|
Result NsDocumentService::ResolveApplicationContentPath(ncm::ProgramId application_id, u8 content_type) {
|
||||||
|
/* Always succeed for web applets asking about HBL. */
|
||||||
|
/* This enables hbl html. */
|
||||||
|
bool is_hbl;
|
||||||
|
if (R_SUCCEEDED(pm::info::IsHblProgramId(&is_hbl, application_id)) && is_hbl) {
|
||||||
|
nswebResolveApplicationContentPath(this->srv.get(), static_cast<u64>(application_id), static_cast<NcmContentType>(content_type));
|
||||||
|
return ResultSuccess();
|
||||||
|
}
|
||||||
|
return nswebResolveApplicationContentPath(this->srv.get(), static_cast<u64>(application_id), static_cast<NcmContentType>(content_type));
|
||||||
|
}
|
||||||
|
|
||||||
|
Result NsDocumentService::GetRunningApplicationProgramId(sf::Out<ncm::ProgramId> out, ncm::ProgramId application_id) {
|
||||||
|
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) {
|
||||||
|
/* 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);
|
||||||
|
return ResultSuccess();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
|
@ -16,25 +16,58 @@
|
||||||
#pragma once
|
#pragma once
|
||||||
#include <stratosphere.hpp>
|
#include <stratosphere.hpp>
|
||||||
|
|
||||||
|
#include "ns_shim.h"
|
||||||
|
|
||||||
namespace ams::mitm::ns {
|
namespace ams::mitm::ns {
|
||||||
|
|
||||||
|
class NsDocumentService : public sf::IServiceObject {
|
||||||
|
private:
|
||||||
|
enum class CommandId {
|
||||||
|
GetApplicationContentPath = 21,
|
||||||
|
ResolveApplicationContentPath = 23,
|
||||||
|
GetRunningApplicationProgramId = 92,
|
||||||
|
};
|
||||||
|
private:
|
||||||
|
sm::MitmProcessInfo client_info;
|
||||||
|
std::unique_ptr<::NsDocumentInterface> srv;
|
||||||
|
public:
|
||||||
|
NsDocumentService(const sm::MitmProcessInfo &cl, std::unique_ptr<::NsDocumentInterface> s) : client_info(cl), srv(std::move(s)) { /* .. */ }
|
||||||
|
|
||||||
|
virtual ~NsDocumentService() {
|
||||||
|
nsDocumentInterfaceClose(this->srv.get());
|
||||||
|
}
|
||||||
|
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_600),
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
class NsWebMitmService : public sf::IMitmServiceObject {
|
class NsWebMitmService : public sf::IMitmServiceObject {
|
||||||
private:
|
private:
|
||||||
enum class CommandId {
|
enum class CommandId {
|
||||||
/* TODO */
|
GetDocumentInterface = 7999,
|
||||||
};
|
};
|
||||||
public:
|
public:
|
||||||
static bool ShouldMitm(const sm::MitmProcessInfo &client_info) {
|
static bool ShouldMitm(const sm::MitmProcessInfo &client_info) {
|
||||||
/* TODO */
|
/* We will mitm:
|
||||||
return false;
|
* - web applets, to facilitate hbl web browser launching.
|
||||||
|
*/
|
||||||
|
return ncm::IsWebAppletProgramId(client_info.program_id);
|
||||||
}
|
}
|
||||||
public:
|
public:
|
||||||
SF_MITM_SERVICE_OBJECT_CTOR(NsWebMitmService) { /* ... */ }
|
SF_MITM_SERVICE_OBJECT_CTOR(NsWebMitmService) { /* ... */ }
|
||||||
protected:
|
protected:
|
||||||
/* TODO */
|
Result GetDocumentInterface(sf::Out<std::shared_ptr<NsDocumentService>> out);
|
||||||
public:
|
public:
|
||||||
DEFINE_SERVICE_DISPATCH_TABLE {
|
DEFINE_SERVICE_DISPATCH_TABLE {
|
||||||
/* TODO */
|
MAKE_SERVICE_COMMAND_META(GetDocumentInterface),
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -421,6 +421,14 @@ namespace ams::ncm {
|
||||||
return ProgramId::ApplicationStart <= program_id && program_id <= ProgramId::ApplicationEnd;
|
return ProgramId::ApplicationStart <= program_id && program_id <= ProgramId::ApplicationEnd;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
inline constexpr bool IsWebAppletProgramId(const ProgramId &program_id) {
|
||||||
|
return program_id == ProgramId::AppletWeb ||
|
||||||
|
program_id == ProgramId::AppletShop ||
|
||||||
|
program_id == ProgramId::AppletOfflineWeb ||
|
||||||
|
program_id == ProgramId::AppletLoginShare ||
|
||||||
|
program_id == ProgramId::AppletWifiWebAuth;
|
||||||
|
}
|
||||||
|
|
||||||
static_assert(sizeof(ProgramId) == sizeof(u64) && std::is_pod<ProgramId>::value, "ProgramId definition!");
|
static_assert(sizeof(ProgramId) == sizeof(u64) && std::is_pod<ProgramId>::value, "ProgramId definition!");
|
||||||
|
|
||||||
/* Program Location. */
|
/* Program Location. */
|
||||||
|
|
|
@ -31,4 +31,7 @@ namespace ams::pm::info {
|
||||||
/* Information convenience API. */
|
/* Information convenience API. */
|
||||||
bool HasLaunchedProgram(ncm::ProgramId program_id);
|
bool HasLaunchedProgram(ncm::ProgramId program_id);
|
||||||
|
|
||||||
|
Result IsHblProcessId(bool *out, os::ProcessId process_id);
|
||||||
|
Result IsHblProgramId(bool *out, ncm::ProgramId program_id);
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
|
@ -20,7 +20,10 @@
|
||||||
|
|
||||||
namespace ams::sf {
|
namespace ams::sf {
|
||||||
|
|
||||||
class IServiceObject{};
|
class IServiceObject {
|
||||||
|
public:
|
||||||
|
virtual ~IServiceObject() { /* ... */ }
|
||||||
|
};
|
||||||
|
|
||||||
class IMitmServiceObject : public IServiceObject {
|
class IMitmServiceObject : public IServiceObject {
|
||||||
protected:
|
protected:
|
||||||
|
@ -29,6 +32,8 @@ namespace ams::sf {
|
||||||
public:
|
public:
|
||||||
IMitmServiceObject(std::shared_ptr<::Service> &&s, const sm::MitmProcessInfo &c) : forward_service(std::move(s)), client_info(c) { /* ... */ }
|
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);
|
static bool ShouldMitm(os::ProcessId process_id, ncm::ProgramId program_id);
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
|
@ -73,4 +73,21 @@ namespace ams::pm::info {
|
||||||
return has_launched;
|
return has_launched;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
Result IsHblProcessId(bool *out, os::ProcessId process_id) {
|
||||||
|
ncm::ProgramLocation loc;
|
||||||
|
cfg::OverrideStatus override_status;
|
||||||
|
R_TRY(GetProcessInfo(&loc, &override_status, process_id));
|
||||||
|
|
||||||
|
*out = override_status.IsHbl();
|
||||||
|
return ResultSuccess();
|
||||||
|
}
|
||||||
|
|
||||||
|
Result IsHblProgramId(bool *out, ncm::ProgramId program_id) {
|
||||||
|
os::ProcessId process_id;
|
||||||
|
R_TRY(GetProcessId(&process_id, program_id));
|
||||||
|
|
||||||
|
return IsHblProcessId(out, process_id);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue