Begin clarifying allocation patterns by changing from heap_allocator to specific arenas

This commit is contained in:
gingerBill
2020-11-15 18:08:52 +00:00
parent 9f93042163
commit 3c1c10a178
10 changed files with 209 additions and 201 deletions
+3 -1
View File
@@ -690,8 +690,10 @@ void add_global_type_entity(String name, Type *type) {
void init_universal(void) {
BuildContext *bc = &build_context;
// NOTE(bill): No need to free these
gbAllocator a = heap_allocator();
// gbAllocator a = heap_allocator();
gbAllocator a = permanent_allocator();
builtin_pkg = gb_alloc_item(a, AstPackage);
builtin_pkg->name = str_lit("builtin");
-2
View File
@@ -337,8 +337,6 @@ struct Checker {
gb_global AstPackage *builtin_pkg = nullptr;
gb_global AstPackage *intrinsics_pkg = nullptr;
gb_global AstPackage *config_pkg = nullptr;
+40 -8
View File
@@ -373,8 +373,8 @@ typedef struct Arena {
gbAllocator backing;
isize block_size;
gbMutex mutex;
isize total_used;
bool use_mutex;
} Arena;
#define ARENA_MIN_ALIGNMENT 16
@@ -388,8 +388,9 @@ void arena_init(Arena *arena, gbAllocator backing, isize block_size=ARENA_DEFAUL
}
void arena_grow(Arena *arena, isize min_size) {
// gb_mutex_lock(&arena->mutex);
// defer (gb_mutex_unlock(&arena->mutex));
if (arena->use_mutex) {
gb_mutex_lock(&arena->mutex);
}
isize size = gb_max(arena->block_size, min_size);
size = ALIGN_UP(size, ARENA_MIN_ALIGNMENT);
@@ -399,11 +400,16 @@ void arena_grow(Arena *arena, isize min_size) {
GB_ASSERT(arena->ptr == ALIGN_DOWN_PTR(arena->ptr, ARENA_MIN_ALIGNMENT));
arena->end = arena->ptr + size;
array_add(&arena->blocks, arena->ptr);
if (arena->use_mutex) {
gb_mutex_unlock(&arena->mutex);
}
}
void *arena_alloc(Arena *arena, isize size, isize alignment) {
// gb_mutex_lock(&arena->mutex);
// defer (gb_mutex_unlock(&arena->mutex));
if (arena->use_mutex) {
gb_mutex_lock(&arena->mutex);
}
arena->total_used += size;
@@ -419,12 +425,17 @@ void *arena_alloc(Arena *arena, isize size, isize alignment) {
GB_ASSERT(arena->ptr <= arena->end);
GB_ASSERT(ptr == ALIGN_DOWN_PTR(ptr, align));
// zero_size(ptr, size);
if (arena->use_mutex) {
gb_mutex_unlock(&arena->mutex);
}
return ptr;
}
void arena_free_all(Arena *arena) {
// gb_mutex_lock(&arena->mutex);
// defer (gb_mutex_unlock(&arena->mutex));
if (arena->use_mutex) {
gb_mutex_lock(&arena->mutex);
}
for_array(i, arena->blocks) {
gb_free(arena->backing, arena->blocks[i]);
@@ -432,6 +443,10 @@ void arena_free_all(Arena *arena) {
array_clear(&arena->blocks);
arena->ptr = nullptr;
arena->end = nullptr;
if (arena->use_mutex) {
gb_mutex_unlock(&arena->mutex);
}
}
@@ -460,7 +475,14 @@ GB_ALLOCATOR_PROC(arena_allocator_proc) {
// GB_PANIC("gbAllocation_Free not supported");
break;
case gbAllocation_Resize:
GB_PANIC("gbAllocation_Resize: not supported");
if (size == 0) {
ptr = nullptr;
} else if (size <= old_size) {
ptr = old_memory;
} else {
ptr = arena_alloc(arena, size, alignment);
gb_memmove(ptr, old_memory, old_size);
}
break;
case gbAllocation_FreeAll:
arena_free_all(arena);
@@ -472,6 +494,16 @@ GB_ALLOCATOR_PROC(arena_allocator_proc) {
gb_global Arena permanent_arena = {};
gb_global Arena temporary_arena = {};
gbAllocator permanent_allocator() {
return arena_allocator(&permanent_arena);
}
gbAllocator temporary_allocator() {
return arena_allocator(&temporary_arena);
}
+1 -1
View File
@@ -220,7 +220,7 @@ bool entity_has_deferred_procedure(Entity *e) {
gb_global u64 global_entity_id = 0;
Entity *alloc_entity(EntityKind kind, Scope *scope, Token token, Type *type) {
gbAllocator a = heap_allocator();
gbAllocator a = permanent_allocator();
Entity *entity = gb_alloc_item(a, Entity);
entity->kind = kind;
entity->state = EntityState_Unresolved;
+6 -1
View File
@@ -276,6 +276,9 @@ Type *alloc_type_struct_from_field_types(Type **field_types, isize field_count,
}
Type *alloc_type_tuple_from_field_types(Type **field_types, isize field_count, bool is_packed, bool must_be_tuple) {
if (field_count == 0) {
return nullptr;
}
if (!must_be_tuple && field_count == 1) {
return field_types[0];
}
@@ -297,7 +300,9 @@ Type *alloc_type_proc_from_types(Type **param_types, unsigned param_count, Type
Type *params = alloc_type_tuple_from_field_types(param_types, param_count, false, true);
isize results_count = 0;
if (results != nullptr) {
GB_ASSERT(results->kind == Type_Tuple);
if (results->kind != Type_Tuple) {
results = alloc_type_tuple_from_field_types(&results, 1, false, true);
}
results_count = results->Tuple.variables.count;
}
+114 -165
View File
File diff suppressed because it is too large Load Diff
+15 -1
View File
@@ -1643,12 +1643,15 @@ int main(int arg_count, char const **arg_ptr) {
timings_init(timings, str_lit("Total Time"), 128);
defer (timings_destroy(timings));
arena_init(&permanent_arena, heap_allocator());
arena_init(&temporary_arena, heap_allocator());
arena_init(&global_ast_arena, heap_allocator());
init_string_buffer_memory();
init_string_interner();
init_global_error_collector();
init_keyword_hash_table();
global_big_int_init();
arena_init(&global_ast_arena, heap_allocator());
array_init(&library_collections, heap_allocator());
// NOTE(bill): 'core' cannot be (re)defined by the user
@@ -1795,6 +1798,8 @@ int main(int arg_count, char const **arg_ptr) {
return 1;
}
arena_free_all(&temporary_arena);
if (build_context.generate_docs) {
// generate_documentation(&parser);
return 0;
@@ -1812,6 +1817,7 @@ int main(int arg_count, char const **arg_ptr) {
check_parsed_files(&checker);
}
arena_free_all(&temporary_arena);
if (build_context.no_output_files) {
if (build_context.query_data_set_settings.ok) {
@@ -1842,6 +1848,8 @@ int main(int arg_count, char const **arg_ptr) {
}
lb_generate_code(&gen);
arena_free_all(&temporary_arena);
switch (build_context.build_mode) {
case BuildMode_Executable:
case BuildMode_DynamicLibrary:
@@ -1919,12 +1927,18 @@ int main(int arg_count, char const **arg_ptr) {
timings_start_section(timings, str_lit("llvm ir gen"));
ir_gen_tree(&ir_gen);
arena_free_all(&temporary_arena);
timings_start_section(timings, str_lit("llvm ir opt tree"));
ir_opt_tree(&ir_gen);
arena_free_all(&temporary_arena);
timings_start_section(timings, str_lit("llvm ir print"));
print_llvm_ir(&ir_gen);
arena_free_all(&temporary_arena);
String output_name = ir_gen.output_name;
String output_base = ir_gen.output_base;
+25 -18
View File
@@ -108,6 +108,30 @@ Token ast_token(Ast *node) {
return empty_token;
}
gb_global gbAtomic64 total_allocated_node_memory = {0};
gb_global gbAtomic64 total_subtype_node_memory_test = {0};
isize ast_node_size(AstKind kind) {
return align_formula_isize(gb_size_of(AstCommonStuff) + ast_variant_sizes[kind], gb_align_of(void *));
}
// NOTE(bill): And this below is why is I/we need a new language! Discriminated unions are a pain in C/C++
Ast *alloc_ast_node(AstFile *f, AstKind kind) {
gbAllocator a = ast_allocator(f);
isize size = ast_node_size(kind);
gb_atomic64_fetch_add(&total_allocated_node_memory, cast(i64)(gb_size_of(Ast)));
gb_atomic64_fetch_add(&total_subtype_node_memory_test, cast(i64)(gb_size_of(AstCommonStuff) + ast_variant_sizes[kind]));
// Ast *node = gb_alloc_item(a, Ast);
Ast *node = cast(Ast *)gb_alloc(a, size);
node->kind = kind;
node->file = f;
return node;
}
Ast *clone_ast(Ast *node);
Array<Ast *> clone_ast_array(Array<Ast *> array) {
Array<Ast *> result = {};
@@ -125,7 +149,7 @@ Ast *clone_ast(Ast *node) {
return nullptr;
}
Ast *n = alloc_ast_node(node->file, node->kind);
gb_memmove(n, node, gb_size_of(Ast));
gb_memmove(n, node, ast_node_size(node->kind));
switch (n->kind) {
default: GB_PANIC("Unhandled Ast %.*s", LIT(ast_strings[n->kind])); break;
@@ -463,23 +487,6 @@ bool ast_node_expect(Ast *node, AstKind kind) {
return true;
}
gb_global gbAtomic64 total_allocated_node_memory = {0};
gb_global gbAtomic64 total_subtype_node_memory_test = {0};
// NOTE(bill): And this below is why is I/we need a new language! Discriminated unions are a pain in C/C++
Ast *alloc_ast_node(AstFile *f, AstKind kind) {
gbAllocator a = ast_allocator(f);
gb_atomic64_fetch_add(&total_allocated_node_memory, cast(i64)(gb_size_of(Ast)));
gb_atomic64_fetch_add(&total_subtype_node_memory_test, cast(i64)(gb_size_of(AstCommonStuff) + ast_variant_sizes[kind]));
Ast *node = gb_alloc_item(a, Ast);
node->kind = kind;
node->file = f;
return node;
}
Ast *ast_bad_expr(AstFile *f, Token begin, Token end) {
Ast *result = alloc_ast_node(f, Ast_BadExpr);
result->BadExpr.begin = begin;
+1
View File
@@ -655,6 +655,7 @@ struct Ast {
Scope * scope;
TypeAndValue tav;
// IMPORTANT NOTE(bill): This must be at the end since the AST is allocated to be size of the variant
union {
#define AST_KIND(_kind_name_, name, ...) GB_JOIN2(Ast, _kind_name_) _kind_name_;
AST_KINDS
+4 -4
View File
@@ -771,7 +771,8 @@ void set_base_type(Type *t, Type *base) {
Type *alloc_type(TypeKind kind) {
gbAllocator a = heap_allocator();
// gbAllocator a = heap_allocator();
gbAllocator a = permanent_allocator();
Type *t = gb_alloc_item(a, Type);
zero_item(t);
t->kind = kind;
@@ -2340,7 +2341,7 @@ Selection lookup_field_from_index(Type *type, i64 index) {
GB_ASSERT(is_type_struct(type) || is_type_union(type) || is_type_tuple(type));
type = base_type(type);
gbAllocator a = heap_allocator();
gbAllocator a = permanent_allocator();
isize max_count = 0;
switch (type->kind) {
case Type_Struct: max_count = type->Struct.fields.count; break;
@@ -2397,7 +2398,6 @@ Selection lookup_field_with_selection(Type *type_, String field_name, bool is_ty
return empty_selection;
}
gbAllocator a = heap_allocator();
Type *type = type_deref(type_);
bool is_ptr = type != type_;
sel.indirect = sel.indirect || is_ptr;
@@ -2986,7 +2986,7 @@ i64 type_align_of_internal(Type *t, TypePath *path) {
}
Array<i64> type_set_offsets_of(Array<Entity *> const &fields, bool is_packed, bool is_raw_union) {
gbAllocator a = heap_allocator();
gbAllocator a = permanent_allocator();
auto offsets = array_make<i64>(a, fields.count);
i64 curr_offset = 0;
if (is_raw_union) {