mirror of
https://github.com/switchbrew/libnx.git
synced 2025-06-21 20:42:44 +02:00
hidsys: Updated for new-ipc. Updated param types. Fixed cmd order. Fixed _hidsysGetMaskedSupportedNpadStyleSet to actually use the input AppletResourceUserId, not g_hidsysAppletResourceUserId. Added hidsysAcquireSleepButtonEventHandle to the .h, which was previously missing. Minor changes + improved docs.
This commit is contained in:
parent
d3376aa816
commit
55f769e0b8
@ -7,7 +7,7 @@
|
||||
#include "../types.h"
|
||||
#include "../kernel/event.h"
|
||||
#include "../services/hid.h"
|
||||
#include "../services/sm.h"
|
||||
#include "../sf/service.h"
|
||||
|
||||
/// Mini Cycle struct for \ref HidsysNotificationLedPattern.
|
||||
typedef struct {
|
||||
@ -32,24 +32,49 @@ typedef struct {
|
||||
u8 pad_x46[0x2]; ///< Padding
|
||||
} HidsysNotificationLedPattern;
|
||||
|
||||
/// Initialize hidsys.
|
||||
Result hidsysInitialize(void);
|
||||
|
||||
/// Exit hidsys.
|
||||
void hidsysExit(void);
|
||||
|
||||
/// Gets the Service object for the actual hidsys service session.
|
||||
Service* hidsysGetServiceSession(void);
|
||||
|
||||
Result hidsysEnableAppletToGetInput(bool enable);
|
||||
/**
|
||||
* @brief Returns an event that fires when the home button is pressed, this will prevent the home menu from opening when the button is pressed.
|
||||
* @note The Event must be closed by the user once finished with it.
|
||||
* @param[out] out_event Output Event with autoclear=false.
|
||||
**/
|
||||
Result hidsysAcquireHomeButtonEventHandle(Event* out_event);
|
||||
|
||||
/**
|
||||
* @brief Returns an event that fires when the home button is pressed, this will prevent the home menu from opening when the button is pressed. This event does not auto clear.
|
||||
* @brief Returns an event that fires when the sleep button is pressed.
|
||||
* @note The Event must be closed by the user once finished with it.
|
||||
* @param[out] out_event Output Event with autoclear=false.
|
||||
**/
|
||||
Result hidsysAcquireHomeButtonEventHandle(Event* event_out);
|
||||
Result hidsysAcquireSleepButtonEventHandle(Event* out_event);
|
||||
|
||||
/**
|
||||
* @brief Returns an event that fires when the capture button is pressed. This event does not auto clear.
|
||||
* @brief Returns an event that fires when the capture button is pressed.
|
||||
* @note The Event must be closed by the user once finished with it.
|
||||
* @param[out] out_event Output Event with autoclear=false.
|
||||
**/
|
||||
Result hidsysAcquireCaptureButtonEventHandle(Event* event_out);
|
||||
Result hidsysAcquireCaptureButtonEventHandle(Event* out_event);
|
||||
|
||||
/**
|
||||
* @brief ActivateHomeButton
|
||||
**/
|
||||
Result hidsysActivateHomeButton(void);
|
||||
|
||||
/**
|
||||
* @brief ActivateSleepButton
|
||||
**/
|
||||
Result hidsysActivateSleepButton(void);
|
||||
|
||||
/**
|
||||
* @brief ActivateCaptureButton
|
||||
**/
|
||||
Result hidsysActivateCaptureButton(void);
|
||||
|
||||
/**
|
||||
@ -67,7 +92,13 @@ Result hidsysGetSupportedNpadStyleSetOfCallerApplet(HidControllerType *out);
|
||||
* @param Max number of entries for the UniquePadIds array.
|
||||
* @param total_entries Total output array entries. Optional, can be NULL.
|
||||
*/
|
||||
Result hidsysGetUniquePadsFromNpad(HidControllerID id, u64 *UniquePadIds, size_t count, size_t *total_entries);
|
||||
Result hidsysGetUniquePadsFromNpad(HidControllerID id, u64 *UniquePadIds, s32 count, s32 *total_entries);
|
||||
|
||||
/**
|
||||
* @brief EnableAppletToGetInput
|
||||
* @param[in] enable Input flag.
|
||||
**/
|
||||
Result hidsysEnableAppletToGetInput(bool enable);
|
||||
|
||||
/**
|
||||
* @brief Gets a list of all UniquePadIds.
|
||||
@ -75,7 +106,7 @@ Result hidsysGetUniquePadsFromNpad(HidControllerID id, u64 *UniquePadIds, size_t
|
||||
* @param Max number of entries for the UniquePadIds array.
|
||||
* @param total_entries Total output array entries. Optional, can be NULL.
|
||||
*/
|
||||
Result hidsysGetUniquePadIds(u64 *UniquePadIds, size_t count, size_t *total_entries);
|
||||
Result hidsysGetUniquePadIds(u64 *UniquePadIds, s32 count, s32 *total_entries);
|
||||
|
||||
/**
|
||||
* @brief Sets the HOME-button notification LED pattern, for the specified controller.
|
||||
|
@ -1,26 +1,19 @@
|
||||
#define NX_SERVICE_ASSUME_NON_DOMAIN
|
||||
#include "service_guard.h"
|
||||
#include <string.h>
|
||||
#include "types.h"
|
||||
#include "result.h"
|
||||
#include "arm/atomics.h"
|
||||
#include "kernel/ipc.h"
|
||||
#include "kernel/event.h"
|
||||
#include "services/applet.h"
|
||||
#include "services/hidsys.h"
|
||||
#include "services/hid.h"
|
||||
#include "services/sm.h"
|
||||
#include "runtime/hosversion.h"
|
||||
|
||||
static Service g_hidsysSrv;
|
||||
static u64 g_hidsysRefCnt;
|
||||
|
||||
static u64 g_hidsysAppletResourceUserId = 0;
|
||||
|
||||
Result hidsysInitialize(void) {
|
||||
atomicIncrement64(&g_hidsysRefCnt);
|
||||
|
||||
if (serviceIsActive(&g_hidsysSrv))
|
||||
return 0;
|
||||
NX_GENERATE_SERVICE_GUARD(hidsys);
|
||||
|
||||
Result _hidsysInitialize(void) {
|
||||
Result rc = smGetService(&g_hidsysSrv, "hid:sys");
|
||||
if (R_FAILED(rc))
|
||||
return rc;
|
||||
@ -32,146 +25,48 @@ Result hidsysInitialize(void) {
|
||||
return 0;
|
||||
}
|
||||
|
||||
void hidsysExit(void) {
|
||||
if (atomicDecrement64(&g_hidsysRefCnt) == 0) {
|
||||
void _hidsysCleanup(void) {
|
||||
serviceClose(&g_hidsysSrv);
|
||||
}
|
||||
}
|
||||
|
||||
Service* hidsysGetServiceSession(void) {
|
||||
return &g_hidsysSrv;
|
||||
}
|
||||
|
||||
Result hidsysEnableAppletToGetInput(bool enable) {
|
||||
IpcCommand c;
|
||||
ipcInitialize(&c);
|
||||
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 cmdid;
|
||||
u8 permitInput;
|
||||
u64 appletResourceUserId;
|
||||
} *raw;
|
||||
|
||||
raw = serviceIpcPrepareHeader(&g_hidsysSrv, &c, sizeof(*raw));
|
||||
|
||||
raw->magic = SFCI_MAGIC;
|
||||
raw->cmdid = 503;
|
||||
raw->permitInput = enable != 0;
|
||||
raw->appletResourceUserId = g_hidsysAppletResourceUserId;
|
||||
|
||||
Result rc = serviceIpcDispatch(&g_hidsysSrv);
|
||||
|
||||
if (R_SUCCEEDED(rc)) {
|
||||
IpcParsedCommand r;
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 result;
|
||||
} *resp;
|
||||
|
||||
serviceIpcParse(&g_hidsysSrv, &r, sizeof(*resp));
|
||||
resp = r.Raw;
|
||||
|
||||
rc = resp->result;
|
||||
static Result _hidsysCmdWithResIdAndPid(u32 cmd_id) {
|
||||
return serviceDispatchIn(&g_hidsysSrv, cmd_id, g_hidsysAppletResourceUserId,
|
||||
.in_send_pid = true,
|
||||
);
|
||||
}
|
||||
|
||||
return rc;
|
||||
static Result _hidsysCmdGetHandle(Handle* handle_out, u32 cmd_id) {
|
||||
return serviceDispatchIn(&g_hidsysSrv, cmd_id, g_hidsysAppletResourceUserId,
|
||||
.in_send_pid = true,
|
||||
.out_handle_attrs = { SfOutHandleAttr_HipcCopy },
|
||||
.out_handles = handle_out,
|
||||
);
|
||||
}
|
||||
|
||||
static Result _hidsysCmdWithResIdAndPid(u64 cmd_id) {
|
||||
IpcCommand c;
|
||||
ipcInitialize(&c);
|
||||
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 cmd_id;
|
||||
u64 AppletResourceUserId;
|
||||
} *raw;
|
||||
|
||||
ipcSendPid(&c);
|
||||
raw = serviceIpcPrepareHeader(&g_hidsysSrv, &c, sizeof(*raw));
|
||||
|
||||
raw->magic = SFCI_MAGIC;
|
||||
raw->cmd_id = cmd_id;
|
||||
raw->AppletResourceUserId = g_hidsysAppletResourceUserId;
|
||||
|
||||
Result rc = serviceIpcDispatch(&g_hidsysSrv);
|
||||
|
||||
if (R_SUCCEEDED(rc)) {
|
||||
IpcParsedCommand r;
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 result;
|
||||
} *resp;
|
||||
|
||||
serviceIpcParse(&g_hidsysSrv, &r, sizeof(*resp));
|
||||
resp = r.Raw;
|
||||
|
||||
rc = resp->result;
|
||||
}
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
static Result _hidsysGetHandle(Handle* handle_out, u64 cmd_id) {
|
||||
IpcCommand c;
|
||||
ipcInitialize(&c);
|
||||
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 cmd_id;
|
||||
u64 AppletResourceUserId;
|
||||
} *raw;
|
||||
|
||||
ipcSendPid(&c);
|
||||
raw = serviceIpcPrepareHeader(&g_hidsysSrv, &c, sizeof(*raw));
|
||||
|
||||
raw->magic = SFCI_MAGIC;
|
||||
raw->cmd_id = cmd_id;
|
||||
raw->AppletResourceUserId = g_hidsysAppletResourceUserId;
|
||||
|
||||
Result rc = serviceIpcDispatch(&g_hidsysSrv);
|
||||
|
||||
if (R_SUCCEEDED(rc)) {
|
||||
IpcParsedCommand r;
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 result;
|
||||
} *resp;
|
||||
|
||||
serviceIpcParse(&g_hidsysSrv, &r, sizeof(*resp));
|
||||
resp = r.Raw;
|
||||
|
||||
rc = resp->result;
|
||||
|
||||
if (R_SUCCEEDED(rc)) {
|
||||
*handle_out = r.Handles[0];
|
||||
}
|
||||
}
|
||||
|
||||
return rc;
|
||||
}
|
||||
|
||||
static Result _hidsysGetEvent(Event* event_out, u64 cmd_id, bool autoclear) {
|
||||
Handle tmp_handle=0;
|
||||
static Result _hidsysCmdGetEvent(Event* out_event, bool autoclear, u32 cmd_id) {
|
||||
Handle tmp_handle = INVALID_HANDLE;
|
||||
Result rc = 0;
|
||||
|
||||
rc = _hidsysGetHandle(&tmp_handle, cmd_id);
|
||||
if (R_SUCCEEDED(rc)) eventLoadRemote(event_out, tmp_handle, autoclear);
|
||||
rc = _hidsysCmdGetHandle(&tmp_handle, cmd_id);
|
||||
if (R_SUCCEEDED(rc)) eventLoadRemote(out_event, tmp_handle, autoclear);
|
||||
return rc;
|
||||
}
|
||||
|
||||
Result hidsysAcquireHomeButtonEventHandle(Event* event_out) {
|
||||
return _hidsysGetEvent(event_out, 101, false);
|
||||
Result hidsysAcquireHomeButtonEventHandle(Event* out_event) {
|
||||
return _hidsysCmdGetEvent(out_event, false, 101);
|
||||
}
|
||||
|
||||
//These functions don't seem to work in the overlaydisp applet context
|
||||
Result hidsysAcquireCaptureButtonEventHandle(Event* event_out) {
|
||||
return _hidsysGetEvent(event_out, 141, false);
|
||||
Result hidsysAcquireSleepButtonEventHandle(Event* out_event) {
|
||||
return _hidsysCmdGetEvent(out_event, false, 121);
|
||||
}
|
||||
|
||||
Result hidsysAcquireSleepButtonEventHandle(Event* event_out) {
|
||||
return _hidsysGetEvent(event_out, 121, false);
|
||||
Result hidsysAcquireCaptureButtonEventHandle(Event* out_event) {
|
||||
return _hidsysCmdGetEvent(out_event, false, 141);
|
||||
}
|
||||
|
||||
Result hidsysActivateHomeButton(void) {
|
||||
@ -190,39 +85,9 @@ static Result _hidsysGetMaskedSupportedNpadStyleSet(u64 AppletResourceUserId, Hi
|
||||
if (hosversionBefore(6,0,0))
|
||||
return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer);
|
||||
|
||||
IpcCommand c;
|
||||
ipcInitialize(&c);
|
||||
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 cmd_id;
|
||||
u64 AppletResourceUserId;
|
||||
} *raw;
|
||||
|
||||
raw = serviceIpcPrepareHeader(&g_hidsysSrv, &c, sizeof(*raw));
|
||||
|
||||
raw->magic = SFCI_MAGIC;
|
||||
raw->cmd_id = 310;
|
||||
raw->AppletResourceUserId = g_hidsysAppletResourceUserId;
|
||||
|
||||
Result rc = serviceIpcDispatch(&g_hidsysSrv);
|
||||
|
||||
if (R_SUCCEEDED(rc)) {
|
||||
IpcParsedCommand r;
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 result;
|
||||
u32 out;
|
||||
} *resp;
|
||||
|
||||
serviceIpcParse(&g_hidsysSrv, &r, sizeof(*resp));
|
||||
resp = r.Raw;
|
||||
|
||||
rc = resp->result;
|
||||
|
||||
if (R_SUCCEEDED(rc) && out) *out = resp->out;
|
||||
}
|
||||
|
||||
u32 tmp=0;
|
||||
Result rc = serviceDispatchInOut(&g_hidsysSrv, 310, AppletResourceUserId, tmp);
|
||||
if (R_SUCCEEDED(rc) && out) *out = tmp;
|
||||
return rc;
|
||||
}
|
||||
|
||||
@ -236,82 +101,36 @@ Result hidsysGetSupportedNpadStyleSetOfCallerApplet(HidControllerType *out) {
|
||||
return _hidsysGetMaskedSupportedNpadStyleSet(AppletResourceUserId, out);
|
||||
}
|
||||
|
||||
Result hidsysGetUniquePadsFromNpad(HidControllerID id, u64 *UniquePadIds, size_t count, size_t *total_entries) {
|
||||
Result hidsysGetUniquePadsFromNpad(HidControllerID id, u64 *UniquePadIds, s32 count, s32 *total_entries) {
|
||||
if (hosversionBefore(3,0,0))
|
||||
return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer);
|
||||
|
||||
Result rc;
|
||||
|
||||
IpcCommand c;
|
||||
ipcInitialize(&c);
|
||||
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 cmd_id;
|
||||
u32 id;
|
||||
} PACKED *raw;
|
||||
|
||||
ipcAddRecvStatic(&c, UniquePadIds, sizeof(u64)*count, 0);
|
||||
|
||||
raw = serviceIpcPrepareHeader(&g_hidsysSrv, &c, sizeof(*raw));
|
||||
|
||||
raw->magic = SFCI_MAGIC;
|
||||
raw->cmd_id = 321;
|
||||
raw->id = hidControllerIDToOfficial(id);
|
||||
|
||||
rc = serviceIpcDispatch(&g_hidsysSrv);
|
||||
|
||||
if (R_SUCCEEDED(rc)) {
|
||||
IpcParsedCommand r;
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 result;
|
||||
u64 total_entries;
|
||||
} *resp;
|
||||
|
||||
serviceIpcParse(&g_hidsysSrv, &r, sizeof(*resp));
|
||||
resp = r.Raw;
|
||||
|
||||
if (R_SUCCEEDED(rc) && total_entries) *total_entries = resp->total_entries;
|
||||
}
|
||||
|
||||
u32 tmp=hidControllerIDToOfficial(id);
|
||||
s64 out=0;
|
||||
Result rc = serviceDispatchInOut(&g_hidsysSrv, 321, tmp, out,
|
||||
.buffer_attrs = { SfBufferAttr_HipcPointer | SfBufferAttr_Out },
|
||||
.buffers = { { UniquePadIds, count*sizeof(u64) } },
|
||||
);
|
||||
if (R_SUCCEEDED(rc) && total_entries) *total_entries = out;
|
||||
return rc;
|
||||
}
|
||||
|
||||
Result hidsysGetUniquePadIds(u64 *UniquePadIds, size_t count, size_t *total_entries) {
|
||||
Result rc;
|
||||
Result hidsysEnableAppletToGetInput(bool enable) {
|
||||
const struct {
|
||||
u8 permitInput;
|
||||
u64 appletResourceUserId;
|
||||
} in = { enable!=0, g_hidsysAppletResourceUserId };
|
||||
|
||||
IpcCommand c;
|
||||
ipcInitialize(&c);
|
||||
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 cmd_id;
|
||||
} *raw;
|
||||
|
||||
ipcAddRecvStatic(&c, UniquePadIds, sizeof(u64)*count, 0);
|
||||
|
||||
raw = serviceIpcPrepareHeader(&g_hidsysSrv, &c, sizeof(*raw));
|
||||
|
||||
raw->magic = SFCI_MAGIC;
|
||||
raw->cmd_id = 703;
|
||||
|
||||
rc = serviceIpcDispatch(&g_hidsysSrv);
|
||||
|
||||
if (R_SUCCEEDED(rc)) {
|
||||
IpcParsedCommand r;
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 result;
|
||||
u64 total_entries;
|
||||
} *resp;
|
||||
|
||||
serviceIpcParse(&g_hidsysSrv, &r, sizeof(*resp));
|
||||
resp = r.Raw;
|
||||
|
||||
if (R_SUCCEEDED(rc) && total_entries) *total_entries = resp->total_entries;
|
||||
return serviceDispatchIn(&g_hidsysSrv, 503, in);
|
||||
}
|
||||
|
||||
Result hidsysGetUniquePadIds(u64 *UniquePadIds, s32 count, s32 *total_entries) {
|
||||
s64 out=0;
|
||||
Result rc = serviceDispatchOut(&g_hidsysSrv, 703, out,
|
||||
.buffer_attrs = { SfBufferAttr_HipcPointer | SfBufferAttr_Out },
|
||||
.buffers = { { UniquePadIds, count*sizeof(u64) } },
|
||||
);
|
||||
if (R_SUCCEEDED(rc) && total_entries) *total_entries = out;
|
||||
return rc;
|
||||
}
|
||||
|
||||
@ -319,81 +138,21 @@ Result hidsysSetNotificationLedPattern(const HidsysNotificationLedPattern *patte
|
||||
if (hosversionBefore(7,0,0))
|
||||
return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer);
|
||||
|
||||
Result rc;
|
||||
|
||||
IpcCommand c;
|
||||
ipcInitialize(&c);
|
||||
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 cmd_id;
|
||||
const struct {
|
||||
HidsysNotificationLedPattern pattern;
|
||||
u64 UniquePadId;
|
||||
} *raw;
|
||||
} in = { *pattern, UniquePadId };
|
||||
|
||||
raw = serviceIpcPrepareHeader(&g_hidsysSrv, &c, sizeof(*raw));
|
||||
|
||||
raw->magic = SFCI_MAGIC;
|
||||
raw->cmd_id = 830;
|
||||
memcpy(&raw->pattern, pattern, sizeof(*pattern));
|
||||
raw->UniquePadId = UniquePadId;
|
||||
|
||||
rc = serviceIpcDispatch(&g_hidsysSrv);
|
||||
|
||||
if (R_SUCCEEDED(rc)) {
|
||||
IpcParsedCommand r;
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 result;
|
||||
} *resp;
|
||||
|
||||
serviceIpcParse(&g_hidsysSrv, &r, sizeof(*resp));
|
||||
resp = r.Raw;
|
||||
}
|
||||
|
||||
return rc;
|
||||
return serviceDispatchIn(&g_hidsysSrv, 830, in);
|
||||
}
|
||||
|
||||
Result hidsysGetUniquePadSerialNumber(u64 UniquePadId, char *serial) {
|
||||
if (hosversionBefore(5,0,0))
|
||||
return MAKERESULT(Module_Libnx, LibnxError_IncompatSysVer);
|
||||
|
||||
IpcCommand c;
|
||||
ipcInitialize(&c);
|
||||
|
||||
char out[0x18]={0};
|
||||
if (serial) memset(serial, 0, 0x19);
|
||||
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 cmd_id;
|
||||
u64 UniquePadId;
|
||||
} *raw;
|
||||
|
||||
raw = serviceIpcPrepareHeader(&g_hidsysSrv, &c, sizeof(*raw));
|
||||
|
||||
raw->magic = SFCI_MAGIC;
|
||||
raw->cmd_id = 809;
|
||||
raw->UniquePadId = UniquePadId;
|
||||
|
||||
Result rc = serviceIpcDispatch(&g_hidsysSrv);
|
||||
|
||||
if (R_SUCCEEDED(rc)) {
|
||||
IpcParsedCommand r;
|
||||
|
||||
struct {
|
||||
u64 magic;
|
||||
u64 result;
|
||||
char serial[0x18];
|
||||
} *resp;
|
||||
|
||||
serviceIpcParse(&g_hidsysSrv, &r, sizeof(*resp));
|
||||
resp = r.Raw;
|
||||
|
||||
rc = resp->result;
|
||||
|
||||
if (R_SUCCEEDED(rc) && serial)
|
||||
memcpy(serial, resp->serial, 0x18);
|
||||
}
|
||||
|
||||
Result rc = serviceDispatchInOut(&g_hidsysSrv, 809, UniquePadId, out);
|
||||
if (R_SUCCEEDED(rc) && serial) memcpy(serial, out, 0x18);
|
||||
return rc;
|
||||
}
|
||||
|
Loading…
Reference in New Issue
Block a user