mirror of
https://github.com/switchbrew/libnx.git
synced 2025-06-21 12:32:40 +02:00
99 lines
1.8 KiB
C
99 lines
1.8 KiB
C
// Copyright 2017 plutoo
|
|
#include <switch.h>
|
|
#include <malloc.h>
|
|
|
|
Result tmemCreate(TransferMemory* t, size_t size, Permission perm)
|
|
{
|
|
Result rc = 0;
|
|
|
|
t->MemHandle = INVALID_HANDLE;
|
|
t->Size = size;
|
|
t->Perm = perm;
|
|
t->MappedAddr = NULL;
|
|
t->SourceAddr = memalign(0x1000, size);
|
|
|
|
if (t->SourceAddr == NULL) {
|
|
rc = MAKERESULT(MODULE_LIBNX, LIBNX_OUTOFMEM);
|
|
}
|
|
|
|
if (R_SUCCEEDED(rc)) {
|
|
rc = svcCreateTransferMemory(&t->MemHandle, t->SourceAddr, size, perm);
|
|
}
|
|
|
|
return rc;
|
|
}
|
|
|
|
void tmemLoadRemote(TransferMemory* t, Handle handle, size_t size, Permission perm)
|
|
{
|
|
t->MemHandle = handle;
|
|
t->Size = size;
|
|
t->Perm = perm;
|
|
t->MappedAddr = NULL;
|
|
t->SourceAddr = NULL;
|
|
}
|
|
|
|
Result tmemMap(TransferMemory* t)
|
|
{
|
|
Result rc = 0;
|
|
|
|
if (t->MappedAddr == NULL)
|
|
{
|
|
void* addr = virtmemReserve(t->Size);
|
|
|
|
rc = svcMapTransferMemory(t->MemHandle, addr, t->Size, t->Perm);
|
|
|
|
if (R_SUCCEEDED(rc)) {
|
|
t->MappedAddr = addr;
|
|
}
|
|
else {
|
|
virtmemFree(addr, t->Size);
|
|
}
|
|
}
|
|
else {
|
|
rc = LIBNX_ALREADYMAPPED;
|
|
}
|
|
|
|
return rc;
|
|
}
|
|
|
|
Result tmemUnmap(TransferMemory* t)
|
|
{
|
|
Result rc;
|
|
|
|
rc = svcUnmapTransferMemory(t->MemHandle, t->MappedAddr, t->Size);
|
|
|
|
if (R_SUCCEEDED(rc)) {
|
|
t->MappedAddr = NULL;
|
|
}
|
|
|
|
return rc;
|
|
}
|
|
|
|
void* tmemGetAddr(TransferMemory* t) {
|
|
return t->MappedAddr;
|
|
}
|
|
|
|
Result tmemClose(TransferMemory* t)
|
|
{
|
|
Result rc = 0;
|
|
|
|
if (t->SourceAddr != NULL) {
|
|
free(t->SourceAddr);
|
|
}
|
|
|
|
if (t->MappedAddr != NULL) {
|
|
rc = tmemUnmap(t);
|
|
}
|
|
|
|
if (R_SUCCEEDED(rc)) {
|
|
if (t->MemHandle != INVALID_HANDLE) {
|
|
rc = svcCloseHandle(t->MemHandle);
|
|
}
|
|
|
|
t->SourceAddr = NULL;
|
|
t->MemHandle = INVALID_HANDLE;
|
|
}
|
|
|
|
return rc;
|
|
}
|