I am trying to write a custom stack allocator for a game I am working on. To deal with memory alignment, I am using C11’s stdalign.h
header; however, since I do not have prior experience with alignment issues, I’d like a expert opinion on whether I am doing it right.
The majority of the alignment stuff happens in alignup
and aligndown
macros. Specifically, in alignup
, I try to go up to the nearest multiple of alignof(max_align_t)
(unless we were already a multiple) by shooting past it by adding alignof(max_align_t) - 1
and then coming back using the bitwise AND. In aligndown
, I first go below the last multiple of alignof(max_align_t)
and then come up using alignup
.
NOTE: The stack is in a memory arena and it grows down in memory instead of going up.
typedef size_t Size; typedef uintptr_t Uptr; typedef char Byte; #define alignup(p) ((void*)((((Uptr)(p)) + (alignof(max_align_t) - 1)) & (~ (alignof(max_align_t) - 1)))) #define aligndown(p) ((void*)(alignup((((Uptr)(p)) - (alignof(max_align_t) - 1))))) struct _Mem_Stack_Header { Size allocation_size; Size total_size; }; // This contains the "head" of the stack. The stack grows down, instead of up. void *stack_head; internal_function void* memPush (Size s) { void *head = stack_head; void *mem = (Byte*)head - s; mem = aligndown(mem); struct _Mem_Stack_Header *h = (void*)((Byte*)mem - sizeof(*h)); h = aligndown(h); h->allocation_size = s; h->total_size = (Uptr)head - (Uptr)h; stack_head = h; return mem; } internal_function void memPop (void) { struct _Mem_Stack_Header *h = stack_head; stack_head = (Byte*)stack_head + h->total_size; return; }
Is this the correct way of doing this kind of stuff? Any improvements I can make?