From 4018a784b316621c1510d71e9c5243793aab5106 Mon Sep 17 00:00:00 2001 From: Hitalo Souza <63821277+enghitalo@users.noreply.github.com> Date: Wed, 13 Dec 2023 16:24:16 -0400 Subject: [PATCH] checker: cast sumtype to its variant generic type (#20166) --- vlib/v/checker/checker.v | 5 +++-- .../tests/cast_sumtype_as_generic_err.out | 13 +++++++++++++ .../tests/cast_sumtype_as_generic_err.vv | 16 ++++++++++++++++ vlib/v/tests/cast_sumtype_as_generic_test.v | 17 +++++++++++++++++ 4 files changed, 49 insertions(+), 2 deletions(-) create mode 100644 vlib/v/checker/tests/cast_sumtype_as_generic_err.out create mode 100644 vlib/v/checker/tests/cast_sumtype_as_generic_err.vv create mode 100644 vlib/v/tests/cast_sumtype_as_generic_test.v diff --git a/vlib/v/checker/checker.v b/vlib/v/checker/checker.v index a488b69d0..1cce6dd20 100644 --- a/vlib/v/checker/checker.v +++ b/vlib/v/checker/checker.v @@ -2628,10 +2628,11 @@ pub fn (mut c Checker) expr(mut node ast.Expr) ast.Type { ast.AsCast { node.expr_type = c.expr(mut node.expr) expr_type_sym := c.table.sym(node.expr_type) - type_sym := c.table.sym(node.typ) + type_sym := c.table.sym(c.unwrap_generic(node.typ)) if expr_type_sym.kind == .sum_type { c.ensure_type_exists(node.typ, node.pos) - if !c.table.sumtype_has_variant(node.expr_type, node.typ, true) { + if !c.table.sumtype_has_variant(c.unwrap_generic(node.expr_type), c.unwrap_generic(node.typ), + true) { addr := '&'.repeat(node.typ.nr_muls()) c.error('cannot cast `${expr_type_sym.name}` to `${addr}${type_sym.name}`', node.pos) diff --git a/vlib/v/checker/tests/cast_sumtype_as_generic_err.out b/vlib/v/checker/tests/cast_sumtype_as_generic_err.out new file mode 100644 index 000000000..3cb132890 --- /dev/null +++ b/vlib/v/checker/tests/cast_sumtype_as_generic_err.out @@ -0,0 +1,13 @@ +vlib/v/checker/tests/cast_sumtype_as_generic_err.vv:15:10: error: cannot cast `bool` to `SumType` + 13 | fn main() { + 14 | println(SumType('la').cast_to[string]()) + 15 | println(SumType(true).cast_to[bool]()) + | ~~~~~~~~~~~~~ + 16 | } +vlib/v/checker/tests/cast_sumtype_as_generic_err.vv:10:11: error: cannot cast `SumType` to `bool` + 8 | + 9 | fn (a SumType) cast_to[T]() T { + 10 | return a as T + | ~~ + 11 | } + 12 | \ No newline at end of file diff --git a/vlib/v/checker/tests/cast_sumtype_as_generic_err.vv b/vlib/v/checker/tests/cast_sumtype_as_generic_err.vv new file mode 100644 index 000000000..986d7e5bd --- /dev/null +++ b/vlib/v/checker/tests/cast_sumtype_as_generic_err.vv @@ -0,0 +1,16 @@ +module main + +struct Chacabum { + a int +} + +type SumType = Chacabum | int | string + +fn (a SumType) cast_to[T]() T { + return a as T +} + +fn main() { + println(SumType('la').cast_to[string]()) + println(SumType(true).cast_to[bool]()) +} diff --git a/vlib/v/tests/cast_sumtype_as_generic_test.v b/vlib/v/tests/cast_sumtype_as_generic_test.v new file mode 100644 index 000000000..77a8beaef --- /dev/null +++ b/vlib/v/tests/cast_sumtype_as_generic_test.v @@ -0,0 +1,17 @@ +module main + +struct Chacabum { + a int +} + +type SumType = Chacabum | int | string + +fn (a SumType) cast_to[T]() T { + return a as T +} + +fn test_cast_to_generics() { + assert SumType(1).cast_to[int]() == 1 + assert SumType('la').cast_to[string]() == 'la' + assert SumType(Chacabum{}).cast_to[Chacabum]() == Chacabum{} +} -- 2.39.5