Fix generic struct monomorphization and C output for imports

- Fix nested Lcx_GenerateStructInstance overwriting parent slot by
  incrementing structCount BEFORE field processing
- Fix Lcx_LowerModule to skip generic structs from hm.structs (was missing
  continue due to bootstrap compiler codegen limitation)
- Fix C backend to forward-declare ALL structs at top, removing second
  generic-only forward declaration section that came too late
- Add empty-name guard in CBE_EmitStructDef
- Import system: parser supports ::* glob imports, sema two-pass resolution
This commit is contained in:
2026-06-09 23:33:44 +03:00
parent b36df0f5b7
commit 40bcbeb710
4 changed files with 154 additions and 165 deletions
+5 -20
View File
@@ -747,6 +747,7 @@ func CBE_StructHasValueStructField(st: *HirStruct) -> bool {
}
func CBE_EmitStructDef(cbe: *CEmitter, st: *HirStruct) {
if String_Eq(st.name, "") { return; }
StringBuilder_Append(&cbe.sb, "struct ");
StringBuilder_Append(&cbe.sb, st.name);
StringBuilder_Append(&cbe.sb, " {\n");
@@ -848,10 +849,10 @@ func CBackend_Generate(mod: *HirModule) -> String {
StringBuilder_Append(&cbe.sb, "void* bux_alloc(unsigned int size);\n");
StringBuilder_Append(&cbe.sb, "void bux_free(void* ptr);\n\n");
// Forward declare all struct types (skip generics)
// Forward declare all struct types (skip empty names)
var si: int = 0;
while si < mod.structCount {
if !CBE_StructHasGeneric(&mod.structs[si]) {
if !String_Eq(mod.structs[si].name, "") {
StringBuilder_Append(&cbe.sb, "typedef struct ");
StringBuilder_Append(&cbe.sb, mod.structs[si].name);
StringBuilder_Append(&cbe.sb, " ");
@@ -972,7 +973,7 @@ func CBackend_Generate(mod: *HirModule) -> String {
// Pass 1: emit structs with no value-typed struct fields (leaf structs)
si = 0;
while si < mod.structCount {
if CBE_StructHasGeneric(&mod.structs[si]) {
if String_Eq(mod.structs[si].name, "") || CBE_StructHasGeneric(&mod.structs[si]) {
si = si + 1;
continue;
}
@@ -986,7 +987,7 @@ func CBackend_Generate(mod: *HirModule) -> String {
// Pass 2: emit structs that contain value-typed struct fields
si = 0;
while si < mod.structCount {
if CBE_StructHasGeneric(&mod.structs[si]) {
if String_Eq(mod.structs[si].name, "") || CBE_StructHasGeneric(&mod.structs[si]) {
si = si + 1;
continue;
}
@@ -998,22 +999,6 @@ func CBackend_Generate(mod: *HirModule) -> String {
si = si + 1;
}
// Opaque forward declarations for generic structs (used only by pointer)
si = 0;
while si < mod.structCount {
if CBE_StructHasGeneric(&mod.structs[si]) {
StringBuilder_Append(&cbe.sb, "typedef struct ");
StringBuilder_Append(&cbe.sb, mod.structs[si].name);
StringBuilder_Append(&cbe.sb, " ");
StringBuilder_Append(&cbe.sb, mod.structs[si].name);
StringBuilder_Append(&cbe.sb, ";\n");
}
si = si + 1;
}
if mod.structCount > 0 {
StringBuilder_Append(&cbe.sb, "\n");
}
// Forward declarations for all functions (skip generics)
var i: int = 0;
while i < mod.funcCount {