if lp, ok := p.AcceptToken(token.LPAREN); ok { var rp token.Token astc := &ast.CallExpr{ FuncName: &ast.Ident{ NamePos: tok.Pos, Name: tok.Literal, }, } for { if rp, ok = p.AcceptToken(token.RPAREN); ok { break } arg := p.parseExpr() astc.Args = append(astc.Args, arg) p.AcceptToken(token.COMMA) } astc.Lparen = lp.Pos astc.Rparen = rp.Pos asti.Offset = astc
return asti }
函数表
函数表被记录于全局函数中,这里主要是通过函数表完成与函数有关的各种错误检查
错误类型:函数重复定义
1 2 3 4 5 6 7 8
func(p *Parser)checkFuncName(name string)bool { for _, fu := range p.file.Funcs { if fu.Name.Name == name { returntrue } } returnfalse }
1 2 3 4 5
tokFunc := p.MustAcceptToken(token.FUNC) tokFuncIdent := p.MustAcceptToken(token.IDENT) if ok := p.checkFuncName(tokFuncIdent.Literal); ok { p.errorf(tokFuncIdent.Pos, "duplicate function declaration: %s", tokFuncIdent.Literal) }
错误类型:函数未定义
1 2 3 4 5 6 7 8 9 10 11
if lp, ok := p.AcceptToken(token.LPAREN); ok { if ok = p.checkFuncName(tok.Literal); !ok { p.errorf(lp.Pos, "Function name:%s not find", tok.Literal) } var rp token.Token astc := &ast.CallExpr{ FuncName: &ast.Ident{ NamePos: tok.Pos, Name: tok.Literal, }, }
for i, arg := range fu.Params.List { myType := reflect.TypeOf(args[i]) if arg.Type.Name == "string" && myType.String() != "*ast.Strings" { returnfalse } if arg.Type.Name == "bool" && myType.String() != "*ast.Bool" { returnfalse } } break } returntrue }
1 2 3 4 5 6 7 8 9 10 11
for { if rp, ok = p.AcceptToken(token.RPAREN); ok { break } arg := p.parseExpr() astc.Args = append(astc.Args, arg) p.AcceptToken(token.COMMA) } if ok = p.checkFuncArgs(tok.Literal, astc.Args); !ok { p.errorf(lp.Pos, "The function parameters do not match") }