arena allocators are fully implemented
This commit is contained in:
+5
-5
@@ -4,7 +4,7 @@
|
||||
#include <assert.h>
|
||||
#include <stdbool.h>
|
||||
|
||||
void *borrow_allocator_alloc_func(borrow_allocator_t *this, size_t bytes) {
|
||||
static void *borrow_allocator_alloc_func(borrow_allocator_t *this, size_t bytes) {
|
||||
linked_allocation_node_t *node = malloc(sizeof(*this->head) + bytes);
|
||||
if (node == NULL) { return NULL; }
|
||||
node->prev = NULL;
|
||||
@@ -17,7 +17,7 @@ void *borrow_allocator_alloc_func(borrow_allocator_t *this, size_t bytes) {
|
||||
return &node->data;
|
||||
}
|
||||
|
||||
void *borrow_allocator_resize_func(borrow_allocator_t *this, void *old_ptr, size_t bytes) {
|
||||
static void *borrow_allocator_resize_func(borrow_allocator_t *this, void *old_ptr, size_t bytes) {
|
||||
linked_allocation_node_t *old_node = PTR_FROM_FIELD_PTR(linked_allocation_node_t, data, old_ptr);
|
||||
linked_allocation_node_t *new_node = realloc(old_node, sizeof(*old_node) + bytes);
|
||||
if (new_node == NULL) { return NULL; }
|
||||
@@ -31,7 +31,7 @@ void *borrow_allocator_resize_func(borrow_allocator_t *this, void *old_ptr, size
|
||||
}
|
||||
|
||||
// TODO: remove
|
||||
void borrow_allocator_free(borrow_allocator_t *this, void *old_ptr) {
|
||||
static void borrow_allocator_free(borrow_allocator_t *this, void *old_ptr) {
|
||||
linked_allocation_node_t *node = PTR_FROM_FIELD_PTR(linked_allocation_node_t, data, old_ptr);
|
||||
if (node->prev != NULL) { node->prev->next = node->next; }
|
||||
if (node->next != NULL) { node->next->prev = node->prev; }
|
||||
@@ -43,7 +43,7 @@ void borrow_allocator_free(borrow_allocator_t *this, void *old_ptr) {
|
||||
free(node);
|
||||
}
|
||||
|
||||
void borrow_allocator_free_all(borrow_allocator_t *this) {
|
||||
static void borrow_allocator_free_all(borrow_allocator_t *this) {
|
||||
if (this->head == NULL) {
|
||||
return;
|
||||
}
|
||||
@@ -57,7 +57,7 @@ void borrow_allocator_free_all(borrow_allocator_t *this) {
|
||||
this->head = NULL;
|
||||
}
|
||||
|
||||
size_t borrow_allocator_count_allocations(borrow_allocator_t *this) {
|
||||
static size_t borrow_allocator_count_allocations(borrow_allocator_t *this) {
|
||||
size_t output = 0;
|
||||
for (linked_allocation_node_t *node = this->head; node != NULL; node = node->next) {
|
||||
output++;
|
||||
|
||||
+3
-3
@@ -1,6 +1,6 @@
|
||||
#include "cig.h"
|
||||
|
||||
void *buffer_allocator_alloc(buffer_allocator_t *this, size_t bytes) {
|
||||
static void *buffer_allocator_alloc(buffer_allocator_t *this, size_t bytes) {
|
||||
size_t address_of_new_data = (size_t) &this->data[this->size];
|
||||
size_t offset = address_of_new_data % MAX_ALIGN;
|
||||
size_t new_size = this->size + offset + bytes;
|
||||
@@ -13,7 +13,7 @@ void *buffer_allocator_alloc(buffer_allocator_t *this, size_t bytes) {
|
||||
return ptr;
|
||||
}
|
||||
|
||||
void *buffer_allocator_resize(buffer_allocator_t *this, void *old_ptr, size_t bytes) {
|
||||
static void *buffer_allocator_resize(buffer_allocator_t *this, void *old_ptr, size_t bytes) {
|
||||
void *new_ptr = buffer_allocator_alloc(this, bytes);
|
||||
if (new_ptr == NULL) {
|
||||
return NULL;
|
||||
@@ -26,7 +26,7 @@ void *buffer_allocator_resize(buffer_allocator_t *this, void *old_ptr, size_t by
|
||||
return new_ptr;
|
||||
}
|
||||
|
||||
void buffer_allocator_reset(buffer_allocator_t *this) {
|
||||
static void buffer_allocator_reset(buffer_allocator_t *this) {
|
||||
this->size = 0;
|
||||
}
|
||||
|
||||
|
||||
@@ -92,14 +92,16 @@ typedef struct arena_allocator {
|
||||
uint8_t *data;
|
||||
} arena_allocator_t;
|
||||
|
||||
#define arena_allocator_value(INITIAL_CAPACITY) ((arena_allocator_t) { \
|
||||
.allocator=borrow_allocator_create(), \
|
||||
#define arena_allocator_value(BACKING_ALLOCATOR, INITIAL_CAPACITY) ((arena_allocator_t) { \
|
||||
.allocator=BACKING_ALLOCATOR, \
|
||||
.size=0, \
|
||||
.capacity=INITIAL_CAPACITY, \
|
||||
.data=NULL \
|
||||
})
|
||||
|
||||
allocator_t allocator_from_arena(arena_allocator_t *this);
|
||||
#define arena_allocator_create(BACKING_ALLOCATOR, INITIAL_CAPACITY) \
|
||||
allocator_from_arena(&arena_allocator_value(BACKING_ALLOCATOR, INITIAL_CAPACITY))
|
||||
|
||||
// dynamic arrays //////////////////////////////////////////////////////////////
|
||||
|
||||
|
||||
@@ -0,0 +1,79 @@
|
||||
#include <criterion/criterion.h>
|
||||
#include <criterion/internal/assert.h>
|
||||
#include "cig.h"
|
||||
|
||||
Test(arena_allocator, test) {
|
||||
with_borrow(backing) {
|
||||
allocator_t arena = arena_allocator_create(backing, 4 * MB);
|
||||
for ( size_t i = 0; i < 1000; i++ ) {
|
||||
allocator_reset(arena);
|
||||
allocator_alloc(arena, 4 * MB);
|
||||
}
|
||||
|
||||
borrow_allocator_t *concrete = (borrow_allocator_t*)backing.this;
|
||||
size_t n_allocations = 0;
|
||||
for (linked_allocation_node_t *node = concrete->head; node != NULL; node = node->next) {
|
||||
n_allocations++;
|
||||
}
|
||||
cr_assert_eq(n_allocations, 1);
|
||||
}
|
||||
|
||||
with_borrow(backing) {
|
||||
allocator_t arena = arena_allocator_create(backing, 0);
|
||||
for ( size_t i = 0; i < 1000; i++ ) {
|
||||
allocator_reset(arena);
|
||||
allocator_alloc(arena, 1 * MB);
|
||||
allocator_alloc(arena, 1 * MB);
|
||||
allocator_alloc(arena, 1 * MB);
|
||||
allocator_alloc(arena, 1 * MB);
|
||||
}
|
||||
|
||||
borrow_allocator_t *concrete = (borrow_allocator_t*)backing.this;
|
||||
size_t n_allocations = 0;
|
||||
for (linked_allocation_node_t *node = concrete->head; node != NULL; node = node->next) {
|
||||
n_allocations++;
|
||||
}
|
||||
cr_assert_eq(n_allocations, 1);
|
||||
}
|
||||
|
||||
with_borrow(backing) {
|
||||
allocator_t arena = arena_allocator_create(backing, 0);
|
||||
for ( size_t i = 0; i < 1000; i++ ) {
|
||||
allocator_reset(arena);
|
||||
allocator_alloc(arena, 1 * MB);
|
||||
allocator_alloc(arena, 1 * MB);
|
||||
allocator_alloc(arena, 1 * MB);
|
||||
allocator_alloc(arena, 1 * MB);
|
||||
}
|
||||
|
||||
borrow_allocator_t *concrete_borrow = (borrow_allocator_t*)backing.this;
|
||||
arena_allocator_t *concrete_arena = (arena_allocator_t*)arena.this;
|
||||
size_t n_allocations = 0;
|
||||
for (linked_allocation_node_t *node = concrete_borrow->head; node != NULL; node = node->next) {
|
||||
n_allocations++;
|
||||
}
|
||||
cr_assert_eq(n_allocations, 1);
|
||||
cr_assert_eq(concrete_arena->capacity, 4 * MB);
|
||||
}
|
||||
|
||||
with_borrow(backing) {
|
||||
allocator_t arena = arena_allocator_create(backing, 0);
|
||||
for ( size_t i = 0; i < 1000; i++ ) {
|
||||
allocator_reset(arena);
|
||||
allocator_alloc(arena, 1);
|
||||
allocator_alloc(arena, 1);
|
||||
allocator_alloc(arena, 1);
|
||||
allocator_alloc(arena, 1);
|
||||
}
|
||||
|
||||
borrow_allocator_t *concrete_borrow = (borrow_allocator_t*)backing.this;
|
||||
arena_allocator_t *concrete_arena = (arena_allocator_t*)arena.this;
|
||||
size_t n_allocations = 0;
|
||||
for (linked_allocation_node_t *node = concrete_borrow->head; node != NULL; node = node->next) {
|
||||
n_allocations++;
|
||||
}
|
||||
cr_assert_eq(n_allocations, 1);
|
||||
const size_t expected_capacity = 4 * MAX_ALIGN;
|
||||
cr_assert_eq(concrete_arena->capacity, expected_capacity);
|
||||
}
|
||||
}
|
||||
@@ -9,4 +9,5 @@ Test(std_allocator, test) {
|
||||
void *new_ptr = allocator_resize(this, ptr, 1024*1024*500);
|
||||
cr_assert(new_ptr != ((void *)0), "non null from realloc");
|
||||
cr_assert(new_ptr != ptr, "realloc is not the same ptr as malloc");
|
||||
free(new_ptr);
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user