Skip to content

Commit

Permalink
checker: detect unknown type to iterate with $for (#8971)
Browse files Browse the repository at this point in the history
  • Loading branch information
ntrel committed Feb 26, 2021
1 parent 3a08262 commit 59d4d0e
Show file tree
Hide file tree
Showing 5 changed files with 31 additions and 2 deletions.
1 change: 1 addition & 0 deletions vlib/v/ast/ast.v
Original file line number Diff line number Diff line change
Expand Up @@ -723,6 +723,7 @@ pub:
stmts []Stmt
kind CompForKind
pos token.Position
typ_pos token.Position
pub mut:
// expr Expr
typ table.Type
Expand Down
7 changes: 6 additions & 1 deletion vlib/v/checker/checker.v
Original file line number Diff line number Diff line change
Expand Up @@ -3109,7 +3109,12 @@ fn (mut c Checker) stmt(node ast.Stmt) {
c.branch_stmt(node)
}
ast.CompFor {
// node.typ = c.expr(node.expr)
if node.typ > table.void_type {
sym := c.table.get_type_symbol(node.typ)
if sym.kind == .placeholder {
c.error('unknown type `$sym.name`', node.typ_pos)
}
}
c.stmts(node.stmts)
}
ast.ConstDecl {
Expand Down
12 changes: 12 additions & 0 deletions vlib/v/checker/tests/comptime_for.out
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
vlib/v/checker/tests/comptime_for.vv:2:12: error: unknown type `Huh`
1 | fn unknown() {
2 | $for m in Huh.methods {}
| ~~~
3 | $for f in Huh.fields {}
4 | }
vlib/v/checker/tests/comptime_for.vv:3:12: error: unknown type `Huh`
1 | fn unknown() {
2 | $for m in Huh.methods {}
3 | $for f in Huh.fields {}
| ~~~
4 | }
4 changes: 4 additions & 0 deletions vlib/v/checker/tests/comptime_for.vv
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
fn unknown() {
$for m in Huh.methods {}
$for f in Huh.fields {}
}
9 changes: 8 additions & 1 deletion vlib/v/parser/comptime.v
Original file line number Diff line number Diff line change
Expand Up @@ -217,26 +217,32 @@ fn (mut p Parser) comp_for() ast.CompFor {
// $for field in App(fields) {
p.next()
p.check(.key_for)
var_pos := p.tok.position()
val_var := p.check_name()
p.check(.key_in)
mut typ_pos := p.tok.position()
lang := p.parse_language()
typ := p.parse_any_type(lang, false, false)
typ_pos = typ_pos.extend(p.prev_tok.position())
p.check(.dot)
for_val := p.check_name()
mut kind := ast.CompForKind.methods
if for_val == 'methods' {
p.scope.register(ast.Var{
name: val_var
typ: p.table.find_type_idx('FunctionData')
pos: var_pos
})
} else if for_val == 'fields' {
p.scope.register(ast.Var{
name: val_var
typ: p.table.find_type_idx('FieldData')
pos: var_pos
})
kind = .fields
} else {
p.error('unknown kind `$for_val`, available are: `methods` or `fields`')
p.error_with_pos('unknown kind `$for_val`, available are: `methods` or `fields`',
p.prev_tok.position())
return ast.CompFor{}
}
spos := p.tok.position()
Expand All @@ -246,6 +252,7 @@ fn (mut p Parser) comp_for() ast.CompFor {
stmts: stmts
kind: kind
typ: typ
typ_pos: typ_pos
pos: spos.extend(p.tok.position())
}
}
Expand Down

0 comments on commit 59d4d0e

Please sign in to comment.