aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/compiler.h3
-rw-r--r--src/compiler.c155
2 files changed, 49 insertions, 109 deletions
diff --git a/include/compiler.h b/include/compiler.h
index 4e24f11..69d0254 100644
--- a/include/compiler.h
+++ b/include/compiler.h
@@ -21,8 +21,7 @@ struct amal_compiler {
int usable_thread_count;
bool started;
amal_mutex mutex;
- int resolve_ast_index;
- int generate_ssa_index;
+ int generic_work_object_index;
};
CHECK_RESULT int amal_compiler_init(amal_compiler *self);
diff --git a/src/compiler.c b/src/compiler.c
index f464005..dc703f8 100644
--- a/src/compiler.c
+++ b/src/compiler.c
@@ -38,8 +38,7 @@ int amal_compiler_init(amal_compiler *self) {
am_memset(&self->allocator, 0, sizeof(self->allocator));
am_memset(&self->main_thread_allocator, 0, sizeof(self->main_thread_allocator));
self->started = bool_false;
- self->resolve_ast_index = 0;
- self->generate_ssa_index = 0;
+ self->generic_work_object_index = 0;
amal_mutex_init(&self->mutex);
return_if_error(scoped_allocator_init(&self->allocator));
@@ -77,6 +76,12 @@ int amal_compiler_deinit(amal_compiler *self) {
return result;
}
+typedef enum {
+ THREAD_WORK_PARSE,
+ THREAD_WORK_RESOLVE_AST,
+ THREAD_WORK_GENERATE_SSA
+} ThreadWorkType;
+
typedef struct {
amal_compiler *compiler;
ParserThreadData *parser_thread_data;
@@ -87,19 +92,8 @@ typedef struct {
amal_compiler *compiler;
ParserThreadData *parser_thread_data;
Parser *parser;
-} CompilerAstResolverThreadUserData;
-
-typedef struct {
- amal_compiler *compiler;
- ParserThreadData *parser_thread_data;
- Parser *parser;
-} CompilerSsaGeneratorThreadUserData;
-
-typedef enum {
- THREAD_WORK_PARSE,
- THREAD_WORK_RESOLVE_AST,
- THREAD_WORK_GENERATE_SSA
-} ThreadWorkType;
+ ThreadWorkType work_type;
+} CompilerGenericThreadUserData;
typedef struct {
union {
@@ -156,79 +150,52 @@ static void* thread_callback_parse_file(void *userdata) {
return result;
}
-/* TODO: Handle errors (stop resolving ast in all other threads and report errors/warnings) */
-static void* thread_callback_resolve_ast(void *userdata) {
- CompilerAstResolverThreadUserData compiler_ast_resolver_userdata;
+/* TODO: Handle errors (stop work in all other threads and report errors/warnings) */
+static void* thread_callback_generic(void *userdata) {
+ CompilerGenericThreadUserData compiler_userdata;
Parser *parser;
AstCompilerContext compiler_context;
void *result;
assert(!amal_thread_is_main());
- am_memcpy(&compiler_ast_resolver_userdata, userdata, sizeof(compiler_ast_resolver_userdata));
+ am_memcpy(&compiler_userdata, userdata, sizeof(compiler_userdata));
am_free(userdata);
- parser = compiler_ast_resolver_userdata.parser;
+ parser = compiler_userdata.parser;
compiler_context.parser = parser;
result = (void*)AMAL_COMPILER_ERR;
for(;;) {
int result;
- amal_log_debug("Resolving AST for file: %.*s", parser->tokenizer.code_name.size, parser->tokenizer.code_name.data);
result = setjmp(compiler_context.env);
- if(result == 0)
- scope_resolve(&parser->scope, &compiler_context);
- else {
- /* TODO: stop resolving ast in all other threads */
- break;
- }
- cleanup_if_error(amal_mutex_lock(&compiler_ast_resolver_userdata.compiler->mutex, "thread_callback_resolve_ast"));
- if(compiler_ast_resolver_userdata.compiler->resolve_ast_index + 1 >= (int)buffer_get_size(&compiler_ast_resolver_userdata.compiler->parsers, Parser))
- break;
- ++compiler_ast_resolver_userdata.compiler->resolve_ast_index;
- parser = buffer_get(&compiler_ast_resolver_userdata.compiler->parsers, compiler_ast_resolver_userdata.compiler->resolve_ast_index, sizeof(Parser));
- amal_mutex_tryunlock(&compiler_ast_resolver_userdata.compiler->mutex);
- }
- result = NULL;
-
- cleanup:
- compiler_ast_resolver_userdata.parser_thread_data->status = PARSER_THREAD_STATUS_IDLE;
- amal_mutex_tryunlock(&compiler_ast_resolver_userdata.compiler->mutex);
- return result;
-}
-
-/* TODO: Handle errors (stop generating ssa in all other threads and report errors/warnings) */
-static void* thread_callback_generate_ssa(void *userdata) {
- CompilerSsaGeneratorThreadUserData compiler_ssa_generator_userdata;
- Parser *parser;
- AstCompilerContext compiler_context;
- void *result;
- assert(!amal_thread_is_main());
-
- am_memcpy(&compiler_ssa_generator_userdata, userdata, sizeof(compiler_ssa_generator_userdata));
- am_free(userdata);
- parser = compiler_ssa_generator_userdata.parser;
- compiler_context.parser = parser;
- result = (void*)AMAL_COMPILER_ERR;
- for(;;) {
- int result;
- amal_log_debug("Generating SSA for file: %.*s", parser->tokenizer.code_name.size, parser->tokenizer.code_name.data);
- result = setjmp(compiler_context.env);
- if(result == 0)
- scope_generate_ssa(&parser->scope, &compiler_context);
- else {
- /* TODO: stop generating ssa in all other threads */
+ if(result == 0) {
+ switch(compiler_userdata.work_type) {
+ case THREAD_WORK_PARSE:
+ assert(bool_false && "Thread work type can't ge 'parse' for generic work");
+ break;
+ case THREAD_WORK_RESOLVE_AST:
+ amal_log_debug("Resolving AST for file: %.*s", parser->tokenizer.code_name.size, parser->tokenizer.code_name.data);
+ scope_resolve(&parser->scope, &compiler_context);
+ break;
+ case THREAD_WORK_GENERATE_SSA:
+ amal_log_debug("Generating SSA for file: %.*s", parser->tokenizer.code_name.size, parser->tokenizer.code_name.data);
+ scope_generate_ssa(&parser->scope, &compiler_context);
+ break;
+ }
+ } else {
+ /* TODO: stop work in all other threads */
break;
}
- cleanup_if_error(amal_mutex_lock(&compiler_ssa_generator_userdata.compiler->mutex, "thread_callback_generate_ssa"));
- if(compiler_ssa_generator_userdata.compiler->generate_ssa_index + 1 >= (int)buffer_get_size(&compiler_ssa_generator_userdata.compiler->parsers, Parser))
+ cleanup_if_error(amal_mutex_lock(&compiler_userdata.compiler->mutex, "thread_callback_generic"));
+ if(compiler_userdata.compiler->generic_work_object_index + 1 >= (int)buffer_get_size(&compiler_userdata.compiler->parsers, Parser))
break;
- ++compiler_ssa_generator_userdata.compiler->generate_ssa_index;
- parser = buffer_get(&compiler_ssa_generator_userdata.compiler->parsers, compiler_ssa_generator_userdata.compiler->generate_ssa_index, sizeof(Parser));
- amal_mutex_tryunlock(&compiler_ssa_generator_userdata.compiler->mutex);
+ ++compiler_userdata.compiler->generic_work_object_index;
+ parser = buffer_get(&compiler_userdata.compiler->parsers, compiler_userdata.compiler->generic_work_object_index, sizeof(Parser));
+ amal_mutex_tryunlock(&compiler_userdata.compiler->mutex);
}
result = NULL;
cleanup:
- compiler_ssa_generator_userdata.parser_thread_data->status = PARSER_THREAD_STATUS_IDLE;
- amal_mutex_tryunlock(&compiler_ssa_generator_userdata.compiler->mutex);
+ compiler_userdata.parser_thread_data->status = PARSER_THREAD_STATUS_IDLE;
+ amal_mutex_tryunlock(&compiler_userdata.compiler->mutex);
return result;
}
@@ -258,26 +225,17 @@ static CHECK_RESULT int amal_compiler_select_thread_for_work(amal_compiler *self
result = parser_thread_data_start(parser_thread_data, thread_callback_parse_file, userdata);
break;
}
- case THREAD_WORK_RESOLVE_AST: {
- CompilerAstResolverThreadUserData *userdata;
- cleanup_if_error(am_malloc(sizeof(CompilerAstResolverThreadUserData), (void**)&userdata));
- thread_user_data = userdata;
- userdata->compiler = self;
- userdata->parser_thread_data = parser_thread_data;
- userdata->parser = work_data.value.parser;
- ++self->resolve_ast_index;
- result = parser_thread_data_start(parser_thread_data, thread_callback_resolve_ast, userdata);
- break;
- }
+ case THREAD_WORK_RESOLVE_AST:
case THREAD_WORK_GENERATE_SSA: {
- CompilerSsaGeneratorThreadUserData *userdata;
- cleanup_if_error(am_malloc(sizeof(CompilerSsaGeneratorThreadUserData), (void**)&userdata));
+ CompilerGenericThreadUserData *userdata;
+ cleanup_if_error(am_malloc(sizeof(CompilerGenericThreadUserData), (void**)&userdata));
thread_user_data = userdata;
userdata->compiler = self;
userdata->parser_thread_data = parser_thread_data;
userdata->parser = work_data.value.parser;
- ++self->generate_ssa_index;
- result = parser_thread_data_start(parser_thread_data, thread_callback_generate_ssa, userdata);
+ userdata->work_type = work_data.type;
+ ++self->generic_work_object_index;
+ result = parser_thread_data_start(parser_thread_data, thread_callback_generic, userdata);
break;
}
}
@@ -358,33 +316,16 @@ static CHECK_RESULT int amal_compiler_load_file_join_threads(amal_compiler *self
return result;
}
-static CHECK_RESULT int amal_compiler_resolve_ast(amal_compiler *self) {
- Parser *parser;
- Parser *parser_end;
- parser = buffer_start(&self->parsers);
- parser_end = buffer_end(&self->parsers);
- for(; parser != parser_end; ++parser) {
- ParserThreadData *thread_selected;
- ThreadWorkData thread_work_data;
- thread_work_data.type = THREAD_WORK_RESOLVE_AST;
- thread_work_data.value.parser = parser;
- return_if_error(amal_compiler_select_thread_for_work(self, thread_work_data, &thread_selected));
- /* After all threads have been used, they will handle using the remaining parsers or stop if there is an error */
- if(!thread_selected)
- break;
- }
- return amal_compiler_load_file_join_threads(self);
-}
-
-static CHECK_RESULT int amal_compiler_generate_ssa(amal_compiler *self) {
+static CHECK_RESULT int amal_compiler_dispatch_generic(amal_compiler *self, ThreadWorkType work_type) {
Parser *parser;
Parser *parser_end;
parser = buffer_start(&self->parsers);
parser_end = buffer_end(&self->parsers);
+ self->generic_work_object_index = 0;
for(; parser != parser_end; ++parser) {
ParserThreadData *thread_selected;
ThreadWorkData thread_work_data;
- thread_work_data.type = THREAD_WORK_GENERATE_SSA;
+ thread_work_data.type = work_type;
thread_work_data.value.parser = parser;
return_if_error(amal_compiler_select_thread_for_work(self, thread_work_data, &thread_selected));
/* After all threads have been used, they will handle using the remaining parsers or stop if there is an error */
@@ -414,9 +355,9 @@ int amal_compiler_load_file(amal_compiler *self, BufferView filepath) {
/*return_if_error(amal_compiler_load_first_this_thread(self, filepath, &self->main_thread_allocator));*/
return_if_error(amal_compiler_load_file_join_threads(self));
amal_log_debug("Finished parsing all files, resolving AST");
- return_if_error(amal_compiler_resolve_ast(self));
+ return_if_error(amal_compiler_dispatch_generic(self, THREAD_WORK_RESOLVE_AST));
amal_log_debug("Finished resolving AST, generating SSA");
- return_if_error(amal_compiler_generate_ssa(self));
+ return_if_error(amal_compiler_dispatch_generic(self, THREAD_WORK_GENERATE_SSA));
return AMAL_COMPILER_OK;
}