2026-03-29 10:40:09 -06:00
|
|
|
#include "arena.h"
|
2026-03-29 17:53:10 -06:00
|
|
|
#include <stdbool.h>
|
2026-03-30 11:26:05 -06:00
|
|
|
#include <stddef.h>
|
|
|
|
|
#include <stdint.h>
|
2026-03-29 17:53:10 -06:00
|
|
|
#include <stdlib.h>
|
2026-03-29 18:35:13 -06:00
|
|
|
#include <string.h>
|
2026-03-29 17:53:10 -06:00
|
|
|
|
2026-03-30 11:26:05 -06:00
|
|
|
ArenaResult arena_init(size_t capacity) {
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
if (capacity < 1) {
|
2026-03-29 17:53:10 -06:00
|
|
|
ArenaResult err = {
|
|
|
|
|
.is_valid = false,
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
.err = ARENA_INVALID_SIZE,
|
2026-03-29 17:53:10 -06:00
|
|
|
};
|
|
|
|
|
return err;
|
|
|
|
|
}
|
|
|
|
|
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
void *buffer = malloc(capacity);
|
|
|
|
|
if (buffer == NULL) {
|
2026-03-29 17:53:10 -06:00
|
|
|
ArenaResult err = {
|
|
|
|
|
.is_valid = false,
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
.err = ARENA_BAD_ALLOC,
|
2026-03-29 17:53:10 -06:00
|
|
|
};
|
|
|
|
|
return err;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
Arena new_arena = {
|
2026-03-29 19:06:49 -06:00
|
|
|
.buffer = buffer,
|
2026-03-30 11:26:05 -06:00
|
|
|
.capacity = capacity,
|
2026-03-29 17:53:10 -06:00
|
|
|
.offset = 0,
|
|
|
|
|
};
|
|
|
|
|
ArenaResult val = {
|
|
|
|
|
.is_valid = true,
|
|
|
|
|
.arena = new_arena,
|
|
|
|
|
};
|
|
|
|
|
|
|
|
|
|
return val;
|
|
|
|
|
}
|
2026-03-29 18:00:57 -06:00
|
|
|
|
|
|
|
|
void arena_destroy(Arena *arena) {
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
free(arena->buffer);
|
|
|
|
|
arena->buffer = NULL;
|
2026-03-29 18:00:57 -06:00
|
|
|
arena->offset = 0;
|
2026-03-30 11:26:05 -06:00
|
|
|
arena->capacity = 0;
|
2026-03-29 18:00:57 -06:00
|
|
|
}
|
2026-03-29 18:35:13 -06:00
|
|
|
|
|
|
|
|
ArenaPointer arena_alloc(Arena *arena, size_t size, size_t alignment) {
|
|
|
|
|
if (arena == NULL) {
|
|
|
|
|
ArenaPointer err = {
|
|
|
|
|
.is_valid = false,
|
|
|
|
|
.err = ARENA_NULL_ARG,
|
|
|
|
|
};
|
|
|
|
|
return err;
|
|
|
|
|
}
|
|
|
|
|
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
SizeResult padding = get_arena_align_padding(arena, alignment);
|
|
|
|
|
if (!padding.is_valid) {
|
2026-03-29 20:59:32 -06:00
|
|
|
ArenaPointer err = {
|
|
|
|
|
.is_valid = false,
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
.err = padding.err,
|
2026-03-29 20:59:32 -06:00
|
|
|
};
|
|
|
|
|
return err;
|
|
|
|
|
}
|
|
|
|
|
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
|
|
|
|
|
if (arena->offset + padding.val >= arena->capacity) {
|
2026-03-29 18:35:13 -06:00
|
|
|
ArenaPointer err = {
|
|
|
|
|
.is_valid = false,
|
|
|
|
|
.err = ARENA_OUT_OF_SPACE,
|
|
|
|
|
};
|
|
|
|
|
return err;
|
|
|
|
|
}
|
|
|
|
|
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
if (arena->offset > SIZE_MAX - padding.val - size) {
|
|
|
|
|
ArenaPointer err = {
|
|
|
|
|
.is_valid = false,
|
|
|
|
|
.err = ARENA_CAPACITY_OVERFLOW,
|
|
|
|
|
};
|
|
|
|
|
return err;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
size_t aligned_offset = arena->offset + padding.val;
|
2026-03-29 18:35:13 -06:00
|
|
|
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
arena->offset = aligned_offset + size;
|
2026-03-29 18:35:13 -06:00
|
|
|
ArenaPointer val = {
|
|
|
|
|
.is_valid = true,
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
.address = arena->buffer + aligned_offset,
|
2026-03-29 18:35:13 -06:00
|
|
|
};
|
|
|
|
|
return val;
|
|
|
|
|
}
|
2026-03-29 19:06:49 -06:00
|
|
|
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
ArenaErr arena_ensure_capacity(Arena *arena, size_t size, size_t alignment) {
|
|
|
|
|
if (arena == NULL) {
|
|
|
|
|
return ARENA_NULL_ARG;
|
|
|
|
|
}
|
|
|
|
|
|
2026-04-03 12:51:49 -06:00
|
|
|
SizeResult padding = get_arena_align_padding(arena, alignment);
|
|
|
|
|
if (!padding.is_valid) {
|
|
|
|
|
return padding.err;
|
|
|
|
|
}
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
while (true) {
|
|
|
|
|
if (arena->offset > SIZE_MAX - padding.val - size) {
|
|
|
|
|
return ARENA_CAPACITY_OVERFLOW;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
size_t required = arena->offset + padding.val + size;
|
|
|
|
|
|
|
|
|
|
if (required <= arena->capacity) {
|
|
|
|
|
return ARENA_OK;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
size_t new_capacity;
|
|
|
|
|
if (mul_size_t_safe(arena->capacity, 2, &new_capacity)) {
|
|
|
|
|
return ARENA_CAPACITY_OVERFLOW;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
ArenaErr err = arena_realloc(arena, new_capacity);
|
|
|
|
|
if (err != ARENA_OK) {
|
|
|
|
|
return err;
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
}
|
|
|
|
|
|
test and rework: Added push test and cahnged arena_push return
So added a little test that just adds 3 ints to an arena, nothing much
but the basics work, also changed arena_push because it only pushed and
didn't returned a ponter (wich is fucking useless) so also fixed that,
everything seems fine now, need more tests.
# Tipos:
# feat, fix, refactor, docs, style, test, chore
2026-03-31 19:15:37 -06:00
|
|
|
ArenaPointer arena_push(Arena *arena, void *data, size_t size, size_t alignment) {
|
2026-03-29 19:06:49 -06:00
|
|
|
if (arena == NULL || data == NULL) {
|
test and rework: Added push test and cahnged arena_push return
So added a little test that just adds 3 ints to an arena, nothing much
but the basics work, also changed arena_push because it only pushed and
didn't returned a ponter (wich is fucking useless) so also fixed that,
everything seems fine now, need more tests.
# Tipos:
# feat, fix, refactor, docs, style, test, chore
2026-03-31 19:15:37 -06:00
|
|
|
ArenaPointer bad_pointer = {
|
|
|
|
|
.is_valid = false,
|
|
|
|
|
.err = ARENA_NULL_ARG,
|
|
|
|
|
};
|
|
|
|
|
return bad_pointer;
|
2026-03-29 19:06:49 -06:00
|
|
|
}
|
|
|
|
|
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
ArenaErr err = arena_ensure_capacity(arena, size, alignment);
|
|
|
|
|
if (err != ARENA_OK) {
|
|
|
|
|
ArenaPointer bad_pointer = {
|
|
|
|
|
.is_valid = false,
|
|
|
|
|
.err = err,
|
|
|
|
|
};
|
|
|
|
|
return bad_pointer;
|
|
|
|
|
}
|
2026-03-29 19:06:49 -06:00
|
|
|
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
ArenaPointer pointer = arena_alloc(arena, size, alignment);
|
2026-03-29 19:06:49 -06:00
|
|
|
if (!pointer.is_valid) {
|
test and rework: Added push test and cahnged arena_push return
So added a little test that just adds 3 ints to an arena, nothing much
but the basics work, also changed arena_push because it only pushed and
didn't returned a ponter (wich is fucking useless) so also fixed that,
everything seems fine now, need more tests.
# Tipos:
# feat, fix, refactor, docs, style, test, chore
2026-03-31 19:15:37 -06:00
|
|
|
return pointer;
|
2026-03-30 11:26:05 -06:00
|
|
|
}
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
|
2026-03-29 19:06:49 -06:00
|
|
|
memcpy(
|
|
|
|
|
pointer.address,
|
|
|
|
|
data,
|
|
|
|
|
size);
|
|
|
|
|
|
test and rework: Added push test and cahnged arena_push return
So added a little test that just adds 3 ints to an arena, nothing much
but the basics work, also changed arena_push because it only pushed and
didn't returned a ponter (wich is fucking useless) so also fixed that,
everything seems fine now, need more tests.
# Tipos:
# feat, fix, refactor, docs, style, test, chore
2026-03-31 19:15:37 -06:00
|
|
|
return pointer;
|
2026-03-29 19:06:49 -06:00
|
|
|
}
|
|
|
|
|
|
2026-03-30 11:26:05 -06:00
|
|
|
ArenaErr arena_realloc(Arena *arena, size_t new_capacity) {
|
2026-03-29 19:06:49 -06:00
|
|
|
if (arena == NULL) {
|
|
|
|
|
return ARENA_NULL_ARG;
|
|
|
|
|
}
|
|
|
|
|
|
2026-03-30 11:26:05 -06:00
|
|
|
uint8_t *tmp = realloc(arena->buffer, new_capacity);
|
2026-03-29 19:06:49 -06:00
|
|
|
if (tmp == NULL) {
|
|
|
|
|
return ARENA_BAD_ALLOC;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
arena->buffer = tmp;
|
2026-03-30 11:26:05 -06:00
|
|
|
arena->capacity = new_capacity;
|
2026-03-29 19:06:49 -06:00
|
|
|
return ARENA_OK;
|
|
|
|
|
}
|
2026-03-29 20:59:32 -06:00
|
|
|
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
SizeResult get_arena_align_padding(Arena *arena, size_t alignment) {
|
2026-03-29 21:08:34 -06:00
|
|
|
if (arena == NULL) {
|
|
|
|
|
SizeResult err = {
|
|
|
|
|
.is_valid = false,
|
|
|
|
|
.err = ARENA_NULL_ARG,
|
|
|
|
|
};
|
|
|
|
|
return err;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (alignment < 1) {
|
|
|
|
|
SizeResult err = {
|
|
|
|
|
.is_valid = false,
|
|
|
|
|
.err = ARENA_INVALID_ALIGN,
|
|
|
|
|
};
|
|
|
|
|
return err;
|
|
|
|
|
}
|
|
|
|
|
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
uintptr_t current_address = (uintptr_t) (arena->buffer + arena->offset);
|
|
|
|
|
uintptr_t aligned = ((current_address + (alignment - 1)) & ~(alignment - 1));
|
2026-03-29 21:08:34 -06:00
|
|
|
SizeResult val = {
|
|
|
|
|
.is_valid = true,
|
refactor(all): Fixed alloc and moved growing logic to another function
OK, so evrything was a fucknig mess, it still kinda is, AI helped
me to clean my own mess, it really sucks but the fucking debugger
and address sanitizer were not working, also, there were small
small errors so no big deal but still, a bit sad, also changed a
the way i cast from uint8_t to double and int in the tests, may
change that i guess, verything else i might say is good :)
2026-04-03 12:44:01 -06:00
|
|
|
.val = aligned - current_address,
|
2026-03-29 21:08:34 -06:00
|
|
|
};
|
|
|
|
|
return val;
|
|
|
|
|
}
|
2026-03-29 20:59:32 -06:00
|
|
|
|
2026-03-30 11:26:05 -06:00
|
|
|
bool mul_size_t_safe(size_t a, size_t b, size_t *out) {
|
|
|
|
|
if (out == NULL) {
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
if (a != 0 && b > SIZE_MAX / a) {
|
|
|
|
|
return true;
|
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
*out = a * b;
|
|
|
|
|
return false;
|
|
|
|
|
}
|
|
|
|
|
|