From b3b6ce5b97c74cd174040ec635fb2d3f9a2a77b6 Mon Sep 17 00:00:00 2001 From: Swastik Baranwal Date: Sun, 21 Jul 2024 16:11:01 +0530 Subject: [PATCH] checker: improve checks for embed in anon struct (#21877) --- vlib/v/checker/checker.v | 16 ++++++++++++++++ ...type_alias_decl_anon_struct_invalid_embed.out | 12 ++++++++++++ .../type_alias_decl_anon_struct_invalid_embed.vv | 4 ++++ .../tests/struct_anon_invalid_embed_err.out | 6 ++++++ .../tests/struct_anon_invalid_embed_err.vv | 4 ++++ 5 files changed, 42 insertions(+) create mode 100644 vlib/v/checker/tests/type_alias_decl_anon_struct_invalid_embed.out create mode 100644 vlib/v/checker/tests/type_alias_decl_anon_struct_invalid_embed.vv create mode 100644 vlib/v/parser/tests/struct_anon_invalid_embed_err.out create mode 100644 vlib/v/parser/tests/struct_anon_invalid_embed_err.vv diff --git a/vlib/v/checker/checker.v b/vlib/v/checker/checker.v index a2cb58297..a011bac38 100644 --- a/vlib/v/checker/checker.v +++ b/vlib/v/checker/checker.v @@ -561,6 +561,22 @@ fn (mut c Checker) alias_type_decl(node ast.AliasTypeDecl) { c.error('unknown type `${ct_sym.name}`', node.type_pos) } } + // check if embed types are struct + for embed_type in parent_typ_sym.info.embeds { + final_embed_sym := c.table.final_sym(embed_type) + if final_embed_sym.kind != .struct_ { + c.error('cannot embed non-struct `${c.table.sym(embed_type).name}`', + node.type_pos) + } + } + if parent_typ_sym.info.is_anon { + for field in parent_typ_sym.info.fields { + if c.table.final_sym(field.typ).kind != .struct_ { + c.error('cannot embed non-struct `${c.table.sym(field.typ).name}`', + field.type_pos) + } + } + } } } .array { diff --git a/vlib/v/checker/tests/type_alias_decl_anon_struct_invalid_embed.out b/vlib/v/checker/tests/type_alias_decl_anon_struct_invalid_embed.out new file mode 100644 index 000000000..663c448f3 --- /dev/null +++ b/vlib/v/checker/tests/type_alias_decl_anon_struct_invalid_embed.out @@ -0,0 +1,12 @@ +vlib/v/checker/tests/type_alias_decl_anon_struct_invalid_embed.vv:2:16: error: cannot embed non-struct `Int` + 1 | type Int = int + 2 | type MyIndex = struct { + | ~~~~~~~~ + 3 | Int + 4 | } +vlib/v/checker/tests/type_alias_decl_anon_struct_invalid_embed.vv:3:2: error: cannot embed non-struct `Int` + 1 | type Int = int + 2 | type MyIndex = struct { + 3 | Int + | ~~~ + 4 | } diff --git a/vlib/v/checker/tests/type_alias_decl_anon_struct_invalid_embed.vv b/vlib/v/checker/tests/type_alias_decl_anon_struct_invalid_embed.vv new file mode 100644 index 000000000..885a2c3c1 --- /dev/null +++ b/vlib/v/checker/tests/type_alias_decl_anon_struct_invalid_embed.vv @@ -0,0 +1,4 @@ +type Int = int +type MyIndex = struct { + Int +} diff --git a/vlib/v/parser/tests/struct_anon_invalid_embed_err.out b/vlib/v/parser/tests/struct_anon_invalid_embed_err.out new file mode 100644 index 000000000..8e59b9a3d --- /dev/null +++ b/vlib/v/parser/tests/struct_anon_invalid_embed_err.out @@ -0,0 +1,6 @@ +vlib/v/parser/tests/struct_anon_invalid_embed_err.vv:3:6: error: cannot embed non-struct `Int` + 1 | type Int = int + 2 | type MyIndex = struct { + 3 | Int Int + | ~~~ + 4 | } diff --git a/vlib/v/parser/tests/struct_anon_invalid_embed_err.vv b/vlib/v/parser/tests/struct_anon_invalid_embed_err.vv new file mode 100644 index 000000000..a8ceda30e --- /dev/null +++ b/vlib/v/parser/tests/struct_anon_invalid_embed_err.vv @@ -0,0 +1,4 @@ +type Int = int +type MyIndex = struct { + Int Int +} -- 2.39.5