Introduce the allocator stuff again
This commit is contained in:
68
base.cpp
68
base.cpp
@@ -139,7 +139,6 @@ typedef double F64;
|
||||
#define JOIN(X,Y) JOIN1(X,Y)
|
||||
#define string_expand(x) (int)x.len, x.str
|
||||
|
||||
#define CORE_STRINGS
|
||||
struct String{
|
||||
U8 *str;
|
||||
S64 len;
|
||||
@@ -150,6 +149,14 @@ union Intern_String{ // Basically just String
|
||||
struct{ U8 *str; S64 len; };
|
||||
};
|
||||
|
||||
struct Allocator {
|
||||
typedef void *Allocate(Allocator *, size_t);
|
||||
typedef void Deallocate(Allocator *, void *p);
|
||||
|
||||
Allocate *allocate;
|
||||
Deallocate *deallocate;
|
||||
};
|
||||
|
||||
global String string_null = {(U8 *)"null", 4};
|
||||
#include <stdio.h>
|
||||
#define STB_SPRINTF_IMPLEMENTATION
|
||||
@@ -405,10 +412,20 @@ operator!=(Intern_String a, Intern_String b){
|
||||
#define Iter_Named(list, it) for(auto it = iterate(list); should_we_continue(&it); advance(&it))
|
||||
#define Iter(list) Iter_Named(list, it)
|
||||
|
||||
enum Alloc_Flag{
|
||||
AF_None,
|
||||
AF_ZeroMemory
|
||||
};
|
||||
#define allocate_array(a, T, size,...) (T *)allocate_size(a, sizeof(T)*(size),##__VA_ARGS__)
|
||||
#define allocate_struct(a, T, ...) allocate_array(a, T, 1,##__VA_ARGS__)
|
||||
CORE_Static void *allocate_size(Allocator *allocator, size_t size, bool zero_memory = true) {
|
||||
void *result = allocator->allocate(allocator, size);
|
||||
if (zero_memory) {
|
||||
memory_zero(result, size);
|
||||
}
|
||||
return result;
|
||||
}
|
||||
|
||||
CORE_Static void deallocate(Allocator *allocator, void *p) {
|
||||
assert(p);
|
||||
allocator->deallocate(allocator, p);
|
||||
}
|
||||
|
||||
//-----------------------------------------------------------------------------
|
||||
// Memory OS
|
||||
@@ -428,13 +445,12 @@ CORE_Static B32 os_decommit_pos(OS_Memory *m, size_t pos);
|
||||
global const size_t default_reserve_size = gib(4);
|
||||
global const size_t default_alignment = 8;
|
||||
global const size_t additional_commit_size = mib(1);
|
||||
struct Arena{
|
||||
struct Arena : Allocator {
|
||||
OS_Memory memory;
|
||||
size_t alignment;
|
||||
size_t len;
|
||||
String debug_string;
|
||||
};
|
||||
CORE_Static void arena_init(Arena *arena, String debug_name);
|
||||
|
||||
CORE_Static void
|
||||
arena_pop_pos(Arena *arena, size_t pos){
|
||||
@@ -459,15 +475,15 @@ arena_clear(Arena *arena){
|
||||
arena_pop_pos(arena, 0);
|
||||
}
|
||||
|
||||
#define arena_push_array(a, T, size,...) (T *)arena_push_size(a, sizeof(T)*(size),##__VA_ARGS__)
|
||||
#define arena_push_type(a, T, ...) arena_push_array(a, T, 1,##__VA_ARGS__)
|
||||
CORE_Static void
|
||||
deallocate_stub(Allocator *, void *) {
|
||||
}
|
||||
|
||||
CORE_Static void *
|
||||
arena_push_size(Arena *a, size_t size, Alloc_Flag flags = AF_None){
|
||||
arena_push_size(Arena *a, size_t size){
|
||||
size_t generous_size = size + a->alignment;
|
||||
if(a->len+generous_size>a->memory.commit){
|
||||
if(a->memory.reserve == 0){
|
||||
arena_init(a, "Zero initialized arena"_s);
|
||||
}
|
||||
assert(a->memory.reserve > 0);
|
||||
B32 result = os_commit(&a->memory, generous_size+additional_commit_size);
|
||||
assert(result);
|
||||
}
|
||||
@@ -477,10 +493,6 @@ arena_push_size(Arena *a, size_t size, Alloc_Flag flags = AF_None){
|
||||
void *result = (U8*)a->memory.data + a->len;
|
||||
a->len += size;
|
||||
|
||||
if(flags & AF_ZeroMemory){
|
||||
memory_zero(result, size);
|
||||
}
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
@@ -489,6 +501,8 @@ arena_init(Arena *a, String debug_name){
|
||||
a->memory = os_reserve(default_reserve_size);
|
||||
a->alignment = default_alignment;
|
||||
a->debug_string = debug_name;
|
||||
a->allocate = (Allocator::Allocate *)arena_push_size;
|
||||
a->deallocate = (Allocator::Deallocate *)deallocate_stub;
|
||||
}
|
||||
|
||||
enum Log_Kind{Log_Kind_Normal_No_NewLine, Log_Kind_Normal, Log_Kind_Error, Log_Kind_Trace};
|
||||
@@ -536,6 +550,7 @@ struct Scratch{
|
||||
arena_pop_pos(arena, saved_pos);
|
||||
}
|
||||
force_inline operator Arena*(){ return arena; }
|
||||
force_inline operator Allocator*(){ return arena; }
|
||||
|
||||
// @Note: Disable copy constructors, cause it caused lots of confusing errors
|
||||
// Where it passed scratch instead of the arena into the constructor
|
||||
@@ -557,7 +572,7 @@ thread_ctx_init(){
|
||||
//-----------------------------------------------------------------------------
|
||||
template<class T>
|
||||
struct Array{
|
||||
Arena *allocator;
|
||||
Allocator *allocator;
|
||||
T *data;
|
||||
S64 cap;
|
||||
S64 len;
|
||||
@@ -578,13 +593,14 @@ struct Array{
|
||||
void grow(S64 required_size){
|
||||
if(cap == 0){
|
||||
S64 new_cap = max(required_size*2, (S64)16);
|
||||
data = arena_push_array(allocator, T, new_cap);
|
||||
data = allocate_array(allocator, T, new_cap);
|
||||
cap = new_cap;
|
||||
}
|
||||
else if(len + required_size > cap){
|
||||
U64 new_cap = max(cap * 2, len+required_size+1);
|
||||
T *new_data = arena_push_array(allocator, T, new_cap);
|
||||
T *new_data = allocate_array(allocator, T, new_cap);
|
||||
memory_copy(new_data, data, cap*sizeof(T));
|
||||
deallocate(allocator, data);
|
||||
data = new_data;
|
||||
cap = new_cap;
|
||||
}
|
||||
@@ -622,7 +638,7 @@ struct Array{
|
||||
|
||||
void init(Arena *a, S64 size = 16){
|
||||
allocator = a;
|
||||
data = arena_push_array(a, T, size);
|
||||
data = allocate_array(a, T, size);
|
||||
cap = size;
|
||||
}
|
||||
|
||||
@@ -631,7 +647,7 @@ struct Array{
|
||||
result.len = len;
|
||||
result.cap = len*2;
|
||||
result.allocator = a;
|
||||
result.data = arena_push_array(a, T, result.cap);
|
||||
result.data = allocate_array(a, T, result.cap);
|
||||
memory_copy(result.data, data, sizeof(T)*result.len);
|
||||
return result;
|
||||
}
|
||||
@@ -641,7 +657,7 @@ struct Array{
|
||||
result.len = len;
|
||||
result.cap = len;
|
||||
result.allocator = 0;
|
||||
result.data = arena_push_array(a, T, len);
|
||||
result.data = allocate_array(a, T, len);
|
||||
memory_copy(result.data, data, sizeof(T)*len);
|
||||
return result;
|
||||
}
|
||||
@@ -731,7 +747,7 @@ struct Map_Key_Value{
|
||||
};
|
||||
|
||||
struct Map{
|
||||
Arena *allocator;
|
||||
Allocator *allocator;
|
||||
Map_Key_Value *data;
|
||||
S64 len;
|
||||
S64 cap;
|
||||
@@ -746,7 +762,7 @@ map_grow(Map *map, S64 new_size){
|
||||
assert(map->allocator);
|
||||
|
||||
Map new_map = {};
|
||||
new_map.data = arena_push_array(map->allocator, Map_Key_Value, new_size, AF_ZeroMemory);
|
||||
new_map.data = allocate_array(map->allocator, Map_Key_Value, new_size);
|
||||
new_map.cap = new_size;
|
||||
new_map.allocator = map->allocator;
|
||||
|
||||
@@ -755,7 +771,7 @@ map_grow(Map *map, S64 new_size){
|
||||
map_insert(&new_map, map->data[i].key, map->data[i].value);
|
||||
}
|
||||
}
|
||||
// if(map->data) exp_free(map->allocator, map->data);
|
||||
if(map->data) deallocate(map->allocator, map->data);
|
||||
*map = new_map;
|
||||
}
|
||||
|
||||
|
||||
@@ -77,7 +77,7 @@ operator==(String a, String b){
|
||||
|
||||
CORE_Static String
|
||||
string_copy(Arena *a, String string){
|
||||
U8 *copy = arena_push_array(a, U8, string.len+1);
|
||||
U8 *copy = allocate_array(a, U8, string.len+1);
|
||||
memory_copy(copy, string.str, string.len);
|
||||
copy[string.len] = 0;
|
||||
return String{copy, string.len};
|
||||
@@ -90,7 +90,7 @@ string_fmtv(Arena *a, const char *str, va_list args1) {
|
||||
S64 len = stbsp_vsnprintf(0, 0, str, args2);
|
||||
va_end(args2);
|
||||
|
||||
char *result = arena_push_array(a, char, len + 1);
|
||||
char *result = allocate_array(a, char, len + 1);
|
||||
stbsp_vsnprintf(result, len + 1, str, args1);
|
||||
|
||||
String res = {(U8 *)result, len};
|
||||
|
||||
@@ -160,7 +160,7 @@ utf16_to_utf32(U16 *c, S32 max_advance) {
|
||||
|
||||
CORE_Static String32
|
||||
string16_to_string32(Arena *allocator, String16 string){
|
||||
String32 result = {arena_push_array(allocator, U32, string.len+1)};
|
||||
String32 result = {allocate_array(allocator, U32, string.len+1)};
|
||||
for(S64 i = 0; i < string.len;){
|
||||
UTF32_Result decode = utf16_to_utf32(string.str + i, string.len - i);
|
||||
if(!decode.error){
|
||||
@@ -176,7 +176,7 @@ string16_to_string32(Arena *allocator, String16 string){
|
||||
|
||||
CORE_Static String32
|
||||
string8_to_string32(Arena *allocator, String string){
|
||||
String32 result = {arena_push_array(allocator, U32, string.len+1)};
|
||||
String32 result = {allocate_array(allocator, U32, string.len+1)};
|
||||
for(S64 i = 0; i < string.len;){
|
||||
UTF32_Result decode = utf8_to_utf32(string.str + i, string.len - i);
|
||||
if(!decode.error){
|
||||
@@ -191,7 +191,7 @@ string8_to_string32(Arena *allocator, String string){
|
||||
|
||||
CORE_Static String16
|
||||
string8_to_string16(Arena *allocator, String in){
|
||||
String16 result = {arena_push_array(allocator, U16, (in.len*2)+1)}; // @Note(Krzosa): Should be more then enough space
|
||||
String16 result = {allocate_array(allocator, U16, (in.len*2)+1)}; // @Note(Krzosa): Should be more then enough space
|
||||
for(S64 i = 0; i < in.len;){
|
||||
UTF32_Result decode = utf8_to_utf32(in.str + i, in.len - i);
|
||||
if(!decode.error){
|
||||
@@ -213,7 +213,7 @@ string8_to_string16(Arena *allocator, String in){
|
||||
|
||||
CORE_Static String
|
||||
string16_to_string8(Arena *allocator, String16 in){
|
||||
String result = {arena_push_array(allocator, U8, in.len*4+1)};
|
||||
String result = {allocate_array(allocator, U8, in.len*4+1)};
|
||||
for(S64 i = 0; i < in.len;){
|
||||
UTF32_Result decode = utf16_to_utf32(in.str + i, in.len - i);
|
||||
if(!decode.error){
|
||||
@@ -267,7 +267,7 @@ string16_from_widechar(wchar_t *string){
|
||||
|
||||
CORE_Static String
|
||||
string16_copy(Arena *a, String string){
|
||||
U8 *copy = arena_push_array(a, U8, string.len+1);
|
||||
U8 *copy = allocate_array(a, U8, string.len+1);
|
||||
memory_copy(copy, string.str, string.len);
|
||||
copy[string.len] = 0;
|
||||
return String{copy, string.len};
|
||||
|
||||
@@ -55,7 +55,7 @@ bigint_copy(Arena *allocator, BigInt *src){
|
||||
dest.digit_count = src->digit_count;
|
||||
|
||||
count_bigint_alloc();
|
||||
dest.digits = arena_push_array(allocator, uint64_t, dest.digit_count, AF_ZeroMemory);
|
||||
dest.digits = allocate_array(allocator, uint64_t, dest.digit_count);
|
||||
memcpy(dest.digits, src->digits, sizeof(uint64_t) * dest.digit_count);
|
||||
return dest;
|
||||
}
|
||||
|
||||
@@ -9,7 +9,7 @@ enum CmpRes
|
||||
};
|
||||
|
||||
#define count_bigint_alloc() (bigint_allocator != thread_ctx.scratch ? bigint_allocation_count++ : 0)
|
||||
#define malloc_arena(x) (count_bigint_alloc(), arena_push_size(bigint_allocator, x, AF_ZeroMemory))
|
||||
#define malloc_arena(x) (count_bigint_alloc(), allocate_size(bigint_allocator, x))
|
||||
#define ALLOC_DIGITS(_digits) (uint64_t *)((_digits) ? malloc_arena(sizeof(uint64_t) * (_digits)) : NULL)
|
||||
#define FATAL_ERROR(x) compiler_error(0, x)
|
||||
|
||||
|
||||
@@ -1,7 +1,7 @@
|
||||
|
||||
|
||||
#define AST_NEW(T,ikind,ipos,iflags) \
|
||||
Ast_##T *result = arena_push_type(pctx->perm, Ast_##T, AF_ZeroMemory);\
|
||||
Ast_##T *result = allocate_struct(pctx->perm, Ast_##T); \
|
||||
result->flags = iflags; \
|
||||
result->kind = AST_##ikind; \
|
||||
result->parent_scope = pctx->currently_parsed_scope; \
|
||||
@@ -11,7 +11,7 @@
|
||||
#define ast_new(T,kind,pos,flags) (T *)_ast_new(sizeof(T), kind, pos, flags)
|
||||
CORE_Static Ast *
|
||||
_ast_new(size_t size, Ast_Kind kind, Token *pos, Ast_Flag flags = 0){
|
||||
Ast *result = (Ast *)arena_push_size(pctx->perm, size, AF_ZeroMemory);
|
||||
Ast *result = (Ast *)allocate_size(pctx->perm, size);
|
||||
result->flags = flags;
|
||||
result->kind = kind;
|
||||
result->parent_scope = pctx->currently_parsed_scope;
|
||||
|
||||
@@ -98,7 +98,7 @@ parse_init(Parse_Ctx *ctx, Arena *perm_allocator) {
|
||||
CORE_Static void
|
||||
begin_compilation() {
|
||||
init_ctx_time_begin = os_time();
|
||||
Parse_Ctx *ctx = arena_push_type(&pernament_arena, Parse_Ctx, AF_ZeroMemory);
|
||||
Parse_Ctx *ctx = allocate_struct(&pernament_arena, Parse_Ctx);
|
||||
parse_init(ctx, &pernament_arena);
|
||||
init_ctx_time_end = os_time();
|
||||
}
|
||||
|
||||
@@ -20,6 +20,7 @@ struct Lexer{
|
||||
U32 token_debug_ids;
|
||||
|
||||
Intern_String intern(String string){
|
||||
assert(string.len > 0);
|
||||
return intern_string(&interns, string);
|
||||
}
|
||||
};
|
||||
|
||||
@@ -13,6 +13,15 @@ struct Ast_Expr;
|
||||
|
||||
#ifndef CORE_BASE
|
||||
#define CORE_BASE
|
||||
|
||||
struct Allocator {
|
||||
typedef void *Allocate(Allocator *, size_t);
|
||||
typedef void Deallocate(Allocator *, void *p);
|
||||
|
||||
Allocate *allocate;
|
||||
Deallocate *deallocate;
|
||||
};
|
||||
|
||||
struct String{
|
||||
uint8_t *str;
|
||||
int64_t len;
|
||||
|
||||
@@ -286,6 +286,8 @@ For modules it's a bit different cause they should be distributed as valid.
|
||||
|
||||
|
||||
int main(int argument_count, char **arguments){
|
||||
thread_ctx_init();
|
||||
|
||||
Scratch scratch;
|
||||
Array<String> args = {scratch};
|
||||
for(int i = 1; i < argument_count; i+=1){
|
||||
@@ -326,7 +328,6 @@ int main(int argument_count, char **arguments){
|
||||
test_os_memory();
|
||||
#endif
|
||||
|
||||
thread_ctx_init();
|
||||
test_unicode();
|
||||
|
||||
map_test();
|
||||
|
||||
@@ -59,7 +59,7 @@ force_inline B32 is_numeric(Ast_Type *type){
|
||||
//-----------------------------------------------------------------------------
|
||||
CORE_Static Ast_Type *
|
||||
type_new(Arena *allocator, Ast_Type_Kind kind, size_t size, size_t align){
|
||||
Ast_Type *result = arena_push_type(allocator, Ast_Type, AF_ZeroMemory);
|
||||
Ast_Type *result = allocate_struct(allocator, Ast_Type, true);
|
||||
result->kind = kind;
|
||||
result->size = size;
|
||||
result->align = align;
|
||||
@@ -71,7 +71,7 @@ type_new(Arena *allocator, Ast_Type_Kind kind, size_t size, size_t align){
|
||||
CORE_Static Ast_Type *
|
||||
type_copy(Arena *a, Ast_Type *type){
|
||||
// @warning: This changes type id !!!!
|
||||
Ast_Type *result = arena_push_type(a, Ast_Type);
|
||||
Ast_Type *result = allocate_struct(a, Ast_Type);
|
||||
memory_copy(result, type, sizeof(Ast_Type));
|
||||
result->type_id = pctx->type_ids++;
|
||||
add(pctx->perm, &pctx->all_types, result);
|
||||
|
||||
@@ -162,7 +162,7 @@ os_get_absolute_path(Arena *a, String path){
|
||||
Scratch scratch(a);
|
||||
String16 path16 = string8_to_string16(scratch, path);
|
||||
|
||||
wchar_t *buffer = arena_push_array(scratch, wchar_t, 2048);
|
||||
wchar_t *buffer = allocate_array(scratch, wchar_t, 2048);
|
||||
DWORD written = GetFullPathNameW((wchar_t *)path16.str, 2048, buffer, 0);
|
||||
if(written == 0) return {};
|
||||
|
||||
|
||||
Reference in New Issue
Block a user