checker: add error for struct not init (fix #24893) (#25134)

This commit is contained in:
Krchi 2025-08-19 19:34:50 +08:00 committed by GitHub
parent c68e37e3e5
commit b85782b7e7
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
7 changed files with 82 additions and 28 deletions

View file

@ -4377,8 +4377,10 @@ fn (mut c Checker) ident(mut node ast.Ident) ast.Type {
}
}
}
c.error(util.new_suggestion(node.name, const_names_in_mod).say('undefined ident: `${node.name}`'),
node.pos)
c.check_known_struct_name(node) or {
c.error(util.new_suggestion(node.name, const_names_in_mod).say('undefined ident: `${node.name}`'),
node.pos)
}
} else {
// If a variable is not found in the scope of an anonymous function
// but is in an external scope, then we can suggest the user add it to the capturing list.
@ -4398,13 +4400,32 @@ fn (mut c Checker) ident(mut node ast.Ident) ast.Type {
}
}
c.error('undefined ident: `${node.name}`', node.pos)
c.check_known_struct_name(node) or {
c.error('undefined ident: `${node.name}`', node.pos)
}
}
}
}
return ast.void_type
}
fn (mut c Checker) check_known_struct_name(ident ast.Ident) ? {
mut is_struct := false
if ident.mod == 'builtin' || ident.mod == 'main' {
is_struct = c.table.find_type(ident.name) != 0
if !is_struct {
is_struct = c.table.find_type('main.${ident.name}') != 0
}
} else {
is_struct = c.table.find_type('${ident.mod}.${ident.name}') != 0
}
if is_struct {
c.error('`${ident.name}` must be initialized', ident.pos)
return
}
return none
}
fn (mut c Checker) concat_expr(mut node ast.ConcatExpr) ast.Type {
mut mr_types := []ast.Type{}
for mut expr in node.vals {

View file

@ -1,5 +1,5 @@
vlib/v/checker/tests/globals/assign_no_value.vv:2:9: error: undefined ident: `int`
vlib/v/checker/tests/globals/assign_no_value.vv:2:9: error: undefined ident: `int_i`
1 | __global (
2 | test = int
| ~~~
2 | test = int_i
| ~~~~~
3 | )

View file

@ -1,3 +1,3 @@
__global (
test = int
test = int_i
)

View file

@ -1,21 +1,20 @@
vlib/v/checker/tests/match_undefined_cond.vv:4:15: error: undefined ident: `Asd`
2 |
3 | fn main() {
4 | res := match Asd {
vlib/v/checker/tests/match_undefined_cond.vv:2:15: error: undefined ident: `asd`
1 | fn main() {
2 | res := match asd {
| ~~~
5 | 1 { 'foo' }
6 | 2 { 'test' }
vlib/v/checker/tests/match_undefined_cond.vv:5:3: error: cannot match `void` with `int literal`
3 | fn main() {
4 | res := match Asd {
5 | 1 { 'foo' }
3 | 1 { 'foo' }
4 | 2 { 'test' }
vlib/v/checker/tests/match_undefined_cond.vv:3:3: error: cannot match `void` with `int literal`
1 | fn main() {
2 | res := match asd {
3 | 1 { 'foo' }
| ^
6 | 2 { 'test' }
7 | else { '' }
vlib/v/checker/tests/match_undefined_cond.vv:6:3: error: cannot match `void` with `int literal`
4 | res := match Asd {
5 | 1 { 'foo' }
6 | 2 { 'test' }
4 | 2 { 'test' }
5 | else { '' }
vlib/v/checker/tests/match_undefined_cond.vv:4:3: error: cannot match `void` with `int literal`
2 | res := match asd {
3 | 1 { 'foo' }
4 | 2 { 'test' }
| ^
7 | else { '' }
8 | }
5 | else { '' }
6 | }

View file

@ -1,7 +1,5 @@
type Asd = int
fn main() {
res := match Asd {
res := match asd {
1 { 'foo' }
2 { 'test' }
else { '' }

View file

@ -0,0 +1,21 @@
vlib/v/checker/tests/struct_not_init_err.vv:11:7: error: `Data` must be initialized
9 |
10 | fn main() {
11 | _ := Data
| ~~~~
12 | _ := DataCollection
13 | _ := ast.Type
vlib/v/checker/tests/struct_not_init_err.vv:12:7: error: `DataCollection` must be initialized
10 | fn main() {
11 | _ := Data
12 | _ := DataCollection
| ~~~~~~~~~~~~~~
13 | _ := ast.Type
14 | // _ := gui.Animate // for vpm mod
vlib/v/checker/tests/struct_not_init_err.vv:13:11: error: `v.ast.Type` must be initialized
11 | _ := Data
12 | _ := DataCollection
13 | _ := ast.Type
| ~~~~
14 | // _ := gui.Animate // for vpm mod
15 | }

View file

@ -0,0 +1,15 @@
module main
import v.ast
struct Data {
}
type DataCollection = Data
fn main() {
_ := Data
_ := DataCollection
_ := ast.Type
// _ := gui.Animate // for vpm mod
}