cgen: fix generics method with sumtype arguments (#13166)
parent
104e0c5692
commit
879d1d2f11
|
@ -1471,7 +1471,37 @@ fn (mut g Gen) call_args(node ast.CallExpr) {
|
||||||
} else {
|
} else {
|
||||||
node.args
|
node.args
|
||||||
}
|
}
|
||||||
expected_types := node.expected_arg_types
|
mut expected_types := node.expected_arg_types
|
||||||
|
// unwrap generics fn/method arguments to concretes
|
||||||
|
if node.concrete_types.len > 0 && node.concrete_types.all(!it.has_flag(.generic)) {
|
||||||
|
if node.is_method {
|
||||||
|
if func := g.table.find_method(g.table.sym(node.left_type), node.name) {
|
||||||
|
if func.generic_names.len > 0 {
|
||||||
|
for i in 0 .. expected_types.len {
|
||||||
|
mut muttable := unsafe { &ast.Table(g.table) }
|
||||||
|
if utyp := muttable.resolve_generic_to_concrete(node.expected_arg_types[i],
|
||||||
|
func.generic_names, node.concrete_types)
|
||||||
|
{
|
||||||
|
expected_types[i] = utyp
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
if func := g.table.find_fn(node.name) {
|
||||||
|
if func.generic_names.len > 0 {
|
||||||
|
for i in 0 .. expected_types.len {
|
||||||
|
mut muttable := unsafe { &ast.Table(g.table) }
|
||||||
|
if utyp := muttable.resolve_generic_to_concrete(node.expected_arg_types[i],
|
||||||
|
func.generic_names, node.concrete_types)
|
||||||
|
{
|
||||||
|
expected_types[i] = utyp
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
// only v variadic, C variadic args will be appeneded like normal args
|
// only v variadic, C variadic args will be appeneded like normal args
|
||||||
is_variadic := expected_types.len > 0 && expected_types.last().has_flag(.variadic)
|
is_variadic := expected_types.len > 0 && expected_types.last().has_flag(.variadic)
|
||||||
&& node.language == .v
|
&& node.language == .v
|
||||||
|
|
|
@ -0,0 +1,26 @@
|
||||||
|
module main
|
||||||
|
|
||||||
|
fn test_generics_method_with_sumtype_args() {
|
||||||
|
mut me := CatDad{}
|
||||||
|
ret := me.adopt<CatType, Cat>(CatType.black, BlackCat{})
|
||||||
|
println(ret)
|
||||||
|
assert ret == 22
|
||||||
|
}
|
||||||
|
|
||||||
|
[flag]
|
||||||
|
enum CatType {
|
||||||
|
black
|
||||||
|
white
|
||||||
|
}
|
||||||
|
|
||||||
|
type Cat = BlackCat | WhiteCat
|
||||||
|
|
||||||
|
struct BlackCat {}
|
||||||
|
|
||||||
|
struct WhiteCat {}
|
||||||
|
|
||||||
|
struct CatDad {}
|
||||||
|
|
||||||
|
fn (mut foo CatDad) adopt<D, T>(d D, t T) int {
|
||||||
|
return 22
|
||||||
|
}
|
Loading…
Reference in New Issue