Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

PoC: poisoning #7236

Closed
wants to merge 3 commits into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
23 changes: 17 additions & 6 deletions vlib/v/ast/ast.v
Original file line number Diff line number Diff line change
Expand Up @@ -10,21 10,27 @@ import v.errors
pub type TypeDecl = AliasTypeDecl | FnTypeDecl | SumTypeDecl

pub type Expr = AnonFn | ArrayDecompose | ArrayInit | AsCast | Assoc | AtExpr | BoolLiteral |
CTempVar | CallExpr | CastExpr | ChanInit | CharLiteral | Comment | ComptimeCall | ComptimeSelector |
CTempVar | CallArg | CallExpr | CastExpr | ChanInit | CharLiteral | Comment | ComptimeCall | ComptimeSelector |
ConcatExpr | EnumVal | FloatLiteral | Ident | IfExpr | IfGuardExpr | IndexExpr | InfixExpr |
IntegerLiteral | Likely | LockExpr | MapInit | MatchExpr | None | OrExpr | ParExpr | PostfixExpr |
PrefixExpr | RangeExpr | SelectExpr | SelectorExpr | SizeOf | SqlExpr | StringInterLiteral |
StringLiteral | StructInit | Type | TypeOf | UnsafeExpr
StringLiteral | StructInit | Type | TypeOf | UnsafeExpr | Error

pub type Stmt = AssertStmt | AssignStmt | Block | BranchStmt | CompFor | ConstDecl | DeferStmt |
EnumDecl | ExprStmt | FnDecl | ForCStmt | ForInStmt | ForStmt | GlobalDecl | GoStmt |
GotoLabel | GotoStmt | HashStmt | Import | InterfaceDecl | Module | Return | SqlStmt |
StructDecl | TypeDecl
StructDecl | TypeDecl | Error

// NB: when you add a new Expr or Stmt type with a .pos field, remember to update
// the .position() token.Position methods too.
pub type ScopeObject = ConstField | GlobalField | Var

pub struct Error {
pub:
message string
pos token.Position
}

