diff options
| author | 2022-08-11 20:27:48 +0200 | |
|---|---|---|
| committer | 2022-08-11 20:27:48 +0200 | |
| commit | 19f1093f0929b989a06cdee2e7d175e6db15559c (patch) | |
| tree | acf82e3cb1b8e81ff132978b7656c178249c5f15 /src/mem.hff | |
| parent | c7961d732e5d67e8ea1b0be05e979bf24361f794 (diff) | |
things
Diffstat (limited to 'src/mem.hff')
| -rw-r--r-- | src/mem.hff | 62 |
1 files changed, 62 insertions, 0 deletions
diff --git a/src/mem.hff b/src/mem.hff new file mode 100644 index 0000000..9fee910 --- /dev/null +++ b/src/mem.hff @@ -0,0 +1,62 @@ +import "all.hff"; + +def ARENA_SIZE = 16 * 1024; + +struct ArenaRegion { + prev *ArenaRegion, + idx int, + mem [ARENA_SIZE]u8, +} + +struct Arena { + r *ArenaRegion, + + fn allocf(a *void, n usize) *void { + let a *Arena = a; + n = ALIGNUP(n, 16); + if ARENA_SIZE < n { + return xmalloc(n); + } else if a.r == #null { + a.r = xcalloc(1, sizeof ArenaRegion); + return allocf(a, n); + } else if ARENA_SIZE - a.r.idx >= n { + let ptr = &a.r.mem[a.r.idx]; + a.r.idx += n; + return ptr; + } else { + let rp = xmalloc(sizeof ArenaRegion); + *rp = a.r; + let r = ArenaRegion { .prev: rp }; + return allocf(a, n); + } + } +} + +struct Mallocator { + fn allocf(*void, n usize) *void { + return xmalloc(n); + } + + fn freef(*void, ptr *void) void { + free(ptr); + } +} + +struct Allocator { + a *void, + allocf *fn(a *void, n usize) *void, + freef *fn(a *void, ptr *void) void, + + fn alloc(self *Allocator, n usize) *void { + if self.allocf { + return self.allocf(self.a, n); + } + return #null; + } + + fn free(self *Allocator, ptr *void) void { + if self.freef { + self.freef(self.a, ptr); + } + } +} |