aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorgingerBill <gingerBill@users.noreply.github.com>2025-09-12 17:17:22 +0100
committergingerBill <gingerBill@users.noreply.github.com>2025-09-12 17:17:22 +0100
commita2d9c795086e17c6778a667423ddd4ce00451f7d (patch)
treeb253128c9188ee83bdfc4c362266dbd313f4926f
parent96e42b25c190f5cc963f427486cc69460b20ddd1 (diff)
Spawn function passes as procedures are generated for the module
-rw-r--r--src/entity.cpp5
-rw-r--r--src/llvm_backend.cpp22
-rw-r--r--src/llvm_backend.hpp1
-rw-r--r--src/llvm_backend_const.cpp17
-rw-r--r--src/llvm_backend_general.cpp9
-rw-r--r--src/llvm_backend_opt.cpp6
-rw-r--r--src/llvm_backend_type.cpp10
7 files changed, 60 insertions, 10 deletions
diff --git a/src/entity.cpp b/src/entity.cpp
index e07e882f3..0c64ebe42 100644
--- a/src/entity.cpp
+++ b/src/entity.cpp
@@ -166,6 +166,8 @@ struct Entity {
std::atomic<EntityState> state;
std::atomic<i32> min_dep_count;
Token token;
+ u32 name_hash;
+
Scope * scope;
Type * type;
std::atomic<Ast *> identifier; // Can be nullptr
@@ -345,6 +347,9 @@ gb_internal Entity *alloc_entity(EntityKind kind, Scope *scope, Token token, Typ
entity->state = EntityState_Unresolved;
entity->scope = scope;
entity->token = token;
+ if (token.string.len > 0) {
+ entity->name_hash = string_hash(token.string);
+ }
entity->type = type;
entity->id = 1 + global_entity_id.fetch_add(1);
if (token.pos.file_id) {
diff --git a/src/llvm_backend.cpp b/src/llvm_backend.cpp
index d9e62dede..7e9d5bd73 100644
--- a/src/llvm_backend.cpp
+++ b/src/llvm_backend.cpp
@@ -2063,7 +2063,11 @@ gb_internal lbProcedure *lb_create_startup_runtime(lbModule *main_module, lbProc
wd->global_variables = global_variables;
// TODO(bill): determine whether or not this is better multithreaded or not
- lb_create_startup_runtime_worker_proc(wd);
+ if (main_module->gen->do_threading) {
+ thread_pool_add_task(lb_create_startup_runtime_worker_proc, wd);
+ } else {
+ lb_create_startup_runtime_worker_proc(wd);
+ }
return p;
}
@@ -2267,7 +2271,9 @@ gb_internal void lb_llvm_function_pass_per_function_internal(lbModule *module, l
gb_internal WORKER_TASK_PROC(lb_llvm_function_pass_per_module) {
lbModule *m = cast(lbModule *)data;
- {
+
+
+ if (m->function_pass_managers[0] == nullptr) {
GB_ASSERT(m->function_pass_managers[lbFunctionPassManager_default] == nullptr);
for (i32 i = 0; i < lbFunctionPassManager_COUNT; i++) {
@@ -2445,6 +2451,10 @@ gb_internal WORKER_TASK_PROC(lb_generate_procedures_in_a_module_worker_proc) {
lb_module_timing_end(&module_timing);
+ if (m->gen->do_threading && !build_context.ODIN_DEBUG) {
+ thread_pool_add_task(lb_llvm_function_pass_per_module, m);
+ }
+
return 0;
}
@@ -2478,6 +2488,10 @@ gb_internal WORKER_TASK_PROC(lb_generate_missing_procedures_to_check_worker_proc
lb_module_timing_end(&module_timing);
+ if (m->gen->do_threading && !build_context.ODIN_DEBUG) {
+ thread_pool_add_task(lb_llvm_function_pass_per_module, m);
+ }
+
return 0;
}
@@ -3506,7 +3520,9 @@ gb_internal bool lb_generate_code(lbGenerator *gen) {
}
TIME_SECTION("LLVM Function Pass");
- lb_llvm_function_passes(gen, gen->do_threading && !build_context.ODIN_DEBUG);
+ if (!(gen->do_threading && !build_context.ODIN_DEBUG)) {
+ lb_llvm_function_passes(gen, gen->do_threading && !build_context.ODIN_DEBUG);
+ }
TIME_SECTION("LLVM Module Pass and Verification");
lb_llvm_module_passes_and_verification(gen, gen->do_threading);
diff --git a/src/llvm_backend.hpp b/src/llvm_backend.hpp
index 6c260bc7b..4c2adfec4 100644
--- a/src/llvm_backend.hpp
+++ b/src/llvm_backend.hpp
@@ -368,6 +368,7 @@ struct lbProcedure {
bool is_export;
bool is_entry_point;
bool is_startup;
+ bool has_had_passes;
lbFunctionType *abi_function_type;
diff --git a/src/llvm_backend_const.cpp b/src/llvm_backend_const.cpp
index e64be49f2..e9fa50318 100644
--- a/src/llvm_backend_const.cpp
+++ b/src/llvm_backend_const.cpp
@@ -244,7 +244,24 @@ gb_internal lbValue lb_const_undef(lbModule *m, Type *type) {
return lbValue{v, type};
}
+gb_internal lbValue lb_const_string_with_hash(lbModule *m, String const &value, u32 hash) {
+ isize len = value.len;
+ LLVMValueRef ptr = nullptr;
+ if (len == 0) {
+ ptr = LLVMConstNull(lb_type(m, t_u8_ptr));
+ } else {
+ ptr = lb_find_or_add_entity_string_ptr(m, value, false, hash);
+ }
+
+ LLVMValueRef str_len = LLVMConstInt(lb_type(m, t_int), len, true);
+
+ lbValue res = {};
+ res.type = t_string;
+ res.value = llvm_const_string_internal(m, t_string, ptr, str_len);
+
+ return res;
+}
gb_internal lbValue lb_const_int(lbModule *m, Type *type, u64 value) {
lbValue res = {};
diff --git a/src/llvm_backend_general.cpp b/src/llvm_backend_general.cpp
index 3f7be703d..76d8d2d5e 100644
--- a/src/llvm_backend_general.cpp
+++ b/src/llvm_backend_general.cpp
@@ -2710,12 +2710,17 @@ general_end:;
-gb_internal LLVMValueRef lb_find_or_add_entity_string_ptr(lbModule *m, String const &str, bool custom_link_section) {
+gb_internal LLVMValueRef lb_find_or_add_entity_string_ptr(lbModule *m, String const &str, bool custom_link_section, u32 hash=0) {
StringHashKey key = {};
LLVMValueRef *found = nullptr;
if (!custom_link_section) {
- key = string_hash_string(str);
+ if (hash) {
+ key.hash = hash;
+ key.string = str;
+ } else {
+ key = string_hash_string(str);
+ }
found = string_map_get(&m->const_strings, key);
}
if (found != nullptr) {
diff --git a/src/llvm_backend_opt.cpp b/src/llvm_backend_opt.cpp
index 8d5cfcb70..400acb820 100644
--- a/src/llvm_backend_opt.cpp
+++ b/src/llvm_backend_opt.cpp
@@ -479,6 +479,10 @@ gb_internal void lb_run_function_pass_manager(LLVMPassManagerRef fpm, lbProcedur
if (p == nullptr) {
return;
}
+ if (p->has_had_passes) {
+ return;
+ }
+
// NOTE(bill): LLVMAddDCEPass doesn't seem to be exported in the official DLL's for LLVM
// which means we cannot rely upon it
// This is also useful for read the .ll for debug purposes because a lot of instructions
@@ -499,6 +503,8 @@ gb_internal void lb_run_function_pass_manager(LLVMPassManagerRef fpm, lbProcedur
}
LLVMRunFunctionPassManager(fpm, p->value);
+
+ p->has_had_passes = true;
}
gb_internal void llvm_delete_function(LLVMValueRef func) {
diff --git a/src/llvm_backend_type.cpp b/src/llvm_backend_type.cpp
index d1e7c0559..4b3bc522b 100644
--- a/src/llvm_backend_type.cpp
+++ b/src/llvm_backend_type.cpp
@@ -403,7 +403,7 @@ gb_internal void lb_setup_type_info_data_giant_array(lbModule *m, i64 global_typ
lbValue loc = lb_const_source_code_location_as_global_ptr(m, proc_name, pos);
LLVMValueRef vals[4] = {
- lb_const_string(m, t->Named.type_name->token.string).value,
+ lb_const_string_with_hash(m, t->Named.type_name->token.string, t->Named.type_name->name_hash).value,
get_type_info_ptr(m, t->Named.base),
pkg_name,
loc.value
@@ -705,7 +705,7 @@ gb_internal void lb_setup_type_info_data_giant_array(lbModule *m, i64 global_typ
lb_global_type_info_member_types_values[type_offset+i] = get_type_info_ptr(m, f->type);
if (f->token.string.len > 0) {
- lb_global_type_info_member_names_values[name_offset+i] = lb_const_string(m, f->token.string).value;
+ lb_global_type_info_member_names_values[name_offset+i] = lb_const_string_with_hash(m, f->token.string, f->name_hash).value;
}
}
@@ -747,7 +747,7 @@ gb_internal void lb_setup_type_info_data_giant_array(lbModule *m, i64 global_typ
GB_ASSERT(is_type_integer(t->Enum.base_type));
for_array(i, fields) {
- name_values[i] = lb_const_string(m, fields[i]->token.string).value;
+ name_values [i] = lb_const_string_with_hash(m, fields[i]->token.string, fields[i]->name_hash).value;
value_values[i] = lb_const_value(m, t_i64, fields[i]->Constant.value).value;
}
@@ -884,7 +884,7 @@ gb_internal void lb_setup_type_info_data_giant_array(lbModule *m, i64 global_typ
lb_global_type_info_member_usings_values[usings_offset+source_index] = lb_const_bool(m, t_bool, (f->flags&EntityFlag_Using) != 0).value;
if (f->token.string.len > 0) {
- lb_global_type_info_member_names_values[names_offset+source_index] = lb_const_string(m, f->token.string).value;
+ lb_global_type_info_member_names_values[names_offset+source_index] = lb_const_string_with_hash(m, f->token.string, f->name_hash).value;
}
if (t->Struct.tags != nullptr) {
@@ -1007,7 +1007,7 @@ gb_internal void lb_setup_type_info_data_giant_array(lbModule *m, i64 global_typ
lbValue index = lb_const_int(m, t_int, source_index);
if (f->token.string.len > 0) {
- lb_global_type_info_member_names_values[names_offset+source_index] = lb_const_string(m, f->token.string).value;
+ lb_global_type_info_member_names_values[names_offset+source_index] = lb_const_string_with_hash(m, f->token.string, f->name_hash).value;
}
lb_global_type_info_member_types_values[types_offset+source_index] = get_type_info_ptr(m, f->type);