diff options
| author | gingerBill <bill@gingerbill.org> | 2023-06-26 16:48:43 +0100 |
|---|---|---|
| committer | gingerBill <bill@gingerbill.org> | 2023-06-26 16:48:43 +0100 |
| commit | 8182ba4ee05473d13c6619500457da9a1e0845ca (patch) | |
| tree | 6aeff0288ae0e1ccc746078ab15fd3c0b62b0a6f /src/check_expr.cpp | |
| parent | 3d9328fd79f45c85f1ecc513b2c05071f9c1d1a3 (diff) | |
Improve internal names for parapoly records
Diffstat (limited to 'src/check_expr.cpp')
| -rw-r--r-- | src/check_expr.cpp | 49 |
1 files changed, 46 insertions, 3 deletions
diff --git a/src/check_expr.cpp b/src/check_expr.cpp index e0e78b441..b12c6d114 100644 --- a/src/check_expr.cpp +++ b/src/check_expr.cpp @@ -6828,15 +6828,15 @@ gb_internal CallArgumentError check_polymorphic_record_type(CheckerContext *c, O return err; } - String generated_name = make_string_c(expr_to_string(call)); - CheckerContext ctx = *c; // NOTE(bill): We need to make sure the lookup scope for the record is the same as where it was created ctx.scope = polymorphic_record_parent_scope(original_type); GB_ASSERT(ctx.scope != nullptr); - Type *named_type = alloc_type_named(generated_name, nullptr, nullptr); Type *bt = base_type(original_type); + String generated_name = make_string_c(expr_to_string(call)); + + Type *named_type = alloc_type_named(generated_name, nullptr, nullptr); if (bt->kind == Type_Struct) { Ast *node = clone_ast(bt->Struct.node); Type *struct_type = alloc_type_struct(); @@ -6861,6 +6861,49 @@ gb_internal CallArgumentError check_polymorphic_record_type(CheckerContext *c, O GB_PANIC("Unsupported parametric polymorphic record type"); } + + bt = base_type(named_type); + if (bt->kind == Type_Struct || bt->kind == Type_Union) { + GB_ASSERT(original_type->kind == Type_Named); + Entity *e = original_type->Named.type_name; + GB_ASSERT(e->kind == Entity_TypeName); + + gbString s = gb_string_make_reserve(heap_allocator(), e->token.string.len+3); + s = gb_string_append_fmt(s, "%.*s(", LIT(e->token.string)); + + Type *params = nullptr; + switch (bt->kind) { + case Type_Struct: params = bt->Struct.polymorphic_params; break; + case Type_Union: params = bt->Union.polymorphic_params; break; + } + + if (params != nullptr) for_array(i, params->Tuple.variables) { + Entity *v = params->Tuple.variables[i]; + String name = v->token.string; + if (i > 0) { + s = gb_string_append_fmt(s, ", "); + } + s = gb_string_append_fmt(s, "$%.*s", LIT(name)); + + if (v->kind == Entity_TypeName) { + if (v->type->kind != Type_Generic) { + s = gb_string_append_fmt(s, "="); + s = write_type_to_string(s, v->type, false); + } + } else if (v->kind == Entity_Constant) { + s = gb_string_append_fmt(s, "="); + s = write_exact_value_to_string(s, v->Constant.value); + } + } + s = gb_string_append_fmt(s, ")"); + + String new_name = make_string_c(s); + named_type->Named.name = new_name; + if (named_type->Named.type_name) { + named_type->Named.type_name->token.string = new_name; + } + } + operand->mode = Addressing_Type; operand->type = named_type; } |