aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authordec05eba <dec05eba@protonmail.com>2019-09-18 13:33:05 +0200
committerdec05eba <dec05eba@protonmail.com>2020-07-25 14:36:46 +0200
commitab0c5259e5a3238e176e4b1aed942f5384a2d0c6 (patch)
tree20111eefcafa13d92485ba6a0738c480f5c0c319
parent7028a74894eba649beb9e1881dabaf94a29961a0 (diff)
Fix leak on parse failure
-rw-r--r--include/parser.h3
-rw-r--r--src/compiler.c24
-rw-r--r--src/std/arena_allocator.c3
-rw-r--r--tests/glfw.amal2
-rw-r--r--tests/main.c2
5 files changed, 20 insertions, 14 deletions
diff --git a/include/parser.h b/include/parser.h
index ae5cfa6..88bed93 100644
--- a/include/parser.h
+++ b/include/parser.h
@@ -27,8 +27,7 @@ struct Parser {
LhsExpr file_decl;
Scope *current_scope;
bool has_func_parent;
- /* Borrowed from @compiler for faster access to allocator. The allocator is thread-specific */
- ArenaAllocator *allocator;
+ ArenaAllocator *allocator; /* Owned */
amal_compiler *compiler;
Ssa *ssa;
bool started;
diff --git a/src/compiler.c b/src/compiler.c
index c10ccc9..7fd4426 100644
--- a/src/compiler.c
+++ b/src/compiler.c
@@ -180,22 +180,23 @@ typedef struct {
static CHECK_RESULT int amal_compiler_load_in_this_thread(amal_compiler *compiler, FileScopeReference *file_scope) {
Parser *parser;
- int result;
BufferView filepath;
ArenaAllocator *parser_allocator;
+ int result;
+
+ parser = NULL;
+ parser_allocator = NULL;
result = AMAL_COMPILER_ERR;
- cleanup_if_error(amal_mutex_lock(&compiler->mutex, "amal_compiler_load_in_this_thread, create arena allocator"));
- cleanup_if_error(arena_allocator_alloc(&compiler->allocator, sizeof(ArenaAllocator), (void**)&parser_allocator));
- amal_mutex_tryunlock(&compiler->mutex);
- return_if_error(arena_allocator_init(parser_allocator));
+ return_if_error(arena_allocator_alloc(&compiler->allocator, sizeof(ArenaAllocator), (void**)&parser_allocator));
+ cleanup_if_error(arena_allocator_init(parser_allocator));
filepath = create_buffer_view(file_scope->canonical_path.data, file_scope->canonical_path.size);
amal_log_info("Started parsing %.*s", filepath.size, filepath.data);
- return_if_error(arena_allocator_alloc(parser_allocator, sizeof(Parser), (void**)&parser));
- return_if_error(parser_init(parser, compiler, parser_allocator));
+ cleanup_if_error(arena_allocator_alloc(parser_allocator, sizeof(Parser), (void**)&parser));
+ cleanup_if_error(parser_init(parser, compiler, parser_allocator));
file_scope->parser = parser;
- return_if_error(parser_parse_file(parser, filepath));
+ cleanup_if_error(parser_parse_file(parser, filepath));
cleanup_if_error(amal_mutex_lock(&compiler->mutex, "amal_compiler_load_in_this_thread, add parser"));
parser->index = buffer_get_size(&compiler->parsers, Parser*);
cleanup_if_error(buffer_append(&compiler->parsers, &parser, sizeof(parser)));
@@ -204,6 +205,13 @@ static CHECK_RESULT int amal_compiler_load_in_this_thread(amal_compiler *compile
cleanup:
amal_mutex_tryunlock(&compiler->mutex);
+ /*
+ This also free's the parser, since it's allocated inside the allocator.
+ The allocator itself is allocated inside the compiler allocator so that will be free'd
+ when the compiler allocator is free'd
+ */
+ if(result != AMAL_COMPILER_OK)
+ arena_allocator_deinit(parser_allocator);
return result;
}
diff --git a/src/std/arena_allocator.c b/src/std/arena_allocator.c
index 8b0083d..5e49035 100644
--- a/src/std/arena_allocator.c
+++ b/src/std/arena_allocator.c
@@ -102,8 +102,7 @@ int arena_allocator_alloc(ArenaAllocator *self, usize size, void **mem) {
}
int arena_allocator_add_mem(ArenaAllocator *self, usize *result_index) {
- void *null_data;
- null_data = NULL;
+ void *null_data = NULL;
*result_index = self->mems.size;
return buffer_append(&self->mems, &null_data, sizeof(void*));
}
diff --git a/tests/glfw.amal b/tests/glfw.amal
index d0f02d4..e3c2fc6 100644
--- a/tests/glfw.amal
+++ b/tests/glfw.amal
@@ -1,3 +1,5 @@
+#!/usr/bin/env amalgam
+
extern const glfwInit: fn() i32;
extern const glfwTerminate: fn() i32; // should return void....
extern const glfwCreateWindow: fn(x: i32, y: i32, title: str, monitor: usize, share: usize) usize;
diff --git a/tests/main.c b/tests/main.c
index 265a0ea..019f8d9 100644
--- a/tests/main.c
+++ b/tests/main.c
@@ -190,8 +190,6 @@ static void test_load_gl(void) {
FAIL_TEST_CLEANUP(full_path);
}
- printf("glfw init ptr: %p, glfw terminate: %p\n", glfwInit, glfwTerminate);
-
if(amal_program_register_extern_func(&program, create_buffer_view_auto("glfwInit"), glfwInit, 0) != 0) {
fprintf(stderr, "Unexpected error (alloc failure)\n");
FAIL_TEST_CLEANUP(full_path);