diff --git a/axl_memory.c b/axl_memory.c index 86741ba..461d466 100644 --- a/axl_memory.c +++ b/axl_memory.c @@ -12,11 +12,18 @@ struct mb_header typedef struct mb_header mb_header; -#define MB_HEADER_SIZE sizeof(mb_header) - static mb_header* root = NULL; static mb_header* nomad = NULL; +#define AXL_ALIGNMENT 8 + +static inline u32 axl_align(u32 size) +{ + return (size + (AXL_ALIGNMENT - 1)) & ~(AXL_ALIGNMENT - 1); +} + +#define MB_HEADER_SIZE axl_align(sizeof(mb_header)) + void* axl_memset(void* ptr, i8 c, u32 n) { if(ptr) @@ -46,7 +53,7 @@ void axl_init(void) } } -static mb_header* axl_get_mb_header(void* ptr) +static inline mb_header* axl_get_mb_header(void* ptr) { return (mb_header*)((u8*)ptr - MB_HEADER_SIZE); } @@ -81,28 +88,42 @@ static mb_header* axl_find_mb(u32 req_size) return NULL; } -static void axl_split_mb(mb_header* block, u32 size) +static b8 axl_split_mb(mb_header* block, u32 size) { - if(block->size > size + MB_HEADER_SIZE * 2) + if(block->size > size) { - mb_header* new_block = (mb_header*)((u8*)block + MB_HEADER_SIZE + size); - new_block->size = block->size - size - MB_HEADER_SIZE; - new_block->is_free = true; - new_block->next = block->next; - new_block->prev = block; - - if(new_block->next) + if(block->size - size >= MB_HEADER_SIZE + AXL_ALIGNMENT) { - new_block->next->prev = new_block; - } + mb_header* new_block = (mb_header*)((u8*)block + MB_HEADER_SIZE + size); + new_block->size = block->size - size - MB_HEADER_SIZE; + new_block->is_free = true; + new_block->next = block->next; + new_block->prev = block; - block->size = size; - block->next = new_block; + if(new_block->next) + { + new_block->next->prev = new_block; + } + + block->size = size; + block->next = new_block; + + return true; + } } + + return false; } void* axl_malloc(u32 size) { + if(size == 0) + { + return NULL; + } + + size = axl_align(size); + if(size > AXL_HEAP_SIZE - MB_HEADER_SIZE) { return NULL; @@ -139,6 +160,25 @@ void* axl_memcpy(void* dst, const void* src, u32 count) void* axl_realloc(void* ptr, u32 size) { + if(size == 0) + { + axl_free(ptr); + return NULL; + } + + size = axl_align(size); + + if(!ptr) + { + return axl_malloc(size); + } + + mb_header* old = axl_get_mb_header(ptr); + if(axl_split_mb(old, size)) + { + return ptr; + } + void* new = axl_malloc(size); if(!new) @@ -146,7 +186,6 @@ void* axl_realloc(void* ptr, u32 size) return NULL; } - mb_header* old = axl_get_mb_header(ptr); size = size < old->size ? size : old->size; axl_memcpy(new, ptr, size);