diff --git a/nx/Makefile b/nx/Makefile index adb01059..27fcee88 100644 --- a/nx/Makefile +++ b/nx/Makefile @@ -24,7 +24,7 @@ VERSION := $(LIBNX_MAJOR).$(LIBNX_MINOR).$(LIBNX_PATCH) #--------------------------------------------------------------------------------- TARGET := nx #BUILD := build -SOURCES := source/system source/kernel source/services source/heap +SOURCES := source/system source/kernel source/services DATA := data INCLUDES := include diff --git a/nx/include/switch.h b/nx/include/switch.h index 0019a082..1d7706dd 100644 --- a/nx/include/switch.h +++ b/nx/include/switch.h @@ -12,7 +12,6 @@ extern "C" { #include #include #include -#include #include #include diff --git a/nx/include/switch/heap.h b/nx/include/switch/heap.h deleted file mode 100644 index 1092774c..00000000 --- a/nx/include/switch/heap.h +++ /dev/null @@ -1,2 +0,0 @@ -void* heapAllocPages(size_t size); -void* heapAlloc(size_t size); diff --git a/nx/source/heap/heap.c b/nx/source/heap/heap.c deleted file mode 100644 index f0558256..00000000 --- a/nx/source/heap/heap.c +++ /dev/null @@ -1,105 +0,0 @@ -// Copyright 2017 plutoo -// Worst heap ever xD -#include - -typedef struct HeapHeader HeapHeader; - -typedef enum { - USED = 0x55534544, - FREE = 0x46524545 -} HeapState; - -struct HeapHeader { - size_t State; - size_t Size; - HeapHeader* Next; - HeapHeader* Prev; -}; - -static HeapHeader g_LastFree; - -void heapInit(void* base, size_t size) { - HeapHeader* hdr = (HeapHeader*) base; - - hdr->Next = &g_LastFree; - hdr->Prev = &g_LastFree; - hdr->Size = size - sizeof(HeapHeader); - hdr->State = FREE; - - g_LastFree.Next = hdr; - g_LastFree.Prev = hdr; -} - -void heapSetup() { - // Called by crt0. - #define INNER_HEAP_SIZE 0x20000 - #define OUTER_HEAP_SIZE (0x2000000*4) - - void* addr; - Result rc = svcSetHeapSize(&addr, OUTER_HEAP_SIZE); - - if (R_SUCCEEDED(rc)) { - heapInit(addr, OUTER_HEAP_SIZE); - } - else { - static u8 g_Heap[INNER_HEAP_SIZE]; - heapInit(&g_Heap[0], INNER_HEAP_SIZE); - } -} - -void* heapAllocPages(size_t size) { - void* ptr = heapAlloc(size + 0x1000); - - if (ptr != NULL) { - ptr = (void*) ((((uintptr_t) ptr) + 0xFFF) &~ 0xFFF); - } - - return ptr; -} - -void* heapAlloc(size_t size) { - size = (size + 15) &~ 15; - - HeapHeader* hdr = &g_LastFree; - - while ((hdr = hdr->Next) != &g_LastFree) { - if (hdr->Size >= size) { - size_t rem = hdr->Size - size; - - if (rem < sizeof(HeapHeader)) { - size = hdr->Size; - rem = 0; - } - - hdr->State = USED; - hdr->Size = size; - - hdr->Prev->Next = hdr->Next; - hdr->Next->Prev = hdr->Prev; - - if (rem != 0) { - HeapHeader* rem_hdr = (HeapHeader*) (((uintptr_t)(hdr + 1)) + size); - rem_hdr->State = FREE; - rem_hdr->Size = rem - sizeof(HeapHeader); - - rem_hdr->Next = g_LastFree.Next; - rem_hdr->Prev = &g_LastFree; - g_LastFree.Next = rem_hdr; - } - - return (void*) (((uintptr_t) hdr) + sizeof(HeapHeader)); - } - } - - return NULL; -} - -void heapFree(void* ptr) { - HeapHeader* hdr = (HeapHeader*) (((uintptr_t) ptr) - sizeof(HeapHeader)); - hdr->State = FREE; - - hdr->Next = g_LastFree.Next; - g_LastFree.Next = hdr; - hdr->Prev = &g_LastFree; -} - diff --git a/nx/source/kernel/thread.c b/nx/source/kernel/thread.c index a8e33647..20663e24 100644 --- a/nx/source/kernel/thread.c +++ b/nx/source/kernel/thread.c @@ -1,5 +1,6 @@ // Copyright 2017 plutoo #include +#include static void _EntryWrap(Thread* t) { t->entry(t->arg); @@ -11,7 +12,7 @@ Result threadCreate( int cpuid) { Result rc = 0; - void* stack = heapAllocPages(stack_sz); + void* stack = memalign(0x1000, stack_sz); if (stack == NULL) { rc = MAKERESULT(MODULE_LIBNX, LIBNX_OUTOFMEM); @@ -47,7 +48,7 @@ Result threadCreate( if (R_FAILED(rc)) { virtmemFreeMap(stack_mirror, stack_sz); - //heapFree(stack); + free(stack); } } @@ -69,7 +70,7 @@ Result threadClose(Thread* t) { rc = svcUnmapMemory(t->stack_mirror, t->stack_mem, t->stack_sz); virtmemFreeMap(t->stack_mirror, t->stack_sz); - //heapFree(t->stack); + free(t->stack_mem); svcCloseHandle(t->handle); return rc; diff --git a/nx/source/kernel/tmem.c b/nx/source/kernel/tmem.c index e2c05b5e..b0129b5f 100644 --- a/nx/source/kernel/tmem.c +++ b/nx/source/kernel/tmem.c @@ -1,5 +1,6 @@ // Copyright 2017 plutoo #include +#include Result tmemCreate(TransferMemory* t, size_t size, Permission perm) { @@ -9,7 +10,7 @@ Result tmemCreate(TransferMemory* t, size_t size, Permission perm) t->Size = size; t->Perm = perm; t->MappedAddr = NULL; - t->SourceAddr = heapAllocPages(size); + t->SourceAddr = memalign(0x1000, size); if (t->SourceAddr == NULL) { rc = MAKERESULT(MODULE_LIBNX, LIBNX_OUTOFMEM); @@ -77,8 +78,7 @@ Result tmemClose(TransferMemory* t) Result rc = 0; if (t->SourceAddr != NULL) { - // todo: Free is currently broken for page-aligned allocs. - //heapFree(t->SourceAddr); + free(t->SourceAddr); } if (t->MappedAddr != NULL) { diff --git a/nx/source/system/init.c b/nx/source/system/init.c index 01e8dd37..d1f15534 100644 --- a/nx/source/system/init.c +++ b/nx/source/system/init.c @@ -1,15 +1,31 @@ #include -#include -#include -#include -#include -#include - void __nx_exit(int rc); void virtmemSetup(); -void heapSetup(); +void newlibSetup(); + +static void _SetupHeap() { + #define INNER_HEAP_SIZE 0x20000 + #define OUTER_HEAP_SIZE (0x2000000*4) + + char* addr; + Result rc = svcSetHeapSize((void**)&addr, OUTER_HEAP_SIZE); + size_t size = OUTER_HEAP_SIZE; + + if (R_FAILED(rc)) { + static char g_Heap[INNER_HEAP_SIZE]; + addr = &g_Heap[0]; + size = INNER_HEAP_SIZE; + } + + // Multilib + extern char* fake_heap_start; + extern char* fake_heap_end; + + fake_heap_start = addr; + fake_heap_end = addr + size; +} void __attribute__((weak)) __appInit(void) { @@ -27,13 +43,10 @@ void __attribute__((weak)) __libnx_init(void) { // Called by crt0. - // Newlib initialization goes here. - void exitImpl(int rc); - __syscalls.exit = exitImpl; - // Libnx initialization goes here. + newlibSetup(); virtmemSetup(); - heapSetup(); + _SetupHeap(); // Initialize services. __appInit(); @@ -55,8 +68,3 @@ void __attribute__((weak)) NORETURN __libnx_exit(void) svcExitProcess(); while(1); } - -void NORETURN exitImpl(int rc) -{ - __libnx_exit(); -} diff --git a/nx/source/system/newlib.c b/nx/source/system/newlib.c new file mode 100644 index 00000000..537f5431 --- /dev/null +++ b/nx/source/system/newlib.c @@ -0,0 +1,18 @@ +#include +#include +#include +#include +#include + +void __attribute__((weak)) NORETURN __libnx_exit(void); + + +static void NORETURN _ExitImpl(int rc) { + __libnx_exit(); +} + +void newlibSetup() { + void exitImpl(int rc); + __syscalls.exit = _ExitImpl; + +}