// TOOD: replace table.Param
pub type Node = ConstField | EnumField | Expr | Field | File | GlobalField | IfBranch |
MatchBranch | ScopeObject | SelectBranch | Stmt | StructField | StructInitField | table.Param
Expand Down Expand Up @@ -353,7 359,7 @@ pub mut:
args []CallArg
expected_arg_types []table.Type
language table.Language
or_block OrExpr
or_block Expr // OrExpr | Error
left_type table.Type // type of `user`
receiver_type table.Type // User
return_type table.Type
Expand Down Expand Up @@ -1187,6 1193,9 @@ pub fn (expr Expr) position() token.Position {
CTempVar {
return token.Position{}
}
Error {
return expr.pos
}
// Please, do NOT use else{} here.
// This match is exhaustive *on purpose*, to help force
// maintaining/implementing proper .pos fields.
Expand Down Expand Up @@ -1257,7 1266,9 @@ pub fn (stmt Stmt) position() token.Position {
TypeDecl {
match stmt {
AliasTypeDecl, FnTypeDecl, SumTypeDecl { return stmt.pos }
}
} }
Error {
return stmt.pos
}
// Please, do NOT use else{} here.
// This match is exhaustive *on purpose*, to help force
Expand Down Expand Up @@ -1326,7 1337,7 @@ pub fn (node Node) children() []Node {
}
CallExpr {
children << node.left
children << Expr(node.or_block)
children << node.or_block
}
InfixExpr {
children << node.left
Expand Down
13 changes: 4 additions & 9 deletions vlib/v/ast/str.v
Original file line number Diff line number Diff line change
Expand Up @@ -199,8 199,11 @@ pub fn (x Expr) str() string {
AtExpr {
return '$x.val'
}
CallArg {
return x.str()
}
CallExpr {
sargs := args2str(x.args)
sargs := x.args.map(it.str()).join(', ')
if x.is_method {
return '${x.left.str()}.${x.name}($sargs)'
}
Expand Down Expand Up @@ -298,14 301,6 @@ pub fn (a CallArg) str() string {
return '$a.expr.str()'
}

pub fn args2str(args []CallArg) string {
mut res := []string{}
for a in args {
res << a.str()
}
return res.join(', ')
}

pub fn (node &BranchStmt) str() string {
mut s := '$node.kind'
if node.label.len > 0 {
Expand Down
6 changes: 6 additions & 0 deletions vlib/v/checker/checker.v
Original file line number Diff line number Diff line change
Expand Up @@ -2805,6 2805,9 @@ fn (mut c Checker) stmt(node ast.Stmt) {
ast.EnumDecl {
c.enum_decl(node)
}
ast.Error {
c.error(node.message, node.pos)
}
ast.ExprStmt {
node.typ = c.expr(node.expr)
c.expected_type = table.void_type
Expand Down Expand Up @@ -3240,6 3243,9 @@ pub fn (mut c Checker) expr(node ast.Expr) table.Type {
ast.EnumVal {
return c.enum_val(mut node)
}
ast.Error {
c.error(node.message, node.pos)
}
ast.FloatLiteral {
return table.any_flt_type
}
Expand Down
5 changes: 5 additions & 0 deletions vlib/v/gen/cgen.v
Original file line number Diff line number Diff line change
Expand Up @@ -1166,6 1166,7 @@ fn (mut g Gen) stmt(node ast.Stmt) {
ast.TypeDecl {
g.writeln('// TypeDecl')
}
ast.Error {}
}
if !g.skip_stmt_pos { // && g.stmt_path_pos.len > 0 {
g.stmt_path_pos.delete_last()
Expand Down Expand Up @@ -2398,6 2399,9 @@ fn (mut g Gen) expr(node ast.Expr) {
}
ast.BoolLiteral {
g.write(node.val.str())
}
ast.CallArg {

}
ast.CallExpr {
// if g.fileis('1.strings') {
Expand Down Expand Up @@ -2761,6 2765,7 @@ fn (mut g Gen) expr(node ast.Expr) {
ast.UnsafeExpr {
g.expr(node.expr)
}
ast.Error {}
}
}

Expand Down
2 changes: 2 additions & 0 deletions vlib/v/gen/js/js.v
Original file line number Diff line number Diff line change
Expand Up @@ -423,6 423,7 @@ fn (mut g JsGen) stmt(node ast.Stmt) {
ast.TypeDecl {
// skip JS has no typedecl
}
ast.Error {}
}
}

Expand Down Expand Up @@ -579,6 580,7 @@ fn (mut g JsGen) expr(node ast.Expr) {
ast.UnsafeExpr {
g.expr(node.expr)
}
ast.Error {}
ast.ArrayDecompose {}
}
}
Expand Down
20 changes: 10 additions & 10 deletions vlib/v/parser/containers.v
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 6,10 @@ module parser
import v.ast
import v.table

fn (mut p Parser) array_init() ast.ArrayInit {
fn (mut p Parser) array_init() ast.Expr {
first_pos := p.tok.position()
mut last_pos := p.tok.position()
p.check(.lsbr)
p.check(.lsbr) or { return p.error(err) }
// p.warn('array_init() exp=$p.expected_type')
mut array_type := table.void_type
mut elem_type := table.void_type
Expand Down Expand Up @@ -53,7 53,7 @@ fn (mut p Parser) array_init() ast.ArrayInit {
_ = tcc_stack_bug
}
last_pos = p.tok.position()
p.check(.rsbr)
p.check(.rsbr) or { return p.error(err) }
if exprs.len == 1 && p.tok.kind in [.name, .amp] && p.tok.line_nr == line_nr {
// [100]byte
elem_type = p.parse_type()
Expand All @@ -67,12 67,12 @@ fn (mut p Parser) array_init() ast.ArrayInit {
p.error_with_pos('expected `init:`, not `$n`', pos)
return ast.ArrayInit{}
}
p.check(.colon)
p.check(.colon) or { return p.error(err) }
has_default = true
default_expr = p.expr(0)
}
last_pos = p.tok.position()
p.check(.rcbr)
p.check(.rcbr) or { return p.error(err) }
} else {
p.warn_with_pos('use e.g. `x := [1]Type{}` instead of `x := [1]Type`',
last_pos)
Expand Down Expand Up @@ -102,7 102,7 @@ fn (mut p Parser) array_init() ast.ArrayInit {
p.next()
for p.tok.kind != .rcbr {
key := p.check_name()
p.check(.colon)
p.check(.colon) or { return p.error(err) }
match key {
'len' {
has_len = true
Expand All @@ -122,10 122,10 @@ fn (mut p Parser) array_init() ast.ArrayInit {
}
}
if p.tok.kind != .rcbr {
p.check(.comma)
p.check(.comma) or { return p.error(err) }
}
}
p.check(.rcbr)
p.check(.rcbr) or { return p.error(err) }
}
pos := first_pos.extend(last_pos)
return ast.ArrayInit{
Expand All @@ -147,7 147,7 @@ fn (mut p Parser) array_init() ast.ArrayInit {
}
}

fn (mut p Parser) map_init() ast.MapInit {
fn (mut p Parser) map_init() ast.Expr {
pos := p.tok.position()
mut keys := []ast.Expr{}
mut vals := []ast.Expr{}
Expand All @@ -157,7 157,7 @@ fn (mut p Parser) map_init() ast.MapInit {
p.error_with_pos('maps do not support floating point keys yet', key.pos)
}
keys << key
p.check(.colon)
p.check(.colon) or { return p.error(err) }
val := p.expr(0)
vals << val
if p.tok.kind == .comma {
Expand Down
35 changes: 17 additions & 18 deletions vlib/v/parser/fn.v
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 8,7 @@ import v.table
import v.token
import v.util

pub fn (mut p Parser) call_expr(language table.Language, mod string) ast.CallExpr {
pub fn (mut p Parser) call_expr(language table.Language, mod string) ast.Expr {
// pub fn (mut p Parser) call_expr(language table.Language, mod string) ast.Expr {
first_pos := p.tok.position()
mut fn_name := if language == .c {
Expand Down Expand Up @@ -36,7 36,7 @@ pub fn (mut p Parser) call_expr(language table.Language, mod string) ast.CallExp
p.next() // `<`
p.expr_mod = ''
generic_type = p.parse_type()
p.check(.gt) // `>`
p.check(.gt) or { return p.error(err) }
generic_list_pos = generic_list_pos.extend(p.prev_tok.position())
// In case of `foo<T>()`
// T is unwrapped and registered in the checker.
Expand All @@ -49,10 49,10 @@ pub fn (mut p Parser) call_expr(language table.Language, mod string) ast.CallExp
p.table.register_fn_gen_type(full_generic_fn_name, generic_type)
}
}
p.check(.lpar)
p.check(.lpar) or { return p.error(err) }
args := p.call_args()
last_pos := p.tok.position()
p.check(.rpar)
p.check(.rpar) or { return p.error(err) }
// ! in mutable methods
if p.tok.kind == .not {
p.next()
Expand Down Expand Up @@ -109,13 109,12 @@ pub fn (mut p Parser) call_expr(language table.Language, mod string) ast.CallExp
}
}

pub fn (mut p Parser) call_args() []ast.CallArg {
pub fn (mut p Parser) call_args() []ast.Expr {
mut args := []ast.CallArg{}
start_pos := p.tok.position()
for p.tok.kind != .rpar {
if p.tok.kind == .eof {
p.error_with_pos('unexpected eof reached, while parsing call argument', start_pos)
return []
return p.error_with_pos('unexpected eof reached, while parsing call argument', start_pos)
}
is_shared := p.tok.kind == .key_shared
is_atomic := p.tok.kind == .key_atomic
Expand Down Expand Up @@ -147,7 146,7 @@ pub fn (mut p Parser) call_args() []ast.CallArg {
pos: pos
}
if p.tok.kind != .rpar {
p.check(.comma)
p.check(.comma) or { return p.error(err) }
}
}
return args
Expand All @@ -164,7 163,7 @@ fn (mut p Parser) fn_decl() ast.FnDecl {
if is_pub {
p.next()
}
p.check(.key_fn)
p.check(.key_fn) or { return p.error(err) }
p.open_scope()
// C. || JS.
mut language := table.Language.v
Expand All @@ -176,7 175,7 @@ fn (mut p Parser) fn_decl() ast.FnDecl {
}
if language != .v {
p.next()
p.check(.dot)
p.check(.dot) or { return p.error(err) }
p.check_for_impure_v(language, p.tok.position())
}
// Receiver?
Expand Down Expand Up @@ -241,7 240,7 @@ fn (mut p Parser) fn_decl() ast.FnDecl {
is_mut: rec_mut
typ: rec_type
}
p.check(.rpar)
p.check(.rpar) or { return p.error(err) }
}
mut name := ''
if p.tok.kind == .name {
Expand Down Expand Up @@ -285,7 284,7 @@ fn (mut p Parser) fn_decl() ast.FnDecl {
if is_generic {
p.next()
p.next()
p.check(.gt)
p.check(.gt) or { return p.error(err) }
}
// Args
args2, are_args_type_only, is_variadic := p.fn_args()
Expand Down Expand Up @@ -426,7 425,7 @@ fn (mut p Parser) fn_decl() ast.FnDecl {

fn (mut p Parser) anon_fn() ast.AnonFn {
pos := p.tok.position()
p.check(.key_fn)
p.check(.key_fn) or { return p.error(err) }
if p.pref.is_script && p.tok.kind == .name {
p.error_with_pos('function declarations in script mode should be before all script statements',
p.tok.position())
Expand Down Expand Up @@ -497,9 496,9 @@ fn (mut p Parser) anon_fn() ast.AnonFn {
}

// part of fn declaration
fn (mut p Parser) fn_args() ([]table.Param, bool, bool) {
p.check(.lpar)
mut args := []table.Param{}
fn (mut p Parser) fn_args() ([]ast.Expr, bool, bool) {
p.check(.lpar) or { return p.error(err) }
mut args := []ast.Expr{}
mut is_variadic := false
// `int, int, string` (no names, just types)
argname := if p.tok.kind == .name && p.tok.lit.len > 0 && p.tok.lit[0].is_capital() {
Expand Down Expand Up @@ -670,11 669,11 @@ fn (mut p Parser) fn_args() ([]table.Param, bool, bool) {
return []table.Param{}, false, false
}
if p.tok.kind != .rpar {
p.check(.comma)
p.check(.comma) or { return p.error(err) }
}
}
}
p.check(.rpar)
p.check(.rpar) or { return p.error(err) }
return args, types_only, is_variadic
}

Expand Down
Loading