diff options
| author | Daniel Hader <[email protected]> | 2026-06-14 12:58:14 -0500 |
|---|---|---|
| committer | Daniel Hader <[email protected]> | 2026-06-14 12:58:14 -0500 |
| commit | 482ea0261cb9f0def49ce3df542b2a7f811262d1 (patch) | |
| tree | 3bb961316b2ca856409b9f3b2145036ae9f5d704 /src/util/vec.c | |
build and test environment using makefile and basic SDL3 setup
Diffstat (limited to 'src/util/vec.c')
| -rw-r--r-- | src/util/vec.c | 98 |
1 files changed, 98 insertions, 0 deletions
diff --git a/src/util/vec.c b/src/util/vec.c new file mode 100644 index 0000000..1a37bef --- /dev/null +++ b/src/util/vec.c @@ -0,0 +1,98 @@ +#include <stddef.h> +#include <string.h> + +#include "vec.h" +#include "alloc.h" + +static enum LEO_Vec_Error LEO_Vec_grow(struct LEO_Vec *vec) +{ + size_t new_capacity = vec->capacity + * LEO_Vec_GROWTH_FACTOR_NUMER + / LEO_Vec_GROWTH_FACTOR_DENOM; + + if (new_capacity <= vec->capacity) + return LEO_Vec_TOO_BIG; + + vec->capacity = new_capacity; + vec->data = vec->allocator.realloc(vec->data, + vec->capacity * vec->item_size); + + if (vec->data == NULL) + return LEO_Vec_ALLOCATION_FAILURE; + + return LEO_Vec_OK; +} + +enum LEO_Vec_Error LEO_Vec_init(struct LEO_Vec *vec, size_t item_size, + struct LEO_Allocator allocator) +{ + if (vec == NULL) + return LEO_Vec_NULL_VEC_POINTER; + if (item_size == 0) + return LEO_Vec_INVALID_ITEM_SIZE; + + vec->allocator = allocator; + vec->item_size = item_size; + vec->length = 0; + vec->capacity = LEO_Vec_DEFAULT_CAPACITY; + vec->data = vec->allocator.alloc(vec->capacity * vec->item_size); + + if (!vec->data) + return LEO_Vec_ALLOCATION_FAILURE; + + return LEO_Vec_OK; +} + +void LEO_Vec_free(struct LEO_Vec *vec) +{ + if (vec == NULL) + return; + + vec->allocator.free(vec->data); + vec->data = NULL; +} + +enum LEO_Vec_Error LEO_Vec_push(struct LEO_Vec *vec, const void *item) +{ + if (vec == NULL) + return LEO_Vec_NULL_VEC_POINTER; + if (item == NULL) + return LEO_Vec_NULL_ITEM_POINTER; + + if (vec->length >= vec->capacity) { + enum LEO_Vec_Error result = LEO_Vec_grow(vec); + if (result != LEO_Vec_OK) + return result; + } + + unsigned char *dest = (unsigned char *)vec->data + (vec->length++) * vec->item_size; + memcpy(dest, item, vec->item_size); + + return LEO_Vec_OK; +} + +enum LEO_Vec_Error LEO_Vec_pop(struct LEO_Vec *vec, void *item) +{ + if (vec == NULL) + return LEO_Vec_NULL_VEC_POINTER; + if (vec->length == 0) + return LEO_Vec_OUT_OF_BOUNDS; + + void *src = vec->data + (vec->length--) * vec->item_size; + memcpy(item, src, vec->item_size); + + return LEO_Vec_OK; +} + +enum LEO_Vec_Error LEO_Vec_get(struct LEO_Vec *vec, size_t i, void *item) +{ + if (vec == NULL) + return LEO_Vec_NULL_VEC_POINTER; + if (i >= vec->length) + return LEO_Vec_OUT_OF_BOUNDS; + + unsigned char *src = (unsigned char *) vec->data + i * vec->item_size; + memcpy(item, src, vec->item_size); + + return LEO_Vec_OK; +} |
