]> Chaos Git - corbenik/ctrulib.git/commitdiff
Add PxiPM to ctru
authorchaoskagami <chaos.kagami@gmail.com>
Fri, 14 Oct 2016 11:38:15 +0000 (07:38 -0400)
committerchaoskagami <chaos.kagami@gmail.com>
Fri, 14 Oct 2016 11:38:28 +0000 (07:38 -0400)
libctru/include/3ds.h
libctru/include/3ds/services/pxipm.h [new file with mode: 0644]
libctru/source/services/pxipm.c [new file with mode: 0644]

index e417c934d9fe9c9a78fb9525e02e1c4845d93829..7d21548bb080d16cfaaee626fa260ea813ae4018 100644 (file)
@@ -50,6 +50,7 @@ extern "C" {
 #include <3ds/services/ir.h>
 #include <3ds/services/ns.h>
 #include <3ds/services/pm.h>
+#include <3ds/services/pxipm.h>
 #include <3ds/services/ps.h>
 #include <3ds/services/ptmu.h>
 #include <3ds/services/ptmsysm.h>
diff --git a/libctru/include/3ds/services/pxipm.h b/libctru/include/3ds/services/pxipm.h
new file mode 100644 (file)
index 0000000..48b9bc5
--- /dev/null
@@ -0,0 +1,32 @@
+#pragma once
+
+#include <3ds/types.h>
+#include <3ds/exheader.h>
+
+
+/// Initialize PxiPM. Note that you must be able to access this, and few modules can.
+Result pxipmInit(void);
+
+/// Deinitialize PxiPM.
+void   pxipmExit(void);
+
+/**
+ * @brief Register a program (or reregister) a program with PxiPM.
+ * @param prog_handle The program's handle
+ * @param title The program's current info
+ * @param update Information to update if re-registering
+ */
+Result PXIPM_RegisterProgram(u64 *prog_handle, FS_ProgramInfo *title, FS_ProgramInfo *update);
+
+/**
+ * @brief Get a program's information from PxiPM
+ * @param exheader Exheader to place infomation retrieved in
+ * @param prog_handle Handle to retrieve for
+ */
+Result PXIPM_GetProgramInfo(EXHEADER_header *exheader, u64 prog_handle);
+
+/**
+ * @brief Unregister a program from PxiPM.
+ * @param prog_handle Program handle to unregister for.
+ */
+Result PXIPM_UnregisterProgram(u64 prog_handle);
diff --git a/libctru/source/services/pxipm.c b/libctru/source/services/pxipm.c
new file mode 100644 (file)
index 0000000..e73e541
--- /dev/null
@@ -0,0 +1,81 @@
+#include <3ds.h>
+#include <string.h>
+
+static Handle pxipmHandle;
+static int pxipmRefCount;
+
+Result pxipmInit(void)
+{
+       Result ret = 0;
+
+       if (AtomicPostIncrement(&pxipmRefCount))
+               return 0;
+
+       ret = srvGetServiceHandle(&pxipmHandle, "PxiPM");
+
+       if (R_FAILED(ret))
+               AtomicDecrement(&pxipmRefCount);
+
+       return ret;
+}
+
+void pxipmExit(void)
+{
+       if (AtomicDecrement(&pxipmRefCount))
+               return;
+
+       svcCloseHandle(pxipmHandle);
+}
+
+Result PXIPM_RegisterProgram(u64 *prog_handle, FS_ProgramInfo *title, FS_ProgramInfo *update)
+{
+       u32 *cmdbuf = getThreadCommandBuffer();
+
+       cmdbuf[0] = IPC_MakeHeader(0x2, 8, 0); // 0x20200
+       memcpy(&cmdbuf[1], &title->programId, sizeof(u64));
+       *(u8 *)&cmdbuf[3] = title->mediaType;
+       memcpy(((u8 *)&cmdbuf[3]) + 1, &title->padding, 7);
+       memcpy(&cmdbuf[5], &update->programId, sizeof(u64));
+       *(u8 *)&cmdbuf[7] = update->mediaType;
+       memcpy(((u8 *)&cmdbuf[7]) + 1, &update->padding, 7);
+
+       Result ret = 0;
+       if (R_FAILED(ret = svcSendSyncRequest(pxipmHandle)))
+               return ret;
+
+       *prog_handle = *(u64 *)&cmdbuf[2];
+
+       return cmdbuf[1];
+}
+
+Result PXIPM_GetProgramInfo(EXHEADER_header *exheader, u64 prog_handle)
+{
+       u32 *cmdbuf = getThreadCommandBuffer();
+
+       cmdbuf[0] = IPC_MakeHeader(0x1, 2, 2); // 0x10082
+       cmdbuf[1] = (u32)(prog_handle);
+       cmdbuf[2] = (u32)(prog_handle >> 32);
+       cmdbuf[3] = (0x400 << 8) | 0x4;
+       cmdbuf[4] = (u32)exheader;
+
+       Result ret = 0;
+       if (R_FAILED(ret = svcSendSyncRequest(pxipmHandle)))
+               return ret;
+
+       return cmdbuf[1];
+}
+
+Result PXIPM_UnregisterProgram(u64 prog_handle)
+{
+       u32 *cmdbuf = getThreadCommandBuffer();
+
+       cmdbuf[0] = IPC_MakeHeader(0x3, 2, 0); // 0x30080
+       cmdbuf[1] = (u32)(prog_handle);
+       cmdbuf[2] = (u32)(prog_handle >> 32);
+
+       Result ret = 0;
+       if (R_FAILED(ret = svcSendSyncRequest(pxipmHandle)))
+               return ret;
+
+       return cmdbuf[1];
+}