crazy arena implementation
This commit is contained in:
parent
17e458b4e7
commit
df60b5f76f
4 changed files with 113 additions and 22 deletions
|
|
@ -1,9 +1,8 @@
|
||||||
-I./src
|
-Isrc
|
||||||
-I./thirdparty/
|
-Ithirdparty/
|
||||||
-I./thirdparty/blocksruntime/BlocksRuntime/
|
-Ithirdparty/blocksruntime/BlocksRuntime/
|
||||||
-I./thirdparty/blocksruntime/
|
-Ithirdparty/blocksruntime/
|
||||||
--std=c2x
|
--std=c2x
|
||||||
-fblocks
|
-fblocks
|
||||||
|
|
||||||
-xobjective-c
|
-xobjective-c
|
||||||
-DPLATFORM_MACOS -DCHANGE_THESE_LINES_IF_YOURE_ON_A_DIFFERENT_PLATFORM
|
-DPLATFORM_MACOS -DCHANGE_THESE_LINES_IF_YOURE_ON_A_DIFFERENT_PLATFORM
|
||||||
|
|
|
||||||
73
src/arena.c
Normal file
73
src/arena.c
Normal file
|
|
@ -0,0 +1,73 @@
|
||||||
|
#include <string.h>
|
||||||
|
#include <stdlib.h>
|
||||||
|
|
||||||
|
typedef enum { arena__alloc, arena__reset, arena__release } arena__action;
|
||||||
|
|
||||||
|
typedef void* (^Arena)(arena__action, usize, usize, usize*, const char*, sreg);
|
||||||
|
|
||||||
|
#define arena_new(A, T) cast(T*, A(arena__alloc, sizeof(T), alignof(T), 0, __FILE__, __LINE__))
|
||||||
|
#define arena_reset(A) A(arena__reset, 0, 0, 0, __FILE__, __LINE__)
|
||||||
|
#define arena_release(A) A(arena__release, 0, 0, 0, __FILE__, __LINE__)
|
||||||
|
|
||||||
|
// just a nice macro to make these easier to write
|
||||||
|
#define func(a1, a2, a3, a4, a5, a6) ^void* (arena__action a1, usize a2, usize a3, usize* a4, const char* a5, sreg a6)
|
||||||
|
|
||||||
|
static Arena
|
||||||
|
Static(u8* data, usize count) {
|
||||||
|
memset(data, 0, count);
|
||||||
|
|
||||||
|
capture usize offset = 0;
|
||||||
|
return closure(func(action, size, align, _1, _2, _3) {
|
||||||
|
switch (action) {
|
||||||
|
default: {
|
||||||
|
} break;
|
||||||
|
|
||||||
|
case arena__alloc: {
|
||||||
|
offset = (offset + align - 1) & ~(align - 1);
|
||||||
|
if (offset + size > count) return 0;
|
||||||
|
|
||||||
|
void* ptr = data + offset;
|
||||||
|
offset += size;
|
||||||
|
|
||||||
|
return ptr;
|
||||||
|
} break;
|
||||||
|
|
||||||
|
case arena__reset: {
|
||||||
|
offset = 0;
|
||||||
|
} break;
|
||||||
|
}
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
static Arena
|
||||||
|
Linear(usize max_memory) {
|
||||||
|
void* ptr = malloc(max_memory);
|
||||||
|
Arena backing = Static(ptr, max_memory);
|
||||||
|
return closure(func(action, size, align, savepoint, file, line) {
|
||||||
|
if (action == arena__release) {
|
||||||
|
free(ptr);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
return backing(action, size, align, savepoint, file, line);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
static Arena
|
||||||
|
Logger(Arena arena) {
|
||||||
|
return closure(func(action, size, align, savepoint, file, line) {
|
||||||
|
char* action_str = "unknown";
|
||||||
|
switch (action) {
|
||||||
|
case arena__alloc: action_str = "alloc"; break;
|
||||||
|
case arena__reset: action_str = "reset"; break;
|
||||||
|
case arena__release: action_str = "release"; break;
|
||||||
|
}
|
||||||
|
|
||||||
|
printf("[ARENA] %s:%zd: %s (%zu, %zu)\n", file, line, action_str, size, align);
|
||||||
|
return arena(action, size, align, savepoint, file, line);
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
|
#undef func
|
||||||
11
src/base.c
11
src/base.c
|
|
@ -31,14 +31,15 @@ typedef int64_t s64;
|
||||||
typedef float f32;
|
typedef float f32;
|
||||||
typedef double f64;
|
typedef double f64;
|
||||||
|
|
||||||
typedef intptr_t intptr;
|
typedef uintptr_t uptr;
|
||||||
typedef uintptr_t uintptr;
|
typedef intptr_t sptr;
|
||||||
|
|
||||||
|
typedef uptr ureg;
|
||||||
|
typedef sptr sreg;
|
||||||
|
|
||||||
typedef size_t usize;
|
typedef size_t usize;
|
||||||
typedef ptrdiff_t ssize;
|
typedef ptrdiff_t ssize;
|
||||||
|
|
||||||
typedef int64_t sint;
|
|
||||||
typedef uint64_t uint;
|
|
||||||
|
|
||||||
|
|
||||||
// Thanks AZMR
|
// Thanks AZMR
|
||||||
#define cast(to_type, expr) ((to_type)(expr))
|
#define cast(to_type, expr) ((to_type)(expr))
|
||||||
|
|
|
||||||
42
src/main.c
42
src/main.c
|
|
@ -1,5 +1,6 @@
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
#include "base.c"
|
#include "base.c"
|
||||||
|
#include "arena.c"
|
||||||
|
|
||||||
#define SOKOL_IMPL
|
#define SOKOL_IMPL
|
||||||
|
|
||||||
|
|
@ -52,19 +53,36 @@ init(void) {
|
||||||
x += 1;
|
x += 1;
|
||||||
});
|
});
|
||||||
|
|
||||||
s32 i = -10243;
|
printf("x = %d (before)\n", x);
|
||||||
scope_exit {
|
for (ureg i = 0; i < 10; i += 1) {
|
||||||
printf("it works %d!\n", i);
|
inc();
|
||||||
};
|
}
|
||||||
|
printf("x = %d (after)\n", x);
|
||||||
|
|
||||||
printf("x = %d\n", x);
|
auto arena = Logger(Linear(1024 * 1024));
|
||||||
inc();
|
scope_exit { arena_release(arena); };
|
||||||
inc();
|
|
||||||
inc();
|
sreg* a = arena_new(arena, sreg);
|
||||||
inc();
|
sreg* b = arena_new(arena, sreg);
|
||||||
inc();
|
sreg* c = arena_new(arena, sreg);
|
||||||
inc();
|
|
||||||
printf("x = %d\n", x);
|
*a = 1024;
|
||||||
|
*b = 2048;
|
||||||
|
*c = 4096;
|
||||||
|
|
||||||
|
printf("%zu (%p)\n", *a, a);
|
||||||
|
printf("%zu (%p)\n", *b, b);
|
||||||
|
printf("%zu (%p)\n", *c, c);
|
||||||
|
|
||||||
|
arena_reset(arena);
|
||||||
|
|
||||||
|
c = arena_new(arena, sreg);
|
||||||
|
b = arena_new(arena, sreg);
|
||||||
|
a = arena_new(arena, sreg);
|
||||||
|
|
||||||
|
printf("%zu (%p)\n", *a, a);
|
||||||
|
printf("%zu (%p)\n", *b, b);
|
||||||
|
printf("%zu (%p)\n", *c, c);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue