mirror of
https://github.com/switchbrew/libnx.git
synced 2025-06-22 13:02:38 +02:00
Implement ro:1
This commit is contained in:
parent
23bd10f6db
commit
50db74a15b
@ -12,6 +12,9 @@
|
|||||||
Result ldrRoInitialize(void);
|
Result ldrRoInitialize(void);
|
||||||
void ldrRoExit(void);
|
void ldrRoExit(void);
|
||||||
|
|
||||||
|
Result ro1Initialize(void);
|
||||||
|
void ro1Exit(void);
|
||||||
|
|
||||||
Result roDmntInitialize(void);
|
Result roDmntInitialize(void);
|
||||||
void roDmntExit(void);
|
void roDmntExit(void);
|
||||||
|
|
||||||
@ -21,4 +24,10 @@ Result ldrRoLoadNrr(u64 nrr_address, u64 nrr_size);
|
|||||||
Result ldrRoUnloadNrr(u64 nrr_address);
|
Result ldrRoUnloadNrr(u64 nrr_address);
|
||||||
Result ldrRoLoadNrrEx(u64 nrr_address, u64 nrr_size);
|
Result ldrRoLoadNrrEx(u64 nrr_address, u64 nrr_size);
|
||||||
|
|
||||||
|
Result ro1LoadNro(u64* out_address, u64 nro_address, u64 nro_size, u64 bss_address, u64 bss_size);
|
||||||
|
Result ro1UnloadNro(u64 nro_address);
|
||||||
|
Result ro1LoadNrr(u64 nrr_address, u64 nrr_size);
|
||||||
|
Result ro1UnloadNrr(u64 nrr_address);
|
||||||
|
Result ro1LoadNrrEx(u64 nrr_address, u64 nrr_size);
|
||||||
|
|
||||||
Result roDmntGetModuleInfos(u64 pid, LoaderModuleInfo *out_module_infos, size_t max_out_modules, u32 *num_out);
|
Result roDmntGetModuleInfos(u64 pid, LoaderModuleInfo *out_module_infos, size_t max_out_modules, u32 *num_out);
|
||||||
|
@ -8,10 +8,14 @@
|
|||||||
#include "services/ro.h"
|
#include "services/ro.h"
|
||||||
#include "services/sm.h"
|
#include "services/sm.h"
|
||||||
|
|
||||||
static Service g_roSrv, g_dmntSrv;
|
static Service g_roSrv, g_ro1Srv, g_dmntSrv;
|
||||||
static u64 g_roRefCnt, g_dmntRefCnt;
|
static u64 g_roRefCnt, g_ro1RefCnt, g_dmntRefCnt;
|
||||||
|
|
||||||
static Result _ldrRoInitialize(void);
|
static Result _rosrvInitialize(Service* srv);
|
||||||
|
static Result _rosrvLoadNro(Service* srv, u64* out_address, u64 nro_address, u64 nro_size, u64 bss_address, u64 bss_size);
|
||||||
|
static Result _rosrvUnloadNro(Service* srv, u64 nro_address);
|
||||||
|
static Result _rosrvLoadNrr(Service* srv, u64 cmd_id, u64 nrr_address, u64 nrr_size);
|
||||||
|
static Result _rosrvUnloadNrr(Service* srv, u64 nrr_address);
|
||||||
|
|
||||||
Result ldrRoInitialize(void) {
|
Result ldrRoInitialize(void) {
|
||||||
atomicIncrement64(&g_roRefCnt);
|
atomicIncrement64(&g_roRefCnt);
|
||||||
@ -22,7 +26,7 @@ Result ldrRoInitialize(void) {
|
|||||||
Result rc = smGetService(&g_roSrv, "ldr:ro");
|
Result rc = smGetService(&g_roSrv, "ldr:ro");
|
||||||
|
|
||||||
if (R_SUCCEEDED(rc)) {
|
if (R_SUCCEEDED(rc)) {
|
||||||
rc = _ldrRoInitialize();
|
rc = _rosrvInitialize(&g_roSrv);
|
||||||
}
|
}
|
||||||
|
|
||||||
return rc;
|
return rc;
|
||||||
@ -33,6 +37,28 @@ void ldrRoExit(void) {
|
|||||||
serviceClose(&g_roSrv);
|
serviceClose(&g_roSrv);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Result ro1Initialize(void) {
|
||||||
|
if (hosversionBefore(7,0,0)) return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer);
|
||||||
|
|
||||||
|
atomicIncrement64(&g_ro1RefCnt);
|
||||||
|
|
||||||
|
if (serviceIsActive(&g_ro1Srv))
|
||||||
|
return 0;
|
||||||
|
|
||||||
|
Result rc = smGetService(&g_ro1Srv, "ro:1");
|
||||||
|
|
||||||
|
if (R_SUCCEEDED(rc)) {
|
||||||
|
rc = _rosrvInitialize(&g_ro1Srv);
|
||||||
|
}
|
||||||
|
|
||||||
|
return rc;
|
||||||
|
}
|
||||||
|
|
||||||
|
void ro1Exit(void) {
|
||||||
|
if (atomicDecrement64(&g_ro1RefCnt) == 0)
|
||||||
|
serviceClose(&g_ro1Srv);
|
||||||
|
}
|
||||||
|
|
||||||
Result roDmntInitialize(void) {
|
Result roDmntInitialize(void) {
|
||||||
if (hosversionBefore(3,0,0)) return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer);
|
if (hosversionBefore(3,0,0)) return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer);
|
||||||
|
|
||||||
@ -49,7 +75,40 @@ void roDmntExit(void) {
|
|||||||
serviceClose(&g_dmntSrv);
|
serviceClose(&g_dmntSrv);
|
||||||
}
|
}
|
||||||
|
|
||||||
Result ldrRoLoadNro(u64* out_address, u64 nro_address, u64 nro_size, u64 bss_address, u64 bss_size) {
|
Result _rosrvInitialize(Service* srv) {
|
||||||
|
IpcCommand c;
|
||||||
|
ipcInitialize(&c);
|
||||||
|
ipcSendHandleCopy(&c, CUR_PROCESS_HANDLE);
|
||||||
|
|
||||||
|
struct {
|
||||||
|
u64 magic;
|
||||||
|
u64 cmd_id;
|
||||||
|
} *raw;
|
||||||
|
|
||||||
|
raw = serviceIpcPrepareHeader(srv, &c, sizeof(*raw));
|
||||||
|
|
||||||
|
raw->magic = SFCI_MAGIC;
|
||||||
|
raw->cmd_id = 4;
|
||||||
|
|
||||||
|
Result rc = serviceIpcDispatch(srv);
|
||||||
|
|
||||||
|
if (R_SUCCEEDED(rc)) {
|
||||||
|
IpcParsedCommand r;
|
||||||
|
struct {
|
||||||
|
u64 magic;
|
||||||
|
u64 result;
|
||||||
|
} *resp;
|
||||||
|
|
||||||
|
serviceIpcParse(srv, &r, sizeof(*resp));
|
||||||
|
resp = r.Raw;
|
||||||
|
|
||||||
|
rc = resp->result;
|
||||||
|
}
|
||||||
|
|
||||||
|
return rc;
|
||||||
|
}
|
||||||
|
|
||||||
|
Result _rosrvLoadNro(Service* srv, u64* out_address, u64 nro_address, u64 nro_size, u64 bss_address, u64 bss_size) {
|
||||||
IpcCommand c;
|
IpcCommand c;
|
||||||
ipcInitialize(&c);
|
ipcInitialize(&c);
|
||||||
ipcSendPid(&c);
|
ipcSendPid(&c);
|
||||||
@ -64,7 +123,7 @@ Result ldrRoLoadNro(u64* out_address, u64 nro_address, u64 nro_size, u64 bss_add
|
|||||||
u64 bss_size;
|
u64 bss_size;
|
||||||
} *raw;
|
} *raw;
|
||||||
|
|
||||||
raw = serviceIpcPrepareHeader(&g_roSrv, &c, sizeof(*raw));
|
raw = serviceIpcPrepareHeader(srv, &c, sizeof(*raw));
|
||||||
|
|
||||||
raw->magic = SFCI_MAGIC;
|
raw->magic = SFCI_MAGIC;
|
||||||
raw->cmd_id = 0;
|
raw->cmd_id = 0;
|
||||||
@ -74,7 +133,7 @@ Result ldrRoLoadNro(u64* out_address, u64 nro_address, u64 nro_size, u64 bss_add
|
|||||||
raw->bss_address = bss_address;
|
raw->bss_address = bss_address;
|
||||||
raw->bss_size = bss_size;
|
raw->bss_size = bss_size;
|
||||||
|
|
||||||
Result rc = serviceIpcDispatch(&g_roSrv);
|
Result rc = serviceIpcDispatch(srv);
|
||||||
|
|
||||||
if (R_SUCCEEDED(rc)) {
|
if (R_SUCCEEDED(rc)) {
|
||||||
IpcParsedCommand r;
|
IpcParsedCommand r;
|
||||||
@ -84,7 +143,7 @@ Result ldrRoLoadNro(u64* out_address, u64 nro_address, u64 nro_size, u64 bss_add
|
|||||||
u64 out_address;
|
u64 out_address;
|
||||||
} *resp;
|
} *resp;
|
||||||
|
|
||||||
serviceIpcParse(&g_roSrv, &r, sizeof(*resp));
|
serviceIpcParse(srv, &r, sizeof(*resp));
|
||||||
resp = r.Raw;
|
resp = r.Raw;
|
||||||
|
|
||||||
rc = resp->result;
|
rc = resp->result;
|
||||||
@ -97,7 +156,7 @@ Result ldrRoLoadNro(u64* out_address, u64 nro_address, u64 nro_size, u64 bss_add
|
|||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
Result ldrRoUnloadNro(u64 nro_address) {
|
Result _rosrvUnloadNro(Service* srv, u64 nro_address) {
|
||||||
IpcCommand c;
|
IpcCommand c;
|
||||||
ipcInitialize(&c);
|
ipcInitialize(&c);
|
||||||
ipcSendPid(&c);
|
ipcSendPid(&c);
|
||||||
@ -109,14 +168,14 @@ Result ldrRoUnloadNro(u64 nro_address) {
|
|||||||
u64 nro_address;
|
u64 nro_address;
|
||||||
} *raw;
|
} *raw;
|
||||||
|
|
||||||
raw = serviceIpcPrepareHeader(&g_roSrv, &c, sizeof(*raw));
|
raw = serviceIpcPrepareHeader(srv, &c, sizeof(*raw));
|
||||||
|
|
||||||
raw->magic = SFCI_MAGIC;
|
raw->magic = SFCI_MAGIC;
|
||||||
raw->cmd_id = 1;
|
raw->cmd_id = 1;
|
||||||
raw->pid = 0;
|
raw->pid = 0;
|
||||||
raw->nro_address = nro_address;
|
raw->nro_address = nro_address;
|
||||||
|
|
||||||
Result rc = serviceIpcDispatch(&g_roSrv);
|
Result rc = serviceIpcDispatch(srv);
|
||||||
|
|
||||||
if (R_SUCCEEDED(rc)) {
|
if (R_SUCCEEDED(rc)) {
|
||||||
IpcParsedCommand r;
|
IpcParsedCommand r;
|
||||||
@ -125,7 +184,7 @@ Result ldrRoUnloadNro(u64 nro_address) {
|
|||||||
u64 result;
|
u64 result;
|
||||||
} *resp;
|
} *resp;
|
||||||
|
|
||||||
serviceIpcParse(&g_roSrv, &r, sizeof(*resp));
|
serviceIpcParse(srv, &r, sizeof(*resp));
|
||||||
resp = r.Raw;
|
resp = r.Raw;
|
||||||
|
|
||||||
rc = resp->result;
|
rc = resp->result;
|
||||||
@ -134,7 +193,7 @@ Result ldrRoUnloadNro(u64 nro_address) {
|
|||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
static Result _ldrRoLoadNrr(u64 cmd_id, u64 nrr_address, u64 nrr_size) {
|
Result _rosrvLoadNrr(Service* srv, u64 cmd_id, u64 nrr_address, u64 nrr_size) {
|
||||||
IpcCommand c;
|
IpcCommand c;
|
||||||
ipcInitialize(&c);
|
ipcInitialize(&c);
|
||||||
ipcSendPid(&c);
|
ipcSendPid(&c);
|
||||||
@ -147,7 +206,7 @@ static Result _ldrRoLoadNrr(u64 cmd_id, u64 nrr_address, u64 nrr_size) {
|
|||||||
u64 nrr_size;
|
u64 nrr_size;
|
||||||
} *raw;
|
} *raw;
|
||||||
|
|
||||||
raw = serviceIpcPrepareHeader(&g_roSrv, &c, sizeof(*raw));
|
raw = serviceIpcPrepareHeader(srv, &c, sizeof(*raw));
|
||||||
|
|
||||||
raw->magic = SFCI_MAGIC;
|
raw->magic = SFCI_MAGIC;
|
||||||
raw->cmd_id = cmd_id;
|
raw->cmd_id = cmd_id;
|
||||||
@ -155,7 +214,7 @@ static Result _ldrRoLoadNrr(u64 cmd_id, u64 nrr_address, u64 nrr_size) {
|
|||||||
raw->nrr_address = nrr_address;
|
raw->nrr_address = nrr_address;
|
||||||
raw->nrr_size = nrr_size;
|
raw->nrr_size = nrr_size;
|
||||||
|
|
||||||
Result rc = serviceIpcDispatch(&g_roSrv);
|
Result rc = serviceIpcDispatch(srv);
|
||||||
|
|
||||||
if (R_SUCCEEDED(rc)) {
|
if (R_SUCCEEDED(rc)) {
|
||||||
IpcParsedCommand r;
|
IpcParsedCommand r;
|
||||||
@ -164,7 +223,7 @@ static Result _ldrRoLoadNrr(u64 cmd_id, u64 nrr_address, u64 nrr_size) {
|
|||||||
u64 result;
|
u64 result;
|
||||||
} *resp;
|
} *resp;
|
||||||
|
|
||||||
serviceIpcParse(&g_roSrv, &r, sizeof(*resp));
|
serviceIpcParse(srv, &r, sizeof(*resp));
|
||||||
resp = r.Raw;
|
resp = r.Raw;
|
||||||
|
|
||||||
rc = resp->result;
|
rc = resp->result;
|
||||||
@ -173,11 +232,7 @@ static Result _ldrRoLoadNrr(u64 cmd_id, u64 nrr_address, u64 nrr_size) {
|
|||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
Result ldrRoLoadNrr(u64 nrr_address, u64 nrr_size) {
|
Result _rosrvUnloadNrr(Service* srv, u64 nrr_address) {
|
||||||
return _ldrRoLoadNrr(2, nrr_address, nrr_size);
|
|
||||||
}
|
|
||||||
|
|
||||||
Result ldrRoUnloadNrr(u64 nrr_address) {
|
|
||||||
IpcCommand c;
|
IpcCommand c;
|
||||||
ipcInitialize(&c);
|
ipcInitialize(&c);
|
||||||
ipcSendPid(&c);
|
ipcSendPid(&c);
|
||||||
@ -189,14 +244,14 @@ Result ldrRoUnloadNrr(u64 nrr_address) {
|
|||||||
u64 nrr_address;
|
u64 nrr_address;
|
||||||
} *raw;
|
} *raw;
|
||||||
|
|
||||||
raw = serviceIpcPrepareHeader(&g_roSrv, &c, sizeof(*raw));
|
raw = serviceIpcPrepareHeader(srv, &c, sizeof(*raw));
|
||||||
|
|
||||||
raw->magic = SFCI_MAGIC;
|
raw->magic = SFCI_MAGIC;
|
||||||
raw->cmd_id = 3;
|
raw->cmd_id = 3;
|
||||||
raw->pid = 0;
|
raw->pid = 0;
|
||||||
raw->nrr_address = nrr_address;
|
raw->nrr_address = nrr_address;
|
||||||
|
|
||||||
Result rc = serviceIpcDispatch(&g_roSrv);
|
Result rc = serviceIpcDispatch(srv);
|
||||||
|
|
||||||
if (R_SUCCEEDED(rc)) {
|
if (R_SUCCEEDED(rc)) {
|
||||||
IpcParsedCommand r;
|
IpcParsedCommand r;
|
||||||
@ -205,7 +260,7 @@ Result ldrRoUnloadNrr(u64 nrr_address) {
|
|||||||
u64 result;
|
u64 result;
|
||||||
} *resp;
|
} *resp;
|
||||||
|
|
||||||
serviceIpcParse(&g_roSrv, &r, sizeof(*resp));
|
serviceIpcParse(srv, &r, sizeof(*resp));
|
||||||
resp = r.Raw;
|
resp = r.Raw;
|
||||||
|
|
||||||
rc = resp->result;
|
rc = resp->result;
|
||||||
@ -214,44 +269,47 @@ Result ldrRoUnloadNrr(u64 nrr_address) {
|
|||||||
return rc;
|
return rc;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Result ldrRoLoadNro(u64* out_address, u64 nro_address, u64 nro_size, u64 bss_address, u64 bss_size) {
|
||||||
|
return _rosrvLoadNro(&g_roSrv, out_address, nro_address, nro_size, bss_address, bss_size);
|
||||||
|
}
|
||||||
|
|
||||||
|
Result ldrRoUnloadNro(u64 nro_address) {
|
||||||
|
return _rosrvUnloadNro(&g_roSrv, nro_address);
|
||||||
|
}
|
||||||
|
|
||||||
|
Result ldrRoLoadNrr(u64 nrr_address, u64 nrr_size) {
|
||||||
|
return _rosrvLoadNrr(&g_roSrv, 2, nrr_address, nrr_size);
|
||||||
|
}
|
||||||
|
|
||||||
|
Result ldrRoUnloadNrr(u64 nrr_address) {
|
||||||
|
return _rosrvUnloadNrr(&g_roSrv, nrr_address);
|
||||||
|
}
|
||||||
|
|
||||||
Result ldrRoLoadNrrEx(u64 nrr_address, u64 nrr_size) {
|
Result ldrRoLoadNrrEx(u64 nrr_address, u64 nrr_size) {
|
||||||
if (hosversionBefore(7,0,0)) {
|
if (hosversionBefore(7,0,0)) {
|
||||||
return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer);
|
return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer);
|
||||||
}
|
}
|
||||||
return _ldrRoLoadNrr(10, nrr_address, nrr_size);
|
return _rosrvLoadNrr(&g_roSrv, 10, nrr_address, nrr_size);
|
||||||
}
|
}
|
||||||
|
|
||||||
Result _ldrRoInitialize(void) {
|
Result ro1LoadNro(u64* out_address, u64 nro_address, u64 nro_size, u64 bss_address, u64 bss_size) {
|
||||||
IpcCommand c;
|
return _rosrvLoadNro(&g_ro1Srv, out_address, nro_address, nro_size, bss_address, bss_size);
|
||||||
ipcInitialize(&c);
|
|
||||||
ipcSendHandleCopy(&c, CUR_PROCESS_HANDLE);
|
|
||||||
|
|
||||||
struct {
|
|
||||||
u64 magic;
|
|
||||||
u64 cmd_id;
|
|
||||||
} *raw;
|
|
||||||
|
|
||||||
raw = serviceIpcPrepareHeader(&g_roSrv, &c, sizeof(*raw));
|
|
||||||
|
|
||||||
raw->magic = SFCI_MAGIC;
|
|
||||||
raw->cmd_id = 4;
|
|
||||||
|
|
||||||
Result rc = serviceIpcDispatch(&g_roSrv);
|
|
||||||
|
|
||||||
if (R_SUCCEEDED(rc)) {
|
|
||||||
IpcParsedCommand r;
|
|
||||||
struct {
|
|
||||||
u64 magic;
|
|
||||||
u64 result;
|
|
||||||
} *resp;
|
|
||||||
|
|
||||||
serviceIpcParse(&g_roSrv, &r, sizeof(*resp));
|
|
||||||
resp = r.Raw;
|
|
||||||
|
|
||||||
rc = resp->result;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return rc;
|
Result ro1UnloadNro(u64 nro_address) {
|
||||||
|
return _rosrvUnloadNro(&g_ro1Srv, nro_address);
|
||||||
|
}
|
||||||
|
|
||||||
|
Result ro1LoadNrr(u64 nrr_address, u64 nrr_size) {
|
||||||
|
return _rosrvLoadNrr(&g_ro1Srv, 2, nrr_address, nrr_size);
|
||||||
|
}
|
||||||
|
|
||||||
|
Result ro1UnloadNrr(u64 nrr_address) {
|
||||||
|
return _rosrvUnloadNrr(&g_ro1Srv, nrr_address);
|
||||||
|
}
|
||||||
|
|
||||||
|
Result ro1LoadNrrEx(u64 nrr_address, u64 nrr_size) {
|
||||||
|
return _rosrvLoadNrr(&g_ro1Srv, 10, nrr_address, nrr_size);
|
||||||
}
|
}
|
||||||
|
|
||||||
Result roDmntGetModuleInfos(u64 pid, LoaderModuleInfo *out_module_infos, size_t max_out_modules, u32 *num_out) {
|
Result roDmntGetModuleInfos(u64 pid, LoaderModuleInfo *out_module_infos, size_t max_out_modules, u32 *num_out) {
|
||||||
|
Loading…
Reference in New Issue
Block a user