diff --git a/cig.h b/cig.h index 798a64f..7fd77e4 100644 --- a/cig.h +++ b/cig.h @@ -127,7 +127,8 @@ typedef struct arena_allocator { size_t chunk_size; } arena_allocator_t; void *arena_allocator_alloc_func(arena_allocator_t *this, size_t bytes, const char *file, int line); -#define arena_allocator_alloc(THIS, BYTES) arena_allocator_alloc_func(THIS, BYTES, __FILE__, __LINE__) +#define arena_allocator_alloc(THIS, BYTES) \ + arena_allocator_alloc_func(THIS, BYTES, __FILE__, __LINE__) // TODO finish this shite // dynamic arrays ////////////////////////////////////////////////////////////// @@ -173,23 +174,31 @@ typedef struct dyn_array_create_non_crashing_func_args { allocator_t allocator; size_t itemsize; size_t initial_capacity; + const char *file; + size_t line; } dyn_array_create_non_crashing_func_args_t; void *dyn_array_create_non_crashing_func(dyn_array_create_non_crashing_func_args_t args); // This version returns a NULL pointer instead of crashing if the allocator return NULL. // It is up to you to check that the pointer returned isn't NULL #define dyn_array_create_non_crashing(ALLOCATOR, TYPE, ...) \ - ((TYPE *)dyn_array_create_func((dyn_array_create_non_crashing_func_args_t){ \ - .allocator = ALLOCATOR, .itemsize = sizeof(TYPE), __VA_ARGS__})) + ((TYPE *)dyn_array_create_non_crashing_func( \ + (dyn_array_create_non_crashing_func_args_t){.allocator = ALLOCATOR, \ + .itemsize = sizeof(TYPE), \ + .file = __FILE__, \ + .line = __LINE__, \ + __VA_ARGS__})) // This version returns a NULL pointer instead of crashing if the allocator return NULL. // It is up to you to check that the pointer returned isn't NULL // Always reassign the array. if multiple variables reference the same growing // array, then you should be using pointer pointers. -void *dyn_array_grow_non_crashing_func(void *this, size_t n_new_items); +void *dyn_array_grow_non_crashing_func(void *this, size_t n_new_items, const char *file, int line); #define dyn_array_grow_non_crashing(THIS, N_NEW_ITEMS) dyn_array_grow_non_crashing_func(THIS, N_NEW_ITEMS) size_t dyn_array_length(void *this); size_t dyn_array_capacity(void *this); +void dyn_array_destroy(void *this); + #define dyn_array_append(THIS, VAL) do { \ THIS = dyn_array_grow(THIS, 1); \ THIS[dyn_array_length(THIS)-1] = VAL; \ diff --git a/dyn_array.c b/dyn_array.c index 5860ca5..1fc4081 100644 --- a/dyn_array.c +++ b/dyn_array.c @@ -7,6 +7,8 @@ void *dyn_array_create_func(dyn_array_create_func_args_t args) { .allocator=args.allocator, .itemsize=args.itemsize, .initial_capacity=args.initial_capacity, + .file=args.file, + .line=args.line } ); if (bytes == NULL) { @@ -22,7 +24,7 @@ void *dyn_array_create_func(dyn_array_create_func_args_t args) { } void *dyn_array_grow_func(void *this, size_t n_new_items, const char *file, int line) { - void *bytes = dyn_array_grow_non_crashing_func(this, n_new_items); + void *bytes = dyn_array_grow_non_crashing_func(this, n_new_items, file, line); if (bytes == NULL) { fprintf( stderr, @@ -35,9 +37,11 @@ void *dyn_array_grow_func(void *this, size_t n_new_items, const char *file, int } void *dyn_array_create_non_crashing_func(dyn_array_create_non_crashing_func_args_t args) { - dyn_array_header_t *header = allocator_alloc( + dyn_array_header_t *header = allocator_alloc_func( args.allocator, - sizeof(dyn_array_header_t) + args.itemsize * args.initial_capacity + sizeof(dyn_array_header_t) + args.itemsize * args.initial_capacity, + args.file, + args.line ); if (header == NULL) { return NULL; } header->size = 0; @@ -47,7 +51,7 @@ void *dyn_array_create_non_crashing_func(dyn_array_create_non_crashing_func_args return &header->bytes; } -void *dyn_array_grow_non_crashing_func(void *this, size_t n_new_items) { +void *dyn_array_grow_non_crashing_func(void *this, size_t n_new_items, const char *file, int line) { dyn_array_header_t *header = PTR_FROM_FIELD_PTR(dyn_array_header_t, bytes, this); size_t new_size = header->size + n_new_items; @@ -57,13 +61,16 @@ void *dyn_array_grow_non_crashing_func(void *this, size_t n_new_items) { cap_times_2 < new_size ? new_size : cap_times_2; - header = allocator_resize( + header = allocator_resize_func( header->allocator, header, - sizeof(dyn_array_header_t) + header->itemsize * new_capacity + sizeof(dyn_array_header_t) + header->itemsize * new_capacity, + file, + line ); if (header == NULL) { return NULL; } header->capacity = new_capacity; + header->size = new_size; } return &header->bytes; } @@ -92,3 +99,8 @@ size_t dyn_array_capacity(void *this) { dyn_array_header_t *header = PTR_FROM_FIELD_PTR(dyn_array_header_t, bytes, this); return header->capacity; } + +void dyn_array_destroy(void *this) { + dyn_array_header_t *header = PTR_FROM_FIELD_PTR(dyn_array_header_t, bytes, this); + allocator_free(header->allocator, header); +} diff --git a/makefile b/makefile index 1279a08..6682961 100644 --- a/makefile +++ b/makefile @@ -19,7 +19,6 @@ test: valgrind --leak-check=full --show-leak-kinds=all --trace-children=yes --error-exitcode=1 $(TESTBIN); \ fi - PROJECT_ROOT := $(shell pwd) PROJECT_C_FILES := $(shell find $(PROJECT_ROOT) \( -name '*.c' -o -name '*.h' \)) CRITERION_HEADERS := $(shell find /usr/include/criterion) diff --git a/test_dynamic_array.c b/test_dynamic_array.c index a1f6d0d..f725fc9 100644 --- a/test_dynamic_array.c +++ b/test_dynamic_array.c @@ -47,5 +47,6 @@ Test(dynamic_arrays, pop) { int num = dyn_array_pop(numbers); cr_assert_eq(num, 50-i); } + dyn_array_destroy(numbers); } }