mirror of
https://github.com/switchbrew/libnx.git
synced 2025-06-25 06:12:40 +02:00
IPC: Improve information available in IpcParsedCommand (#72)
* IPC: Add C descriptor support to IpcParsedCommand * Add Command Type to IpcParsedCommand * Replace constants with IpcCommandType where relevant. * Add RawWithoutPadding pointer, required for serverside deserialization calculations.
This commit is contained in:
parent
b18854555a
commit
f40f544a07
@ -37,6 +37,17 @@ typedef enum {
|
|||||||
BufferDirection_Exch=2,
|
BufferDirection_Exch=2,
|
||||||
} BufferDirection;
|
} BufferDirection;
|
||||||
|
|
||||||
|
typedef enum {
|
||||||
|
IpcCommandType_Invalid = 0,
|
||||||
|
IpcCommandType_LegacyRequest = 1,
|
||||||
|
IpcCommandType_Close = 2,
|
||||||
|
IpcCommandType_LegacyControl = 3,
|
||||||
|
IpcCommandType_Request = 4,
|
||||||
|
IpcCommandType_Control = 5,
|
||||||
|
IpcCommandType_RequestWithContext = 6,
|
||||||
|
IpcCommandType_ControlWithContext = 7
|
||||||
|
} IpcCommandType;
|
||||||
|
|
||||||
typedef struct {
|
typedef struct {
|
||||||
size_t NumSend; // A
|
size_t NumSend; // A
|
||||||
size_t NumRecv; // B
|
size_t NumRecv; // B
|
||||||
@ -199,7 +210,7 @@ static inline void ipcSendHandleMove(IpcCommand* cmd, Handle h) {
|
|||||||
static inline void* ipcPrepareHeader(IpcCommand* cmd, size_t sizeof_raw) {
|
static inline void* ipcPrepareHeader(IpcCommand* cmd, size_t sizeof_raw) {
|
||||||
u32* buf = (u32*)armGetTls();
|
u32* buf = (u32*)armGetTls();
|
||||||
size_t i;
|
size_t i;
|
||||||
*buf++ = 4 | (cmd->NumStaticIn << 16) | (cmd->NumSend << 20) | (cmd->NumRecv << 24) | (cmd->NumExch << 28);
|
*buf++ = IpcCommandType_Request | (cmd->NumStaticIn << 16) | (cmd->NumSend << 20) | (cmd->NumRecv << 24) | (cmd->NumExch << 28);
|
||||||
|
|
||||||
u32* fill_in_size_later = buf;
|
u32* fill_in_size_later = buf;
|
||||||
|
|
||||||
@ -292,6 +303,8 @@ static inline Result ipcDispatch(Handle session) {
|
|||||||
|
|
||||||
/// IPC parsed command (response) structure.
|
/// IPC parsed command (response) structure.
|
||||||
typedef struct {
|
typedef struct {
|
||||||
|
IpcCommandType CommandType; ///< Type of the command
|
||||||
|
|
||||||
bool HasPid; ///< true if the 'Pid' field is filled out.
|
bool HasPid; ///< true if the 'Pid' field is filled out.
|
||||||
u64 Pid; ///< PID included in the response (only if HasPid is true)
|
u64 Pid; ///< PID included in the response (only if HasPid is true)
|
||||||
|
|
||||||
@ -313,8 +326,11 @@ typedef struct {
|
|||||||
void* Statics[IPC_MAX_BUFFERS]; ///< Pointers to the statics.
|
void* Statics[IPC_MAX_BUFFERS]; ///< Pointers to the statics.
|
||||||
size_t StaticSizes[IPC_MAX_BUFFERS]; ///< Sizes of the statics.
|
size_t StaticSizes[IPC_MAX_BUFFERS]; ///< Sizes of the statics.
|
||||||
u8 StaticIndices[IPC_MAX_BUFFERS]; ///< Indices of the statics.
|
u8 StaticIndices[IPC_MAX_BUFFERS]; ///< Indices of the statics.
|
||||||
|
|
||||||
|
size_t NumStaticsOut; ///< Number of output statics available in the response.
|
||||||
|
|
||||||
void* Raw; ///< Pointer to the raw embedded data structure in the response.
|
void* Raw; ///< Pointer to the raw embedded data structure in the response.
|
||||||
|
void* RawWithoutPadding; ///< Pointer to the raw embedded data structure, without padding.
|
||||||
size_t RawSize; ///< Size of the raw embedded data.
|
size_t RawSize; ///< Size of the raw embedded data.
|
||||||
} IpcParsedCommand;
|
} IpcParsedCommand;
|
||||||
|
|
||||||
@ -329,9 +345,14 @@ static inline Result ipcParse(IpcParsedCommand* r) {
|
|||||||
u32 ctrl1 = *buf++;
|
u32 ctrl1 = *buf++;
|
||||||
size_t i;
|
size_t i;
|
||||||
|
|
||||||
|
r->CommandType = (IpcCommandType) (ctrl0 & 0xffff);
|
||||||
r->HasPid = false;
|
r->HasPid = false;
|
||||||
r->RawSize = (ctrl1 & 0x1ff) * 4;
|
r->RawSize = (ctrl1 & 0x1ff) * 4;
|
||||||
r->NumHandles = 0;
|
r->NumHandles = 0;
|
||||||
|
|
||||||
|
r->NumStaticsOut = (ctrl1 >> 10) & 15;
|
||||||
|
if (r->NumStaticsOut >> 1) r->NumStaticsOut--; // Value 2 -> Single descriptor
|
||||||
|
if (r->NumStaticsOut >> 1) r->NumStaticsOut--; // Value 3+ -> (Value - 2) descriptors
|
||||||
|
|
||||||
if (ctrl1 & 0x80000000) {
|
if (ctrl1 & 0x80000000) {
|
||||||
u32 ctrl2 = *buf++;
|
u32 ctrl2 = *buf++;
|
||||||
@ -385,6 +406,7 @@ static inline Result ipcParse(IpcParsedCommand* r) {
|
|||||||
|
|
||||||
size_t num_bufs = num_bufs_send + num_bufs_recv + num_bufs_exch;
|
size_t num_bufs = num_bufs_send + num_bufs_recv + num_bufs_exch;
|
||||||
r->Raw = (void*)(((uintptr_t)(buf + num_bufs*3) + 15) &~ 15);
|
r->Raw = (void*)(((uintptr_t)(buf + num_bufs*3) + 15) &~ 15);
|
||||||
|
r->RawWithoutPadding = (void*)((uintptr_t)(buf + num_bufs*3));
|
||||||
|
|
||||||
if (num_bufs > IPC_MAX_BUFFERS)
|
if (num_bufs > IPC_MAX_BUFFERS)
|
||||||
num_bufs = IPC_MAX_BUFFERS;
|
num_bufs = IPC_MAX_BUFFERS;
|
||||||
@ -418,7 +440,7 @@ static inline Result ipcParse(IpcParsedCommand* r) {
|
|||||||
static inline Result ipcQueryPointerBufferSize(Handle session, size_t *size) {
|
static inline Result ipcQueryPointerBufferSize(Handle session, size_t *size) {
|
||||||
u32* buf = (u32*)armGetTls();
|
u32* buf = (u32*)armGetTls();
|
||||||
|
|
||||||
buf[0] = 5;
|
buf[0] = IpcCommandType_Control;
|
||||||
buf[1] = 8;
|
buf[1] = 8;
|
||||||
buf[2] = 0;
|
buf[2] = 0;
|
||||||
buf[3] = 0;
|
buf[3] = 0;
|
||||||
@ -456,7 +478,7 @@ static inline Result ipcQueryPointerBufferSize(Handle session, size_t *size) {
|
|||||||
*/
|
*/
|
||||||
static inline Result ipcCloseSession(Handle session) {
|
static inline Result ipcCloseSession(Handle session) {
|
||||||
u32* buf = (u32*)armGetTls();
|
u32* buf = (u32*)armGetTls();
|
||||||
buf[0] = 2;
|
buf[0] = IpcCommandType_Close;
|
||||||
return ipcDispatch(session);
|
return ipcDispatch(session);
|
||||||
}
|
}
|
||||||
///@}
|
///@}
|
||||||
@ -473,7 +495,7 @@ static inline Result ipcCloseSession(Handle session) {
|
|||||||
static inline Result ipcConvertSessionToDomain(Handle session, u32* object_id_out) {
|
static inline Result ipcConvertSessionToDomain(Handle session, u32* object_id_out) {
|
||||||
u32* buf = (u32*)armGetTls();
|
u32* buf = (u32*)armGetTls();
|
||||||
|
|
||||||
buf[0] = 5;
|
buf[0] = IpcCommandType_Control;
|
||||||
buf[1] = 8;
|
buf[1] = 8;
|
||||||
buf[4] = SFCI_MAGIC;
|
buf[4] = SFCI_MAGIC;
|
||||||
buf[5] = 0;
|
buf[5] = 0;
|
||||||
|
Loading…
Reference in New Issue
Block a user