Skip to content

Commit

Permalink
cgen: fix generic sumtype with repeated concrete type (#21948)
Browse files Browse the repository at this point in the history
  • Loading branch information
felipensp authored Jul 29, 2024
1 parent 58827fa commit 104eb25
Show file tree
Hide file tree
Showing 3 changed files with 32 additions and 0 deletions.
5 changes: 5 additions & 0 deletions vlib/v/gen/c/auto_str_methods.v
Original file line number Diff line number Diff line change
Expand Up @@ -442,7 +442,12 @@ fn (mut g Gen) gen_str_for_union_sum_type(info ast.SumType, styp string, typ_str
clean_sum_type_v_type_name = util.strip_main_name(typ_str)
}
fn_builder.writeln('\tswitch(x._typ) {')
mut idxs := []int{}
for typ in info.variants {
if typ in idxs {
continue
}
idxs << typ
typ_name := g.typ(typ)
mut func_name := g.get_str_fn(typ)
sym := g.table.sym(typ)
Expand Down
20 changes: 20 additions & 0 deletions vlib/v/gen/c/cgen.v
Original file line number Diff line number Diff line change
Expand Up @@ -1000,9 +1000,14 @@ pub fn (mut g Gen) write_typeof_functions() {
tidx := g.table.find_type_idx(sym.name)
g.writeln('\tswitch(sidx) {')
g.writeln('\t\tcase ${tidx}: return "${util.strip_main_name(sym.name)}";')
mut idxs := []int{}
for v in sum_info.variants {
if v in idxs {
continue
}
subtype := g.table.sym(v)
g.writeln('\t\tcase ${int(v)}: return "${util.strip_main_name(subtype.name)}";')
idxs << v
}
g.writeln('\t\tdefault: return "unknown ${util.strip_main_name(sym.name)}";')
g.writeln('\t}')
Expand All @@ -1021,8 +1026,13 @@ pub fn (mut g Gen) write_typeof_functions() {
tidx := g.table.find_type_idx(sym.name)
g.writeln('\tswitch(sidx) {')
g.writeln('\t\tcase ${tidx}: return ${int(ityp)};')
mut idxs := []int{}
for v in sum_info.variants {
if v in idxs {
continue
}
g.writeln('\t\tcase ${int(v)}: return ${int(v)};')
idxs << v
}
g.writeln('\t\tdefault: return ${int(ityp)};')
g.writeln('\t}')
Expand Down Expand Up @@ -6678,12 +6688,22 @@ fn (mut g Gen) write_types(symbols []&ast.TypeSymbol) {
g.typedefs.writeln('typedef struct ${name} ${name};')
g.type_definitions.writeln('')
g.type_definitions.writeln('// Union sum type ${name} = ')
mut idxs := []int{}
for variant in sym.info.variants {
if variant in idxs {
continue
}
g.type_definitions.writeln('// | ${variant:4d} = ${g.typ(variant.idx()):-20s}')
idxs << variant
}
idxs.clear()
g.type_definitions.writeln('struct ${name} {')
g.type_definitions.writeln('\tunion {')
for variant in sym.info.variants {
if variant in idxs {
continue
}
idxs << variant
variant_sym := g.table.sym(variant)
mut var := if variant.has_flag(.option) { variant } else { variant.ref() }
variant_name := g.get_sumtype_variant_name(variant, variant_sym)
Expand Down
7 changes: 7 additions & 0 deletions vlib/v/tests/generic_sumtype_repeated_test.v
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
type Name[T] = T | int | string

fn test_main() {
a := Name[int](123)
assert dump(a) == Name[int](123)
println(a)
}

0 comments on commit 104eb25

Please sign in to comment.