From a97686125dfbe45f5a505413cf6d190785ae0670 Mon Sep 17 00:00:00 2001 From: Laytan Laats Date: Sat, 25 Mar 2023 15:00:17 +0100 Subject: [PATCH] refactor!: drop php5 support --- internal/php5/node.go | 85 - internal/php5/parser.go | 66 - internal/php5/parser_test.go | 50781 --------------------- internal/php5/php5.go | Bin 265218 -> 0 bytes internal/php5/php5.y | 5698 --- internal/php5/php5_bench_test.go | 30 - internal/php5/test.php | 381 - pkg/parser/parser.go | 14 +- pkg/visitor/printer/printer_php5_test.go | 1439 - 9 files changed, 1 insertion(+), 58493 deletions(-) delete mode 100644 internal/php5/node.go delete mode 100644 internal/php5/parser.go delete mode 100644 internal/php5/parser_test.go delete mode 100644 internal/php5/php5.go delete mode 100644 internal/php5/php5.y delete mode 100644 internal/php5/php5_bench_test.go delete mode 100644 internal/php5/test.php delete mode 100644 pkg/visitor/printer/printer_php5_test.go diff --git a/internal/php5/node.go b/internal/php5/node.go deleted file mode 100644 index e0963fa..0000000 --- a/internal/php5/node.go +++ /dev/null @@ -1,85 +0,0 @@ -package php5 - -import ( - "github.com/VKCOM/php-parser/pkg/ast" - "github.com/VKCOM/php-parser/pkg/position" - "github.com/VKCOM/php-parser/pkg/token" -) - -type ParserBrackets struct { - Position *position.Position - OpenBracketTkn *token.Token - Child ast.Vertex - CloseBracketTkn *token.Token -} - -func (n *ParserBrackets) Accept(v ast.Visitor) { - // do nothing -} - -func (n *ParserBrackets) GetPosition() *position.Position { - return n.Position -} - -type ParserSeparatedList struct { - Position *position.Position - Items []ast.Vertex - SeparatorTkns []*token.Token -} - -func (n *ParserSeparatedList) Accept(v ast.Visitor) { - // do nothing -} - -func (n *ParserSeparatedList) GetPosition() *position.Position { - return n.Position -} - -// TraitAdaptationList node -type TraitAdaptationList struct { - Position *position.Position - OpenCurlyBracketTkn *token.Token - Adaptations []ast.Vertex - CloseCurlyBracketTkn *token.Token -} - -func (n *TraitAdaptationList) Accept(v ast.Visitor) { - // do nothing -} - -func (n *TraitAdaptationList) GetPosition() *position.Position { - return n.Position -} - -// ArgumentList node -type ArgumentList struct { - Position *position.Position - OpenParenthesisTkn *token.Token - Arguments []ast.Vertex - SeparatorTkns []*token.Token - CloseParenthesisTkn *token.Token -} - -func (n *ArgumentList) Accept(v ast.Visitor) { - // do nothing -} - -func (n *ArgumentList) GetPosition() *position.Position { - return n.Position -} - -// TraitMethodRef node -type TraitMethodRef struct { - Position *position.Position - Trait ast.Vertex - DoubleColonTkn *token.Token - Method ast.Vertex -} - -func (n *TraitMethodRef) Accept(v ast.Visitor) { - // do nothing -} - -func (n *TraitMethodRef) GetPosition() *position.Position { - return n.Position -} diff --git a/internal/php5/parser.go b/internal/php5/parser.go deleted file mode 100644 index 8fd6578..0000000 --- a/internal/php5/parser.go +++ /dev/null @@ -1,66 +0,0 @@ -package php5 - -import ( - "github.com/VKCOM/php-parser/internal/position" - "github.com/VKCOM/php-parser/internal/scanner" - "github.com/VKCOM/php-parser/pkg/ast" - "github.com/VKCOM/php-parser/pkg/conf" - "github.com/VKCOM/php-parser/pkg/errors" - "github.com/VKCOM/php-parser/pkg/token" -) - -// Parser structure -type Parser struct { - Lexer *scanner.Lexer - currentToken *token.Token - rootNode ast.Vertex - errHandlerFunc func(*errors.Error) - builder *position.Builder -} - -// NewParser creates and returns new Parser -func NewParser(lexer *scanner.Lexer, config conf.Config) *Parser { - return &Parser{ - Lexer: lexer, - errHandlerFunc: config.ErrorHandlerFunc, - builder: position.NewBuilder(), - } -} - -// Lex proxy to scanner Lex -func (p *Parser) Lex(lval *yySymType) int { - t := p.Lexer.Lex() - - p.currentToken = t - lval.token = t - - return int(t.ID) -} - -func (p *Parser) Error(msg string) { - if p.errHandlerFunc == nil { - return - } - - p.errHandlerFunc(errors.NewError(msg, p.currentToken.Position)) -} - -// Parse the php7 Parser entrypoint -func (p *Parser) Parse() int { - p.rootNode = nil - return yyParse(p) -} - -// GetRootNode returns root node -func (p *Parser) GetRootNode() ast.Vertex { - return p.rootNode -} - -// helpers - -func lastNode(nn []ast.Vertex) ast.Vertex { - if len(nn) == 0 { - return nil - } - return nn[len(nn)-1] -} diff --git a/internal/php5/parser_test.go b/internal/php5/parser_test.go deleted file mode 100644 index dbab6a2..0000000 --- a/internal/php5/parser_test.go +++ /dev/null @@ -1,50781 +0,0 @@ -package php5_test - -import ( - "testing" - - "gotest.tools/assert" - - "github.com/VKCOM/php-parser/internal/php5" - "github.com/VKCOM/php-parser/internal/scanner" - "github.com/VKCOM/php-parser/pkg/ast" - "github.com/VKCOM/php-parser/pkg/conf" - "github.com/VKCOM/php-parser/pkg/errors" - "github.com/VKCOM/php-parser/pkg/position" - "github.com/VKCOM/php-parser/pkg/token" - "github.com/VKCOM/php-parser/pkg/version" -) - -func TestIdentifier(t *testing.T) { - src := `bar($a, ...$b); - foo::bar($a, ...$b); - $foo::bar($a, ...$b); - new foo($a, ...$b);` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 2, - EndLine: 7, - StartPos: 5, - EndPos: 132, - }, - Stmts: []ast.Vertex{ - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 2, - EndLine: 2, - StartPos: 5, - EndPos: 20, - }, - Expr: &ast.ExprFunctionCall{ - Position: &position.Position{ - StartLine: 2, - EndLine: 2, - StartPos: 5, - EndPos: 19, - }, - Function: &ast.Name{ - Position: &position.Position{ - StartLine: 2, - EndLine: 2, - StartPos: 5, - EndPos: 8, - }, - Parts: []ast.Vertex{ - &ast.NamePart{ - Position: &position.Position{ - StartLine: 2, - EndLine: 2, - StartPos: 5, - EndPos: 8, - }, - StringTkn: &token.Token{ - ID: token.T_STRING, - Value: []byte("foo"), - Position: &position.Position{ - StartLine: 2, - EndLine: 2, - StartPos: 5, - EndPos: 8, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte(""), - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 46, - EndPos: 48, - }, - }, - Method: &ast.Identifier{ - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 48, - EndPos: 51, - }, - IdentifierTkn: &token.Token{ - ID: token.T_STRING, - Value: []byte("bar"), - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 48, - EndPos: 51, - }, - }, - Value: []byte("bar"), - }, - OpenParenthesisTkn: &token.Token{ - ID: token.ID(40), - Value: []byte("("), - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 51, - EndPos: 52, - }, - }, - Args: []ast.Vertex{ - &ast.Argument{ - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 52, - EndPos: 54, - }, - Expr: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 52, - EndPos: 54, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 52, - EndPos: 54, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 52, - EndPos: 54, - }, - }, - Value: []byte("$a"), - }, - }, - }, - &ast.Argument{ - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 56, - EndPos: 61, - }, - VariadicTkn: &token.Token{ - ID: token.T_ELLIPSIS, - Value: []byte("..."), - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 56, - EndPos: 59, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 55, - EndPos: 56, - }, - }, - }, - }, - Expr: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 59, - EndPos: 61, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 59, - EndPos: 61, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 59, - EndPos: 61, - }, - }, - Value: []byte("$b"), - }, - }, - }, - }, - SeparatorTkns: []*token.Token{ - { - ID: token.ID(44), - Value: []byte(","), - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 54, - EndPos: 55, - }, - }, - }, - CloseParenthesisTkn: &token.Token{ - ID: token.ID(41), - Value: []byte(")"), - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 61, - EndPos: 62, - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 4, - EndLine: 4, - StartPos: 62, - EndPos: 63, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 66, - EndPos: 86, - }, - Expr: &ast.ExprStaticCall{ - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 66, - EndPos: 85, - }, - Class: &ast.Name{ - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 66, - EndPos: 69, - }, - Parts: []ast.Vertex{ - &ast.NamePart{ - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 66, - EndPos: 69, - }, - StringTkn: &token.Token{ - ID: token.T_STRING, - Value: []byte("foo"), - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 66, - EndPos: 69, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 4, - EndLine: 5, - StartPos: 63, - EndPos: 66, - }, - }, - }, - }, - Value: []byte("foo"), - }, - }, - }, - DoubleColonTkn: &token.Token{ - ID: token.T_PAAMAYIM_NEKUDOTAYIM, - Value: []byte("::"), - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 69, - EndPos: 71, - }, - }, - Call: &ast.Identifier{ - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 71, - EndPos: 74, - }, - IdentifierTkn: &token.Token{ - ID: token.T_STRING, - Value: []byte("bar"), - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 71, - EndPos: 74, - }, - }, - Value: []byte("bar"), - }, - OpenParenthesisTkn: &token.Token{ - ID: token.ID(40), - Value: []byte("("), - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 74, - EndPos: 75, - }, - }, - Args: []ast.Vertex{ - &ast.Argument{ - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 75, - EndPos: 77, - }, - Expr: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 75, - EndPos: 77, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 75, - EndPos: 77, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 75, - EndPos: 77, - }, - }, - Value: []byte("$a"), - }, - }, - }, - &ast.Argument{ - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 79, - EndPos: 84, - }, - VariadicTkn: &token.Token{ - ID: token.T_ELLIPSIS, - Value: []byte("..."), - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 79, - EndPos: 82, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 78, - EndPos: 79, - }, - }, - }, - }, - Expr: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 82, - EndPos: 84, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 82, - EndPos: 84, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 82, - EndPos: 84, - }, - }, - Value: []byte("$b"), - }, - }, - }, - }, - SeparatorTkns: []*token.Token{ - { - ID: token.ID(44), - Value: []byte(","), - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 77, - EndPos: 78, - }, - }, - }, - CloseParenthesisTkn: &token.Token{ - ID: token.ID(41), - Value: []byte(")"), - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 84, - EndPos: 85, - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 5, - EndLine: 5, - StartPos: 85, - EndPos: 86, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 89, - EndPos: 110, - }, - Expr: &ast.ExprStaticCall{ - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 89, - EndPos: 109, - }, - Class: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 89, - EndPos: 93, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 89, - EndPos: 93, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$foo"), - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 89, - EndPos: 93, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 5, - EndLine: 6, - StartPos: 86, - EndPos: 89, - }, - }, - }, - }, - Value: []byte("$foo"), - }, - }, - DoubleColonTkn: &token.Token{ - ID: token.T_PAAMAYIM_NEKUDOTAYIM, - Value: []byte("::"), - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 93, - EndPos: 95, - }, - }, - Call: &ast.Identifier{ - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 95, - EndPos: 98, - }, - IdentifierTkn: &token.Token{ - ID: token.T_STRING, - Value: []byte("bar"), - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 95, - EndPos: 98, - }, - }, - Value: []byte("bar"), - }, - OpenParenthesisTkn: &token.Token{ - ID: token.ID(40), - Value: []byte("("), - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 98, - EndPos: 99, - }, - }, - Args: []ast.Vertex{ - &ast.Argument{ - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 99, - EndPos: 101, - }, - Expr: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 99, - EndPos: 101, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 99, - EndPos: 101, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 99, - EndPos: 101, - }, - }, - Value: []byte("$a"), - }, - }, - }, - &ast.Argument{ - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 103, - EndPos: 108, - }, - VariadicTkn: &token.Token{ - ID: token.T_ELLIPSIS, - Value: []byte("..."), - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 103, - EndPos: 106, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 102, - EndPos: 103, - }, - }, - }, - }, - Expr: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 106, - EndPos: 108, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 106, - EndPos: 108, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 106, - EndPos: 108, - }, - }, - Value: []byte("$b"), - }, - }, - }, - }, - SeparatorTkns: []*token.Token{ - { - ID: token.ID(44), - Value: []byte(","), - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 101, - EndPos: 102, - }, - }, - }, - CloseParenthesisTkn: &token.Token{ - ID: token.ID(41), - Value: []byte(")"), - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 108, - EndPos: 109, - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 6, - EndLine: 6, - StartPos: 109, - EndPos: 110, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 113, - EndPos: 132, - }, - Expr: &ast.ExprNew{ - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 113, - EndPos: 131, - }, - NewTkn: &token.Token{ - ID: token.T_NEW, - Value: []byte("new"), - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 113, - EndPos: 116, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 6, - EndLine: 7, - StartPos: 110, - EndPos: 113, - }, - }, - }, - }, - Class: &ast.Name{ - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 117, - EndPos: 120, - }, - Parts: []ast.Vertex{ - &ast.NamePart{ - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 117, - EndPos: 120, - }, - StringTkn: &token.Token{ - ID: token.T_STRING, - Value: []byte("foo"), - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 117, - EndPos: 120, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 116, - EndPos: 117, - }, - }, - }, - }, - Value: []byte("foo"), - }, - }, - }, - OpenParenthesisTkn: &token.Token{ - ID: token.ID(40), - Value: []byte("("), - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 120, - EndPos: 121, - }, - }, - Args: []ast.Vertex{ - &ast.Argument{ - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 121, - EndPos: 123, - }, - Expr: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 121, - EndPos: 123, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 121, - EndPos: 123, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 121, - EndPos: 123, - }, - }, - Value: []byte("$a"), - }, - }, - }, - &ast.Argument{ - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 125, - EndPos: 130, - }, - VariadicTkn: &token.Token{ - ID: token.T_ELLIPSIS, - Value: []byte("..."), - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 125, - EndPos: 128, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 124, - EndPos: 125, - }, - }, - }, - }, - Expr: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 128, - EndPos: 130, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 128, - EndPos: 130, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 128, - EndPos: 130, - }, - }, - Value: []byte("$b"), - }, - }, - }, - }, - SeparatorTkns: []*token.Token{ - { - ID: token.ID(44), - Value: []byte(","), - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 123, - EndPos: 124, - }, - }, - }, - CloseParenthesisTkn: &token.Token{ - ID: token.ID(41), - Value: []byte(")"), - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 130, - EndPos: 131, - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 7, - EndLine: 7, - StartPos: 131, - EndPos: 132, - }, - }, - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -func TestPhp5ParameterNode(t *testing.T) { - src := `bar()";` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 22, - }, - Stmts: []ast.Vertex{ - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 22, - }, - Expr: &ast.ScalarEncapsed{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 21, - }, - OpenQuoteTkn: &token.Token{ - ID: token.ID(34), - Value: []byte("\""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 4, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte(""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 13, - EndPos: 15, - }, - }, - Prop: &ast.Identifier{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 15, - EndPos: 18, - }, - IdentifierTkn: &token.Token{ - ID: token.T_STRING, - Value: []byte("bar"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 15, - EndPos: 18, - }, - }, - Value: []byte("bar"), - }, - }, - &ast.ScalarEncapsedStringPart{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 18, - EndPos: 20, - }, - EncapsedStrTkn: &token.Token{ - ID: token.T_ENCAPSED_AND_WHITESPACE, - Value: []byte("()"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 18, - EndPos: 20, - }, - }, - Value: []byte("()"), - }, - }, - CloseQuoteTkn: &token.Token{ - ID: token.ID(34), - Value: []byte("\""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 20, - EndPos: 21, - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 21, - EndPos: 22, - }, - }, - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -func TestScalarEncapsed_DollarOpenCurlyBraces(t *testing.T) { - src := `bar()}";` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 24, - }, - Stmts: []ast.Vertex{ - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 24, - }, - Expr: &ast.ScalarEncapsed{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 23, - }, - OpenQuoteTkn: &token.Token{ - ID: token.ID(34), - Value: []byte("\""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 4, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte(""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 14, - EndPos: 16, - }, - }, - Method: &ast.Identifier{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 16, - EndPos: 19, - }, - IdentifierTkn: &token.Token{ - ID: token.T_STRING, - Value: []byte("bar"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 16, - EndPos: 19, - }, - }, - Value: []byte("bar"), - }, - OpenParenthesisTkn: &token.Token{ - ID: token.ID(40), - Value: []byte("("), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 19, - EndPos: 20, - }, - }, - CloseParenthesisTkn: &token.Token{ - ID: token.ID(41), - Value: []byte(")"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 20, - EndPos: 21, - }, - }, - }, - CloseCurlyBracketTkn: &token.Token{ - ID: token.ID(125), - Value: []byte("}"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 21, - EndPos: 22, - }, - }, - }, - }, - CloseQuoteTkn: &token.Token{ - ID: token.ID(34), - Value: []byte("\""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 22, - EndPos: 23, - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 23, - EndPos: 24, - }, - }, - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -func TestScalarHeredoc_HeredocSimpleLabel(t *testing.T) { - src := ` $v) {}` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 30, - }, - Stmts: []ast.Vertex{ - &ast.StmtForeach{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 30, - }, - ForeachTkn: &token.Token{ - ID: token.T_FOREACH, - Value: []byte("foreach"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 10, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte(""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 21, - EndPos: 23, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 20, - EndPos: 21, - }, - }, - }, - }, - Var: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 24, - EndPos: 26, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 24, - EndPos: 26, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$v"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 24, - EndPos: 26, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 23, - EndPos: 24, - }, - }, - }, - }, - Value: []byte("$v"), - }, - }, - CloseParenthesisTkn: &token.Token{ - ID: token.ID(41), - Value: []byte(")"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 26, - EndPos: 27, - }, - }, - Stmt: &ast.StmtStmtList{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 28, - EndPos: 30, - }, - OpenCurlyBracketTkn: &token.Token{ - ID: token.ID(123), - Value: []byte("{"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 28, - EndPos: 29, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 27, - EndPos: 28, - }, - }, - }, - }, - Stmts: []ast.Vertex{}, - CloseCurlyBracketTkn: &token.Token{ - ID: token.ID(125), - Value: []byte("}"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 29, - EndPos: 30, - }, - }, - }, - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -func TestStmtForeach_ExprWithKey(t *testing.T) { - src := ` $v) {}` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 30, - }, - Stmts: []ast.Vertex{ - &ast.StmtForeach{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 30, - }, - ForeachTkn: &token.Token{ - ID: token.T_FOREACH, - Value: []byte("foreach"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 10, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte(""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 21, - EndPos: 23, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 20, - EndPos: 21, - }, - }, - }, - }, - Var: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 24, - EndPos: 26, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 24, - EndPos: 26, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$v"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 24, - EndPos: 26, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 23, - EndPos: 24, - }, - }, - }, - }, - Value: []byte("$v"), - }, - }, - CloseParenthesisTkn: &token.Token{ - ID: token.ID(41), - Value: []byte(")"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 26, - EndPos: 27, - }, - }, - Stmt: &ast.StmtStmtList{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 28, - EndPos: 30, - }, - OpenCurlyBracketTkn: &token.Token{ - ID: token.ID(123), - Value: []byte("{"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 28, - EndPos: 29, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 27, - EndPos: 28, - }, - }, - }, - }, - Stmts: []ast.Vertex{}, - CloseCurlyBracketTkn: &token.Token{ - ID: token.ID(125), - Value: []byte("}"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 29, - EndPos: 30, - }, - }, - }, - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -func TestStmtForeach_WithRef(t *testing.T) { - src := ` &$v) {}` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 31, - }, - Stmts: []ast.Vertex{ - &ast.StmtForeach{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 31, - }, - ForeachTkn: &token.Token{ - ID: token.T_FOREACH, - Value: []byte("foreach"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 10, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte(""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 21, - EndPos: 23, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 20, - EndPos: 21, - }, - }, - }, - }, - AmpersandTkn: &token.Token{ - ID: token.ID(38), - Value: []byte("&"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 24, - EndPos: 25, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 23, - EndPos: 24, - }, - }, - }, - }, - Var: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 25, - EndPos: 27, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 25, - EndPos: 27, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$v"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 25, - EndPos: 27, - }, - }, - Value: []byte("$v"), - }, - }, - CloseParenthesisTkn: &token.Token{ - ID: token.ID(41), - Value: []byte(")"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 27, - EndPos: 28, - }, - }, - Stmt: &ast.StmtStmtList{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 29, - EndPos: 31, - }, - OpenCurlyBracketTkn: &token.Token{ - ID: token.ID(123), - Value: []byte("{"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 29, - EndPos: 30, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 28, - EndPos: 29, - }, - }, - }, - }, - Stmts: []ast.Vertex{}, - CloseCurlyBracketTkn: &token.Token{ - ID: token.ID(125), - Value: []byte("}"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 30, - EndPos: 31, - }, - }, - }, - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -func TestStmtForeach_WithList(t *testing.T) { - src := ` list($v)) {}` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 36, - }, - Stmts: []ast.Vertex{ - &ast.StmtForeach{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 36, - }, - ForeachTkn: &token.Token{ - ID: token.T_FOREACH, - Value: []byte("foreach"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 10, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte(""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 21, - EndPos: 23, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 20, - EndPos: 21, - }, - }, - }, - }, - Var: &ast.ExprList{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 24, - EndPos: 32, - }, - ListTkn: &token.Token{ - ID: token.T_LIST, - Value: []byte("list"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 24, - EndPos: 28, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 23, - EndPos: 24, - }, - }, - }, - }, - OpenBracketTkn: &token.Token{ - ID: token.ID(40), - Value: []byte("("), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 28, - EndPos: 29, - }, - }, - Items: []ast.Vertex{ - &ast.ExprArrayItem{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 29, - EndPos: 31, - }, - Val: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 29, - EndPos: 31, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 29, - EndPos: 31, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$v"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 29, - EndPos: 31, - }, - }, - Value: []byte("$v"), - }, - }, - }, - }, - CloseBracketTkn: &token.Token{ - ID: token.ID(41), - Value: []byte(")"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 31, - EndPos: 32, - }, - }, - }, - CloseParenthesisTkn: &token.Token{ - ID: token.ID(41), - Value: []byte(")"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 32, - EndPos: 33, - }, - }, - Stmt: &ast.StmtStmtList{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 34, - EndPos: 36, - }, - OpenCurlyBracketTkn: &token.Token{ - ID: token.ID(123), - Value: []byte("{"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 34, - EndPos: 35, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 33, - EndPos: 34, - }, - }, - }, - }, - Stmts: []ast.Vertex{}, - CloseCurlyBracketTkn: &token.Token{ - ID: token.ID(125), - Value: []byte("}"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 35, - EndPos: 36, - }, - }, - }, - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -func TestStmtFunction(t *testing.T) { - src := `
` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 17, - }, - Stmts: []ast.Vertex{ - &ast.StmtNop{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 5, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte("?>"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 5, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte(""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 5, - EndPos: 17, - }, - }, - Value: []byte("
"), - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -func TestStmtInterface(t *testing.T) { - src := `1, &$b,);` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 21, - }, - Stmts: []ast.Vertex{ - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 21, - }, - Expr: &ast.ExprArray{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 20, - }, - ArrayTkn: &token.Token{ - ID: token.T_ARRAY, - Value: []byte("array"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 8, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte(""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 10, - EndPos: 12, - }, - }, - Val: &ast.ScalarLnumber{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 12, - EndPos: 13, - }, - NumberTkn: &token.Token{ - ID: token.T_LNUMBER, - Value: []byte("1"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 12, - EndPos: 13, - }, - }, - Value: []byte("1"), - }, - }, - &ast.ExprArrayItem{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 15, - EndPos: 18, - }, - AmpersandTkn: &token.Token{ - ID: token.ID(38), - Value: []byte("&"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 15, - EndPos: 16, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 14, - EndPos: 15, - }, - }, - }, - }, - Val: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 16, - EndPos: 18, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 16, - EndPos: 18, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 16, - EndPos: 18, - }, - }, - Value: []byte("$b"), - }, - }, - }, - &ast.ExprArrayItem{}, - }, - SeparatorTkns: []*token.Token{ - { - ID: token.ID(44), - Value: []byte(","), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 13, - EndPos: 14, - }, - }, - { - ID: token.ID(44), - Value: []byte(","), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 18, - EndPos: 19, - }, - }, - }, - CloseBracketTkn: &token.Token{ - ID: token.ID(41), - Value: []byte(")"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 19, - EndPos: 20, - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 20, - EndPos: 21, - }, - }, - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -func TestExprBitwiseNot(t *testing.T) { - src := `foo();` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 13, - }, - Stmts: []ast.Vertex{ - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 13, - }, - Expr: &ast.ExprMethodCall{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 12, - }, - Var: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 5, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 5, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 5, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte(""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 5, - EndPos: 7, - }, - }, - Method: &ast.Identifier{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 7, - EndPos: 10, - }, - IdentifierTkn: &token.Token{ - ID: token.T_STRING, - Value: []byte("foo"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 7, - EndPos: 10, - }, - }, - Value: []byte("foo"), - }, - OpenParenthesisTkn: &token.Token{ - ID: token.ID(40), - Value: []byte("("), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 10, - EndPos: 11, - }, - }, - CloseParenthesisTkn: &token.Token{ - ID: token.ID(41), - Value: []byte(")"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 11, - EndPos: 12, - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 12, - EndPos: 13, - }, - }, - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -func TestExprNew(t *testing.T) { - src := `b["c"]()->d["e"]();` - -func TestExprPropertyFetch(t *testing.T) { - src := `foo;` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 11, - }, - Stmts: []ast.Vertex{ - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 11, - }, - Expr: &ast.ExprPropertyFetch{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 10, - }, - Var: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 5, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 5, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 5, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte(""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 5, - EndPos: 7, - }, - }, - Prop: &ast.Identifier{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 7, - EndPos: 10, - }, - IdentifierTkn: &token.Token{ - ID: token.T_STRING, - Value: []byte("foo"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 7, - EndPos: 10, - }, - }, - Value: []byte("foo"), - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 10, - EndPos: 11, - }, - }, - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -func TestExprShellExec(t *testing.T) { - src := "1, &$b,];` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 16, - }, - Stmts: []ast.Vertex{ - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 16, - }, - Expr: &ast.ExprArray{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 15, - }, - OpenBracketTkn: &token.Token{ - ID: token.ID(91), - Value: []byte("["), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 4, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte(""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 5, - EndPos: 7, - }, - }, - Val: &ast.ScalarLnumber{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 7, - EndPos: 8, - }, - NumberTkn: &token.Token{ - ID: token.T_LNUMBER, - Value: []byte("1"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 7, - EndPos: 8, - }, - }, - Value: []byte("1"), - }, - }, - &ast.ExprArrayItem{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 10, - EndPos: 13, - }, - AmpersandTkn: &token.Token{ - ID: token.ID(38), - Value: []byte("&"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 10, - EndPos: 11, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 9, - EndPos: 10, - }, - }, - }, - }, - Val: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 11, - EndPos: 13, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 11, - EndPos: 13, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 11, - EndPos: 13, - }, - }, - Value: []byte("$b"), - }, - }, - }, - &ast.ExprArrayItem{}, - }, - SeparatorTkns: []*token.Token{ - { - ID: token.ID(44), - Value: []byte(","), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 8, - EndPos: 9, - }, - }, - { - ID: token.ID(44), - Value: []byte(","), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 13, - EndPos: 14, - }, - }, - }, - CloseBracketTkn: &token.Token{ - ID: token.ID(93), - Value: []byte("]"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 14, - EndPos: 15, - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 15, - EndPos: 16, - }, - }, - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -func TestExprStaticCall(t *testing.T) { - src := ` $b;` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 18, - }, - Stmts: []ast.Vertex{ - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 18, - }, - Expr: &ast.ExprYield{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 17, - }, - YieldTkn: &token.Token{ - ID: token.T_YIELD, - Value: []byte("yield"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 8, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte(""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 12, - EndPos: 14, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 11, - EndPos: 12, - }, - }, - }, - }, - Val: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 15, - EndPos: 17, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 15, - EndPos: 17, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 15, - EndPos: 17, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 14, - EndPos: 15, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 17, - EndPos: 18, - }, - }, - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -func TestExprYield_Expr(t *testing.T) { - src := ` 1;` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 17, - }, - Stmts: []ast.Vertex{ - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 17, - }, - Expr: &ast.ExprYield{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 16, - }, - YieldTkn: &token.Token{ - ID: token.T_YIELD, - Value: []byte("yield"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 3, - EndPos: 8, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte(""), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 12, - EndPos: 14, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 11, - EndPos: 12, - }, - }, - }, - }, - Val: &ast.ScalarLnumber{ - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 15, - EndPos: 16, - }, - NumberTkn: &token.Token{ - ID: token.T_LNUMBER, - Value: []byte("1"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 15, - EndPos: 16, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 14, - EndPos: 15, - }, - }, - }, - }, - Value: []byte("1"), - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 1, - EndLine: 1, - StartPos: 16, - EndPos: 17, - }, - }, - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -// expr assign - -func TestExprAssign(t *testing.T) { - src := `>= $b;` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 2, - EndLine: 17, - StartPos: 5, - EndPos: 210, - }, - Stmts: []ast.Vertex{ - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 2, - EndLine: 2, - StartPos: 5, - EndPos: 13, - }, - Expr: &ast.ExprAssign{ - Position: &position.Position{ - StartLine: 2, - EndLine: 2, - StartPos: 5, - EndPos: 12, - }, - Var: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 2, - EndLine: 2, - StartPos: 5, - EndPos: 7, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 2, - EndLine: 2, - StartPos: 5, - EndPos: 7, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 2, - EndLine: 2, - StartPos: 5, - EndPos: 7, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte(">="), - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 203, - EndPos: 206, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 202, - EndPos: 203, - }, - }, - }, - }, - Expr: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 207, - EndPos: 209, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 207, - EndPos: 209, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 207, - EndPos: 209, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 206, - EndPos: 207, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 209, - EndPos: 210, - }, - }, - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -// expr binary - -func TestExprBinary_BitwiseAnd(t *testing.T) { - src := `= $b; - $a > $b; - $a === $b; - $a and $b; - $a or $b; - $a xor $b; - $a - $b; - $a % $b; - $a * $b; - $a != $b; - $a !== $b; - $a + $b; - $a ** $b; - $a << $b; - $a >> $b; - $a <= $b; - $a < $b;` - - expected := &ast.Root{ - Position: &position.Position{ - StartLine: 2, - EndLine: 26, - StartPos: 5, - EndPos: 295, - }, - Stmts: []ast.Vertex{ - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 2, - EndLine: 2, - StartPos: 5, - EndPos: 13, - }, - Expr: &ast.ExprBinaryBitwiseAnd{ - Position: &position.Position{ - StartLine: 2, - EndLine: 2, - StartPos: 5, - EndPos: 12, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 2, - EndLine: 2, - StartPos: 5, - EndPos: 7, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 2, - EndLine: 2, - StartPos: 5, - EndPos: 7, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 2, - EndLine: 2, - StartPos: 5, - EndPos: 7, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_OPEN_TAG, - Value: []byte("="), - Position: &position.Position{ - StartLine: 10, - EndLine: 10, - StartPos: 99, - EndPos: 101, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 10, - EndLine: 10, - StartPos: 98, - EndPos: 99, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 10, - EndLine: 10, - StartPos: 102, - EndPos: 104, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 10, - EndLine: 10, - StartPos: 102, - EndPos: 104, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 10, - EndLine: 10, - StartPos: 102, - EndPos: 104, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 10, - EndLine: 10, - StartPos: 101, - EndPos: 102, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 10, - EndLine: 10, - StartPos: 104, - EndPos: 105, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 11, - EndLine: 11, - StartPos: 108, - EndPos: 116, - }, - Expr: &ast.ExprBinaryGreater{ - Position: &position.Position{ - StartLine: 11, - EndLine: 11, - StartPos: 108, - EndPos: 115, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 11, - EndLine: 11, - StartPos: 108, - EndPos: 110, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 11, - EndLine: 11, - StartPos: 108, - EndPos: 110, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 11, - EndLine: 11, - StartPos: 108, - EndPos: 110, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 10, - EndLine: 11, - StartPos: 105, - EndPos: 108, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.ID(62), - Value: []byte(">"), - Position: &position.Position{ - StartLine: 11, - EndLine: 11, - StartPos: 111, - EndPos: 112, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 11, - EndLine: 11, - StartPos: 110, - EndPos: 111, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 11, - EndLine: 11, - StartPos: 113, - EndPos: 115, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 11, - EndLine: 11, - StartPos: 113, - EndPos: 115, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 11, - EndLine: 11, - StartPos: 113, - EndPos: 115, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 11, - EndLine: 11, - StartPos: 112, - EndPos: 113, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 11, - EndLine: 11, - StartPos: 115, - EndPos: 116, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 12, - EndLine: 12, - StartPos: 119, - EndPos: 129, - }, - Expr: &ast.ExprBinaryIdentical{ - Position: &position.Position{ - StartLine: 12, - EndLine: 12, - StartPos: 119, - EndPos: 128, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 12, - EndLine: 12, - StartPos: 119, - EndPos: 121, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 12, - EndLine: 12, - StartPos: 119, - EndPos: 121, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 12, - EndLine: 12, - StartPos: 119, - EndPos: 121, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 11, - EndLine: 12, - StartPos: 116, - EndPos: 119, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.T_IS_IDENTICAL, - Value: []byte("==="), - Position: &position.Position{ - StartLine: 12, - EndLine: 12, - StartPos: 122, - EndPos: 125, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 12, - EndLine: 12, - StartPos: 121, - EndPos: 122, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 12, - EndLine: 12, - StartPos: 126, - EndPos: 128, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 12, - EndLine: 12, - StartPos: 126, - EndPos: 128, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 12, - EndLine: 12, - StartPos: 126, - EndPos: 128, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 12, - EndLine: 12, - StartPos: 125, - EndPos: 126, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 12, - EndLine: 12, - StartPos: 128, - EndPos: 129, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 13, - EndLine: 13, - StartPos: 132, - EndPos: 142, - }, - Expr: &ast.ExprBinaryLogicalAnd{ - Position: &position.Position{ - StartLine: 13, - EndLine: 13, - StartPos: 132, - EndPos: 141, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 13, - EndLine: 13, - StartPos: 132, - EndPos: 134, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 13, - EndLine: 13, - StartPos: 132, - EndPos: 134, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 13, - EndLine: 13, - StartPos: 132, - EndPos: 134, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 12, - EndLine: 13, - StartPos: 129, - EndPos: 132, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.T_LOGICAL_AND, - Value: []byte("and"), - Position: &position.Position{ - StartLine: 13, - EndLine: 13, - StartPos: 135, - EndPos: 138, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 13, - EndLine: 13, - StartPos: 134, - EndPos: 135, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 13, - EndLine: 13, - StartPos: 139, - EndPos: 141, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 13, - EndLine: 13, - StartPos: 139, - EndPos: 141, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 13, - EndLine: 13, - StartPos: 139, - EndPos: 141, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 13, - EndLine: 13, - StartPos: 138, - EndPos: 139, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 13, - EndLine: 13, - StartPos: 141, - EndPos: 142, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 14, - EndLine: 14, - StartPos: 145, - EndPos: 154, - }, - Expr: &ast.ExprBinaryLogicalOr{ - Position: &position.Position{ - StartLine: 14, - EndLine: 14, - StartPos: 145, - EndPos: 153, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 14, - EndLine: 14, - StartPos: 145, - EndPos: 147, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 14, - EndLine: 14, - StartPos: 145, - EndPos: 147, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 14, - EndLine: 14, - StartPos: 145, - EndPos: 147, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 13, - EndLine: 14, - StartPos: 142, - EndPos: 145, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.T_LOGICAL_OR, - Value: []byte("or"), - Position: &position.Position{ - StartLine: 14, - EndLine: 14, - StartPos: 148, - EndPos: 150, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 14, - EndLine: 14, - StartPos: 147, - EndPos: 148, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 14, - EndLine: 14, - StartPos: 151, - EndPos: 153, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 14, - EndLine: 14, - StartPos: 151, - EndPos: 153, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 14, - EndLine: 14, - StartPos: 151, - EndPos: 153, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 14, - EndLine: 14, - StartPos: 150, - EndPos: 151, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 14, - EndLine: 14, - StartPos: 153, - EndPos: 154, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 15, - EndLine: 15, - StartPos: 157, - EndPos: 167, - }, - Expr: &ast.ExprBinaryLogicalXor{ - Position: &position.Position{ - StartLine: 15, - EndLine: 15, - StartPos: 157, - EndPos: 166, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 15, - EndLine: 15, - StartPos: 157, - EndPos: 159, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 15, - EndLine: 15, - StartPos: 157, - EndPos: 159, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 15, - EndLine: 15, - StartPos: 157, - EndPos: 159, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 14, - EndLine: 15, - StartPos: 154, - EndPos: 157, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.T_LOGICAL_XOR, - Value: []byte("xor"), - Position: &position.Position{ - StartLine: 15, - EndLine: 15, - StartPos: 160, - EndPos: 163, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 15, - EndLine: 15, - StartPos: 159, - EndPos: 160, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 15, - EndLine: 15, - StartPos: 164, - EndPos: 166, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 15, - EndLine: 15, - StartPos: 164, - EndPos: 166, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 15, - EndLine: 15, - StartPos: 164, - EndPos: 166, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 15, - EndLine: 15, - StartPos: 163, - EndPos: 164, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 15, - EndLine: 15, - StartPos: 166, - EndPos: 167, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 16, - EndLine: 16, - StartPos: 170, - EndPos: 178, - }, - Expr: &ast.ExprBinaryMinus{ - Position: &position.Position{ - StartLine: 16, - EndLine: 16, - StartPos: 170, - EndPos: 177, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 16, - EndLine: 16, - StartPos: 170, - EndPos: 172, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 16, - EndLine: 16, - StartPos: 170, - EndPos: 172, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 16, - EndLine: 16, - StartPos: 170, - EndPos: 172, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 15, - EndLine: 16, - StartPos: 167, - EndPos: 170, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.ID(45), - Value: []byte("-"), - Position: &position.Position{ - StartLine: 16, - EndLine: 16, - StartPos: 173, - EndPos: 174, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 16, - EndLine: 16, - StartPos: 172, - EndPos: 173, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 16, - EndLine: 16, - StartPos: 175, - EndPos: 177, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 16, - EndLine: 16, - StartPos: 175, - EndPos: 177, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 16, - EndLine: 16, - StartPos: 175, - EndPos: 177, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 16, - EndLine: 16, - StartPos: 174, - EndPos: 175, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 16, - EndLine: 16, - StartPos: 177, - EndPos: 178, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 181, - EndPos: 189, - }, - Expr: &ast.ExprBinaryMod{ - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 181, - EndPos: 188, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 181, - EndPos: 183, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 181, - EndPos: 183, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 181, - EndPos: 183, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 16, - EndLine: 17, - StartPos: 178, - EndPos: 181, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.ID(37), - Value: []byte("%"), - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 184, - EndPos: 185, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 183, - EndPos: 184, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 186, - EndPos: 188, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 186, - EndPos: 188, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 186, - EndPos: 188, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 185, - EndPos: 186, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 17, - EndLine: 17, - StartPos: 188, - EndPos: 189, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 18, - EndLine: 18, - StartPos: 192, - EndPos: 200, - }, - Expr: &ast.ExprBinaryMul{ - Position: &position.Position{ - StartLine: 18, - EndLine: 18, - StartPos: 192, - EndPos: 199, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 18, - EndLine: 18, - StartPos: 192, - EndPos: 194, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 18, - EndLine: 18, - StartPos: 192, - EndPos: 194, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 18, - EndLine: 18, - StartPos: 192, - EndPos: 194, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 17, - EndLine: 18, - StartPos: 189, - EndPos: 192, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.ID(42), - Value: []byte("*"), - Position: &position.Position{ - StartLine: 18, - EndLine: 18, - StartPos: 195, - EndPos: 196, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 18, - EndLine: 18, - StartPos: 194, - EndPos: 195, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 18, - EndLine: 18, - StartPos: 197, - EndPos: 199, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 18, - EndLine: 18, - StartPos: 197, - EndPos: 199, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 18, - EndLine: 18, - StartPos: 197, - EndPos: 199, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 18, - EndLine: 18, - StartPos: 196, - EndPos: 197, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 18, - EndLine: 18, - StartPos: 199, - EndPos: 200, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 19, - EndLine: 19, - StartPos: 203, - EndPos: 212, - }, - Expr: &ast.ExprBinaryNotEqual{ - Position: &position.Position{ - StartLine: 19, - EndLine: 19, - StartPos: 203, - EndPos: 211, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 19, - EndLine: 19, - StartPos: 203, - EndPos: 205, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 19, - EndLine: 19, - StartPos: 203, - EndPos: 205, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 19, - EndLine: 19, - StartPos: 203, - EndPos: 205, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 18, - EndLine: 19, - StartPos: 200, - EndPos: 203, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.T_IS_NOT_EQUAL, - Value: []byte("!="), - Position: &position.Position{ - StartLine: 19, - EndLine: 19, - StartPos: 206, - EndPos: 208, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 19, - EndLine: 19, - StartPos: 205, - EndPos: 206, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 19, - EndLine: 19, - StartPos: 209, - EndPos: 211, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 19, - EndLine: 19, - StartPos: 209, - EndPos: 211, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 19, - EndLine: 19, - StartPos: 209, - EndPos: 211, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 19, - EndLine: 19, - StartPos: 208, - EndPos: 209, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 19, - EndLine: 19, - StartPos: 211, - EndPos: 212, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 20, - EndLine: 20, - StartPos: 215, - EndPos: 225, - }, - Expr: &ast.ExprBinaryNotIdentical{ - Position: &position.Position{ - StartLine: 20, - EndLine: 20, - StartPos: 215, - EndPos: 224, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 20, - EndLine: 20, - StartPos: 215, - EndPos: 217, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 20, - EndLine: 20, - StartPos: 215, - EndPos: 217, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 20, - EndLine: 20, - StartPos: 215, - EndPos: 217, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 19, - EndLine: 20, - StartPos: 212, - EndPos: 215, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.T_IS_NOT_IDENTICAL, - Value: []byte("!=="), - Position: &position.Position{ - StartLine: 20, - EndLine: 20, - StartPos: 218, - EndPos: 221, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 20, - EndLine: 20, - StartPos: 217, - EndPos: 218, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 20, - EndLine: 20, - StartPos: 222, - EndPos: 224, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 20, - EndLine: 20, - StartPos: 222, - EndPos: 224, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 20, - EndLine: 20, - StartPos: 222, - EndPos: 224, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 20, - EndLine: 20, - StartPos: 221, - EndPos: 222, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 20, - EndLine: 20, - StartPos: 224, - EndPos: 225, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 21, - EndLine: 21, - StartPos: 228, - EndPos: 236, - }, - Expr: &ast.ExprBinaryPlus{ - Position: &position.Position{ - StartLine: 21, - EndLine: 21, - StartPos: 228, - EndPos: 235, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 21, - EndLine: 21, - StartPos: 228, - EndPos: 230, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 21, - EndLine: 21, - StartPos: 228, - EndPos: 230, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 21, - EndLine: 21, - StartPos: 228, - EndPos: 230, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 20, - EndLine: 21, - StartPos: 225, - EndPos: 228, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.ID(43), - Value: []byte("+"), - Position: &position.Position{ - StartLine: 21, - EndLine: 21, - StartPos: 231, - EndPos: 232, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 21, - EndLine: 21, - StartPos: 230, - EndPos: 231, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 21, - EndLine: 21, - StartPos: 233, - EndPos: 235, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 21, - EndLine: 21, - StartPos: 233, - EndPos: 235, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 21, - EndLine: 21, - StartPos: 233, - EndPos: 235, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 21, - EndLine: 21, - StartPos: 232, - EndPos: 233, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 21, - EndLine: 21, - StartPos: 235, - EndPos: 236, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 22, - EndLine: 22, - StartPos: 239, - EndPos: 248, - }, - Expr: &ast.ExprBinaryPow{ - Position: &position.Position{ - StartLine: 22, - EndLine: 22, - StartPos: 239, - EndPos: 247, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 22, - EndLine: 22, - StartPos: 239, - EndPos: 241, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 22, - EndLine: 22, - StartPos: 239, - EndPos: 241, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 22, - EndLine: 22, - StartPos: 239, - EndPos: 241, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 21, - EndLine: 22, - StartPos: 236, - EndPos: 239, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.T_POW, - Value: []byte("**"), - Position: &position.Position{ - StartLine: 22, - EndLine: 22, - StartPos: 242, - EndPos: 244, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 22, - EndLine: 22, - StartPos: 241, - EndPos: 242, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 22, - EndLine: 22, - StartPos: 245, - EndPos: 247, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 22, - EndLine: 22, - StartPos: 245, - EndPos: 247, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 22, - EndLine: 22, - StartPos: 245, - EndPos: 247, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 22, - EndLine: 22, - StartPos: 244, - EndPos: 245, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 22, - EndLine: 22, - StartPos: 247, - EndPos: 248, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 23, - EndLine: 23, - StartPos: 251, - EndPos: 260, - }, - Expr: &ast.ExprBinaryShiftLeft{ - Position: &position.Position{ - StartLine: 23, - EndLine: 23, - StartPos: 251, - EndPos: 259, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 23, - EndLine: 23, - StartPos: 251, - EndPos: 253, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 23, - EndLine: 23, - StartPos: 251, - EndPos: 253, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 23, - EndLine: 23, - StartPos: 251, - EndPos: 253, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 22, - EndLine: 23, - StartPos: 248, - EndPos: 251, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.T_SL, - Value: []byte("<<"), - Position: &position.Position{ - StartLine: 23, - EndLine: 23, - StartPos: 254, - EndPos: 256, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 23, - EndLine: 23, - StartPos: 253, - EndPos: 254, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 23, - EndLine: 23, - StartPos: 257, - EndPos: 259, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 23, - EndLine: 23, - StartPos: 257, - EndPos: 259, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 23, - EndLine: 23, - StartPos: 257, - EndPos: 259, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 23, - EndLine: 23, - StartPos: 256, - EndPos: 257, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 23, - EndLine: 23, - StartPos: 259, - EndPos: 260, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 24, - EndLine: 24, - StartPos: 263, - EndPos: 272, - }, - Expr: &ast.ExprBinaryShiftRight{ - Position: &position.Position{ - StartLine: 24, - EndLine: 24, - StartPos: 263, - EndPos: 271, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 24, - EndLine: 24, - StartPos: 263, - EndPos: 265, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 24, - EndLine: 24, - StartPos: 263, - EndPos: 265, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 24, - EndLine: 24, - StartPos: 263, - EndPos: 265, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 23, - EndLine: 24, - StartPos: 260, - EndPos: 263, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.T_SR, - Value: []byte(">>"), - Position: &position.Position{ - StartLine: 24, - EndLine: 24, - StartPos: 266, - EndPos: 268, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 24, - EndLine: 24, - StartPos: 265, - EndPos: 266, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 24, - EndLine: 24, - StartPos: 269, - EndPos: 271, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 24, - EndLine: 24, - StartPos: 269, - EndPos: 271, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 24, - EndLine: 24, - StartPos: 269, - EndPos: 271, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 24, - EndLine: 24, - StartPos: 268, - EndPos: 269, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 24, - EndLine: 24, - StartPos: 271, - EndPos: 272, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 25, - EndLine: 25, - StartPos: 275, - EndPos: 284, - }, - Expr: &ast.ExprBinarySmallerOrEqual{ - Position: &position.Position{ - StartLine: 25, - EndLine: 25, - StartPos: 275, - EndPos: 283, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 25, - EndLine: 25, - StartPos: 275, - EndPos: 277, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 25, - EndLine: 25, - StartPos: 275, - EndPos: 277, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 25, - EndLine: 25, - StartPos: 275, - EndPos: 277, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 24, - EndLine: 25, - StartPos: 272, - EndPos: 275, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.T_IS_SMALLER_OR_EQUAL, - Value: []byte("<="), - Position: &position.Position{ - StartLine: 25, - EndLine: 25, - StartPos: 278, - EndPos: 280, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 25, - EndLine: 25, - StartPos: 277, - EndPos: 278, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 25, - EndLine: 25, - StartPos: 281, - EndPos: 283, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 25, - EndLine: 25, - StartPos: 281, - EndPos: 283, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 25, - EndLine: 25, - StartPos: 281, - EndPos: 283, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 25, - EndLine: 25, - StartPos: 280, - EndPos: 281, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 25, - EndLine: 25, - StartPos: 283, - EndPos: 284, - }, - }, - }, - &ast.StmtExpression{ - Position: &position.Position{ - StartLine: 26, - EndLine: 26, - StartPos: 287, - EndPos: 295, - }, - Expr: &ast.ExprBinarySmaller{ - Position: &position.Position{ - StartLine: 26, - EndLine: 26, - StartPos: 287, - EndPos: 294, - }, - Left: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 26, - EndLine: 26, - StartPos: 287, - EndPos: 289, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 26, - EndLine: 26, - StartPos: 287, - EndPos: 289, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$a"), - Position: &position.Position{ - StartLine: 26, - EndLine: 26, - StartPos: 287, - EndPos: 289, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte("\n\t\t"), - Position: &position.Position{ - StartLine: 25, - EndLine: 26, - StartPos: 284, - EndPos: 287, - }, - }, - }, - }, - Value: []byte("$a"), - }, - }, - OpTkn: &token.Token{ - ID: token.ID(60), - Value: []byte("<"), - Position: &position.Position{ - StartLine: 26, - EndLine: 26, - StartPos: 290, - EndPos: 291, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 26, - EndLine: 26, - StartPos: 289, - EndPos: 290, - }, - }, - }, - }, - Right: &ast.ExprVariable{ - Position: &position.Position{ - StartLine: 26, - EndLine: 26, - StartPos: 292, - EndPos: 294, - }, - Name: &ast.Identifier{ - Position: &position.Position{ - StartLine: 26, - EndLine: 26, - StartPos: 292, - EndPos: 294, - }, - IdentifierTkn: &token.Token{ - ID: token.T_VARIABLE, - Value: []byte("$b"), - Position: &position.Position{ - StartLine: 26, - EndLine: 26, - StartPos: 292, - EndPos: 294, - }, - FreeFloating: []*token.Token{ - { - ID: token.T_WHITESPACE, - Value: []byte(" "), - Position: &position.Position{ - StartLine: 26, - EndLine: 26, - StartPos: 291, - EndPos: 292, - }, - }, - }, - }, - Value: []byte("$b"), - }, - }, - }, - SemiColonTkn: &token.Token{ - ID: token.ID(59), - Value: []byte(";"), - Position: &position.Position{ - StartLine: 26, - EndLine: 26, - StartPos: 294, - EndPos: 295, - }, - }, - }, - }, - EndTkn: &token.Token{}, - } - - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - actual := php5parser.GetRootNode() - assert.DeepEqual(t, expected, actual) -} - -// expr cast - -func TestExprCast_Array(t *testing.T) { - src := `w4VQnJ)O7x{BIJwIqf|oOLVMhS@KA9diUe@XlSZrvrUoQB;}Yp z?YXPDjk%_I-}hVJI-r26f=oG1B0VAshjsYQCoBLTemJ^+{$e@$c6qkEJi1=K7=3dy z`u6tq z<>mS1)iy1!&%a-uy?5vC28hSao$H&6<>=<-+0Cm%?g8r8$Je93+}XLgxf+c~t~)zt z?)_zsuOQwHP0?3Dm*y2|LES+z>I0a8eNJ@vxMipXEwnsVfpOe z9v=FPk`0GhB*_m;LG8|$6xv|3EMwD zISfRfB|Ja<^6~w{hff}dVG^RBhEwx|pg3*~=LyHB2Zvui^~MRu!>9iqn&#L=YRnUQ zpFVti@6jV~ozOe{?CFz#3u7eozH|c36J`$~i3j%{JPE2hPw4&e(UVW^1>Kk@O}ufyRr3-NR?;Y(nnf^Dhnqz>9?5XZIc*K8OAN0&?u*Co~~X&w_+3G9;hg zb0f4!NIrZFz5O(5-6ElS@IMYIJpuZJ=)=#ycy#dj!Q(@}l#qS$$^UV1|M2;fFAkpG zI}A$G>?gz@Joyr4=lQ*-PVQzu;s5C2Gb2i~pU_9sdxn0qpU}S#E=B{^?6)v~eqS&* z`z_q#`Go!F2Zx_Mfr$zo67m$*csk)u8yMOqtUq;Q(u@#2=U+vIPjF5e*FCYmro!4`}0rW0uD?hnsFkIU1U2Oze*(f;@-W_@BRD3 z&!0a&_}4EVJUQfkXq4zh2bR1-QzdFWe&!6S5~UtIG<9gIL>e@FcJKvUR20c7QRm>% zqlaHSdl&$(5^WCt6tuai5=ovO{GVSw47R$d5;?;8JsjKR$%SK6izv6AAp% z|A^NT=6(&%(Wp`<+-ZjHA@O#U`OBTOH0O>@ee> z?i~glY!ZfFJbiKq({teSCM>^z$%*qOED^?q!4r~jx8YnuQOG?1^y!lznoYtJxIc#% z4WQ@Inwh!mTEf>Nm%Lv>S;j8El<*FgH5)SF{>hUkkMdp#cR8B;Qo{fKlY5U2o`qnm znIs}e*`9s&@CzfwB$49rlY=N4S#9$C=lOvne!f;Teu;NIhCIA)0wekmG!w5D9TyL>ju%AmNV&87;GDF7(VVCON>xXP?8LAHbUwbeboLK$|}z0!5_K zZi7_yhoej6eaPL;j$SRV0QOgVdwX9a|2sMR7U|!6|Fk@N@!kj6QP!!we|mlPy>?sInadGP~ zg~>jS2gl(!g~Z`R5eSEKS@;{y^aZ`)atd|BiLL-QT#8|>A19(AgiR-7;2KVOxax-p zQp0WtLCd4uka;{Ab=Ob8qlI361|}q&Nr7fKf$%cyDX0wl3=AH+b>xAcXV@6_6)c8* zMO9(n0>g0N;b1sa5E%AD=ogPdz~{#b^TGjwyRZin6ZTRd7aLjl<}Fju7S3d$S~!ye zv~VH|%fgu$jD_PAf`t?A^TS~bx5BXnS>YgsR^dbzQ27}Tqr8g;PvJO*OyM{Wlza#e zkHT>bio&tGjv>r^}ZNR8V;hpzndf4uk4w)207-@k<4pTh4S!tY1n_xrL z*AhV*su1gMWlW}vd1}J@Cf7&b;0A|C>L2cv!d z;zVWV+ovaLzd!k4)YKC;*`N9@dn2n3{m1(pVYc{SRM*_o)v<=-tm7tJZEVD5j?T@@ z8&0&xh7&d%Z!uxDua*tqsR0x^HJn_#23kZ7qxFqBw*H(x^p7w_)T$ZLAZiA@Mvo9z zi+Q+O*M!Irce2zX%h=FmL+h+Ppj(SVMm2RIO~;}iug=(RTmwboGOlO71M1ls03|fh zubOFk^;-<;NAgex>bVWN?R=!V^^=rr4W~1^o=fVQ{eVpa7zDx85uFA^NwrGUu=z-< z@z(uF4eMtjv*moEhV_#GZ9CuGrM_MWzb%9r6<}cmc8(iYpRwr&h|)~^2a?!M#)5DP z%xqU;7A3fu8o@C9WGr2=mSUjPSVE+kM51j#o=2q{PvV%iYqQ5O=TfiEF$Mit$}}cS zw%dY!VbIfL%$zuru}e|2khDw1vdgYwlghO>8K!#bA~C7Cw`ef4?ArpCF6==IY>&`5 zE|XxsdKfjCnuPUTmS_Zj0pHRRev)qG7Gp` z%Z^c?XM+^IUO1^|2LG0dUduAte3IX-`#E=Jb8&vlex^h=-w;K|9hP7qX7eG6j+-#C zpXtJOh6T52Vn1odmWBm)alGGx@>sf!dgd}Z$9Q*k=qxJ347?vlUd+Y&8d5N>D0lGI zzE}I+xS<;8axVM}S(ybDLsOL3h>8uXJq@cp4Qq&MSnd{G8{%a;NIIGhYEL@Iy`sIe zyrPcHqvW#rudk$RGtA%c^kPF(yPz7w!|?+^&G|=HW61Qa5W>InkY_z%|mQK z+W<)kE~TcJ0e_t1MGg!bI;vo@6rUj;;}mc@77W&CUV*@)TBNSgQ!W=BYw?*v(m-QI zLSe#@*=NFGraT023xZQYl58`EBLl$fu#mYY*b5sPAUEI%4l(4I7%bol0Uvj$p;N?$ zxXKZ*Gq12SW7pZ3vvOoQHxLPjHRdN>F-k@9E!3A3n8Mj$1F)uqpsp~RK`Yxm6}vde z0`3$2aCuIuO%Z-zLv-K+;HYr5p&~B`2zZU-IcFKGjk*}XIM-0R=WtY*isC%wuoHMt zL^TASdsEKGs1|(WEEJ&`O&=j<7YBJd<4F(^7^ok*FpwNgDP=QGRm;oQJg&%zilJ34 zDI*$V*Z^#BZbJUG(Vs%WFaf}sQnscuwu$J^C=P;n0>a=R+Fe>3VTgb zj(KjpPx>yXoC{L1CNoF_5Shv#5t#6@M5iWd0(L?1UdSg?1T657Fi77B_Lu@)O9Bzb zV^oYcp+OS|ASHy1M8GASWkLa@G3?x^L*@u%%0bPm^_W7|l3LR!ijG8pS(6P@n@mw% z#z;qCc!V1VBM-*Zrnvwm$TLE#bF~GaI?0qscvM7nN~MuZj}cQqYDiETqp>+lPB=z{ zhYe}Fz_3%Q&y+Tzq7l<(DnKfluG*}at^nUk(nfs86uB{3GNy>vv<6ea0Bc8(C-gi< zOpPrgL;)R_GCiJ4_htDgjEy9j>}a7eBcEmxGUZ_nQJpa)TafZbWcekMts*$VqF~gS zY*NFpQw*#~g9QyxC3_jssANcau91vY)H|K5X)`ME&T!#aNi`AHNo>GMqEXS}Odt*D zjLiZm^=MA&Gr|q$NQk+DCPvCo1Ryl0A(5cX#eFJ+z+Q0Dh76loBtQ^}Pep-k5cQ3w z#J-{3z`b&8kVhD{6BA^b>M2KUWcdM$w1f7(rUH?bylg?Zh*uL|o}x*bkfx$nBazxC zQlgDH@`m`;w3`~Hp(!^O2)%tdN{u006yVND`59eXL)&A_A;lWGM$wlVha39b$a$$D zBc_I^Pbi=j@vli8rg3mLyg=2M!+Jm=sRt86F(Jupk2BjIXVC~|<&*(cbS=yffFW_G zjB$R41Y^q*>)c$nbxs*rP?8zkf)kvNT_%um0ER#MLQ$}i*w^&RqF^IE7Kcc3rq9ON zO7`4s(48GYV+v0xWgWq(#yP1ElDKGtXeWsu)u$pzGC~t^kldb93&f_efGDr%99wY)khCD5jlB3&RO8mf2=hr=!aDor($h(?v4 zaTW<49kF;9$UGw(<(DT6v|5%+nmkeP4Ia_80!EE9q4j1$rOXbF343Z?OJR}E!nY}8 zrjcF{Axei0Nc+&*o3h0e1Oj9BsSQ&~%YtTiLg5snfZ~GIaZZ*@sV-EOxlFu_5ygK_ zv(HQ9)l9yNGGNA2-N z;7eMz2-cn;Qln;OZYgY3S-J3;%nGfNV5uRMWFdt@(n7mGC;Y+kVJwN-jIuQ&(6b<0 z7-C8}!n$T`NLaC_v3QRCOdNxh!E;Fn3CWCNKO<^0&OB3aD;G{BnUWxtVx1WkT;ZQ+ zFr~qsQs1Shrq-rr0U_{Es1iZR?M$ILV;w_?`Y%AHloqVk0{S|hDF~5hrnUflGnzlJLbS{$*dO|9R%S;|YQll8bh)haTK;^GybVv;{6Y|9c zzM@`MbY~5fbxu;wc252+(Eua;;8I{Dl@E|Y6RL)IGoyZpylErp<<$U~8dmfaH7Scg zo6w82B$*tic~6ruhJ-Vcl~oSR1<1z4I?3x;wubG*{5jQC?c~N6ea=UTn-i-!ot_vyr-aYRR1@Sm z1&h0c6MVp?p?8q8T2RX8yeM=Q<{~6v3JnR)oXBhF1;tuOEhrz_L$L#J&6QLF;yLX? z@_Ukx37y}Z25QP~Q^+oQtkWf!VX>6c5&MO@OsI6mfIe9(( zd4>YDkgC!|3kn{h17%{y;9PB{RKclYGLet6Ln{Q=j(G_IY85zVtTxj?L1TJAXs3is z_JuZ}ftRBr25Pmeq;eHD8I#>?ryEn;;okyw5>}O57qT--|C|9@L%E!iWHvMBn=ojY zK$2PQV{b*%gl<9M=YWm$Khh-31O5>&lRMguiUQAyCo~3=RWU4I$Z9A@O_W{G;w}_6 zS}2Kra}J%F%)u|QoW@~aVIG|;8wq}BDy9`1aQl^e*x)1ug_T_xAe|+aa{@e8(u6n+)6mNFk!83Mm?TGi!cR=STSXo%1x1}m6B6-V-TX)7mdbprs83xf*&=Dt)ysaJ0SdsSp&Gn(+e~NmmT8iUEfNiGrcDZ|dhF7n83`e?^MZZ*~6ogFryozyQHE~uS2m@`q5 zI)#Q@G6KJ}I%h-PqY>xUcQ%IFiu3K<00cQ~bRb}1?w zR0v}(sPd^{Mb=5t1X5HrGzKlAttJ3qiK;Xhc1o$9Qpl$i@(c!eia^BdBpXaJvfCw1 z2(w`|uhyn!&R^_QZrUS;&Xuxe6$`cWSEK8uK z3?rt@eC#?~lLY#utgm zRy433CMKfc#F;USDSMlBo*|%7qmJ=2x8>ushQOgIA`ByfHq~^glQVkV8NKd|UUx=A zIa6drdo-h(&Xf(!Xi;Z02s3)!87}L`1CGSjES@+C2deFe;TX`GOoZ>@OHdYI2X@(H6tUup)DWk`eXS)ZJ(pFS}sNW)3DXI}=5K zJ4|dA^d3}htACJv_+u8L)ya%{MOBEMCS!6D|0~x57Rq`8v4VVtn3MslHD_k7Jq@Em z3$D?xF$PuRshhGB2Tjwa*#MX>?g=?ZR{kCD;+k2 zc{&P<4t+KnbVd?rtAH1~iYn3AY&b5^M#Kqh#{uVT`K7g1i$)FOmu3qF3j?^-va#T5 z;0nkA{7uOyrt!E&DaH?L1!}3u$wSr4DcCqIi@`xn2q0xl!f>9{N84^OGlK;=%Me-> zGyu=3k^C7X9fC&4AZI`}6EvI?>O{q;jWY=g^V-hmtLBN8-#*$$EKM5JC zG#DGBV5n{(%lom}IspT5gcv9WP5K87;!$F4-B|}BY1U1INQmJnwIO=+>v2rWrLgYpY!sH4Y zMqree8z}~Ukn|NR6`BVb5;;4plnary{`sL(3s)Vkh*&0EsBQs$$d&;p(j*&2s4^1; zmyHuqxN4eZ#Y&lgMKeVvzy##(ki$g*;{oIgC&$c%Vw$FVb zT5zt&I+HG#zRX5(J-%D1AYkkiMp`Rikdh!@E40N3xslTKF(ZcP2-_kS{9raxTf~qu zNWwrX?qKSoOj4RD##L}8Xr!V8h#TybA(x?OMC#gRuxz-TixTQBplGsF8YTKWPMpb- zyE}*pnJ-zwZ8$7!gS0%9^+;LvU4+)R&T3xVtb{X{P`Y zQSOr@_JJV5Zvg@9yT41ODoK)!p8>}9rjOXO{}d#k=OI;(BxNJ@Ns>oY2nCH+Hhw8d z2(=|hkSLIy$xeqPWs^lPS9VIQx-XZK#ONtW5+~7(;Mlc8lFZ{#kTl&|N%}=1bOSb- zB!ShoNk!OXj|kmHbnb+5%6CapGD)=6CTeR!CxjTeICgtIpRZez+$6E`1!-E1&D&u6 zagcvM^jZA4xC}u`5jgH3VU`t1%A|I!B(WU?32F{Mv>^yb)2%}A1?oR<5`<&?BufNL zF*tsC0qVjtJ?@Pmq}veN>2Pl}ETGkDrdM`d4Z^$K8))`-7KW3+7Rt7BIno|-)Dwhv z_%_g*o~*NIAVxaPCFz-SLvhF$Zo0!Te1VE2v$F|aR4`jv;<3l`&(K{88W>T8nM;n^T1@1pHg7s!Nw>XC;xIQ~b8wik@+k|4=a zgi>;^AiWE=p=n8w+DG3tW-FB=^PdvQb4M0``BsUcs z0;G45wgon(2whtzWb0ZMAR)tGy3!*^6qCPNtSxzh+ntB1a9>UGU962%1Gi4Z>@CXP zEnz4RdnCpitz6DTiNXRoGBC`&_Z1}HcC0<+8r80nq=4%aB;D!_`NWD%GRqp0e;B%+ z?EhVH+tXf&%!<6YAQ?Hc%d3LKCdk>;rcaRGRkk~8NEuy0#I6vD1t{n!7YqE|R<TpD0o=FUT6X)D4@pH`$z|xlEDjrASfH zES*_%lMRY%Z48?HhOM1RfR~cwH~xS5+qHm;K5fCcqG)@a7j@YXoR$ za%wKjNrIE**(ZdS_9NTA1X3AxU!5KoFe2 zr`Xv^lMoClz1CTQ`N3Cpku(<^U0?64`XlEETsvlt7qC+bPJg_NrkPVPxYAM`y*DLu z3O<9{ajA}Hau7E^&`aLMxBvdgMLeOMY_hfNxrJDw;q#0k z3>^|p=-ulj)XpJ6zecwWb+yVE#k1Lxs+><5Ic&xjpH{CUjNtPZ4xd2;h?Ns8GRddR zFUEZ+ldboRXRt$iOb$g=f@ZZi<=SM<+&Y6r00$h-$IADAeeqS!pps7A4C;)qIv7OD zz?yQdMs2caL0L|om3=|v<}SaQG035w^Pz=ImD&tayQD;IV1BLMhztTTi-q<^iIPFT z0)NzEP}>_#c|W0pLBB441Q-W;qg;gwsR|5|;B9b6&>&b2M1ou;4iI`Akqz$>k9N_< zAY_FR-x^gR-&gl5G=%-cp=^X@=Jo3k&CvmnLp)kPwiE<8G_-=JA~1?l5tAkPsYAVpFcVwr|6L*MIFh3Q=sB7ybQsqJ~Lj2bFLAFBUFsTj{2ne4A@doCxv z$r_L`7$BBP17CU~gO0bPBCX>Z`}HpfUBM=U0JHn6;mWt9;&fQOpJSN6A`~r<3h>Qv zteZ zH0$4eM+7xid<(2FL@#zN5sWX1gjv%ouvxw?Ka++-mN~f4BVR)1(9S6UT~si@?Ms!d zw?*2exD78EBnTi%$6_+9I7Z{}hDf7`Pag*RK8G=$bf9Kwntidp&}UIbdZia-H zmc>zSS7G9?L|Sj!YrTrI4{L}nWRqWZq;9QfPf(O>c<0m_l`5R(ms` z;tiqglp?$flcN^A;rK8JMx!Q11jrqwcbR+NVA1UC7gtoE^I&uz%G2$s=zt{KaI~M60H@@NevA}!Ye*) z0kC>FQzM1)owuYcVbOGwr~rE(dPpdf(cZ)nk_qEU`nD7ubm>tS18hP!-%X1?kX^Qixn{@lx5mSQalDcPI+wP0O=tebpgvo+-7 z#ERufCrb8OFu`9Ym|ZTm3+399OSLI^#;nvR z|CCb~%Y9nA=AU@#Qw9i#Cpxeg5aj-N$YIPU?U1gOX5Fg5iAlE7SFB|LD+dtfuF6H* zA!k6WCx6zEtjfN9lnR@wU2t-cC)F-;GWdQu8qU5WyQm6Vn15%aB-1St-NoQ7k(~_H z+t=L$sW6BzJYa{e9C?h7`DiB%$r6cnt z5^olRu28zPYQ2;e9-Ov}KsP4k?BW^53T7RoF2x`+qXWt{kr*Z|pK9@m%JC+}=h-^Q z45R~7O7I37=p!y386GY<-a>CQeE0gipw!{e+Ldbv$!Tyg`;#Y$x%3DL(Op zHIVdHnh9$-E5l>F?H0#s{3^VU&Zh60pk19<0o0+h3*~@1S2oztzjb-0Y-AGNeLvw# zr(%l!FqTL9CVDtE#k&ULq+(#rkA2!8`us7-1{Aolli3z=27z|C!jSm9II#2a z)gbGWkK+C9a?OHUF`xyjy5p$NbB19QR_asT74NrIw1)W%741rXBET}n9npwuIHwOV zFZe1cZ^UJ46+O&!pUe3DG`I}iCAq^H``9_xmQMNDOE|mcr#*GqR3@GGPQq!Gfc5oe zJAvvV-&7E;R-CuanlE@FT;!L1X8P1CzKjrO)%PRwW(yYCLzi8$40S0C0=tEMF%eR{ zPj@toB{eQIvHp!E{I6~ zpsg7$PA`WW8X9@ZURvBy(emdgxw6eCGG7xGs^&GFqKVabqOhIr8sBdQAF)n`q`?L= z`z{^`c6G2l9@h5$TC{E^EW~Nc#fk9%pRmP6LnOEM;WBC-U>LtSJ0fQp zz2H;pNkBrg3R(i?Bx&_o&KU(s-(T0B4R4s%{1B(@YRd=NC^>JmC07Vn8K<$ZAsLf+ zQe&mHoW)v3W;&MCds9Az@a1^r(Oix^kcHwtW{6gkp|T4d)NxA?r|puPF$F_V%bE~k z^}}gOK-3}FnWQM=DIu7tJcln00}y2!1;lYyy&R$9SD=gQ_>dnx!~_gzUl}8mV*-;V z_nvg|6~A`lCyWDvEt#M=wJ4JXBi@Zvn@uS1?G_B3Ns%x<^3?VEX#vZE&m>N@G9z?^ z=?7VGRG|y&x%SJ^h)P=7u-q!c_AWTRfUIsA>XcMy*moZ<=|NxxSBG)76SS6$!-+426iH zw_q8dGd?}6fm9vY&4Sxr4GNTUyyjYeX^dN=QAyI_HVTPxt(VW ztCE=wFhFj1Wl3uqi77)9eX||6H8CMh?ecz|HnWOv*Q>MWPZ5Tt>kY%38uvgVooi-% z1tUyu^u_UpX^K9aJ!i?lDCrogCTejwI~Q=;|tJxC&`A z&P!dV9l(`D8ShIYJRZ|GNS|e=b2R~`diA2&tE8)Xur@dOvx>Elq_nON46tWoW{zP> zeE>Y{BZx_`J4l`SJXS8B_(ZPde~8-{n$JlKz)|r|kT&WvudPbJ8s)swJ+7JyTk+V4 z{4b69Zn@#*{Le&bHpb#!VvZ;6jQT*#p{AZ$e`cV8%$S1Y*ut zpY3L@*z$eEAhG3wOz3hRh1)2G?ZMb$N(Ub>7oC7(JO$s2NqeoUqA|JC+yc)V1WvB5 zVQA9p>}lr4p_tJ4BSr2uuE07Gd1(O0t3uVKVF=JUUPJM z4nMEyG6h>;7EGKPfUr2=jUMmPPwLPlQd~snjEW4iW=d5ku(V0y2XQi*vE*76Gugy-1?`;t1U4zx|EtV&zuK7Zx-}d%&hEu z1iT+uxEC~^CmQR8@ijbh>|8Y|Ww{gU{@zztkEFU$n;uIdz#> z(Hi0y{n&-`vlxpr8s2VJfkT)?U8qk$0=K7xx4yuxLpv#~+MtG- zLU*_KRV7hJdHsFX7m4^jk}l4tg;iE+(^O{dF6XSovuM$wsc4fqme3Y0bhP{2ewi6}-HTo+00mmxX-#zc`DlT1oy@rU6k z?qpN=GoEE9{6hQpXErqDA~1TyPm&~@q<)ecZpaa(DPRNbDgy*Xn!pIVR7m{iAF$;g zWj6aGktieF@K;8_ECI!znh68o8+(q0u^lw1++ebBQ=OpdzMjMqa7f4`N)(m!H>TxC z8)ic4%Q@}+M;uftLCYfZqUUlkHB<=*0uaid{xAWxjP(!wk#hFO>;Ynu{V~AdAH8Gt z2TzN6_(zrVKb4#TiT_#|-K-*-(G;iG^fC@s(7a8_ma-5>jq- zKM#`~cG8+$kfUfN}{P)KSbt);Ra zATV}p0PNtuoP`qvoj_L%W39DSZ_KT>fp&I?Vc6Raur;j8ts{oExPbqFl;$wBcCz3C znd#TCkMTITfr?{HZ({&DJCx6IDq1_+8u0Y4`7s8^p%Dr@yo_RM7$#Y>v1?mc`ySt8H!kz;K+xao2yBT2d#y+~*6l&)@!Kv5}EwGQl zf{J23{EwH7O1K;#$Awl4>m6twyJ9CNuxAt+*{0W+VIp2ebAvpG8QP%fGC}wGc)@TZ zXr@0AY;|G_%tAHsJK}h z!3PHCX~Q06$RCvJkf0z4hiT*atR&aQ6efpcv}4>9g6r&UI?HHG8|kI zAU0>`bTdU|Eut(Gw6Y6Qgy0XIn2e_OR;yH|K!BLRDqA&L6Ae+HY5zD0jjC^8HzrWE zl@!gBa2-;XQ$kBlFwc{gZ1KwIwbO{Yd8o}N*Wv~gxxnaB_WqNgDFy`1}aK% z+C&JO+vySzF*USgB7kBmVnkk3e}aLW1U;B|1QaMyy3CD;$l_6^U@FsC6VpWWl@zmd zqctf~K`lKo6+<&ZB{MGclIB4{1qG*fy~G|zGRcZ(O$XUVc8+DQT@}=6`gI@;FI&$>ttK>bQ$-hyHb70zSX|@q z)b|Man_(g^O8*kQq$xB7Ks7>fGHl2ZKi)O1BPT6!CoEJy(?RM2BpV)BEeI_+Z@4Rp z5OdAR&_O02gjs;8L_=%HB!m|qLLGm=Pw zRS2;`NV}*AQ9X0*h$p49Jknh|Eg{n52GBkt!J2T;f51a>rbvQvMh~~kk{193jnrD? zp|Mr5_jmC&H0-c@m)sOvmsw?rRD07@~R3AVV2f)t2lt=UClzzst;(*VsK z6jWqFj7TQ3P=~Fgj`A4X0~L%io7OzG zvjZ=aS0Nvc``SgOH9;F?qq6$M`nE$c1D~aRUpOYhb1d&UT%z{WV%X_WQGDQcxMW*birJrlZc=y zbC8ahc9^yp=7d0UOq$yW@3KJ^FpE| zwVAlpa{z7iBm~u&*s-^L7c)>83tfW7sRqB|N(itN$t;XQ;FRqUO&1We@+KN&Ddiuu z4&oBj2!bQgkYJmQ;=NKM7bO!`i6HT$Sz}`r6^VvK6b|Z6Cnqxjy+I!gP2=zAh~c`- zTaOR`3Lx*~?Q*38jtzI}6)hnZO08|#1A(Wy=+1-^ePrfjA;%KjOm~B=7p#;jlN7-j zb|qmZOWwdm1;;76h_;GcCCS*@<{`9VI_(Z`4hR2)7QmGf8v> z6-R!R@d;?gb0LZqyKvdO85N#p$c`{5b%%_>d7}_^bPLzUAiBn4?FH-=Ix7|-0%UR! z62VTNh ztpSHop;6pt9l;E!DU9_Yb%nOd3>JAPE=g1*HaOxmk^_?tNRSr*A1q(C3V;vBe;Gc2I0F|Ls4)pNwX=n4v}G;T}o2s$MJ&gI84JX zmjWt7Oy*hymxM@*bcF1d(=@D2R`hv#XrZE=t{93pG(FtLpT0dn0oZR7`7;_55YSj*W^=7!dz! z1}FR_z*+&W<@W(#!CbS>outzGO&DBG7);=pi|Dy>1Vd?FYr;_(UEtTCp~#a6dXTwc z9X4KaKxvzB(q==;aGu8vjXB4p5wQO(9nh(V9xT(@1>Gu$q9n;Q4)8kbVAf2x>>+)O zD;49@zB0(bv6eMaT9i*Q<|#!-i+;5%S`miTN--t%n~5XUP@bKppW_7$Y#7QXZNwGO zNGMbssG?5k36zSuRB@<^>ZE5xEBe6-T7;V@9GB0tV#6+^R7LfvSV*pz;a19Z(G28+ z8?znJHs7zffCIzoe^{`BVMOvoYFuS>M_WP`@~W2Hc}I5lm#$PS_f#M*pd`_-oS7St z(4Gw;g)91^ik3D!QOPa}QPH-cx7JHJY})i{5U@e#@o6ylvp&^ zXbjHqpJ3`SZsmy99j6hsGKdNz>t-B-O6x-|;<*NH=<#Y&Dng<8*;Ws$*VIiteoz0V ziEWJ5R(ZCA#`%LI!LE{E|5ZLo66@{>C)GWXDuAjNpJYR46Dr~}Qt1wgiX?I~5-tla zNuZi`IU57w3~cO8vf*)J;LoY~S0xFQrPrpWD%-P2eC_~-1wHhflI&I$j9GfG4cbg# zZ(%B#0qIfKhMuNjq|q?aPzwqp^`@bY;6V>`Xs9!84fQx4T8jSyqSj@iH9>f7V#I>G z9z~f@25LzFEp$yY$wzU;Lfm6i^M-QH=Y$}9*h7y{{DSj(B#yql^|BsO$i zc8T$_?WyiVcxx%xh`}H+roN9=GEjM*;5OE@OXv?69Vi)ih@ILMR$u zy=|bTF|N7xEm^<_7Elq6Ue z>JlEiL_1|tmhlDitCz`&3)WYQ(W%|eW1J5DAP&y)eOjTZu#aIRu~f0q+UkvTj?6gd zH!kVr1{K$-SIma_${1`wNxZED6IaAb)jPeSNYCgskIXqatE5Y$3kEPw?--&0q*sL-1?=RRvKqjt;m&Po>A?Hcs<- zREV*dh@b+E^fH_<08?^3p{U2h^x?CH@d2MghQLy&8WIJ~>Ek$lkO%(o5Y7nfq(9)1 z)><&y(XC6H#JBX9rdl|oH*NV9M+ZK`M2G^fhfN!z&Z%e%Rg4KJl9_CUAs9*P9b&bM z8KqRId_{{}>2`t5Rq4KIQ2X#&M>MvJe0za&(WRbZfvcQVuU1n_NQUl2a~g_6>;2GZ zGY-_}fLeONF=)vuhRSR}i>3Dw;((L!SwXhNd{lD#ueU9dN1Vl?cFaiDjA>p(apuo? z3|8HRuA63)<&q6g4k$@MFz}xm>Wgw4!=mN@7kRS|D8FYqNC|i_$Kod%|w1YfB zGb$5}yGbpmNv&e^puhs7$>pIT9lX31MvNIAqYYX#CEXZNF)SKVAXlX zKw~{46&{&F`>-kN{%~|U`rXaVvzu3k zXn5B^)llzW1z_(I@i5F623#?Y&b=R|2qQc?KmY#dyXDb~_w7V`gom##PC0y_n7{y( z0SuAw`1{dUH#ZN@POeXmPM=*L9e@Aq1lC}S>pX0z_A37eNpIu#}?Wd8Y7rzrsCmV0Ija4x~g2|H)}X!PFb_vizg z;Y1=&uQ+u9+DD_;XUiWimdDr27wQuQ;{7-cjKB^|&Efgz)zS6wccV{EuFlUs7+t;o z7S`)}baXv>b&lVc=dUkEaV$Z5wRdMHp25_wj=o>M{}ta3tT3zzBU8s@udcp3d3k;G z&FOL!yMJ>8YlN=$e&Me~kFSlEXu~Vcmp`ymmp16a?|<*qJ!2;g`+N5I!{{uE=NZHk zcIXJ$faEtfSb+``a_{*1tFy1aCObH#hz{;k=N!4aym)+ck)2R8XAVeDRzb0L5#-5+L9?q(T~SRU!6!}K!E@HFAA1U{oa(` zq{sjt{r=-or8%$xTO;u?_wwv&bp0I|`sd{cu48#|J%Y?$E?>MpUV@dH?L-6oAx`nN zsP~7Foj2-`OyXGp3|*-&JpC_`Uu`&n-M)3-fx=y%oWcJ%&E7V-jT8?7;&;o@i{;Cs z*QXHd$ajg~H{|FXk=cm!~6uJ>?fVCmJbPd--zogJ6T*2-k3`})hDl!0 zzxoPh;KSd+)PH|={^v8B2Js-_$MhZ!f?%~~PhKD7lhdbM{O0QY-@Lf{A7>E6LZ+5y zcRv`tMmveeU2q)32EivnL0~db^MH?|=3yTv4;_nWYA@@MoHzoW%i|v|+W}kFc4csT zQGJM~?ch)M9-&!`8|~zS^V3ss;;TGZd=420rR)mq=G6&g2Z8X_5|-lZ#pvw(di45g z`GTSJGqZjKkFNaq`>#Iw8cy^vq5-+!eZ<}1$Jy&w-yozg*HoTrMxpFRy{PA`(UGqd$KK(?C*OAkfD! zw2lrb0nwr8B3X~8TwdAYr}rU4H#Zj~0gq)HG|2JyckVzy_95~?P7p3*Z=6mb2MSGb z4&+1XGdc=k6xjru_If#je>s<}7k5PWQW2USMG(}#`2hqQ{pN?3E(D508z2E54+rE; zErizZe;>5&f}Yb1&@-d(8CnzT5GO^sge_Kp|LpGXD$oZ0@#5xvHr7-;Lz(+{#8Xl~ z93pVJK+FPIAmW_Z&g^jto|W{FSZB*WYajH&fv)jW4(PAbusb3RVk34_szPZ9TybX! zQeT}Qv4MCfWX;V>;`hG<7oW)@QE=|x+`uG^q1gEOV1$H8J?V$cst`W7!q6cBhEWyt zD3S{S+$xNLGKM09It=I7S)_NSAkX3X3)K&EpS&0;FqN2qMhTrx@kI+76@nST7l({6 zJb#8`5Y<)vzkA>lPVDaDI*h2(7#$(`I0J44dYf=N@onS~ub6Q#EFU0vT;XFDM$-5v zbeuamj$5;b;K4@xPR0Pbb$R~!+wTyvFp6XtWpO=$+xgMFCHCk#$tV*sMNmJ|FDlek zej6fLoP`eqH=UqZd~8|qIul=wtO(^T!4ucE06 zys?TA4AwZ1el~J(n?8_5S%$)>07~I=?8sI$!|3@&s z-@-MT4ak(tM2wCKWbxF+Z}`zF-PnHfVk$cAQMo7puD64VFy6N13Swv7QnD4yEt2a_=;I(~h5xjchgAANUp zMVB9@J@aWl7+suS(DtM379fy}N4c@Y6$7sdf-x(GI2eefL!$Sa7eP7_9VHh5M$lfi z(hdz&Fb_;4gc^aC2k;wUP@L}&tOe;X6r^z9Fpx2@T~`rE1X-&kXc6a|<@Fy%$EWAt zFm^jRV}PNkz`A!My%FaZCs)TumoKii(FaWtTqXtM;QVFA(FDJIFKYGO%eEQC3M}bq2&$pz25e zarPhAF~UN%3GqvZU7^pxB-a*i!>vLh!okIz9ShlU0+H*tuR&fj1gP%3_hNaB2p@(b z58dC>XcwbhQuS#S;sb@w7baAH79n6RkhwtR{%L=2^aTpy=a;W^!TqrriM`Rom#QeJ zd}i3a$jJja{r~>o4@Unq=HM6SS63(Bz=$EGE`C3Lo57;TE7CGJTF?Ok zz_KUnAd)CA%bBr6&G0%C1vh$6$AM-yH%efTIDdN{PyMHH>024Xq|i8|t_jcoB$inK zw`%{s{Tlu=RX$c5{3jaNV1?~N=^J_cnY({84#})?SXvSM2ftsue)Z}G^}N&5KQPNV z#SM=aBN>m=6C_G-2FEhu!4pdY`Moo9O^D4Phapqs6vFiyS=dK7xVR>Pl}+j9ji+88 zUVL{k(Pr=FBdnD~6FC9%-0%NRdF|!hy5E{wJrHp3~CJr^c7(=hu&E z?LQv<7FEr?r#Lp(^2PZTZj79t5u~!uH?L1lUo0>8a65xtADvuXdt<~3h87A6d#AW? z7kBUQ@7eXM>#L7=GpXIct{uVF>(_xIKo)K;O`KXUF9T zlF$}}OzI@s-n0-o`K%ywlseuDm0;yuQX`YQogFENBs1|1va2?xJ)z}K_G>>mVJCfr zt+(f9y+3inf`oEV9rSUO--tSOKq_kFDs8-pVcJC*Z;??(SzR<|)O!j=G%}2QmndZ|uUpow z5Th*bk^F~ElsT9zCP_BFEaA$?v8{7(RX%&ui6Opc*6rap%V&vLnY^`Q_BZl8Nmk3L zQk>OtJu5UUj7HWtWu=`XgOyuzr{DSX=3PUa&wK-SzPwTz-gZ4gYmJdV)QX<1!U31- zVA(NYrxPxn5L#K*Z}g3_yg~Ua!j{c0^zdg{|5or2VR6J(^{O|q8=_Z>H{;yxFwLcM zg=rD{l3!e*8-j+1FA%<+ygczpb3o`Isah2(FkQOmu|b+ak`zJmc4igx1f5c}(kx3w z-NW~Z9az0CWY|LNHjGe6tHIwVcFvkrvFl9}2Z&uW-Vko|7>svfclM7ecD;3i0ku>- zotHA$4Dm=dtY>gFL|DFnKk+{Lw4lA;aZ=(W) z=Q5{BiVw*K zbZWs?#fNRi2wtFY=vnx=VThue4b{Q?+bByl(;i866A4HE2Fzb?BiELGG6U+N^*f<3 zUw6T~V|ME!7mA&GR?Lg`!X1w_x_5eVge*##c#4?^7xa2q+TzhpnxTx!yz#NUUHZz4J|~mY=xVJQbzAgHm{CvX zHx)O$-3Bx2%{G|P+o&z#<#$O5R&ut^D63$>@Ehnw_tKKe3Wj`ZJ6II)4Tr&MJ*k=m zS)mmlmTOeK6~Y1GJ6;Hs=>Ilzjo!M_5MZkfcR}AQ+yxjd!^Qi*d0aSM?U;2ILx(Nmkg*jr1DP zf0t{(q4q^_TNP@y$yY)kRan8ycy1V?=++}EgkOLGG(#dJJ8;Ch#9*mEqDieH0JtT;(Gy1#^zbcejjNqW1W7(eg6M%`PG z8<1;E>z;?K-sKuSH>Nj4aeqs>M%`Od9FS{Fn{4^Wt!At5a*cPnMpzbF-X8XxWP=&? zX6x^3)V-zZ0Z&{^r!j)i>p8im#hx!;Nj%)JriE$D8e^|LFHUY=Th^@~EZ=6i2Uhai zy@q0vB2!6;PJ*InkPYWvRkux2b0L#GV%ffe*C!QtADs<(@LNUO$H2>Jla>iZkD7uI z$JnGJdo(GnHu#%c&#-gwKVKi6uG4~pA1^LjPZkG4hz>suyV+FtmhgvohI#j+jio41 zRR$~?S|ba{CzNJq;tCTW={H%Bl$Jz{eN?(JF>Ym`R@5nhj`Ev7MZP8_SOc|dR4>$c z`%!wlZbgQ3078bge!a=64mkuKz3%j`%kh@M@D>lW7m0v3%uR26CT^!onxi5cxpz9` zIWRL!9-fd|UFuffMh$+p9}W61_M(Q~%I|4`or--(dlv1ocrZ3C(& zvnoD2z2$@A&23beW>t6S+0I8HQb1WR@n~+NSTw7$%3>DsuA8^FPBDbcJ;~a-d3%$@ z0fu~5XYYT>@QpSxe_p$7%Vm^ov&leq2Q(cvU8jP%%IB7CFAPy>-+yJ#iZ{La*ASuT zS&_X?D0)NQ0hNQB21Sc_m0T} zuZtvlpCt3)a?coCS$f+*n(gkQHy@zsiqA5gM%=wV-q=p5 z-TenDZ+Pz6iD;p~h9_%5LpnigyWzQK2V<4qy+Or*EOC|=5nr5NS$?>lc-=`)L_Z}x z06eC7dB75Kfbz{!oSbhBxuv;1;bP<#UWNt`>>a@&{YB_T9^4(pm&@*K4+JH!UoXqJ zS+fX`)wktD%k=PN+bm@Q4Y*8H9=?q3Bwdc08F|3Tb~ZW|G6(lcm;^Jj4Uh9*-Q8R5 z83gtG>_w`u2LR&ikm=qLIesSWxZ75|8)d68I$o4wLsHlJ!3t7nO%L!rfQK(zjpOV= zB2v>Ckq@Z|?VpjT-L+uMk-yN^*`#84L4g zVWPCrgfw!n^kUhw{wu*-JONMLYQRQW;`Xh&C-&mlnh}Q`7a(=Ili# z9gp@0ww_*@abEGj4Iy zXuu>zzwIaMewzb?Xlr7$O?rql*Dh+>20o5kAe9qi!z4w&?I-Id24aV;iGfeAUF2{g zrU*I4&yx&}TOc)HlA_;M#8~f6Jp|fjsJG!IgYvAq85f!W!ssP?YsW*vv&lB$*)x62 z126c{?=}W2*$=tk%RS-lzTYR`gS{ZqE}d0iN|MTq8@boicJhS$x~(RE8)-iG+S zS&-Iy3t>RDc)sb0girYGoUS7U13@zrcbv@%-gs}F`sX^M*)MOPka7ig69*O>_syC zOu@U2n*sB_*X_GqchKJ+ty~y_lKO;eY4uiQueaDgz~U|Tvq#;tbU2o!p6bKhZ;zU8 zrvf!?I=6YZC3(Fi*a0SQG2U<+>TOf1C3jm<>TSr~^fu~ni@rzvU621^sM%Xw8luIU zic6G(CBBt(el}2(Sz$h8g~OP70u4_-w57-8ZG|CADDMPMIk#ogo5*m=MRvWbF-@;KTe{n9!T> z4AF#1=Kgz`aB%$H`Q1Hk-;4p)|7Yre4f1Otes2;rU`^Cwx*?)?c*d`teRln7Wr33J zE^f*>omPd(&eNtez5=dj3*ER`PSp4Om$%B+2<5lyrniwAEjA_Oe?N|`H#-_|lWCEs z+=DvY^=t?+HVV|A3E^1(Xm<-LRTnHs;( zvK>gSKey&>efo9YHsF+d+ul5Hzygv*`dk9OytzEWw~+D8^r-QuIJblZcY@f;Kn-2C zeCkK>;$wt{PQXSA;zyQ`kIv4{uSehT^Ujycm-rs_+3^zJ z)&?AV_g-BrFRw5XXcA@EKG_{9XLM!jEigfo^_V!y`OIKj8<-ASuRu_&c@5*DUyQ|j zYa0Ws!+1ZvTOdsF&OF#hPv4n`cjf^u;cwME%zBG;1H#JjezRIINecwLWcR?n4}Nzq z?6f?P=L3Zz*&@Qa#?EYN00+|482cJ z&W=t`Z~EE>YOadmZ4`6I`}1s#VJDNmLr&7grgqT(W*? zPG94L5&kcN?j@Jl$*8jc?ZyJMjyt=X#dKl>phb1$eSh>c>!eeEPS-EaA zGaDJzwDgRUBIK2kBNQ%tf`ZzGe1twLDBsZqzGwX6{X$ZtCO>6mODuq8^S!-2#wT8l zne|rj2U&&uTX&f=Jv%wg=jyEs4|r+9c)aNi_93k3Hwa|HZI}d?uAm%Y-tCRT3cr)s zm1bdsB*7MJElCb@l%yyKy=A!}xy(4fJ)22rlw_Dj!kS6Nyf@(=B!TUhy9d=MbRzdl z^IOT?#?#h&9=oQ^k>^c|0*v0AYQSom@p#%wAp;n}FysL6N@f*8?3kN`d2f6@q(D2K z#Wb%d2*2~%5CHQg@4R+*(Caqp@6Kzxt)2JgT!U=wB75{CbGlK(bidr(AVdwJNMQ_f zqadra;u7Y)8N+}DJL76UGXyC>=9Jkjsc?&*a3Y)Nuv`7@Giw&2VijQ8_^nP>)G~+6 zT6D~&cdxy!iUt0m!>OkK+yu6)-J-zSn@@Bc;51~?54JFH^Jz}s4aO3Le)k@|a!^Tb_vL{nMkXtB-`r zF?T8Bu^^aaaHah9hE=KP)s51%Z^V@VGf-9Gj z0qTPvuTkRSH@5R}LhCHFlWbt=cWf?*(f~txtE=6|+sR>swP6Ui0^`G17q+&m4QA-D z3TDy6Ax$T9V7C}!b%4SI4IHiL8%P1;QL5tM<G8qj$5l@q@1YyD_6y~ zS=zMZ@!m-2`Etjl6cbAxWq}*eei2`#M$?#DP{b%SCSjKV-p1T}Ov~Lg1sTr4xAQD0P+F+q8SLJLMh~ zg(x%5sNguqUJC)d~cLvU#ICYt#}^C(kOPy~V*n^1SigDDULi9#kk80o&S_FnhaOlIQV$Z(Vjs zakS}q4@p@Y#d9jmjyy_{|9SS+&CSL2?hv7B+N-XVf96Y|x`b-;ItLaK`gJG^t6?2D zWiXT}yUt<;XOo$y&_qQu$NsA@%8KTV_iv?y+>Bdy!DUx-pYJec?s~l6TSFcs4psN< zm$o?cme2-?!=|@q#OSJRP;H@_FIQW?2!_J(2sND{0Fqg6TTXdEPJ z?X<-}MMRfL?}mYjZXNR5n`jM^p(Z9;MJUvkq22&@6VJFRK2hobq0Dg156Jr6Sy zLa`P3M)E)@Ie^`b$&&!AqwjNYLly}%)795{ggN_kyP!TW>t8d_fim9Dvb?};qHDcA z_^R}D7LGIOZ{yzwi)c3-29v6l;?=O_16X_C$ALk{XO?jwvj;8XGwuzZ1{t6HwGY{3 z(fE97k9wPAmd|r$idMP`EvHJRAd$5<>=^e3XMJPDMKP^QkvP8?tb?N$aI9j!rHa+7ve)Q<196 zV9*@AWHf}X?B+w*tGvJ3{~ES|k3et%K3->VbVKDfO-AX=d)i~US}8L6?Qhd* z+GEXQJ4k~Jv4wBJJ0fIO~!5pF0- zrcgbPk2(4sjO|T321#$z9cDxV_PDGKa-3c-k|i(e z%<(pIT=iyRLlW;vUkcF?1Dh;|NUV64fWh&O-65j`)T>Kw@mucE<0iU!Z`s(-%Ix zQ``eR^5}P9@vQ1C#0;^b)3ijYI~uT0-n4^(l+A9wRkvLh?j#O8+pvD9v{mMY~6R zg)L)i(nrvnQ@iY7TCZS{Et%rB4CBfN-J|S4B(jmp|5gF$){FwVGDd}&GhRh3MZkvHM z>QBvI%_u@n6;yo4U4^B07A`h`tKbM`)`}>$H-a9-i$(XsjTSGO-jI1n*>%3ZA)b3vUUUn5q-|0+ z_^#8Gv~s$&{79v!oF5AGO}UL>QI>93VM}1U6gIRlSUPSSHMf#&%+t493Vn?<33);; zolS27Fhn}%eF;Fv{h{J5#^a_pN*$7C&8zH&S-$SIYkp~P*WK1Oow^v+8|MzvuR2Q$ z|K{)SwaK>r)?T6GvblO$$@T)<8zc_NSm#aTz{PeSOIXdiJtWY*(fl#)pl0QJOgPQ$ zy?mya`zL(+>S{U4LGZ+7APjwZw-1+j%uNu$wU8K71V|Ur& z-VAQYTR7&^c!Ot4OVAxuI`El*;%yIR;ILXHSI#%L58bzm6n7@6&8NL()6k82RDrEw zaD8|abvI@b0$o7^jNJNC@?V)ilim`*AOa14 z`|xi!--qy3H+lQKcNDj<>T9E1Wwfj=C zJL=-u4I3YL)y_`<WL0@!WQC!rMu+Nz z1|9O>8`ciPGP;}6Tl0a^UjvrC@${gWWU=PvR3DbxSn^(`cElqYpL=Ri(c`Mjl!U<` z2^yc<(ju~+^hVYLNLB6kyuWL$*l*$U-jGs7K`ytnSwdJ4Dz@pR)3i6h9$<{C{X7F% zF~(3De7`t z5yGx@wIJ_&TLpsN2c8_J5a$gj5%?;IJd~gIhVp~#S<_nKLoeBl-6e;vMj}6UX9YGw-NbQ`}yY-6Xq1<%=$mOKDs_R9^h>9 z4j-gP8|*Yp)qv<$40c14tdys3fteWd?c6zQ&9nZoX9x3*?O}ViUW4cjgF$?wCqP3w zsglbY*YCV69QfMA&z)yy&s%W)y;<0R1)9}J{9&h3C zW6%!D#~Oce%X6*w8Tn+27B&St?qrfLT*0pYmZ~>(ztOKL-m=gXJcH#ueJA_|XHtaO zy%m-r>F~Jyj%ivs53_$!vFbL(PN&ST!N_E$_?@u1$oza^%kJYx<6Oqxoo}rO3<+?o zk=R=)bdB4I;VBB|-2oG?WP%fNF**U zZ-Hfy_D^$kn)?W|yvIiy0eU%%0B(bv6ya0A)rM>tiKD5$hL z$|DiL?CIp#DDZ0inpTZa1kPD*w_${$n~84u3c&=h44nIc;W^bhd|czo(&k@8nY^`sIOBl=>z}Ld2G>4{yU& zXk>5sXh=nGoR$|Bnz44~-jd9G`|p8PYm=Uw0rixb$zrslB~~{*WaDL=rTDVim6*^A9BVd^Wa}9ZmsK$w2=kq zxhqqs?b;~OiT}oh16Rb8#$Nc};*sy#}7tMjY%O|<05 zVy}n^R|6!ps#`YvIryw>gic~1`+dfDZ2RoigpGelT-`n{PpkzL6Kj^#(v)9E^5~2Y z7l=v@rX>rwhp*@1Uqf>{T~IHq^CE6tJ;E?-s6fOpr6zU2@hMGMQiRU>2G_^wGOO~i z+#pTlo=Rwc7HEn%jw>ciD5unSJ9}07{=KUTYk93;7zu4UNaZ10>Ny4&I(S?u<%Wn( zoGOBarmZ09{-{yklPL?IMI4Q9=~3`RkwF8XpkUOmuq;hk$S0dQisssxNx;BwkQHf4 zZWbmq(Gc%9I6AqBS*29cdv1N8pD|by>ZyR+m)+NUV%( zV>mcveMs5YpauegtrU(!Xxx3x)8%3gjc2gN!~Ez>k4*hfS${#K4rft}OMLl%l|=ylb;lRcV|F6{SQB!YAtLWT z7?#2ibm|MRKZp!*i62TeZ_7F7^l5kv#$gtN{R1V9 zwNx)c}{u4CP9Nx9@;%vcUrQ>8Zoyh`nd#rmLK z7H~n{Bl1t4+UAM@`C4-qG3fgJ;%ZUZyFO4j*E$!5WAql-s>AkmXGDEgce>{aTjDg+vxqdI31IyD>3z(69aprg&CL{O%@qT$_xg~xMHZSld*wei zWuaN5DVcf5v~2K5^Ro#w&R9Gnk>}w>6!TJ2g^{(&H7Q7(Hb_OYq`i`~L~ADmAp~cQ ztxOl{@}0+Ml%rZ@NI9i!fDR$47))pHDC3NUWFiiW4<@OV;Xn&~nfev+K3jnz!+vz4 z(auZ)f0{(c1R5Zb+QOaQ{b39mEb*xRgCl<2WFj76>ddhIi+BVMytOlPqz_U&f|sH6 z1vWSR3)at&gf54p=x$THj=h4za8#)k+T`wqiQPmOLiBMk7QFGm4a2lBJ}v8@dXTH? za8Ds0k#1TmW_vi!91IU1kTfOt4nc(RAA~^dco&mQ96Nl#qa+aPj))ZBlqn2QAo-CK zs2%TNmN}aG$O+Vrlao8E^0*1qV;vcZ$3F@gjK!|HCPihgWII+sa^)O3^Vvf=!BpOR zo@}Y*{iEK|SMi5&+=DiBBZ@$}gE;Qojq=E2kBh6EB-xiooxD-JDQg_j@3FqO*Bt>S@ay{%ASVeZ;O6 z;5iyG>5)W|+L)&opdldUQ;%MRlcv<3;q#bsOXDDv%RQYAn(9!Iil_-tr+VBTCqVyU zgb_k1R`S_%eEl99T@d*|%n2P?6^HqL9~s`C+0y30F&qt%s(8zZ1xa(~c37}}XFAOs z-sku!9Ma?hP$Ji4=7VCFYpBP1sUpX4D8ySZU>U_9sJJgWYNuG%zuK_ZtK!ad1YgaC zxYIc=bP~oT4XYpzpy3?(b;VG4{F(Z4)SxW>3u;QEADypixr>tWS6{q`yY`^{w4Af( zWIsSz8t!t>Sxw5RX7?Bh2s*v|yedBr%uT2j>G)iad@DZ)*&L_$Ra zsgzjQZPFY_H^{%E&4=OUyca{+SmMQ`SM3A~$r@dCCl90VkE7iR95eGk+CAwY0qbkH z2Qfoq52Mc1P6XW02}EGYQua#N=&-~q84tXA&uH}Lmmk+>y1yDyg3X>s8x9|@*;FxM z@nxc+vrz?C%VZWw-b0hSy^<=5Rzl3<(orI{cB38?N5lvtCYFoRgfnve9vkVE6kLqC z_IfEmM3OnZRsyMGroTf>0N@~)U7tVf_gjfjj&Y^j9}R$e@_Gq1BHFBjLBG$&z$9sy zF_*|o@t(G0DKPFo#k!>lQR%a>14*)Y92ccYlEv!T^Ye3jm5vm;*p zJ_{5?&d}5+Vy~**P z6;q9>P?CzJ6&GgGOBd;QHix}Xv%^jV)66<05|uXTBNw%)N@Lv-i90k2X&Hm>ti(q3 zR|D1q5q&1UthM214p_@8(Fc>E4};?_J665XE<1IctJM3e>XT9GF-$X>x1`zAkkJb_ zQ5hORSa1Z>8r5y4agzo2&6Im;59$zP<4ltO0B%v_ExR6VtLRG6=^AdN#9L-O zr35?n21vsO&AFsC*03As(0yPHPa)4wF+cbx2ospE!s=|mI*x*iK>HKi{S0~7I%uSQ zrR{d{VHG<`tr5yy+iCWW7D*^R<^;L4fP{PIDIS>JIYVxr)Qm)i{bu-=&2}|)*E$vz z1eM@N42+$C6ldr9MJpjhYLu)s9fZ7y#jWfbW@4eV&y`{lBmaI?+@+HJ0gEa`7Ge^$ zZ%|s;RqXG@vr6TsIYteQ{CT@+HFw^BI`D~pMYBmFjtoML%s_&6b_Ts!#Gf0qf{P~8 z$Z<;34o=`#U^*_7&9ySJ*O-ttu2>_a5|k1#$upFojhfK~s*{oIk`k0>agIpS&OGIR zoo~ATy{bNSb-OCH954`yW3aWnCR^B!R2bgg-Lk z`&QK+HD(Hz?X<)WOi|_p{{-27>*Of5N&9S1wKMWi%1IILGf+rs83`rS3Y?$zeON3_ zVc@k@P3iB)G2Ueg3Z1&edM@p5d3Nyc82edwEwEEe%_AFEkhm7pLFRZua4mjV-fjgh zabv6ad%72FbVNiyuDydwiv{|9zgQg~0ofprh=5GaDZ*pl-!6}g|AuVXN<_Z6r`#$D z4SrZ#x5+s_D&WAnN{>N&hpoikrjyLsnjpU4E`B{W?qh=~BJPXRU1{!vYL?5nq$KN6 zFkmatemZRg?V)-3u`wWv?nMk3FlO4lGY<4Oi`}OMwAoo59Ti!mE}`P=qTnPGD!!In z`1dFznME2RBI3S#d|=tK;(x7=j*6||ky*bH9(nU|akYC{T^*fKX$6$b22l<>ZI(3= ze_VX{cyv@`k%^=dU^dJgOjo`k_|m%T_WsSc!mzSOg)W5Lb5S;wQjDG6LO)g%Sj~2Me_V5N5glAxaB< zvsleHci*hn%WA$lgm0$IZj}FY%1evc>l>F*#$u*bnbB0*VIu;gn4qYN%`-6R8CK1e?Nu;gn8orHEHIWv5aeE4C>*9t7@ zA5BfVZDJaWk7&q1j;VeyC{ER#Ta{st=md(6o||C@jm?j!sy#A)?Ws;45nyNnO4B5J}IasniCMSU@2n zQmH`HM($s&Ygt%x%pg;zcOOzc|Lt-)zt-2CHzSx^O}JwzojIGZI6_3W_%eWcXiAs# zB*^wa1be$!zMnTEm1jO)09(NdJ=`^g2dk!U7=+}7nd&_bh#gkbw}KdYTw_R=fi#E} z80~23*a~#$O$rv%&`}=|JT^vb2RwuhE;;N4jChnZYzINi3NDFZ!Z+9R<+3_J1>Rxx zVJrBdf6*v{XG!>abBxS5Wif;#mJBUmp&&x*x|~4&ZBxy6N5_m)7Gj7<*l$#FU`cqS z%*f&p5hZb_$&|0CZhN1@0r=Nfv31s-f5xkR1vPkk_=*9r+6hAA7>_JEVO7-iCZ&yW za~bb{vt>n77NiJz1`Yc0ooyDR`1x&J6leh`E;RiTr>y5Mn>nqdvoo{qvY^i#d~+$h zw3%Q2QtfKTMGbx|@sftLX=d8#dm=*hCv2|%l`a3QpNWTP2&RX5UzeywtY?_x79`kQWGYp4TD1)HbB|KdlMlAf%no*YFGb$TWyu3<&4dXtGAom$`0g* z!KSA3Yzb)nXEEts->A^+XdG(u}at~MxCyAay6#)pe7OFJzcm~0(7j4~=;PVhc zsH_Qf8x6A=X~3VJw8#DdY=ns*%vfwDqEIjGK>4- zQbc;Q+bmWeVg;Vj-f#JyI|t?@7FdahG$@oJD%1xhj+6+nZc(d&2ruez)y z!5#%8v6xOoq*C#wB9h7$K1x1f!Ka8sqXt_0AFFNkIN6AGxkWSz4Nj}y7CX`h{yF@@ zaF6;g>g0OeYoLJoiM#Vzd))o{Yt_Tu!c;Xu!z-n<)_0(k9DCJ%fCihSiLG>O6@}u* zN3H#wZ=$}iqi3my4m571nQmyp2lA(TI@xBT+f>itFsceNG#y7h8{SOxziT>B;#D;+ z?xt>oRO-v&Pag2iSb!nozEVe+=bO!X^XB&EW>alzF`@@j_D_9}Tkl>HZtsM6kbi*p zKik0uOj}YvKP*sf6xksb8;DQ|Q{tJK84j(ra5=_cz$E9gGqaAYB=|kN@GaKUc<9Z? zYPo#=Tm2-q2@R@n0UJZpnr-ipJl3KkjG?b5AqiQx#J*Cu_CzlM(%M z1P^0C1qYb8&6NoL@S@=2{QxlGP-a=rl`(G;fd>@N(MKY7!(IWB|KCNml(Z)*8C1g& zdejUhC?~Lf?5wLA#@+1xz4tR{q$f|h%f+hd!iK8w-SWxJ$D5JIv#>|9DazUbM{~4A597_=;Ngi3y36{sbQ&nG)W(qxz9W2jk$>C zr-JX~rU?})T5b)q{bzOOvx@3LZ^|_UU{Rrn z{0tuT`H&O&l|9#+M11BR3yme@AC(Rck`jwJ0Bl$#hf$RTyj6LZWQ0tAS>Rh|k8SoY zv`zE#1Uc|T(KlHHw+|%3bGY*!42QRUp(AqbdTg*jv=^n`GN--pTkBXQAs1{^L9`eB zLUJv;7wrUX+&5xz&}#7w9I2UaaQ+kDzgL<(DT&&w*oiu3R&S!^c~Q9YrSn}o$eo|}TD zO-xoBciItHsr*GRuiyYGE6M>|@}e=J8vo&i`>`A$68e}8dq@K5qfsHs`|x}1{AH^p z`8{-c(9n$EL+hq<^hfs+lC2htfT0cAj{YF&Ak)fxSw1WvcNmU5x<+hn!j^YzN9Gald+Vs~DKwVNG36;za;t zH8+@+CixnS5Oy7hn*0^XFUJeOd5C^1frD|VV|D9jC@E%l^L&-?zC6DKnmcV^B?u=5 zkk0TgYV`_&WtqQaF^d-Sz+x89#)_GHuq0;gxs#afNT&14y~T`;2}yjWalo5GF_Rk# z=U6<{pn{_mGFP6&93_GUv8_N zeM6zfJ{#VWB!$M|@_64US(cf zeyo;IA@nOFHoz@;oRAeBZC#M;0uZnqmoUb*u+7QSE8Fu>OE3Ju0%gY4_Nen}ib+E1?jN?QdZ3Hq$%zq zjR=sfqBcl; z4%i&IB%(c;6^e*+2;aNt%AvnM#IP8(hV#iZw1T1u76{PS`Rn(=sN867>_!-s8$^r+ zxPh8+P%G)*X|5-BsH};zA$n6YT%&`y$%KQBSz0CuQ0w8g?x4s7R&63yADvPe0OGCto)IW|ba76hxH@k^V`1}H_!aa`EslX6s1 zA+i@ZAaqaV$VT%-%5jobjw)doR#$fg$y`%lCvr)V#@7^(v$(2f z2K)o}6hNuBUWLnAm_K|GzWn@e)y}yre?Eg};ctzRwi{J;V*w%CXS7sBGUb855A`#% zNswev+;G|?)glr8IUql&>Fg#UP&aHP(lG0#57T-rV38+$G%VqAzOA~@aIK97HM4$n zb(&_c%5h0oO($LM9Ovbw363=XwbHCMzAD4blhRjSbG-CvG zfFfPe5l1GR(X+v{e1^>JkMVsI0Y-#j-N5=;%7CnMD{)U|%u#F4DJf0Bx@00w8K*Tt zM&w#?$Yybitdyt&uXZ}9{l@dv<@{z_y*JG=R45@``dy57c@G2=SaXwQoer8R7m3A9 zIcx+t1oZWQC>CpvP!j$bu}-Flf8tKev8Dn3QNO~%KVof|h<})iOe0M*V$GK5GnwQL z-bEGcC7;P!CfUr$LO3@RyjR4WFITtM@7$?g$6y+PvHq=AZSK)TpLC;|Ug>djT!``k zm=rPpQO08}r+_ZdYdKOMiu{x=-##+Bum)H}m)v!r^ut#&1y8l%a}6(sMP>cyDK&1xpBi3_(m^|9?jJv;SpQEXeYsY^#?U=}O10s<4liQF zbA%dw%sShGd>&A$=xqN-wW;2(FVhi)c7h2I8OMlF1rzM7Ij_Oyw+VdKFt!nn6(90) zj$;51E>z)wERST}lLlqfx&Z}`$32LlENus5Zca{;$C0rfIvKMFL=b&~t4Pv0C8Vme z%u>YZ-SKSgK<7xV&{;JR-)0V-FiG2arcoNX)Np0m=1Fc?7> z?lCNDiIybeR^V8#AI00PN%DkDgdNANz?)uQo{t^30vCErkyZAaTXDa8p|4QLhq_pa zmN>MfDF& zhaj(+p%PLzVZnt+^X6dK-h80dQCvmnBo>Uk}Teg2nO-7cpiF<*_Z6fTa>v z6BY~$s-ob6yi7HpVz`IzEe%CAS|eH&cj_aq%^p=Qt-$%-G!yhc%w9XM+U~W&^5L{S zu9BqUX!`_ua}rQo6WKRz1o12s%J42pVGQ!387pcNfC?1c2PXEAMcI-tUvH0#WG5_6 zmCbzoLF-8?Xs*v7de3kc5a8_ighg`_ZQeiKqO56fH0joiv(PY1&EHwUF=sbCfD%jyauFR>>c$n^Tg`RkrZK`R=dqNAoi zE{${;iR`b=Xb-J{vQRFNc>5YSX7F<|6{QS4e<@_2N?yXn3v>!(ew@k>vC)^PCJ-o)(Epeh~a4I z*a~VHUSx{%gK>HOPq@D1xEK)*yK=oZB!&fQUz&J|z=%gl!&dOhFz#QHHqLLZ;r@;K zk?c&&@DYTnhZn5?mSL$H*%+0-Z7S&IcVqz^I9=O{B$w{YFeJ2G_riak3F1ZXeLl(ONo*OC zDU|v9ZMChZr684pia^L+OMVzq^458A_1%2At)gNRyPR6yYIwn-n^9Ml)!pp=z4tSi z=_gOR%f+hdE>@rfSM%kQn~ygm{p0-ZtKqPO5g(S=BU5qIF0o%+z1{fc;+WXV#F{-z z?*}PtV)nzXII$lrP?F>khowB?KlUhnx=$KWRauz|Cr?RQVX7oD;#n?@2#z;rv_v#2 zr4coaq~%TbA(Eb}rCci<2jz$)^3jW6(Ox~4P@_6?o>!-uTIqTmqxMKWo&J>-a!E_G zz*}xfdR3vn9g=8uKN*}os8;CC63?wE~7lB|NzoA9$t6GDAYzl~8gd$sO4| z9m#8OcFg!MF-H<@o1=e2mSn-D#7>V&WwZxkN$Za6!;+^Xd5j7S3|F9TLxy89xX2ck za<9Ovg@*I&uDB{TZCUZ5=4KKZASDstB$>gL^FB zpJCWz!Mtco#%cE?HlYAi!7bAbqK7>e*~(^4XG^j(vlvb^v;2;LVUI;d5~qJO$pq$2 zD=XI(HtF`4vz2(9G8Q8J0PYNeB z<~MM-`8~0pvV`YU;ENDQ&v$6eHLH+@?Za>=TF>)9+L-~ zz&`7Mi?}83Rckg$?-7};74K^tBTzRR{!slpGB@jHNW$3Tfv*>vZ#MHgMR{_^cGwTi z4bGu+q5X{EdzC&n3c6S^CE_<4%l^;m&JC_(SDpy&MZFHw{|gqk{zSuvG!zZ4TzW7X zjaEbYc?x_^{Bk+Jlh+Xuh|o1%%l%}|Z}=Iyr$X%wd{w*x!g;KlDRH^R;hqY=kY=1$ z;5o;lK@VEavDQEEg#Sp)T2A4FUjB`B=pU0CSl3^~4O|zZlzrA3K=b}rU9Q_EwI%wE zj-)3LqrI$hK!Qt|tJ7iimwVN&h1FnA6Ie8=u9-;dFwC`p0?qS@IBB1SND^>1<`SL{ zv_oPkxAb*jAJNUrIo*N`#aQqoq8I~y;^ko7%HM=8nwhB@&CbmF*&;cfWq`Dj$%9=8 z1k#~>CWQHbQ%RPKSULT$k)Z=*&-m-OCDfj9sAdk=be*W}17iag6-cCN(vt_q2CX23 z33JjdE6*%G5PkC?-6}XcGwUBpkjZ42K0Z*JS=m$nOOSdMnA!j8HfMdcON^m901GuT zMe0isH089`=3iDT;(w}F&;Fw8iaMRGxoUH%-c%!;|9N+JQ=M7#uVcAiI0@GH>)XY( z?hUKz8{nVoOERZj8U5z(tKG--`)5!DYhZkhLi6y$g0I}e@C^CAdpLRX8$6u& zy?w>{44plQ>UqTNSMMvrCHB{6KidlyJ0_~{IU#kIX>Ck$X)NLaP1R?&o8?_-eg_<| zO#R+4S@WUIG8 zwep79X(^!pYNa)vKqe!Ijg$^ zT4qB4*yLUm4`D#y3^hsJ)c}Dd^iRaqv%h>OKwwu!zd6_uFCvsg@X>Js(XR6Z2v|(Q z;Q>pz98JA?aN8B(0sHIy@PHfh0q{U^=sX@MzMgXXfsRXq$|9hk6?+ZavYek3^)enP z?q-AskbEPZYri~&2aIoS)ud+(I}A~jY?M}VQfxZ*3i_(rU4B&H!goy~j(W1%NfpAd zXyL7Dy@%mK&@v{(8iFMNko2#7Vvckm?5c_g1G|;@1>6d#9+Sw7su=;|Bo6ZHs6==U zXs^U%u>WGAhLyOd4A^BHF3YMB}tmE7bMA zv{S^_@cZi$KxV(F3(`uAcsk1zys3zMFvE;!DaOr+7m23D-_`+Xm)H_|3^^aS-wrl3lt?#1(dbYpc-`Pv5d4jwQC0 zSp6(+kZ4s$mLVx8wi3CY^?YSd+PYZXMRXP$xtF;Av$)HJr2wdNGFdC&Yu1-1D2A?#bH@XN5j#mlv1fUi?4#zs|rMe4~5^(2Ud zscIjxm{fudXG}WDyFG7q&?EVhAj7nVE-2@O>tnSNBA#_etiEpb%1iYHPQe;mVs{a{ zKt$h+S^?j)k*{zKk!IN46M=^#)@hf7nPyCT2QPb;&9Ll@T5&>W0WPGs_MVVI`7|0f zI4u=Yr*+YBjvogaVsaR_;rBuiNRN$J2U7wFW)lzHPJ5wEU}H3g_o5wFPkuAjaMX@- z$H0u3`H3!IojZXR8eK45)Uz|U;pxH5-rpjepPji4Pj7V5^S9WYJiWUR&*A*HeLcMq z>*IsoIz*e@*!s^Q#jo|Le^o6MKl|(>T=_>I zNm*g?ifX7r$H$qClumckli2&D6$iUFN}rX{7R20XaJ8s+^44xh#(XsMbi?@cBtAIx z$X^mPRiXr9aeyHEGwS7!7du9aQGoT>N+fFLZ9@J<)5F?bJ|ayCrPE%uk$PISCwiw7S<|Pz< z5GTlT4a4Y4k6ytmKftT%H8;e$-acCQ>S<>ByMX8A-aLmU72U5*%c(#8Df}9!fqtz@ z*6H|X>aRWLiP_bgse!jlh#*zraj$LEdcT>8b-@vz8-~sqer`o+!#&vGxKNC^p4D6F z;J-%Gchrm|oP>D{8Ke&H3po8{jC{umsr5_XUw*_q+n7DFgOI8^_{Kox%o77)@!Nd}PNd7e0U;r;JTw97tbwkl}J)XEi2fZ$N^^ zolS%>W^5Qk0^|o=3hx28azC8{n;GjA2sa>|(&SZ=7CO@@BVLtUdr6ana8b8`RB; z3okkE&)tmzQ_&o-d(iGB7!rTKsFF7S4eq)6)jE{AY!pV~TMyzAH@oAc0?RMW>Mjzy zo3WT&#Cb6aORYoi^sUY8{{on*na~nh54{gKjUI7!JL=j~Plq|Y8 zPjqrjfhN+P$o*$)df}Ne#8@w5-KWWf1(+J-#;L2eTeG0p{EUqsNMd3`rpK~pOI0gm2y9djOrEgkGSu_dIrwQIgNTgDw;Q3<_sHjMdF+xlQP5Jnry3Z#23ZBe~Ey2r3Q zrVt4muMi1DNG;a&bjrm9y%~#zfmG;cNvSnc-;NGeP7GjEN%Y!@3{N_51hhkyK9FJ6 zuEl@YGht3;&==gQ^d?eYhDH0L4H-p9MPV*g)1z939L0v{FA4RehMVqh7oEUcc44K^ zJy(!I_gGyD88-1u$Z`lAZszW;m&Cw_xke2q4tZ65(mrAt&;}lq;90-V84gie>dilI z;U6VTnvf_0Cb40Q#*o;eM%RORfgCL0~h%*{HC;pf0N!FTD3u+aq@1C+?%h-p^gQ6~*XIKj%E z)naU%lO8LAxllxyrjb^4kJs6|176W~rUWXVOEVv(0@ab2=RK=q@0@BCHh?3d)5Lq0b>~i77PIcx ztIGtflw>|Ez0|x-X=YZF2$d1K_1Lh6NbIM~Aq&?l_xZ1Ldp(_F7NX8dRBMI`ofKIf zQ**|;m;;3pgNzyTfs}EN1@Iznj$5c;0I$B{$LgQAi%o))OZ%~>)Z6)*a&TGddo0YB z&}n=TosVYdba1J+^m+iPZv}^sL)S&BEkzYkewRW0E5g^)C8HjTP0&z z=ROm+_fa2i@l>|XqO8Cc+B38f&l-n@?1W+b;_P-{6yIavf&|5n2fjgQ^O;$XSj2Uu zHix>m__OtDyG!P+jfKf5WTlJwfP#`JH$E^AJ&joy1U!%=9j;8pL_wiBlRDv>XZ7fUDbtzQy1{& OZPoqa$-n*2zx{usRs@Ft diff --git a/internal/php5/php5.y b/internal/php5/php5.y deleted file mode 100644 index 980f50a..0000000 --- a/internal/php5/php5.y +++ /dev/null @@ -1,5698 +0,0 @@ -%{ -package php5 - -import ( - "strconv" - - "github.com/VKCOM/php-parser/pkg/ast" - "github.com/VKCOM/php-parser/pkg/errors" - "github.com/VKCOM/php-parser/pkg/token" -) - -%} - -%union{ - node ast.Vertex - token *token.Token - list []ast.Vertex -} - -%token T_INCLUDE -%token T_INCLUDE_ONCE -%token T_EXIT -%token T_IF -%token T_LNUMBER -%token T_DNUMBER -%token T_STRING -%token T_STRING_VARNAME -%token T_VARIABLE -%token T_NUM_STRING -%token T_INLINE_HTML -%token T_CHARACTER -%token T_BAD_CHARACTER -%token T_ENCAPSED_AND_WHITESPACE -%token T_CONSTANT_ENCAPSED_STRING -%token T_ECHO -%token T_DO -%token T_WHILE -%token T_ENDWHILE -%token T_FOR -%token T_ENDFOR -%token T_FOREACH -%token T_ENDFOREACH -%token T_DECLARE -%token T_ENDDECLARE -%token T_AS -%token T_SWITCH -%token T_ENDSWITCH -%token T_CASE -%token T_DEFAULT -%token T_BREAK -%token T_CONTINUE -%token T_GOTO -%token T_FUNCTION -%token T_FN -%token T_CONST -%token T_RETURN -%token T_TRY -%token T_CATCH -%token T_FINALLY -%token T_THROW -%token T_USE -%token T_INSTEADOF -%token T_GLOBAL -%token T_VAR -%token T_UNSET -%token T_ISSET -%token T_EMPTY -%token T_HALT_COMPILER -%token T_CLASS -%token T_TRAIT -%token T_INTERFACE -%token T_EXTENDS -%token T_IMPLEMENTS -%token T_OBJECT_OPERATOR -%token T_DOUBLE_ARROW -%token T_LIST -%token T_ARRAY -%token T_CALLABLE -%token T_CLASS_C -%token T_TRAIT_C -%token T_METHOD_C -%token T_FUNC_C -%token T_LINE -%token T_FILE -%token T_COMMENT -%token T_DOC_COMMENT -%token T_OPEN_TAG -%token T_OPEN_TAG_WITH_ECHO -%token T_CLOSE_TAG -%token T_WHITESPACE -%token T_START_HEREDOC -%token T_END_HEREDOC -%token T_DOLLAR_OPEN_CURLY_BRACES -%token T_CURLY_OPEN -%token T_PAAMAYIM_NEKUDOTAYIM -%token T_NAMESPACE -%token T_NS_C -%token T_DIR -%token T_NS_SEPARATOR -%token T_ELLIPSIS -%token T_EVAL -%token T_REQUIRE -%token T_REQUIRE_ONCE -%token T_LOGICAL_OR -%token T_LOGICAL_XOR -%token T_LOGICAL_AND -%token T_INSTANCEOF -%token T_NEW -%token T_CLONE -%token T_ELSEIF -%token T_ELSE -%token T_ENDIF -%token T_PRINT -%token T_YIELD -%token T_STATIC -%token T_ABSTRACT -%token T_FINAL -%token T_PRIVATE -%token T_PROTECTED -%token T_PUBLIC -%token T_INC -%token T_DEC -%token T_YIELD_FROM -%token T_INT_CAST -%token T_DOUBLE_CAST -%token T_STRING_CAST -%token T_ARRAY_CAST -%token T_OBJECT_CAST -%token T_BOOL_CAST -%token T_UNSET_CAST -%token T_COALESCE -%token T_SPACESHIP -%token T_NOELSE -%token T_PLUS_EQUAL -%token T_MINUS_EQUAL -%token T_MUL_EQUAL -%token T_POW_EQUAL -%token T_DIV_EQUAL -%token T_CONCAT_EQUAL -%token T_MOD_EQUAL -%token T_AND_EQUAL -%token T_OR_EQUAL -%token T_XOR_EQUAL -%token T_SL_EQUAL -%token T_SR_EQUAL -%token T_COALESCE_EQUAL -%token T_BOOLEAN_OR -%token T_BOOLEAN_AND -%token T_POW -%token T_SL -%token T_SR -%token T_IS_IDENTICAL -%token T_IS_NOT_IDENTICAL -%token T_IS_EQUAL -%token T_IS_NOT_EQUAL -%token T_IS_SMALLER_OR_EQUAL -%token T_IS_GREATER_OR_EQUAL -%token '"' -%token '`' -%token '{' -%token '}' -%token ';' -%token ':' -%token '(' -%token ')' -%token '[' -%token ']' -%token '?' -%token '&' -%token '-' -%token '+' -%token '!' -%token '~' -%token '@' -%token '$' -%token ',' -%token '|' -%token '=' -%token '^' -%token '*' -%token '/' -%token '%' -%token '<' -%token '>' -%token '.' - -%left T_INCLUDE T_INCLUDE_ONCE T_EVAL T_REQUIRE T_REQUIRE_ONCE -%left ',' -%left T_LOGICAL_OR -%left T_LOGICAL_XOR -%left T_LOGICAL_AND -%right T_PRINT -%right T_YIELD -%left '=' T_PLUS_EQUAL T_MINUS_EQUAL T_MUL_EQUAL T_DIV_EQUAL T_CONCAT_EQUAL T_MOD_EQUAL T_AND_EQUAL T_OR_EQUAL T_XOR_EQUAL T_SL_EQUAL T_SR_EQUAL T_POW_EQUAL -%left '?' ':' -%left T_BOOLEAN_OR -%left T_BOOLEAN_AND -%left '|' -%left '^' -%left '&' -%nonassoc T_IS_EQUAL T_IS_NOT_EQUAL T_IS_IDENTICAL T_IS_NOT_IDENTICAL -%nonassoc '<' T_IS_SMALLER_OR_EQUAL '>' T_IS_GREATER_OR_EQUAL -%left T_SL T_SR -%left '+' '-' '.' -%left '*' '/' '%' -%right '!' -%nonassoc T_INSTANCEOF -%right '~' T_INC T_DEC T_INT_CAST T_DOUBLE_CAST T_STRING_CAST T_ARRAY_CAST T_OBJECT_CAST T_BOOL_CAST T_UNSET_CAST '@' -%right T_POW -%right '[' -%nonassoc T_NEW T_CLONE -%left T_ELSEIF -%left T_ELSE -%left T_ENDIF -%right T_STATIC T_ABSTRACT T_FINAL T_PRIVATE T_PROTECTED T_PUBLIC - -%type function interface_entry -%type possible_comma -%type case_separator -%type is_reference is_variadic - -%type top_statement use_declaration use_function_declaration use_const_declaration common_scalar -%type static_class_constant compound_variable reference_variable class_name variable_class_name -%type dim_offset expr expr_without_variable r_variable w_variable rw_variable variable base_variable_with_function_calls -%type base_variable array_function_dereference function_call inner_statement statement unticked_statement -%type statement global_var static_scalar scalar class_constant static_class_name_scalar class_name_scalar -%type encaps_var encaps_var encaps_var_offset general_constant isset_variable internal_functions_in_yacc assignment_list_element -%type variable_name variable_without_objects dynamic_class_name_reference new_expr class_name_reference static_member -%type function_call fully_qualified_class_name combined_scalar combined_scalar_offset general_constant parenthesis_expr -%type exit_expr yield_expr function_declaration_statement class_declaration_statement constant_declaration -%type else_single new_else_single unset_variable declare_statement parameter_list non_empty_parameter_list -%type finally_statement additional_catch unticked_function_declaration_statement unticked_class_declaration_statement -%type optional_class_type parameter class_entry_type class_statement class_constant_declaration -%type trait_use_statement function_call_parameter trait_adaptation_statement trait_precedence trait_alias -%type trait_method_reference_fully_qualified trait_method_reference trait_modifiers member_modifier method -%type static_scalar_value static_operation static_var_list global_var_list -%type ctor_arguments function_call_parameter_list echo_expr_list class_variable_declaration -%type trait_adaptations unset_variables declare_list non_empty_array_pair_list array_pair_list -%type switch_case_list non_empty_function_call_parameter_list assignment_list lexical_var_list -%type method_body trait_reference_list static_array_pair_list non_empty_static_array_pair_list -%type foreach_statement for_statement while_statement isset_variables -%type foreach_variable foreach_optional_arg for_expr non_empty_for_expr -%type extends_from interface_list trait_list namespace_name -%type implements_list use_declarations use_function_declarations use_const_declarations -%type interface_extends_list -%type lexical_vars - -%type top_statement_list -%type inner_statement_list encaps_list -%type elseif_list new_elseif_list -%type case_list catch_statement additional_catches -%type non_empty_additional_catches class_statement_list -%type class_statement_list variable_modifiers method_modifiers -%type trait_adaptation_list non_empty_trait_adaptation_list -%type non_empty_member_modifiers backticks_expr - -%type chaining_dereference chaining_instance_call chaining_method_or_property instance_call variable_property -%type method_or_not array_method_dereference object_property object_dim_list dynamic_class_name_variable_property -%type dynamic_class_name_variable_properties variable_properties - -%type simple_indirect_reference - -%% - -start: - top_statement_list - { - yylex.(*Parser).currentToken.Value = nil - - yylex.(*Parser).rootNode = &ast.Root{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1), - Stmts: $1, - EndTkn: yylex.(*Parser).currentToken, - } - } -; - -top_statement_list: - top_statement_list top_statement - { - if $2 != nil { - $$ = append($1, $2) - } - } - | /* empty */ - { - $$ = []ast.Vertex{} - } -; - -namespace_name: - T_STRING - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{ - &ast.NamePart{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - StringTkn: $1, - Value: $1.Value, - }, - }, - } - } - | namespace_name T_NS_SEPARATOR T_STRING - { - part := &ast.NamePart{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - StringTkn: $3, - Value: $3.Value, - } - - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, part) - - $$ = $1 - } -; - -top_statement: - error - { - // error - $$ = nil - } - | statement - { - $$ = $1 - } - | function_declaration_statement - { - $$ = $1 - } - | class_declaration_statement - { - $$ = $1 - } - | T_HALT_COMPILER '(' ')' ';' - { - $$ = &ast.StmtHaltCompiler{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - HaltCompilerTkn: $1, - OpenParenthesisTkn: $2, - CloseParenthesisTkn: $3, - SemiColonTkn: $4, - } - } - | T_NAMESPACE namespace_name ';' - { - $$ = &ast.StmtNamespace{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - NsTkn: $1, - Name: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($2.(*ParserSeparatedList).Items), - Parts: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - }, - SemiColonTkn: $3, - } - } - | T_NAMESPACE namespace_name '{' top_statement_list '}' - { - $$ = &ast.StmtNamespace{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $5), - NsTkn: $1, - Name: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($2.(*ParserSeparatedList).Items), - Parts: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - }, - OpenCurlyBracketTkn: $3, - Stmts: $4, - CloseCurlyBracketTkn: $5, - } - } - | T_NAMESPACE '{' top_statement_list '}' - { - $$ = &ast.StmtNamespace{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - NsTkn: $1, - OpenCurlyBracketTkn: $2, - Stmts: $3, - CloseCurlyBracketTkn: $4, - } - } - | T_USE use_declarations ';' - { - $$ = &ast.StmtUseList{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - UseTkn: $1, - Uses: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - SemiColonTkn: $3, - } - } - | T_USE T_FUNCTION use_function_declarations ';' - { - $$ = &ast.StmtUseList{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - UseTkn: $1, - Type: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($2), - IdentifierTkn: $2, - Value: $2.Value, - }, - Uses: $3.(*ParserSeparatedList).Items, - SeparatorTkns: $3.(*ParserSeparatedList).SeparatorTkns, - SemiColonTkn: $4, - } - } - | T_USE T_CONST use_const_declarations ';' - { - $$ = &ast.StmtUseList{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - UseTkn: $1, - Type: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($2), - IdentifierTkn: $2, - Value: $2.Value, - }, - Uses: $3.(*ParserSeparatedList).Items, - SeparatorTkns: $3.(*ParserSeparatedList).SeparatorTkns, - SemiColonTkn: $4, - } - } - | constant_declaration ';' - { - $1.(*ast.StmtConstList).SemiColonTkn = $2 - $1.(*ast.StmtConstList).Position = yylex.(*Parser).builder.NewNodeTokenPosition($1, $2) - $$ = $1 - } -; - -use_declarations: - use_declarations ',' use_declaration - { - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, $3) - - $$ = $1 - } - | use_declaration - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{$1}, - } - } -; - -use_declaration: - namespace_name - { - $$ = &ast.StmtUse{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Use: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Parts: $1.(*ParserSeparatedList).Items, - SeparatorTkns: $1.(*ParserSeparatedList).SeparatorTkns, - }, - } - } - | namespace_name T_AS T_STRING - { - $$ = &ast.StmtUse{ - Position: yylex.(*Parser).builder.NewNodeListTokenPosition($1.(*ParserSeparatedList).Items, $3), - Use: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Parts: $1.(*ParserSeparatedList).Items, - SeparatorTkns: $1.(*ParserSeparatedList).SeparatorTkns, - }, - AsTkn: $2, - Alias: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - } - } - | T_NS_SEPARATOR namespace_name - { - $$ = &ast.StmtUse{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $2.(*ParserSeparatedList).Items), - NsSeparatorTkn: $1, - Use: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($2.(*ParserSeparatedList).Items), - Parts: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - }, - } - } - | T_NS_SEPARATOR namespace_name T_AS T_STRING - { - $$ = &ast.StmtUse{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - NsSeparatorTkn: $1, - Use: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($2.(*ParserSeparatedList).Items), - Parts: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - }, - AsTkn: $3, - Alias: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($4), - IdentifierTkn: $4, - Value: $4.Value, - }, - } - } -; - -use_function_declarations: - use_function_declarations ',' use_function_declaration - { - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, $3) - - $$ = $1 - } - | use_function_declaration - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{$1}, - } - } -; - -use_function_declaration: - namespace_name - { - $$ = &ast.StmtUse{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Use: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Parts: $1.(*ParserSeparatedList).Items, - SeparatorTkns: $1.(*ParserSeparatedList).SeparatorTkns, - }, - } - } - | namespace_name T_AS T_STRING - { - $$ = &ast.StmtUse{ - Position: yylex.(*Parser).builder.NewNodeListTokenPosition($1.(*ParserSeparatedList).Items, $3), - Use: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Parts: $1.(*ParserSeparatedList).Items, - SeparatorTkns: $1.(*ParserSeparatedList).SeparatorTkns, - }, - AsTkn: $2, - Alias: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - } - } - | T_NS_SEPARATOR namespace_name - { - $$ = &ast.StmtUse{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $2.(*ParserSeparatedList).Items), - NsSeparatorTkn: $1, - Use: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($2.(*ParserSeparatedList).Items), - Parts: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - }, - } - } - | T_NS_SEPARATOR namespace_name T_AS T_STRING - { - $$ = &ast.StmtUse{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - NsSeparatorTkn: $1, - Use: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($2.(*ParserSeparatedList).Items), - Parts: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - }, - AsTkn: $3, - Alias: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($4), - IdentifierTkn: $4, - Value: $4.Value, - }, - } - } -; - -use_const_declarations: - use_const_declarations ',' use_const_declaration - { - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, $3) - - $$ = $1 - } - | use_const_declaration - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{$1}, - } - } -; - -use_const_declaration: - namespace_name - { - $$ = &ast.StmtUse{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Use: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Parts: $1.(*ParserSeparatedList).Items, - SeparatorTkns: $1.(*ParserSeparatedList).SeparatorTkns, - }, - } - } - | namespace_name T_AS T_STRING - { - $$ = &ast.StmtUse{ - Position: yylex.(*Parser).builder.NewNodeListTokenPosition($1.(*ParserSeparatedList).Items, $3), - Use: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Parts: $1.(*ParserSeparatedList).Items, - SeparatorTkns: $1.(*ParserSeparatedList).SeparatorTkns, - }, - AsTkn: $2, - Alias: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - } - } - | T_NS_SEPARATOR namespace_name - { - $$ = &ast.StmtUse{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $2.(*ParserSeparatedList).Items), - NsSeparatorTkn: $1, - Use: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($2.(*ParserSeparatedList).Items), - Parts: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - }, - } - } - | T_NS_SEPARATOR namespace_name T_AS T_STRING - { - $$ = &ast.StmtUse{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - NsSeparatorTkn: $1, - Use: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($2.(*ParserSeparatedList).Items), - Parts: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - }, - AsTkn: $3, - Alias: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($4), - IdentifierTkn: $4, - Value: $4.Value, - }, - } - } -; - -constant_declaration: - constant_declaration ',' T_STRING '=' static_scalar - { - constList := $1.(*ast.StmtConstList) - constList.Position = yylex.(*Parser).builder.NewNodesPosition($1, $5) - constList.SeparatorTkns = append(constList.SeparatorTkns, $2) - constList.Consts = append(constList.Consts, &ast.StmtConstant{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($3, $5), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - EqualTkn: $4, - Expr: $5, - }) - - $$ = $1 - } - | T_CONST T_STRING '=' static_scalar - { - $$ = &ast.StmtConstList{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $4), - ConstTkn: $1, - Consts: []ast.Vertex{ - &ast.StmtConstant{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($2, $4), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($2), - IdentifierTkn: $2, - Value: $2.Value, - }, - EqualTkn: $3, - Expr: $4, - }, - }, - } - } -; - -inner_statement_list: - inner_statement_list inner_statement - { - if $2 != nil { - $$ = append($1, $2) - } - } - | /* empty */ - { - $$ = []ast.Vertex{} - } -; - - -inner_statement: - error - { - // error - $$ = nil - } - | statement - { - $$ = $1 - } - | function_declaration_statement - { - $$ = $1 - } - | class_declaration_statement - { - $$ = $1 - } - | T_HALT_COMPILER '(' ')' ';' - { - $$ = &ast.StmtHaltCompiler{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - HaltCompilerTkn: $1, - OpenParenthesisTkn: $2, - CloseParenthesisTkn: $3, - SemiColonTkn: $4, - } - } -; - - -statement: - unticked_statement - { - $$ = $1 - } - | T_STRING ':' - { - $$ = &ast.StmtLabel{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $2), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - ColonTkn: $2, - } - } -; - -unticked_statement: - '{' inner_statement_list '}' - { - $$ = &ast.StmtStmtList{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenCurlyBracketTkn: $1, - Stmts: $2, - CloseCurlyBracketTkn: $3, - } - } - | T_IF parenthesis_expr statement elseif_list else_single - { - pos := yylex.(*Parser).builder.NewTokenNodePosition($1, $3) - if $5 != nil { - pos = yylex.(*Parser).builder.NewTokenNodePosition($1, $5) - } else if len($4) > 0 { - pos = yylex.(*Parser).builder.NewTokenNodeListPosition($1, $4) - } - - $$ = &ast.StmtIf{ - Position: pos, - IfTkn: $1, - OpenParenthesisTkn: $2.(*ast.ExprBrackets).OpenParenthesisTkn, - Cond: $2.(*ast.ExprBrackets).Expr, - CloseParenthesisTkn: $2.(*ast.ExprBrackets).CloseParenthesisTkn, - Stmt: $3, - ElseIf: $4, - Else: $5, - } - } - | T_IF parenthesis_expr ':' inner_statement_list new_elseif_list new_else_single T_ENDIF ';' - { - $$ = &ast.StmtIf{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $8), - IfTkn: $1, - OpenParenthesisTkn: $2.(*ast.ExprBrackets).OpenParenthesisTkn, - Cond: $2.(*ast.ExprBrackets).Expr, - CloseParenthesisTkn: $2.(*ast.ExprBrackets).CloseParenthesisTkn, - ColonTkn: $3, - Stmt: &ast.StmtStmtList{ - Position: yylex.(*Parser).builder.NewNodeListPosition($4), - Stmts: $4, - }, - ElseIf: $5, - Else: $6, - EndIfTkn: $7, - SemiColonTkn: $8, - } - } - | T_WHILE parenthesis_expr while_statement - { - $3.(*ast.StmtWhile).WhileTkn = $1 - $3.(*ast.StmtWhile).OpenParenthesisTkn = $2.(*ast.ExprBrackets).OpenParenthesisTkn - $3.(*ast.StmtWhile).Cond = $2.(*ast.ExprBrackets).Expr - $3.(*ast.StmtWhile).CloseParenthesisTkn = $2.(*ast.ExprBrackets).CloseParenthesisTkn - $3.(*ast.StmtWhile).Position = yylex.(*Parser).builder.NewTokenNodePosition($1, $3) - - $$ = $3 - } - | T_DO statement T_WHILE parenthesis_expr ';' - { - $$ = &ast.StmtDo{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $5), - DoTkn: $1, - Stmt: $2, - WhileTkn: $3, - OpenParenthesisTkn: $4.(*ast.ExprBrackets).OpenParenthesisTkn, - Cond: $4.(*ast.ExprBrackets).Expr, - CloseParenthesisTkn: $4.(*ast.ExprBrackets).CloseParenthesisTkn, - SemiColonTkn: $5, - } - } - | T_FOR '(' for_expr ';' for_expr ';' for_expr ')' for_statement - { - $9.(*ast.StmtFor).ForTkn = $1 - $9.(*ast.StmtFor).OpenParenthesisTkn = $2 - $9.(*ast.StmtFor).Init = $3.(*ParserSeparatedList).Items - $9.(*ast.StmtFor).InitSeparatorTkns = $3.(*ParserSeparatedList).SeparatorTkns - $9.(*ast.StmtFor).InitSemiColonTkn = $4 - $9.(*ast.StmtFor).Cond = $5.(*ParserSeparatedList).Items - $9.(*ast.StmtFor).CondSeparatorTkns = $5.(*ParserSeparatedList).SeparatorTkns - $9.(*ast.StmtFor).CondSemiColonTkn = $6 - $9.(*ast.StmtFor).Loop = $7.(*ParserSeparatedList).Items - $9.(*ast.StmtFor).LoopSeparatorTkns = $7.(*ParserSeparatedList).SeparatorTkns - $9.(*ast.StmtFor).CloseParenthesisTkn = $8 - $9.(*ast.StmtFor).Position = yylex.(*Parser).builder.NewTokenNodePosition($1, $9) - - $$ = $9 - } - | T_SWITCH parenthesis_expr switch_case_list - { - $3.(*ast.StmtSwitch).SwitchTkn = $1 - $3.(*ast.StmtSwitch).OpenParenthesisTkn = $2.(*ast.ExprBrackets).OpenParenthesisTkn - $3.(*ast.StmtSwitch).Cond = $2.(*ast.ExprBrackets).Expr - $3.(*ast.StmtSwitch).CloseParenthesisTkn = $2.(*ast.ExprBrackets).CloseParenthesisTkn - $3.(*ast.StmtSwitch).Position = yylex.(*Parser).builder.NewTokenNodePosition($1, $3) - - $$ = $3 - } - | T_BREAK ';' - { - $$ = &ast.StmtBreak{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $2), - BreakTkn: $1, - SemiColonTkn: $2, - } - } - | T_BREAK expr ';' - { - $$ = &ast.StmtBreak{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - BreakTkn: $1, - Expr: $2, - SemiColonTkn: $3, - } - } - | T_CONTINUE ';' - { - $$ = &ast.StmtContinue{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $2), - ContinueTkn: $1, - SemiColonTkn: $2, - } - } - | T_CONTINUE expr ';' - { - $$ = &ast.StmtContinue{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - ContinueTkn: $1, - Expr: $2, - SemiColonTkn: $3, - } - } - | T_RETURN ';' - { - $$ = &ast.StmtReturn{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $2), - ReturnTkn: $1, - SemiColonTkn: $2, - } - } - | T_RETURN expr_without_variable ';' - { - $$ = &ast.StmtReturn{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - ReturnTkn: $1, - Expr: $2, - SemiColonTkn: $3, - } - } - | T_RETURN variable ';' - { - $$ = &ast.StmtReturn{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - ReturnTkn: $1, - Expr: $2, - SemiColonTkn: $3, - } - } - | yield_expr ';' - { - $$ = &ast.StmtExpression{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $2), - Expr: $1, - SemiColonTkn: $2, - } - } - | T_GLOBAL global_var_list ';' - { - $2.(*ast.StmtGlobal).GlobalTkn = $1 - $2.(*ast.StmtGlobal).SemiColonTkn = $3 - $2.(*ast.StmtGlobal).Position = yylex.(*Parser).builder.NewTokensPosition($1, $3) - - $$ = $2 - } - | T_STATIC static_var_list ';' - { - $2.(*ast.StmtStatic).StaticTkn = $1 - $2.(*ast.StmtStatic).SemiColonTkn = $3 - $2.(*ast.StmtStatic).Position = yylex.(*Parser).builder.NewTokensPosition($1, $3) - - $$ = $2 - } - | T_ECHO echo_expr_list ';' - { - $2.(*ast.StmtEcho).EchoTkn = $1 - $2.(*ast.StmtEcho).SemiColonTkn = $3 - $2.(*ast.StmtEcho).Position = yylex.(*Parser).builder.NewTokensPosition($1, $3) - - $$ = $2 - } - | T_INLINE_HTML - { - $$ = &ast.StmtInlineHtml{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - InlineHtmlTkn: $1, - Value: $1.Value, - } - } - | expr ';' - { - $$ = &ast.StmtExpression{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $2), - Expr: $1, - SemiColonTkn: $2, - } - } - | T_UNSET '(' unset_variables ')' ';' - { - $3.(*ast.StmtUnset).UnsetTkn = $1 - $3.(*ast.StmtUnset).OpenParenthesisTkn = $2 - $3.(*ast.StmtUnset).CloseParenthesisTkn = $4 - $3.(*ast.StmtUnset).SemiColonTkn = $5 - $3.(*ast.StmtUnset).Position = yylex.(*Parser).builder.NewTokensPosition($1, $5) - - $$ = $3 - } - | T_FOREACH '(' variable T_AS foreach_variable foreach_optional_arg ')' foreach_statement - { - foreach := $8.(*ast.StmtForeach) - - foreach.Position = yylex.(*Parser).builder.NewTokenNodePosition($1, $8) - foreach.ForeachTkn = $1 - foreach.OpenParenthesisTkn = $2 - foreach.Expr = $3 - foreach.AsTkn = $4 - foreach.Var = $5 - foreach.CloseParenthesisTkn = $7 - - if $6 != nil { - foreach.Key = foreach.Var - foreach.DoubleArrowTkn = $6.(*ast.StmtForeach).DoubleArrowTkn - foreach.Var = $6.(*ast.StmtForeach).Var - } - - if val, ok := foreach.Key.(*ast.StmtForeach); ok { - yylex.(*Parser).errHandlerFunc(errors.NewError("Key element cannot be a reference", val.AmpersandTkn.Position)) - foreach.Key = val.Var - } - - if val, ok := foreach.Var.(*ast.StmtForeach); ok { - foreach.AmpersandTkn = val.AmpersandTkn - foreach.Var = val.Var - } - - $$ = foreach - } - | T_FOREACH '(' expr_without_variable T_AS foreach_variable foreach_optional_arg ')' foreach_statement - { - foreach := $8.(*ast.StmtForeach) - - foreach.Position = yylex.(*Parser).builder.NewTokenNodePosition($1, $8) - foreach.ForeachTkn = $1 - foreach.OpenParenthesisTkn = $2 - foreach.Expr = $3 - foreach.AsTkn = $4 - foreach.Var = $5 - foreach.CloseParenthesisTkn = $7 - - if $6 != nil { - foreach.Key = foreach.Var - foreach.DoubleArrowTkn = $6.(*ast.StmtForeach).DoubleArrowTkn - foreach.Var = $6.(*ast.StmtForeach).Var - } - - if val, ok := foreach.Key.(*ast.StmtForeach); ok { - yylex.(*Parser).errHandlerFunc(errors.NewError("Key element cannot be a reference", val.AmpersandTkn.Position)) - foreach.Key = val.Var - } - - if val, ok := foreach.Var.(*ast.StmtForeach); ok { - foreach.AmpersandTkn = val.AmpersandTkn - foreach.Var = val.Var - } - - $$ = foreach - } - | T_DECLARE '(' declare_list ')' declare_statement - { - $5.(*ast.StmtDeclare).DeclareTkn = $1 - $5.(*ast.StmtDeclare).OpenParenthesisTkn = $2 - $5.(*ast.StmtDeclare).Consts = $3.(*ParserSeparatedList).Items - $5.(*ast.StmtDeclare).SeparatorTkns = $3.(*ParserSeparatedList).SeparatorTkns - $5.(*ast.StmtDeclare).CloseParenthesisTkn = $4 - $5.(*ast.StmtDeclare).Position = yylex.(*Parser).builder.NewTokenNodePosition($1, $5) - - $$ = $5 - } - | ';' - { - $$ = &ast.StmtNop{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - SemiColonTkn: $1, - } - } - | T_TRY '{' inner_statement_list '}' catch_statement finally_statement - { - pos := yylex.(*Parser).builder.NewTokenNodeListPosition($1, $5) - if $6 != nil { - pos = yylex.(*Parser).builder.NewTokenNodePosition($1, $6) - } - - $$ = &ast.StmtTry{ - Position: pos, - TryTkn: $1, - OpenCurlyBracketTkn: $2, - Stmts: $3, - CloseCurlyBracketTkn: $4, - Catches: $5, - Finally: $6, - } - } - | T_THROW expr ';' - { - $$ = &ast.StmtThrow{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - ThrowTkn: $1, - Expr: $2, - SemiColonTkn: $3, - } - } - | T_GOTO T_STRING ';' - { - $$ = &ast.StmtGoto{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - GotoTkn: $1, - Label: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $2, - Value: $2.Value, - }, - SemiColonTkn: $3, - } - } -; - -catch_statement: - /* empty */ - { - $$ = []ast.Vertex{} - } - | T_CATCH '(' fully_qualified_class_name T_VARIABLE ')' '{' inner_statement_list '}' additional_catches - { - catch := &ast.StmtCatch{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $8), - CatchTkn: $1, - OpenParenthesisTkn: $2, - Types: []ast.Vertex{$3}, - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($4), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($4), - IdentifierTkn: $4, - Value: $4.Value, - }, - }, - CloseParenthesisTkn: $5, - OpenCurlyBracketTkn: $6, - Stmts: $7, - CloseCurlyBracketTkn: $8, - } - $$ = append([]ast.Vertex{catch}, $9...) - } -; - -finally_statement: - /* empty */ - { - $$ = nil - } - | T_FINALLY '{' inner_statement_list '}' - { - $$ = &ast.StmtFinally{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - FinallyTkn: $1, - OpenCurlyBracketTkn: $2, - Stmts: $3, - CloseCurlyBracketTkn: $4, - } - } -; - -additional_catches: - non_empty_additional_catches - { - $$ = $1 - } - | /* empty */ - { - $$ = []ast.Vertex{} - } -; - -non_empty_additional_catches: - additional_catch - { - $$ = []ast.Vertex{$1} - } - | non_empty_additional_catches additional_catch - { - $$ = append($1, $2) - } -; - -additional_catch: - T_CATCH '(' fully_qualified_class_name T_VARIABLE ')' '{' inner_statement_list '}' - { - $$ = &ast.StmtCatch{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $8), - CatchTkn: $1, - OpenParenthesisTkn: $2, - Types: []ast.Vertex{$3}, - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($4), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($4), - IdentifierTkn: $4, - Value: $4.Value, - }, - }, - CloseParenthesisTkn: $5, - OpenCurlyBracketTkn: $6, - Stmts: $7, - CloseCurlyBracketTkn: $8, - } - } -; - -unset_variables: - unset_variable - { - $$ = &ast.StmtUnset{ - Vars: []ast.Vertex{$1}, - } - } - | unset_variables ',' unset_variable - { - $1.(*ast.StmtUnset).Vars = append($1.(*ast.StmtUnset).Vars, $3) - $1.(*ast.StmtUnset).SeparatorTkns = append($1.(*ast.StmtUnset).SeparatorTkns, $2) - - $$ = $1 - } -; - -unset_variable: - variable - { - $$ = $1 - } -; - -function_declaration_statement: - unticked_function_declaration_statement - { - $$ = $1 - } -; - -class_declaration_statement: - unticked_class_declaration_statement - { - $$ = $1 - } -; - -is_reference: - /* empty */ - { - $$ = nil - } - | '&' - { - $$ = $1 - } -; - -is_variadic: - /* empty */ - { - $$ = nil - } - | T_ELLIPSIS - { - $$ = $1 - } -; - -unticked_function_declaration_statement: - function is_reference T_STRING '(' parameter_list ')' '{' inner_statement_list '}' - { - $$ = &ast.StmtFunction{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $9), - FunctionTkn: $1, - AmpersandTkn: $2, - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - OpenParenthesisTkn: $4, - Params: $5.(*ParserSeparatedList).Items, - SeparatorTkns: $5.(*ParserSeparatedList).SeparatorTkns, - CloseParenthesisTkn: $6, - OpenCurlyBracketTkn: $7, - Stmts: $8, - CloseCurlyBracketTkn: $9, - } - } -; - -unticked_class_declaration_statement: - class_entry_type T_STRING extends_from implements_list '{' class_statement_list '}' - { - switch n := $1.(type) { - case *ast.StmtClass : - className := &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($2), - IdentifierTkn: $2, - Value: $2.Value, - } - - n.Position = yylex.(*Parser).builder.NewNodeTokenPosition($1, $7) - n.Name = className - n.OpenCurlyBracketTkn = $5 - n.Stmts = $6 - n.CloseCurlyBracketTkn = $7 - - if $3 != nil { - n.ExtendsTkn = $3.(*ast.StmtClass).ExtendsTkn - n.Extends = $3.(*ast.StmtClass).Extends - } - - if $4 != nil { - n.ImplementsTkn = $4.(*ast.StmtClass).ImplementsTkn - n.Implements = $4.(*ast.StmtClass).Implements - n.ImplementsSeparatorTkns = $4.(*ast.StmtClass).ImplementsSeparatorTkns - } - case *ast.StmtTrait : - traitName := &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($2), - IdentifierTkn: $2, - Value: $2.Value, - } - - n.Position = yylex.(*Parser).builder.NewNodeTokenPosition($1, $7) - n.Name = traitName - n.OpenCurlyBracketTkn = $5 - n.Stmts = $6 - n.CloseCurlyBracketTkn = $7 - - if $3 != nil { - yylex.(*Parser).errHandlerFunc(errors.NewError("A trait cannot extend a class. Traits can only be composed from other traits with the 'use' keyword", $3.(*ast.StmtClass).Position)) - } - - if $4 != nil { - yylex.(*Parser).errHandlerFunc(errors.NewError("A trait cannot implement an interface", $4.(*ast.StmtClass).Position)) - } - } - - $$ = $1 - } - | interface_entry T_STRING interface_extends_list '{' class_statement_list '}' - { - iface := &ast.StmtInterface{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $6), - InterfaceTkn: $1, - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($2), - IdentifierTkn: $2, - Value: $2.Value, - }, - OpenCurlyBracketTkn: $4, - Stmts: $5, - CloseCurlyBracketTkn: $6, - } - - if $3 != nil { - iface.ExtendsTkn = $3.(*ast.StmtInterface).ExtendsTkn - iface.Extends = $3.(*ast.StmtInterface).Extends - iface.ExtendsSeparatorTkns = $3.(*ast.StmtInterface).ExtendsSeparatorTkns - } - - $$ = iface - } -; - - -class_entry_type: - T_CLASS - { - $$ = &ast.StmtClass{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - ClassTkn: $1, - } - } - | T_ABSTRACT T_CLASS - { - $$ = &ast.StmtClass{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $2), - Modifiers: []ast.Vertex{ - &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - }, - ClassTkn: $2, - } - } - | T_TRAIT - { - $$ = &ast.StmtTrait{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - TraitTkn: $1, - } - } - | T_FINAL T_CLASS - { - $$ = &ast.StmtClass{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $2), - Modifiers: []ast.Vertex{ - &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - }, - ClassTkn: $2, - } - } -; - -extends_from: - /* empty */ - { - $$ = nil - } - | T_EXTENDS fully_qualified_class_name - { - $$ = &ast.StmtClass{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - ExtendsTkn: $1, - Extends: $2, - } - } -; - -interface_entry: - T_INTERFACE - { - $$ = $1 - } -; - -interface_extends_list: - /* empty */ - { - $$ = nil - } - | T_EXTENDS interface_list - { - $$ = &ast.StmtInterface{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $2.(*ParserSeparatedList).Items), - ExtendsTkn: $1, - Extends: $2.(*ParserSeparatedList).Items, - ExtendsSeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - }; - } -; - -implements_list: - /* empty */ - { - $$ = nil - } - | T_IMPLEMENTS interface_list - { - $$ = &ast.StmtClass{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $2.(*ParserSeparatedList).Items), - ImplementsTkn: $1, - Implements: $2.(*ParserSeparatedList).Items, - ImplementsSeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - }; - } -; - -interface_list: - fully_qualified_class_name - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{$1}, - } - } - | interface_list ',' fully_qualified_class_name - { - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, $3) - - $$ = $1 - } -; - -foreach_optional_arg: - /* empty */ - { - $$ = nil - } - | T_DOUBLE_ARROW foreach_variable - { - $$ = &ast.StmtForeach{ - DoubleArrowTkn: $1, - Var: $2, - } - } -; - -foreach_variable: - variable - { - $$ = $1 - } - | '&' variable - { - $$ = &ast.StmtForeach{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - AmpersandTkn: $1, - Var: $2, - } - } - | T_LIST '(' assignment_list ')' - { - pairList := $3.(*ParserSeparatedList) - fistPair := pairList.Items[0].(*ast.ExprArrayItem) - - if fistPair.Key == nil && fistPair.Val == nil && len(pairList.Items) == 1 { - pairList.Items = nil - } - - $$ = &ast.ExprList{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - ListTkn: $1, - OpenBracketTkn: $2, - Items: $3.(*ParserSeparatedList).Items, - SeparatorTkns: $3.(*ParserSeparatedList).SeparatorTkns, - CloseBracketTkn: $4, - } - } -; - -for_statement: - statement - { - $$ = &ast.StmtFor{ - Position: yylex.(*Parser).builder.NewNodePosition($1), - Stmt: $1, - } - } - | ':' inner_statement_list T_ENDFOR ';' - { - $$ = &ast.StmtFor{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - ColonTkn: $1, - Stmt: &ast.StmtStmtList{ - Position: yylex.(*Parser).builder.NewNodeListPosition($2), - Stmts: $2, - }, - EndForTkn: $3, - SemiColonTkn: $4, - } - } -; - -foreach_statement: - statement - { - $$ = &ast.StmtForeach{ - Position: yylex.(*Parser).builder.NewNodePosition($1), - Stmt: $1, - } - } - | ':' inner_statement_list T_ENDFOREACH ';' - { - $$ = &ast.StmtForeach{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - ColonTkn: $1, - Stmt: &ast.StmtStmtList{ - Position: yylex.(*Parser).builder.NewNodeListPosition($2), - Stmts: $2, - }, - EndForeachTkn: $3, - SemiColonTkn: $4, - } - } -; - - -declare_statement: - statement - { - $$ = &ast.StmtDeclare{ - Position: yylex.(*Parser).builder.NewNodePosition($1), - Stmt: $1, - } - } - | ':' inner_statement_list T_ENDDECLARE ';' - { - $$ = &ast.StmtDeclare{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - ColonTkn: $1, - Stmt: &ast.StmtStmtList{ - Position: yylex.(*Parser).builder.NewNodeListPosition($2), - Stmts: $2, - }, - EndDeclareTkn: $3, - SemiColonTkn: $4, - } - } -; - - -declare_list: - T_STRING '=' static_scalar - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{ - &ast.StmtConstant{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $3), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - EqualTkn: $2, - Expr: $3, - }, - }, - } - } - | declare_list ',' T_STRING '=' static_scalar - { - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append( - $1.(*ParserSeparatedList).Items, - &ast.StmtConstant{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($3, $5), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - EqualTkn: $4, - Expr: $5, - }, - ) - - $$ = $1 - } -; - - -switch_case_list: - '{' case_list '}' - { - $$ = &ast.StmtSwitch{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenCurlyBracketTkn: $1, - Cases: $2, - CloseCurlyBracketTkn: $3, - } - } - | '{' ';' case_list '}' - { - $$ = &ast.StmtSwitch{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - OpenCurlyBracketTkn: $1, - CaseSeparatorTkn: $2, - Cases: $3, - CloseCurlyBracketTkn: $4, - } - } - | ':' case_list T_ENDSWITCH ';' - { - $$ = &ast.StmtSwitch{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - ColonTkn: $1, - Cases: $2, - EndSwitchTkn: $3, - SemiColonTkn: $4, - } - } - | ':' ';' case_list T_ENDSWITCH ';' - { - $$ = &ast.StmtSwitch{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $5), - ColonTkn: $1, - CaseSeparatorTkn: $2, - Cases: $3, - EndSwitchTkn: $4, - SemiColonTkn: $5, - } - } -; - - -case_list: - /* empty */ - { - $$ = nil - } - | case_list T_CASE expr case_separator inner_statement_list - { - $$ = append($1, &ast.StmtCase{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($2, $5), - CaseTkn: $2, - Cond: $3, - CaseSeparatorTkn: $4, - Stmts: $5, - }) - } - | case_list T_DEFAULT case_separator inner_statement_list - { - $$ = append($1, &ast.StmtDefault{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($2, $4), - DefaultTkn: $2, - CaseSeparatorTkn: $3, - Stmts: $4, - }) - } -; - - -case_separator: - ':' - { - $$ = $1 - } - | ';' - { - $$ = $1 - } -; - - -while_statement: - statement - { - $$ = &ast.StmtWhile{ - Position: yylex.(*Parser).builder.NewNodePosition($1), - Stmt: $1, - } - } - | ':' inner_statement_list T_ENDWHILE ';' - { - $$ = &ast.StmtWhile{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - ColonTkn: $1, - Stmt: &ast.StmtStmtList{ - Position: yylex.(*Parser).builder.NewNodeListPosition($2), - Stmts: $2, - }, - EndWhileTkn: $3, - SemiColonTkn: $4, - } - } -; - - - -elseif_list: - /* empty */ - { - $$ = nil - } - | elseif_list T_ELSEIF parenthesis_expr statement - { - $$ = append($1, &ast.StmtElseIf{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($2, $4), - ElseIfTkn: $2, - OpenParenthesisTkn: $3.(*ast.ExprBrackets).OpenParenthesisTkn, - Cond: $3.(*ast.ExprBrackets).Expr, - CloseParenthesisTkn: $3.(*ast.ExprBrackets).CloseParenthesisTkn, - Stmt: $4, - }) - } -; - - -new_elseif_list: - /* empty */ - { - $$ = nil - } - | new_elseif_list T_ELSEIF parenthesis_expr ':' inner_statement_list - { - $$ = append($1, &ast.StmtElseIf{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($2, $5), - ElseIfTkn: $2, - OpenParenthesisTkn: $3.(*ast.ExprBrackets).OpenParenthesisTkn, - Cond: $3.(*ast.ExprBrackets).Expr, - CloseParenthesisTkn: $3.(*ast.ExprBrackets).CloseParenthesisTkn, - ColonTkn: $4, - Stmt: &ast.StmtStmtList{ - Position: yylex.(*Parser).builder.NewNodeListPosition($5), - Stmts: $5, - }, - }) - } -; - - -else_single: - /* empty */ - { - $$ = nil - } - | T_ELSE statement - { - $$ = &ast.StmtElse{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - ElseTkn: $1, - Stmt: $2, - } - } -; - - -new_else_single: - /* empty */ - { - $$ = nil - } - | T_ELSE ':' inner_statement_list - { - $$ = &ast.StmtElse{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $3), - ElseTkn: $1, - ColonTkn: $2, - Stmt: &ast.StmtStmtList{ - Position: yylex.(*Parser).builder.NewNodeListPosition($3), - Stmts: $3, - }, - } - } -; - - -parameter_list: - non_empty_parameter_list - { - $$ = $1 - } - | /* empty */ - { - $$ = &ParserSeparatedList{} - } -; - -non_empty_parameter_list: - parameter - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{$1}, - } - } - | non_empty_parameter_list ',' parameter - { - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, $3) - - $$ = $1 - } -; - -parameter: - optional_class_type is_reference is_variadic T_VARIABLE - { - pos := yylex.(*Parser).builder.NewTokenPosition($4) - if $1 != nil { - pos = yylex.(*Parser).builder.NewNodeTokenPosition($1, $4) - } else if $2 != nil { - pos = yylex.(*Parser).builder.NewTokensPosition($2, $4) - } else if $3 != nil { - pos = yylex.(*Parser).builder.NewTokensPosition($3, $4) - } - - $$ = &ast.Parameter{ - Position: pos, - Type: $1, - AmpersandTkn: $2, - VariadicTkn: $3, - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($4), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($4), - IdentifierTkn: $4, - Value: $4.Value, - }, - }, - } - } - | optional_class_type is_reference is_variadic T_VARIABLE '=' expr - { - pos := yylex.(*Parser).builder.NewTokenNodePosition($4, $6) - if $1 != nil { - pos = yylex.(*Parser).builder.NewNodesPosition($1, $6) - } else if $2 != nil { - pos = yylex.(*Parser).builder.NewTokenNodePosition($2, $6) - } else if $3 != nil { - pos = yylex.(*Parser).builder.NewTokenNodePosition($3, $6) - } - - $$ = &ast.Parameter{ - Position: pos, - Type: $1, - AmpersandTkn: $2, - VariadicTkn: $3, - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($4), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($4), - IdentifierTkn: $4, - Value: $4.Value, - }, - }, - EqualTkn: $5, - DefaultValue: $6, - } - } -; - - -optional_class_type: - /* empty */ - { - $$ = nil - } - | T_ARRAY - { - $$ = &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - } - } - | T_CALLABLE - { - $$ = &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - } - } - | fully_qualified_class_name - { - $$ = $1 - } -; - - -function_call_parameter_list: - '(' ')' - { - $$ = &ArgumentList{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $2), - OpenParenthesisTkn: $1, - CloseParenthesisTkn: $2, - } - } - | '(' non_empty_function_call_parameter_list ')' - { - argumentList := $2.(*ArgumentList) - argumentList.Position = yylex.(*Parser).builder.NewTokensPosition($1, $3) - argumentList.OpenParenthesisTkn = $1 - argumentList.CloseParenthesisTkn = $3 - - $$ = argumentList - } - | '(' yield_expr ')' - { - $$ = &ArgumentList{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenParenthesisTkn: $1, - Arguments: []ast.Vertex{ - &ast.Argument{ - Position: yylex.(*Parser).builder.NewNodePosition($2), - Expr: $2, - }, - }, - CloseParenthesisTkn: $3, - } - } -; - - -non_empty_function_call_parameter_list: - function_call_parameter - { - $$ = &ArgumentList{ - Arguments: []ast.Vertex{$1}, - } - } - | non_empty_function_call_parameter_list ',' function_call_parameter - { - $1.(*ArgumentList).SeparatorTkns = append($1.(*ArgumentList).SeparatorTkns, $2) - $1.(*ArgumentList).Arguments = append($1.(*ArgumentList).Arguments, $3) - - $$ = $1 - } -; - -function_call_parameter: - expr_without_variable - { - $$ = &ast.Argument{ - Position: yylex.(*Parser).builder.NewNodePosition($1), - Expr: $1, - } - } - | variable - { - $$ = &ast.Argument{ - Position: yylex.(*Parser).builder.NewNodePosition($1), - Expr: $1, - } - } - | '&' w_variable - { - $$ = &ast.Argument{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - AmpersandTkn: $1, - Expr: $2, - } - } - | T_ELLIPSIS expr - { - $$ = &ast.Argument{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - VariadicTkn: $1, - Expr: $2, - } - } -; - -global_var_list: - global_var_list ',' global_var - { - $1.(*ast.StmtGlobal).Vars = append($1.(*ast.StmtGlobal).Vars, $3) - $1.(*ast.StmtGlobal).SeparatorTkns = append($1.(*ast.StmtGlobal).SeparatorTkns, $2) - - $$ = $1 - } - | global_var - { - $$ = &ast.StmtGlobal{ - Vars: []ast.Vertex{$1}, - } - } -; - - -global_var: - T_VARIABLE - { - $$ = &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - } - } - | '$' r_variable - { - $$ = &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - DollarTkn: $1, - Name: $2, - } - } - | '$' '{' expr '}' - { - $$ = &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - DollarTkn: $1, - OpenCurlyBracketTkn: $2, - Name: $3, - CloseCurlyBracketTkn: $4, - } - } -; - - -static_var_list: - static_var_list ',' T_VARIABLE - { - $1.(*ast.StmtStatic).Vars = append($1.(*ast.StmtStatic).Vars, &ast.StmtStaticVar{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - }, - }) - $1.(*ast.StmtStatic).SeparatorTkns = append($1.(*ast.StmtStatic).SeparatorTkns, $2) - - $$ = $1 - } - | static_var_list ',' T_VARIABLE '=' static_scalar - { - $1.(*ast.StmtStatic).Vars = append($1.(*ast.StmtStatic).Vars, &ast.StmtStaticVar{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($3, $5), - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - }, - EqualTkn: $4, - Expr: $5, - }) - $1.(*ast.StmtStatic).SeparatorTkns = append($1.(*ast.StmtStatic).SeparatorTkns, $2) - - $$ = $1 - } - | T_VARIABLE - { - $$ = &ast.StmtStatic{ - Vars: []ast.Vertex{ - &ast.StmtStaticVar{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - }, - }, - }, - } - } - | T_VARIABLE '=' static_scalar - { - $$ = &ast.StmtStatic{ - Vars: []ast.Vertex{ - &ast.StmtStaticVar{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $3), - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - }, - EqualTkn: $2, - Expr: $3, - }, - }, - } - } -; - - -class_statement_list: - class_statement_list class_statement - { - $$ = append($1, $2) - } - | /* empty */ - { - $$ = []ast.Vertex{} - } -; - - -class_statement: - variable_modifiers class_variable_declaration ';' - { - $$ = &ast.StmtPropertyList{ - Position: yylex.(*Parser).builder.NewNodeListTokenPosition($1, $3), - Modifiers: $1, - Props: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - SemiColonTkn: $3, - } - } - | class_constant_declaration ';' - { - $1.(*ast.StmtClassConstList).SemiColonTkn = $2 - $1.(*ast.StmtClassConstList).Position = yylex.(*Parser).builder.NewNodeTokenPosition($1, $2) - $$ = $1 - } - | trait_use_statement - { - $$ = $1 - } - | method_modifiers function is_reference T_STRING '(' parameter_list ')' method_body - { - pos := yylex.(*Parser).builder.NewTokenNodePosition($2, $8) - if $1 != nil { - pos = yylex.(*Parser).builder.NewNodeListNodePosition($1, $8) - } - - $$ = &ast.StmtClassMethod{ - Position: pos, - Modifiers: $1, - FunctionTkn: $2, - AmpersandTkn: $3, - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($4), - IdentifierTkn: $4, - Value: $4.Value, - }, - OpenParenthesisTkn: $5, - Params: $6.(*ParserSeparatedList).Items, - SeparatorTkns: $6.(*ParserSeparatedList).SeparatorTkns, - CloseParenthesisTkn: $7, - Stmt: $8, - } - } -; - -trait_use_statement: - T_USE trait_list trait_adaptations - { - traitUse := &ast.StmtTraitUse{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $3), - UseTkn: $1, - Traits: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - } - - switch n := $3.(type) { - case *TraitAdaptationList : - traitUse.OpenCurlyBracketTkn = n.OpenCurlyBracketTkn - traitUse.Adaptations = n.Adaptations - traitUse.CloseCurlyBracketTkn = n.CloseCurlyBracketTkn - case *ast.StmtNop : - traitUse.SemiColonTkn = n.SemiColonTkn - }; - - $$ = traitUse - } -; - -trait_list: - fully_qualified_class_name - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{$1}, - } - } - | trait_list ',' fully_qualified_class_name - { - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, $3) - - $$ = $1 - } -; - -trait_adaptations: - ';' - { - $$ = &ast.StmtNop{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - SemiColonTkn: $1, - } - } - | '{' trait_adaptation_list '}' - { - $$ = &TraitAdaptationList{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenCurlyBracketTkn: $1, - Adaptations: $2, - CloseCurlyBracketTkn: $3, - } - } -; - -trait_adaptation_list: - /* empty */ - { - $$ = nil - } - | non_empty_trait_adaptation_list - { - $$ = $1 - } -; - -non_empty_trait_adaptation_list: - trait_adaptation_statement - { - $$ = []ast.Vertex{$1} - } - | non_empty_trait_adaptation_list trait_adaptation_statement - { - $$ = append($1, $2) - } -; - -trait_adaptation_statement: - trait_precedence ';' - { - $1.(*ast.StmtTraitUsePrecedence).SemiColonTkn = $2 - - $$ = $1; - } - | trait_alias ';' - { - $1.(*ast.StmtTraitUseAlias).SemiColonTkn = $2 - - $$ = $1; - } -; - -trait_precedence: - trait_method_reference_fully_qualified T_INSTEADOF trait_reference_list - { - $$ = &ast.StmtTraitUsePrecedence{ - Position: yylex.(*Parser).builder.NewNodeNodeListPosition($1, $3.(*ParserSeparatedList).Items), - Trait: $1.(*TraitMethodRef).Trait, - DoubleColonTkn: $1.(*TraitMethodRef).DoubleColonTkn, - Method: $1.(*TraitMethodRef).Method, - InsteadofTkn: $2, - Insteadof: $3.(*ParserSeparatedList).Items, - SeparatorTkns: $3.(*ParserSeparatedList).SeparatorTkns, - } - } -; - -trait_reference_list: - fully_qualified_class_name - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{$1}, - } - } - | trait_reference_list ',' fully_qualified_class_name - { - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, $3) - - $$ = $1 - } -; - -trait_method_reference: - T_STRING - { - $$ = &TraitMethodRef{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Method: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - } - } - | trait_method_reference_fully_qualified - { - $$ = $1 - } -; - -trait_method_reference_fully_qualified: - fully_qualified_class_name T_PAAMAYIM_NEKUDOTAYIM T_STRING - { - $$ = &TraitMethodRef{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $3), - Trait: $1, - DoubleColonTkn: $2, - Method: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - } - } -; - -trait_alias: - trait_method_reference T_AS trait_modifiers T_STRING - { - $$ = &ast.StmtTraitUseAlias{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $4), - Trait: $1.(*TraitMethodRef).Trait, - DoubleColonTkn: $1.(*TraitMethodRef).DoubleColonTkn, - Method: $1.(*TraitMethodRef).Method, - AsTkn: $2, - Modifier: $3, - Alias: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($4), - IdentifierTkn: $4, - Value: $4.Value, - }, - } - } - | trait_method_reference T_AS member_modifier - { - $$ = &ast.StmtTraitUseAlias{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Trait: $1.(*TraitMethodRef).Trait, - DoubleColonTkn: $1.(*TraitMethodRef).DoubleColonTkn, - Method: $1.(*TraitMethodRef).Method, - AsTkn: $2, - Modifier: $3, - } - } -; - -trait_modifiers: - /* empty */ - { - $$ = nil - } - | member_modifier - { - $$ = $1 - } -; - -method_body: - ';' /* abstract method */ - { - $$ = &ast.StmtNop{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - SemiColonTkn: $1, - } - } - | '{' inner_statement_list '}' - { - $$ = &ast.StmtStmtList{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenCurlyBracketTkn: $1, - Stmts: $2, - CloseCurlyBracketTkn: $3, - } - } -; - -variable_modifiers: - non_empty_member_modifiers - { - $$ = $1; - } - | T_VAR - { - $$ = []ast.Vertex{ - &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - } - } -; - -method_modifiers: - /* empty */ - { - $$ = nil - } - | non_empty_member_modifiers - { - $$ = $1 - } -; - -non_empty_member_modifiers: - member_modifier - { - $$ = []ast.Vertex{$1} - } - | non_empty_member_modifiers member_modifier - { - $$ = append($1, $2) - } -; - -member_modifier: - T_PUBLIC - { - $$ = &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - } - } - | T_PROTECTED - { - $$ = &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - } - } - | T_PRIVATE - { - $$ = &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - } - } - | T_STATIC - { - $$ = &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - } - } - | T_ABSTRACT - { - $$ = &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - } - } - | T_FINAL - { - $$ = &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - } - } -; - -class_variable_declaration: - class_variable_declaration ',' T_VARIABLE - { - item := &ast.StmtProperty{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - }, - } - - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, item) - - $$ = $1 - } - | class_variable_declaration ',' T_VARIABLE '=' static_scalar - { - item := &ast.StmtProperty{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($3, $5), - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - }, - EqualTkn: $4, - Expr: $5, - } - - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, item) - - $$ = $1 - } - | T_VARIABLE - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{ - &ast.StmtProperty{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - }, - Expr: nil, - }, - }, - } - } - | T_VARIABLE '=' static_scalar - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{ - &ast.StmtProperty{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $3), - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - }, - EqualTkn: $2, - Expr: $3, - }, - }, - } - } -; - -class_constant_declaration: - class_constant_declaration ',' T_STRING '=' static_scalar - { - constList := $1.(*ast.StmtClassConstList) - constList.Position = yylex.(*Parser).builder.NewNodesPosition($1, $5) - constList.SeparatorTkns = append(constList.SeparatorTkns, $2) - constList.Consts = append(constList.Consts, &ast.StmtConstant{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($3, $5), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - EqualTkn: $4, - Expr: $5, - }) - - $$ = $1 - } - | T_CONST T_STRING '=' static_scalar - { - $$ = &ast.StmtClassConstList{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $4), - ConstTkn: $1, - Consts: []ast.Vertex{ - &ast.StmtConstant{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($2, $4), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($2), - IdentifierTkn: $2, - Value: $2.Value, - }, - EqualTkn: $3, - Expr: $4, - }, - }, - } - } -; - -echo_expr_list: - echo_expr_list ',' expr - { - $1.(*ast.StmtEcho).Exprs = append($1.(*ast.StmtEcho).Exprs, $3) - $1.(*ast.StmtEcho).SeparatorTkns = append($1.(*ast.StmtEcho).SeparatorTkns, $2) - - $$ = $1 - } - | expr - { - $$ = &ast.StmtEcho{ - Exprs: []ast.Vertex{$1}, - } - } -; - - -for_expr: - /* empty */ - { - $$ = &ParserSeparatedList{} - } - | non_empty_for_expr - { - $$ = $1 - } -; - -non_empty_for_expr: - non_empty_for_expr ',' expr - { - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, $3) - - $$ = $1 - } - | expr - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{$1}, - } - } -; - -chaining_method_or_property: - chaining_method_or_property variable_property - { - $$ = append($1, $2...) - } - | variable_property - { - $$ = $1 - } -; - -chaining_dereference: - chaining_dereference '[' dim_offset ']' - { - fetch := &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewTokensPosition($2, $4), - Var: nil, - OpenBracketTkn: $2, - Dim: $3, - CloseBracketTkn: $4, - } - - $$ = append($1, fetch) - } - | '[' dim_offset ']' - { - fetch := &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - Var: nil, - OpenBracketTkn: $1, - Dim: $2, - CloseBracketTkn: $3, - } - - $$ = []ast.Vertex{fetch} - } -; - -chaining_instance_call: - chaining_dereference chaining_method_or_property - { - $$ = append($1, $2...) - } - | chaining_dereference - { - $$ = $1 - } - | chaining_method_or_property - { - $$ = $1 - } -; - -instance_call: - /* empty */ - { - $$ = nil - } - | chaining_instance_call - { - $$ = $1 - } -; - -new_expr: - T_NEW class_name_reference ctor_arguments - { - if $3 != nil { - $$ = &ast.ExprNew{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $3), - NewTkn: $1, - Class: $2, - OpenParenthesisTkn: $3.(*ArgumentList).OpenParenthesisTkn, - Args: $3.(*ArgumentList).Arguments, - SeparatorTkns: $3.(*ArgumentList).SeparatorTkns, - CloseParenthesisTkn: $3.(*ArgumentList).CloseParenthesisTkn, - } - } else { - $$ = &ast.ExprNew{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - NewTkn: $1, - Class: $2, - } - } - } -; - -expr_without_variable: - T_LIST '(' assignment_list ')' '=' expr - { - $$ = &ast.ExprAssign{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $6), - Var: &ast.ExprList{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - ListTkn: $1, - OpenBracketTkn: $2, - Items: $3.(*ParserSeparatedList).Items, - SeparatorTkns: $3.(*ParserSeparatedList).SeparatorTkns, - CloseBracketTkn: $4, - }, - EqualTkn: $5, - Expr: $6, - } - } - | variable '=' expr - { - $$ = &ast.ExprAssign{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Var: $1, - EqualTkn: $2, - Expr: $3, - } - } - | variable '=' '&' variable - { - $$ = &ast.ExprAssignReference{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $4), - Var: $1, - EqualTkn: $2, - AmpersandTkn: $3, - Expr: $4, - } - } - | variable '=' '&' T_NEW class_name_reference ctor_arguments - { - var _new *ast.ExprNew - if $6 != nil { - _new = &ast.ExprNew{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($4, $6), - NewTkn: $4, - Class: $5, - OpenParenthesisTkn: $6.(*ArgumentList).OpenParenthesisTkn, - Args: $6.(*ArgumentList).Arguments, - SeparatorTkns: $6.(*ArgumentList).SeparatorTkns, - CloseParenthesisTkn: $6.(*ArgumentList).CloseParenthesisTkn, - } - } else { - _new = &ast.ExprNew{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($4, $5), - NewTkn: $4, - Class: $5, - } - } - - $$ = &ast.ExprAssignReference{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, _new), - Var: $1, - EqualTkn: $2, - AmpersandTkn: $3, - Expr: _new, - } - } - | T_CLONE expr - { - $$ = &ast.ExprClone{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - CloneTkn: $1, - Expr: $2, - } - } - | variable T_PLUS_EQUAL expr - { - $$ = &ast.ExprAssignPlus{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Var: $1, - EqualTkn: $2, - Expr: $3, - } - } - | variable T_MINUS_EQUAL expr - { - $$ = &ast.ExprAssignMinus{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Var: $1, - EqualTkn: $2, - Expr: $3, - } - } - | variable T_MUL_EQUAL expr - { - $$ = &ast.ExprAssignMul{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Var: $1, - EqualTkn: $2, - Expr: $3, - } - } - | variable T_POW_EQUAL expr - { - $$ = &ast.ExprAssignPow{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Var: $1, - EqualTkn: $2, - Expr: $3, - } - } - | variable T_DIV_EQUAL expr - { - $$ = &ast.ExprAssignDiv{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Var: $1, - EqualTkn: $2, - Expr: $3, - } - } - | variable T_CONCAT_EQUAL expr - { - $$ = &ast.ExprAssignConcat{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Var: $1, - EqualTkn: $2, - Expr: $3, - } - } - | variable T_MOD_EQUAL expr - { - $$ = &ast.ExprAssignMod{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Var: $1, - EqualTkn: $2, - Expr: $3, - } - } - | variable T_AND_EQUAL expr - { - $$ = &ast.ExprAssignBitwiseAnd{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Var: $1, - EqualTkn: $2, - Expr: $3, - } - } - | variable T_OR_EQUAL expr - { - $$ = &ast.ExprAssignBitwiseOr{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Var: $1, - EqualTkn: $2, - Expr: $3, - } - } - | variable T_XOR_EQUAL expr - { - $$ = &ast.ExprAssignBitwiseXor{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Var: $1, - EqualTkn: $2, - Expr: $3, - } - } - | variable T_SL_EQUAL expr - { - $$ = &ast.ExprAssignShiftLeft{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Var: $1, - EqualTkn: $2, - Expr: $3, - } - } - | variable T_SR_EQUAL expr - { - $$ = &ast.ExprAssignShiftRight{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Var: $1, - EqualTkn: $2, - Expr: $3, - } - } - | rw_variable T_INC - { - $$ = &ast.ExprPostInc{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $2), - Var: $1, - IncTkn: $2, - } - } - | T_INC rw_variable - { - $$ = &ast.ExprPreInc{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - IncTkn: $1, - Var: $2, - } - } - | rw_variable T_DEC - { - $$ = &ast.ExprPostDec{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $2), - Var: $1, - DecTkn: $2, - } - } - | T_DEC rw_variable - { - $$ = &ast.ExprPreDec{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - DecTkn: $1, - Var: $2, - } - } - | expr T_BOOLEAN_OR expr - { - $$ = &ast.ExprBinaryBooleanOr{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr T_BOOLEAN_AND expr - { - $$ = &ast.ExprBinaryBooleanAnd{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr T_LOGICAL_OR expr - { - $$ = &ast.ExprBinaryLogicalOr{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr T_LOGICAL_AND expr - { - $$ = &ast.ExprBinaryLogicalAnd{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr T_LOGICAL_XOR expr - { - $$ = &ast.ExprBinaryLogicalXor{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr '|' expr - { - $$ = &ast.ExprBinaryBitwiseOr{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr '&' expr - { - $$ = &ast.ExprBinaryBitwiseAnd{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr '^' expr - { - $$ = &ast.ExprBinaryBitwiseXor{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr '.' expr - { - $$ = &ast.ExprBinaryConcat{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr '+' expr - { - $$ = &ast.ExprBinaryPlus{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr '-' expr - { - $$ = &ast.ExprBinaryMinus{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr '*' expr - { - $$ = &ast.ExprBinaryMul{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr T_POW expr - { - $$ = &ast.ExprBinaryPow{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr '/' expr - { - $$ = &ast.ExprBinaryDiv{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr '%' expr - { - $$ = &ast.ExprBinaryMod{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr T_SL expr - { - $$ = &ast.ExprBinaryShiftLeft{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr T_SR expr - { - $$ = &ast.ExprBinaryShiftRight{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | '+' expr %prec T_INC - { - $$ = &ast.ExprUnaryPlus{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - PlusTkn: $1, - Expr: $2, - } - } - | '-' expr %prec T_INC - { - $$ = &ast.ExprUnaryMinus{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - MinusTkn: $1, - Expr: $2, - } - } - | '!' expr - { - $$ = &ast.ExprBooleanNot{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - ExclamationTkn: $1, - Expr: $2, - } - } - | '~' expr - { - $$ = &ast.ExprBitwiseNot{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - TildaTkn: $1, - Expr: $2, - } - } - | expr T_IS_IDENTICAL expr - { - $$ = &ast.ExprBinaryIdentical{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr T_IS_NOT_IDENTICAL expr - { - $$ = &ast.ExprBinaryNotIdentical{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr T_IS_EQUAL expr - { - $$ = &ast.ExprBinaryEqual{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr T_IS_NOT_EQUAL expr - { - $$ = &ast.ExprBinaryNotEqual{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr '<' expr - { - $$ = &ast.ExprBinarySmaller{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr T_IS_SMALLER_OR_EQUAL expr - { - $$ = &ast.ExprBinarySmallerOrEqual{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr '>' expr - { - $$ = &ast.ExprBinaryGreater{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr T_IS_GREATER_OR_EQUAL expr - { - $$ = &ast.ExprBinaryGreaterOrEqual{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | expr T_INSTANCEOF class_name_reference - { - $$ = &ast.ExprInstanceOf{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Expr: $1, - InstanceOfTkn: $2, - Class: $3, - } - } - | parenthesis_expr - { - $$ = $1 - } - | new_expr - { - $$ = $1 - } - | '(' new_expr ')' instance_call - { - $$ = &ast.ExprBrackets{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenParenthesisTkn: $1, - Expr: $2, - CloseParenthesisTkn: $3, - } - - for _, n := range($4) { - switch nn := n.(type) { - case *ast.ExprFunctionCall: - nn.Function = $$ - nn.Position = yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - - case *ast.ExprArrayDimFetch: - nn.Var = $$ - nn.Position = yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - - case *ast.ExprPropertyFetch: - nn.Var = $$ - nn.Position = yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - - case *ast.ExprMethodCall: - nn.Var = $$ - nn.Position = yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - } - } - } - | expr '?' expr ':' expr - { - $$ = &ast.ExprTernary{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $5), - Cond: $1, - QuestionTkn: $2, - IfTrue: $3, - ColonTkn: $4, - IfFalse: $5, - } - } - | expr '?' ':' expr - { - $$ = &ast.ExprTernary{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $4), - Cond: $1, - QuestionTkn: $2, - ColonTkn: $3, - IfFalse: $4, - } - } - | internal_functions_in_yacc - { - $$ = $1 - } - | T_INT_CAST expr - { - $$ = &ast.ExprCastInt{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - CastTkn: $1, - Expr: $2, - } - } - | T_DOUBLE_CAST expr - { - $$ = &ast.ExprCastDouble{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - CastTkn: $1, - Expr: $2, - } - } - | T_STRING_CAST expr - { - $$ = &ast.ExprCastString{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - CastTkn: $1, - Expr: $2, - } - } - | T_ARRAY_CAST expr - { - $$ = &ast.ExprCastArray{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - CastTkn: $1, - Expr: $2, - } - } - | T_OBJECT_CAST expr - { - $$ = &ast.ExprCastObject{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - CastTkn: $1, - Expr: $2, - } - } - | T_BOOL_CAST expr - { - $$ = &ast.ExprCastBool{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - CastTkn: $1, - Expr: $2, - } - } - | T_UNSET_CAST expr - { - $$ = &ast.ExprCastUnset{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - CastTkn: $1, - Expr: $2, - } - } - | T_EXIT exit_expr - { - exit := &ast.ExprExit{ - ExitTkn: $1, - } - - if $2 == nil { - exit.Position = yylex.(*Parser).builder.NewTokenPosition($1) - } else { - exit.Position = yylex.(*Parser).builder.NewTokenNodePosition($1, $2) - exit.OpenParenthesisTkn = $2.(*ast.ExprBrackets).OpenParenthesisTkn - exit.Expr = $2.(*ast.ExprBrackets).Expr - exit.CloseParenthesisTkn = $2.(*ast.ExprBrackets).CloseParenthesisTkn - } - - $$ = exit - } - | '@' expr - { - $$ = &ast.ExprErrorSuppress{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - AtTkn: $1, - Expr: $2, - } - } - | scalar - { - $$ = $1 - } - | combined_scalar_offset - { - $$ = $1 - } - | combined_scalar - { - $$ = $1 - } - | '`' backticks_expr '`' - { - $$ = &ast.ExprShellExec{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenBacktickTkn: $1, - Parts: $2, - CloseBacktickTkn: $3, - } - } - | T_PRINT expr - { - $$ = &ast.ExprPrint{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - PrintTkn: $1, - Expr: $2, - } - } - | T_YIELD - { - $$ = &ast.ExprYield{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - YieldTkn: $1, - } - } - | function is_reference '(' parameter_list ')' lexical_vars '{' inner_statement_list '}' - { - closure := $6.(*ast.ExprClosure) - - closure.Position = yylex.(*Parser).builder.NewTokensPosition($1, $9) - closure.FunctionTkn = $1 - closure.AmpersandTkn = $2 - closure.OpenParenthesisTkn = $3 - closure.Params = $4.(*ParserSeparatedList).Items - closure.SeparatorTkns = $4.(*ParserSeparatedList).SeparatorTkns - closure.CloseParenthesisTkn = $5 - closure.OpenCurlyBracketTkn = $7 - closure.Stmts = $8 - closure.CloseCurlyBracketTkn = $9 - - $$ = closure - } - | T_STATIC function is_reference '(' parameter_list ')' lexical_vars '{' inner_statement_list '}' - { - closure := $7.(*ast.ExprClosure) - - closure.Position = yylex.(*Parser).builder.NewTokensPosition($1, $10) - closure.StaticTkn = $1 - closure.FunctionTkn = $2 - closure.AmpersandTkn = $3 - closure.OpenParenthesisTkn = $4 - closure.Params = $5.(*ParserSeparatedList).Items - closure.SeparatorTkns = $5.(*ParserSeparatedList).SeparatorTkns - closure.CloseParenthesisTkn = $6 - closure.OpenCurlyBracketTkn = $8 - closure.Stmts = $9 - closure.CloseCurlyBracketTkn = $10 - - $$ = closure - } -; - -yield_expr: - T_YIELD expr_without_variable - { - $$ = &ast.ExprYield{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - YieldTkn: $1, - Val: $2, - } - } - | T_YIELD variable - { - $$ = &ast.ExprYield{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - YieldTkn: $1, - Val: $2, - } - } - | T_YIELD expr T_DOUBLE_ARROW expr_without_variable - { - $$ = &ast.ExprYield{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $4), - YieldTkn: $1, - Key: $2, - DoubleArrowTkn: $3, - Val: $4, - } - } - | T_YIELD expr T_DOUBLE_ARROW variable - { - $$ = &ast.ExprYield{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $4), - YieldTkn: $1, - Key: $2, - DoubleArrowTkn: $3, - Val: $4, - } - } -; - -combined_scalar_offset: - combined_scalar '[' dim_offset ']' - { - $$ = &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $4), - Var: $1, - OpenBracketTkn: $2, - Dim: $3, - CloseBracketTkn: $4, - } - } - | combined_scalar_offset '[' dim_offset ']' - { - $$ = &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $4), - Var: $1, - OpenBracketTkn: $2, - Dim: $3, - CloseBracketTkn: $4, - } - } - | T_CONSTANT_ENCAPSED_STRING '[' dim_offset ']' - { - $$ = &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - Var: &ast.ScalarString{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - StringTkn: $1, - Value: $1.Value, - }, - OpenBracketTkn: $2, - Dim: $3, - CloseBracketTkn: $4, - } - } - | general_constant '[' dim_offset ']' - { - $$ = &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $4), - Var: $1, - OpenBracketTkn: $2, - Dim: $3, - CloseBracketTkn: $4, - } - } -; - -combined_scalar: - T_ARRAY '(' array_pair_list ')' - { - $$ = &ast.ExprArray{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - ArrayTkn: $1, - OpenBracketTkn: $2, - Items: $3.(*ParserSeparatedList).Items, - SeparatorTkns: $3.(*ParserSeparatedList).SeparatorTkns, - CloseBracketTkn: $4, - } - } - | '[' array_pair_list ']' - { - $$ = &ast.ExprArray{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenBracketTkn: $1, - Items: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - CloseBracketTkn: $3, - } - } -; - -function: - T_FUNCTION - { - $$ = $1 - } -; - -lexical_vars: - /* empty */ - { - $$ = &ast.ExprClosure{} - } - | T_USE '(' lexical_var_list ')' - { - $$ = &ast.ExprClosure{ - UseTkn: $1, - UseOpenParenthesisTkn: $2, - Uses: $3.(*ParserSeparatedList).Items, - UseSeparatorTkns: $3.(*ParserSeparatedList).SeparatorTkns, - UseCloseParenthesisTkn: $4, - } - } -; - -lexical_var_list: - lexical_var_list ',' T_VARIABLE - { - variable := &ast.ExprClosureUse{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - }, - } - - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, variable) - - $$ = $1 - } - | lexical_var_list ',' '&' T_VARIABLE - { - variable := &ast.ExprClosureUse{ - Position: yylex.(*Parser).builder.NewTokensPosition($3, $4), - AmpersandTkn: $3, - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($4), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($4), - IdentifierTkn: $4, - Value: $4.Value, - }, - }, - } - - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, variable) - - $$ = $1 - } - | T_VARIABLE - { - variable := &ast.ExprClosureUse{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - }, - } - - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{ variable }, - } - } - | '&' T_VARIABLE - { - variable := &ast.ExprClosureUse{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $2), - AmpersandTkn: $1, - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($2), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($2), - IdentifierTkn: $2, - Value: $2.Value, - }, - }, - } - - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{ variable }, - } - } -; - -function_call: - namespace_name function_call_parameter_list - { - $$ = &ast.ExprFunctionCall{ - Position: yylex.(*Parser).builder.NewNodeListNodePosition($1.(*ParserSeparatedList).Items, $2), - Function: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Parts: $1.(*ParserSeparatedList).Items, - SeparatorTkns: $1.(*ParserSeparatedList).SeparatorTkns, - }, - OpenParenthesisTkn: $2.(*ArgumentList).OpenParenthesisTkn, - Args: $2.(*ArgumentList).Arguments, - SeparatorTkns: $2.(*ArgumentList).SeparatorTkns, - CloseParenthesisTkn: $2.(*ArgumentList).CloseParenthesisTkn, - } - } - | T_NAMESPACE T_NS_SEPARATOR namespace_name function_call_parameter_list - { - $$ = &ast.ExprFunctionCall{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $4), - Function: &ast.NameRelative{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $3.(*ParserSeparatedList).Items), - NsTkn: $1, - NsSeparatorTkn: $2, - Parts: $3.(*ParserSeparatedList).Items, - SeparatorTkns: $3.(*ParserSeparatedList).SeparatorTkns, - }, - OpenParenthesisTkn: $4.(*ArgumentList).OpenParenthesisTkn, - Args: $4.(*ArgumentList).Arguments, - SeparatorTkns: $4.(*ArgumentList).SeparatorTkns, - CloseParenthesisTkn: $4.(*ArgumentList).CloseParenthesisTkn, - } - } - | T_NS_SEPARATOR namespace_name function_call_parameter_list - { - $$ = &ast.ExprFunctionCall{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $3), - Function: &ast.NameFullyQualified{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $2.(*ParserSeparatedList).Items), - NsSeparatorTkn: $1, - Parts: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - }, - OpenParenthesisTkn: $3.(*ArgumentList).OpenParenthesisTkn, - Args: $3.(*ArgumentList).Arguments, - SeparatorTkns: $3.(*ArgumentList).SeparatorTkns, - CloseParenthesisTkn: $3.(*ArgumentList).CloseParenthesisTkn, - } - } - | class_name T_PAAMAYIM_NEKUDOTAYIM variable_name function_call_parameter_list - { - staticCall := &ast.ExprStaticCall{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $4), - Class: $1, - DoubleColonTkn: $2, - Call: $3, - OpenParenthesisTkn: $4.(*ArgumentList).OpenParenthesisTkn, - Args: $4.(*ArgumentList).Arguments, - SeparatorTkns: $4.(*ArgumentList).SeparatorTkns, - CloseParenthesisTkn: $4.(*ArgumentList).CloseParenthesisTkn, - } - - if brackets, ok := $3.(*ParserBrackets); ok { - staticCall.OpenCurlyBracketTkn = brackets.OpenBracketTkn - staticCall.Call = brackets.Child - staticCall.CloseCurlyBracketTkn = brackets.CloseBracketTkn - } - - $$ = staticCall - } - | class_name T_PAAMAYIM_NEKUDOTAYIM variable_without_objects function_call_parameter_list - { - $$ = &ast.ExprStaticCall{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $4), - Class: $1, - DoubleColonTkn: $2, - Call: $3, - OpenParenthesisTkn: $4.(*ArgumentList).OpenParenthesisTkn, - Args: $4.(*ArgumentList).Arguments, - SeparatorTkns: $4.(*ArgumentList).SeparatorTkns, - CloseParenthesisTkn: $4.(*ArgumentList).CloseParenthesisTkn, - } - } - | variable_class_name T_PAAMAYIM_NEKUDOTAYIM variable_name function_call_parameter_list - { - staticCall := &ast.ExprStaticCall{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $4), - Class: $1, - DoubleColonTkn: $2, - Call: $3, - OpenParenthesisTkn: $4.(*ArgumentList).OpenParenthesisTkn, - Args: $4.(*ArgumentList).Arguments, - SeparatorTkns: $4.(*ArgumentList).SeparatorTkns, - CloseParenthesisTkn: $4.(*ArgumentList).CloseParenthesisTkn, - } - - if brackets, ok := $3.(*ParserBrackets); ok { - staticCall.OpenCurlyBracketTkn = brackets.OpenBracketTkn - staticCall.Call = brackets.Child - staticCall.CloseCurlyBracketTkn = brackets.CloseBracketTkn - } - - $$ = staticCall - } - | variable_class_name T_PAAMAYIM_NEKUDOTAYIM variable_without_objects function_call_parameter_list - { - $$ = &ast.ExprStaticCall{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $4), - Class: $1, - DoubleColonTkn: $2, - Call: $3, - OpenParenthesisTkn: $4.(*ArgumentList).OpenParenthesisTkn, - Args: $4.(*ArgumentList).Arguments, - SeparatorTkns: $4.(*ArgumentList).SeparatorTkns, - CloseParenthesisTkn: $4.(*ArgumentList).CloseParenthesisTkn, - } - } - | variable_without_objects function_call_parameter_list - { - $$ = &ast.ExprFunctionCall{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $2), - Function: $1, - OpenParenthesisTkn: $2.(*ArgumentList).OpenParenthesisTkn, - Args: $2.(*ArgumentList).Arguments, - SeparatorTkns: $2.(*ArgumentList).SeparatorTkns, - CloseParenthesisTkn: $2.(*ArgumentList).CloseParenthesisTkn, - } - } -; - -class_name: - T_STATIC - { - $$ = &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - } - } - | namespace_name - { - $$ = &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Parts: $1.(*ParserSeparatedList).Items, - SeparatorTkns: $1.(*ParserSeparatedList).SeparatorTkns, - } - } - | T_NAMESPACE T_NS_SEPARATOR namespace_name - { - $$ = &ast.NameRelative{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $3.(*ParserSeparatedList).Items), - NsTkn: $1, - NsSeparatorTkn: $2, - Parts: $3.(*ParserSeparatedList).Items, - SeparatorTkns: $3.(*ParserSeparatedList).SeparatorTkns, - } - } - | T_NS_SEPARATOR namespace_name - { - $$ = &ast.NameFullyQualified{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $2.(*ParserSeparatedList).Items), - NsSeparatorTkn: $1, - Parts: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - } - } -; - -fully_qualified_class_name: - namespace_name - { - $$ = &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Parts: $1.(*ParserSeparatedList).Items, - SeparatorTkns: $1.(*ParserSeparatedList).SeparatorTkns, - } - } - | T_NAMESPACE T_NS_SEPARATOR namespace_name - { - $$ = &ast.NameRelative{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $3.(*ParserSeparatedList).Items), - NsTkn: $1, - NsSeparatorTkn: $2, - Parts: $3.(*ParserSeparatedList).Items, - SeparatorTkns: $3.(*ParserSeparatedList).SeparatorTkns, - } - } - | T_NS_SEPARATOR namespace_name - { - $$ = &ast.NameFullyQualified{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $2.(*ParserSeparatedList).Items), - NsSeparatorTkn: $1, - Parts: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - } - } -; - -class_name_reference: - class_name - { - $$ = $1 - } - | dynamic_class_name_reference - { - $$ = $1 - } -; - -dynamic_class_name_reference: - base_variable T_OBJECT_OPERATOR object_property dynamic_class_name_variable_properties - { - $$ = $1 - - $3[0].(*ast.ExprPropertyFetch).ObjectOperatorTkn = $2 - - for _, n := range($3) { - switch nn := n.(type) { - case *ast.ExprArrayDimFetch: - nn.Var = $$ - *$$.GetPosition() = *yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - - case *ast.ExprPropertyFetch: - nn.Var = $$ - *$$.GetPosition() = *yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - } - } - - for _, n := range($4) { - switch nn := n.(type) { - case *ast.ExprArrayDimFetch: - nn.Var = $$ - *$$.GetPosition() = *yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - - case *ast.ExprPropertyFetch: - nn.Var = $$ - *$$.GetPosition() = *yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - } - } - } - | base_variable - { - $$ = $1 - } -; - - -dynamic_class_name_variable_properties: - dynamic_class_name_variable_properties dynamic_class_name_variable_property - { - $$ = append($1, $2...) - } - | /* empty */ - { - $$ = []ast.Vertex{} - } -; - - -dynamic_class_name_variable_property: - T_OBJECT_OPERATOR object_property - { - $2[0].(*ast.ExprPropertyFetch).ObjectOperatorTkn = $1 - - $$ = $2 - } -; - -exit_expr: - /* empty */ - { - $$ = nil - } - | '(' ')' - { - $$ = &ast.ExprBrackets{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $2), - OpenParenthesisTkn: $1, - CloseParenthesisTkn: $2, - } - } - | parenthesis_expr - { - $$ = $1 - } -; - -backticks_expr: - /* empty */ - { - $$ = []ast.Vertex{} - } - | T_ENCAPSED_AND_WHITESPACE - { - $$ = []ast.Vertex{ - &ast.ScalarEncapsedStringPart{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - EncapsedStrTkn: $1, - Value: $1.Value, - }, - } - } - | encaps_list - { - $$ = $1; - } -; - -ctor_arguments: - /* empty */ - { - $$ = nil - } - | function_call_parameter_list - { - $$ = $1 - } -; - -common_scalar: - T_LNUMBER - { - $$ = &ast.ScalarLnumber{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - NumberTkn: $1, - Value: $1.Value, - } - } - | T_DNUMBER - { - $$ = &ast.ScalarDnumber{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - NumberTkn: $1, - Value: $1.Value, - } - } - | T_CONSTANT_ENCAPSED_STRING - { - $$ = &ast.ScalarString{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - StringTkn: $1, - Value: $1.Value, - } - } - | T_LINE - { - $$ = &ast.ScalarMagicConstant{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - MagicConstTkn: $1, - Value: $1.Value, - } - } - | T_FILE - { - $$ = &ast.ScalarMagicConstant{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - MagicConstTkn: $1, - Value: $1.Value, - } - } - | T_DIR - { - $$ = &ast.ScalarMagicConstant{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - MagicConstTkn: $1, - Value: $1.Value, - } - } - | T_TRAIT_C - { - $$ = &ast.ScalarMagicConstant{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - MagicConstTkn: $1, - Value: $1.Value, - } - } - | T_METHOD_C - { - $$ = &ast.ScalarMagicConstant{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - MagicConstTkn: $1, - Value: $1.Value, - } - } - | T_FUNC_C - { - $$ = &ast.ScalarMagicConstant{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - MagicConstTkn: $1, - Value: $1.Value, - } - } - | T_NS_C - { - $$ = &ast.ScalarMagicConstant{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - MagicConstTkn: $1, - Value: $1.Value, - } - } - | T_START_HEREDOC T_ENCAPSED_AND_WHITESPACE T_END_HEREDOC - { - $$ = &ast.ScalarHeredoc{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenHeredocTkn: $1, - Parts: []ast.Vertex{ - &ast.ScalarEncapsedStringPart{ - Position: yylex.(*Parser).builder.NewTokenPosition($2), - EncapsedStrTkn: $2, - Value: $2.Value, - }, - }, - CloseHeredocTkn: $3, - } - } - | T_START_HEREDOC T_END_HEREDOC - { - $$ = &ast.ScalarHeredoc{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $2), - OpenHeredocTkn: $1, - CloseHeredocTkn: $2, - } - } -; - -static_class_constant: - class_name T_PAAMAYIM_NEKUDOTAYIM T_STRING - { - $$ = &ast.ExprClassConstFetch{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $3), - Class: $1, - DoubleColonTkn: $2, - Const: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - } - } -; - -static_scalar: - static_scalar_value - { - $$ = $1 - } -; - -static_scalar_value: - common_scalar - { - $$ = $1 - } - | static_class_name_scalar - { - $$ = $1 - } - | namespace_name - { - $$ = &ast.ExprConstFetch{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Const: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Parts: $1.(*ParserSeparatedList).Items, - SeparatorTkns: $1.(*ParserSeparatedList).SeparatorTkns, - }, - } - } - | T_NAMESPACE T_NS_SEPARATOR namespace_name - { - $$ = &ast.ExprConstFetch{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $3.(*ParserSeparatedList).Items), - Const: &ast.NameRelative{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $3.(*ParserSeparatedList).Items), - NsTkn: $1, - NsSeparatorTkn: $2, - Parts: $3.(*ParserSeparatedList).Items, - SeparatorTkns: $3.(*ParserSeparatedList).SeparatorTkns, - }, - } - } - | T_NS_SEPARATOR namespace_name - { - $$ = &ast.ExprConstFetch{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $2.(*ParserSeparatedList).Items), - Const: &ast.NameFullyQualified{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $2.(*ParserSeparatedList).Items), - NsSeparatorTkn: $1, - Parts: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - }, - } - } - | T_ARRAY '(' static_array_pair_list ')' - { - $$ = &ast.ExprArray{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - ArrayTkn: $1, - OpenBracketTkn: $2, - Items: $3.(*ParserSeparatedList).Items, - SeparatorTkns: $3.(*ParserSeparatedList).SeparatorTkns, - CloseBracketTkn: $4, - } - } - | '[' static_array_pair_list ']' - { - $$ = &ast.ExprArray{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenBracketTkn: $1, - Items: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - CloseBracketTkn: $3, - } - } - | static_class_constant - { - $$ = $1 - } - | T_CLASS_C - { - $$ = &ast.ScalarMagicConstant{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - MagicConstTkn: $1, - Value: $1.Value, - } - } - | static_operation - { - $$ = $1 - } -; - -static_operation: - static_scalar_value '[' static_scalar_value ']' - { - $$ = &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $4), - Var: $1, - OpenBracketTkn: $2, - Dim: $3, - CloseBracketTkn: $4, - } - } - | static_scalar_value '+' static_scalar_value - { - $$ = &ast.ExprBinaryPlus{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value '-' static_scalar_value - { - $$ = &ast.ExprBinaryMinus{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value '*' static_scalar_value - { - $$ = &ast.ExprBinaryMul{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value T_POW static_scalar_value - { - $$ = &ast.ExprBinaryPow{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value '/' static_scalar_value - { - $$ = &ast.ExprBinaryDiv{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value '%' static_scalar_value - { - $$ = &ast.ExprBinaryMod{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | '!' static_scalar_value - { - $$ = &ast.ExprBooleanNot{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - ExclamationTkn: $1, - Expr: $2, - } - } - | '~' static_scalar_value - { - $$ = &ast.ExprBitwiseNot{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - TildaTkn: $1, - Expr: $2, - } - } - | static_scalar_value '|' static_scalar_value - { - $$ = &ast.ExprBinaryBitwiseOr{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value '&' static_scalar_value - { - $$ = &ast.ExprBinaryBitwiseAnd{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value '^' static_scalar_value - { - $$ = &ast.ExprBinaryBitwiseXor{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value T_SL static_scalar_value - { - $$ = &ast.ExprBinaryShiftLeft{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value T_SR static_scalar_value - { - $$ = &ast.ExprBinaryShiftRight{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value '.' static_scalar_value - { - $$ = &ast.ExprBinaryConcat{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value T_LOGICAL_XOR static_scalar_value - { - $$ = &ast.ExprBinaryLogicalXor{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value T_LOGICAL_AND static_scalar_value - { - $$ = &ast.ExprBinaryLogicalAnd{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value T_LOGICAL_OR static_scalar_value - { - $$ = &ast.ExprBinaryLogicalOr{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value T_BOOLEAN_AND static_scalar_value - { - $$ = &ast.ExprBinaryBooleanAnd{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value T_BOOLEAN_OR static_scalar_value - { - $$ = &ast.ExprBinaryBooleanOr{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value T_IS_IDENTICAL static_scalar_value - { - $$ = &ast.ExprBinaryIdentical{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value T_IS_NOT_IDENTICAL static_scalar_value - { - $$ = &ast.ExprBinaryNotIdentical{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value T_IS_EQUAL static_scalar_value - { - $$ = &ast.ExprBinaryEqual{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value T_IS_NOT_EQUAL static_scalar_value - { - $$ = &ast.ExprBinaryNotEqual{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value '<' static_scalar_value - { - $$ = &ast.ExprBinarySmaller{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value '>' static_scalar_value - { - $$ = &ast.ExprBinaryGreater{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value T_IS_SMALLER_OR_EQUAL static_scalar_value - { - $$ = &ast.ExprBinarySmallerOrEqual{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value T_IS_GREATER_OR_EQUAL static_scalar_value - { - $$ = &ast.ExprBinaryGreaterOrEqual{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Left: $1, - OpTkn: $2, - Right: $3, - } - } - | static_scalar_value '?' ':' static_scalar_value - { - $$ = &ast.ExprTernary{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $4), - Cond: $1, - QuestionTkn: $2, - ColonTkn: $3, - IfFalse: $4, - } - } - | static_scalar_value '?' static_scalar_value ':' static_scalar_value - { - $$ = &ast.ExprTernary{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $5), - Cond: $1, - QuestionTkn: $2, - IfTrue: $3, - ColonTkn: $4, - IfFalse: $5, - } - } - | '+' static_scalar_value - { - $$ = &ast.ExprUnaryPlus{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - PlusTkn: $1, - Expr: $2, - } - } - | '-' static_scalar_value - { - $$ = &ast.ExprUnaryMinus{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - MinusTkn: $1, - Expr: $2, - } - } - | '(' static_scalar_value ')' - { - $$ = &ast.ExprBrackets{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenParenthesisTkn: $1, - Expr: $2, - CloseParenthesisTkn: $3, - } - } -; - -general_constant: - class_constant - { - $$ = $1 - } - | namespace_name - { - $$ = &ast.ExprConstFetch{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Const: &ast.Name{ - Position: yylex.(*Parser).builder.NewNodeListPosition($1.(*ParserSeparatedList).Items), - Parts: $1.(*ParserSeparatedList).Items, - SeparatorTkns: $1.(*ParserSeparatedList).SeparatorTkns, - }, - } - } - | T_NAMESPACE T_NS_SEPARATOR namespace_name - { - $$ = &ast.ExprConstFetch{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $3.(*ParserSeparatedList).Items), - Const: &ast.NameRelative{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $3.(*ParserSeparatedList).Items), - NsTkn: $1, - NsSeparatorTkn: $2, - Parts: $3.(*ParserSeparatedList).Items, - SeparatorTkns: $3.(*ParserSeparatedList).SeparatorTkns, - }, - } - } - | T_NS_SEPARATOR namespace_name - { - $$ = &ast.ExprConstFetch{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $2.(*ParserSeparatedList).Items), - Const: &ast.NameFullyQualified{ - Position: yylex.(*Parser).builder.NewTokenNodeListPosition($1, $2.(*ParserSeparatedList).Items), - NsSeparatorTkn: $1, - Parts: $2.(*ParserSeparatedList).Items, - SeparatorTkns: $2.(*ParserSeparatedList).SeparatorTkns, - }, - } - } -; - -scalar: - T_STRING_VARNAME - { - $$ = &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - } - } - | general_constant - { - $$ = $1 - } - | class_name_scalar - { - $$ = $1 - } - | common_scalar - { - $$ = $1 - } - | '"' encaps_list '"' - { - $$ = &ast.ScalarEncapsed{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenQuoteTkn: $1, - Parts: $2, - CloseQuoteTkn: $3, - } - } - | T_START_HEREDOC encaps_list T_END_HEREDOC - { - $$ = &ast.ScalarHeredoc{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenHeredocTkn: $1, - Parts: $2, - CloseHeredocTkn: $3, - } - } - | T_CLASS_C - { - $$ = &ast.ScalarMagicConstant{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - MagicConstTkn: $1, - Value: $1.Value, - } - } -; - -static_array_pair_list: - /* empty */ - { - $$ = &ParserSeparatedList{} - } - | non_empty_static_array_pair_list possible_comma - { - if $2 != nil { - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, &ast.ExprArrayItem{}) - } - - $$ = $1 - } -; - -possible_comma: - /* empty */ - { - $$ = nil - } - | ',' - { - $$ = $1 - } -; - -non_empty_static_array_pair_list: - non_empty_static_array_pair_list ',' static_scalar_value T_DOUBLE_ARROW static_scalar_value - { - arrayItem := &ast.ExprArrayItem{ - Position: yylex.(*Parser).builder.NewNodesPosition($3, $5), - Key: $3, - DoubleArrowTkn: $4, - Val: $5, - } - - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, arrayItem) - - $$ = $1 - } - | non_empty_static_array_pair_list ',' static_scalar_value - { - arrayItem := &ast.ExprArrayItem{ - Position: yylex.(*Parser).builder.NewNodePosition($3), - Val: $3, - } - - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, arrayItem) - - $$ = $1 - } - | static_scalar_value T_DOUBLE_ARROW static_scalar_value - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{ - &ast.ExprArrayItem{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Key: $1, - DoubleArrowTkn: $2, - Val: $3, - }, - }, - } - } - | static_scalar_value - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{ - &ast.ExprArrayItem{ - Position: yylex.(*Parser).builder.NewNodePosition($1), - Val: $1, - }, - }, - } - } -; - -expr: - r_variable - { - $$ = $1 - } - | expr_without_variable - { - $$ = $1 - } -; - -parenthesis_expr: - '(' expr ')' - { - $$ = &ast.ExprBrackets{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenParenthesisTkn: $1, - Expr: $2, - CloseParenthesisTkn: $3, - } - } - | '(' yield_expr ')' - { - $$ = &ast.ExprBrackets{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenParenthesisTkn: $1, - Expr: $2, - CloseParenthesisTkn: $3, - } - } -; - - -r_variable: - variable - { - $$ = $1 - } -; - - -w_variable: - variable - { - $$ = $1 - } -; - -rw_variable: - variable - { - $$ = $1 - } -; - -variable: - base_variable_with_function_calls T_OBJECT_OPERATOR object_property method_or_not variable_properties - { - $$ = $1 - - $3[0].(*ast.ExprPropertyFetch).ObjectOperatorTkn = $2 - - if $4 != nil { - last := $3[len($3)-1] - switch l := last.(type) { - case *ast.ExprArrayDimFetch: - mc := $4[0].(*ast.ExprMethodCall) - $3 = append($3, &ast.ExprFunctionCall{ - Position: yylex.(*Parser).builder.NewNodePosition(mc), - OpenParenthesisTkn: mc.OpenParenthesisTkn, - Args: mc.Args, - SeparatorTkns: mc.SeparatorTkns, - CloseParenthesisTkn: mc.CloseParenthesisTkn, - }, - ) - $3 = append($3, $4[1:len($4)]...) - case *ast.ExprPropertyFetch: - $4[0].(*ast.ExprMethodCall).OpenCurlyBracketTkn = l.OpenCurlyBracketTkn - $4[0].(*ast.ExprMethodCall).Method = l.Prop - $4[0].(*ast.ExprMethodCall).CloseCurlyBracketTkn = l.CloseCurlyBracketTkn - $4[0].(*ast.ExprMethodCall).ObjectOperatorTkn = l.ObjectOperatorTkn - $3 = append($3[:len($3)-1], $4...) - } - } - - for _, n := range($3) { - switch nn := n.(type) { - case *ast.ExprFunctionCall: - nn.Function = $$ - nn.Position = yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - - case *ast.ExprArrayDimFetch: - nn.Var = $$ - nn.Position = yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - - case *ast.ExprPropertyFetch: - nn.Var = $$ - nn.Position = yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - - case *ast.ExprMethodCall: - nn.Var = $$ - nn.Position = yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - } - } - - for _, n := range($5) { - switch nn := n.(type) { - case *ast.ExprFunctionCall: - nn.Function = $$ - nn.Position = yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - - case *ast.ExprArrayDimFetch: - nn.Var = $$ - nn.Position = yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - - case *ast.ExprPropertyFetch: - nn.Var = $$ - nn.Position = yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - - case *ast.ExprMethodCall: - nn.Var = $$ - nn.Position = yylex.(*Parser).builder.NewNodesPosition($$, nn) - $$ = nn - } - } - } - | base_variable_with_function_calls - { - $$ = $1 - } -; - -variable_properties: - variable_properties variable_property - { - $$ = append($1, $2...) - } - | /* empty */ - { - $$ = []ast.Vertex{} - } -; - - -variable_property: - T_OBJECT_OPERATOR object_property method_or_not - { - $2[0].(*ast.ExprPropertyFetch).ObjectOperatorTkn = $1 - - if $3 != nil { - last := $2[len($2)-1] - switch l := last.(type) { - case *ast.ExprArrayDimFetch: - mc := $3[0].(*ast.ExprMethodCall) - $2 = append($2, &ast.ExprFunctionCall{ - Position: yylex.(*Parser).builder.NewNodePosition(mc), - OpenParenthesisTkn: mc.OpenParenthesisTkn, - Args: mc.Args, - SeparatorTkns: mc.SeparatorTkns, - CloseParenthesisTkn: mc.OpenParenthesisTkn, - }, - ) - $2 = append($2, $3[1:len($3)]...) - case *ast.ExprPropertyFetch: - $3[0].(*ast.ExprMethodCall).OpenCurlyBracketTkn = l.OpenCurlyBracketTkn - $3[0].(*ast.ExprMethodCall).Method = l.Prop - $3[0].(*ast.ExprMethodCall).CloseCurlyBracketTkn = l.CloseCurlyBracketTkn - $3[0].(*ast.ExprMethodCall).ObjectOperatorTkn = l.ObjectOperatorTkn - $2 = append($2[:len($2)-1], $3...) - } - } - - $$ = $2 - } -; - -array_method_dereference: - array_method_dereference '[' dim_offset ']' - { - fetch := &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewTokensPosition($2, $4), - Var: nil, - OpenBracketTkn: $2, - Dim: $3, - CloseBracketTkn: $4, - } - - $$ = append($1, fetch) - } - | method '[' dim_offset ']' - { - fetch := &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewTokensPosition($2, $4), - Var: nil, - OpenBracketTkn: $2, - Dim: $3, - CloseBracketTkn: $4, - } - - $$ = []ast.Vertex{$1, fetch} - } -; - -method: - function_call_parameter_list - { - $$ = &ast.ExprMethodCall{ - Position: yylex.(*Parser).builder.NewNodePosition($1), - OpenParenthesisTkn: $1.(*ArgumentList).OpenParenthesisTkn, - Args: $1.(*ArgumentList).Arguments, - SeparatorTkns: $1.(*ArgumentList).SeparatorTkns, - CloseParenthesisTkn: $1.(*ArgumentList).CloseParenthesisTkn, - } - } -; - -method_or_not: - method - { - $$ = []ast.Vertex{$1} - } - | array_method_dereference - { - $$ = $1 - } - | /* empty */ - { - $$ = nil - } -; - -variable_without_objects: - reference_variable - { - $$ = $1 - } - | simple_indirect_reference reference_variable - { - for i := len($1)-1; i>=0; i-- { - $1[i].(*ast.ExprVariable).Name = $2 - $1[i].(*ast.ExprVariable).Position = yylex.(*Parser).builder.NewNodesPosition($1[i], $2) - $2 = $1[i] - } - - $$ = $1[0] - } -; - -static_member: - class_name T_PAAMAYIM_NEKUDOTAYIM variable_without_objects - { - $$ = &ast.ExprStaticPropertyFetch{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Class: $1, - DoubleColonTkn: $2, - Prop: $3, - } - } - | variable_class_name T_PAAMAYIM_NEKUDOTAYIM variable_without_objects - { - $$ = &ast.ExprStaticPropertyFetch{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Class: $1, - DoubleColonTkn: $2, - Prop: $3, - } - } -; - -variable_class_name: - reference_variable - { - $$ = $1 - } -; - -array_function_dereference: - array_function_dereference '[' dim_offset ']' - { - $$ = &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $4), - Var: $1, - OpenBracketTkn: $2, - Dim: $3, - CloseBracketTkn: $4, - } - } - | function_call '[' dim_offset ']' - { - $$ = &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $4), - Var: $1, - OpenBracketTkn: $2, - Dim: $3, - CloseBracketTkn: $4, - } - } -; - -base_variable_with_function_calls: - base_variable - { - $$ = $1 - } - | array_function_dereference - { - $$ = $1 - } - | function_call - { - $$ = $1 - } -; - - -base_variable: - reference_variable - { - $$ = $1 - } - | simple_indirect_reference reference_variable - { - for i := len($1)-1; i>=0; i-- { - $1[i].(*ast.ExprVariable).Name = $2 - $1[i].(*ast.ExprVariable).Position = yylex.(*Parser).builder.NewNodesPosition($1[i], $2) - $2 = $1[i] - } - - $$ = $1[0] - } - | static_member - { - $$ = $1 - } -; - -reference_variable: - reference_variable '[' dim_offset ']' - { - $$ = &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $4), - Var: $1, - OpenBracketTkn: $2, - Dim: $3, - CloseBracketTkn: $4, - } - } - | reference_variable '{' expr '}' - { - $$ = &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $4), - Var: $1, - OpenBracketTkn: $2, - Dim: $3, - CloseBracketTkn: $4, - } - } - | compound_variable - { - $$ = $1 - } -; - - -compound_variable: - T_VARIABLE - { - $$ = &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - } - } - | '$' '{' expr '}' - { - $$ = &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - DollarTkn: $1, - OpenCurlyBracketTkn: $2, - Name: $3, - CloseCurlyBracketTkn: $4, - } - } -; - -dim_offset: - /* empty */ - { - $$ = nil - } - | expr - { - $$ = $1 - } -; - - -object_property: - object_dim_list - { - $$ = $1 - } - | variable_without_objects - { - $$ = []ast.Vertex{ - &ast.ExprPropertyFetch{ - Position: yylex.(*Parser).builder.NewNodePosition($1), - Prop: $1, - }, - } - } -; - -object_dim_list: - object_dim_list '[' dim_offset ']' - { - fetch := &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewTokensPosition($2, $4), - Var: nil, - OpenBracketTkn: $2, - Dim: $3, - CloseBracketTkn: $4, - } - - $$ = append($1, fetch) - } - | object_dim_list '{' expr '}' - { - fetch := &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewTokensPosition($2, $4), - Var: nil, - OpenBracketTkn: $2, - Dim: $3, - CloseBracketTkn: $4, - } - - $$ = append($1, fetch) - } - | variable_name - { - property := &ast.ExprPropertyFetch{ - Position: yylex.(*Parser).builder.NewNodePosition($1), - Prop: $1, - } - - if brackets, ok := $1.(*ParserBrackets); ok { - property.OpenCurlyBracketTkn = brackets.OpenBracketTkn - property.Prop = brackets.Child - property.CloseCurlyBracketTkn = brackets.CloseBracketTkn - } - - $$ = []ast.Vertex{ property } - } -; - -variable_name: - T_STRING - { - $$ = &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - } - } - | '{' expr '}' - { - $$ = &ParserBrackets{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenBracketTkn: $1, - Child: $2, - CloseBracketTkn: $3, - } - } -; - -simple_indirect_reference: - '$' - { - $$ = []ast.Vertex{ - &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - DollarTkn: $1, - }, - } - } - | simple_indirect_reference '$' - { - $$ = append($1, &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($2), - DollarTkn: $2, - }) - } -; - -assignment_list: - assignment_list ',' assignment_list_element - { - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, $3) - - $$ = $1 - } - | assignment_list_element - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{$1}, - } - } -; - - -assignment_list_element: - variable - { - $$ = &ast.ExprArrayItem{ - Position: yylex.(*Parser).builder.NewNodePosition($1), - Val: $1, - } - } - | T_LIST '(' assignment_list ')' - { - pairList := $3.(*ParserSeparatedList) - fistPair := pairList.Items[0].(*ast.ExprArrayItem) - - if fistPair.Key == nil && fistPair.Val == nil && len(pairList.Items) == 1 { - pairList.Items = nil - } - - $$ = &ast.ExprArrayItem{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - Val: &ast.ExprList{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - ListTkn: $1, - OpenBracketTkn: $2, - Items: $3.(*ParserSeparatedList).Items, - SeparatorTkns: $3.(*ParserSeparatedList).SeparatorTkns, - CloseBracketTkn: $4, - }, - } - } - | /* empty */ - { - $$ = &ast.ExprArrayItem{} - } -; - - -array_pair_list: - /* empty */ - { - $$ = &ParserSeparatedList{} - } - | non_empty_array_pair_list possible_comma - { - if $2 != nil { - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, &ast.ExprArrayItem{}) - } - - $$ = $1 - } -; - -non_empty_array_pair_list: - non_empty_array_pair_list ',' expr T_DOUBLE_ARROW expr - { - arrayItem := &ast.ExprArrayItem{ - Position: yylex.(*Parser).builder.NewNodesPosition($3, $5), - Key: $3, - DoubleArrowTkn: $4, - Val: $5, - } - - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, arrayItem) - - $$ = $1 - } - | non_empty_array_pair_list ',' expr - { - arrayItem := &ast.ExprArrayItem{ - Position: yylex.(*Parser).builder.NewNodePosition($3), - Val: $3, - } - - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, arrayItem) - - $$ = $1 - } - | expr T_DOUBLE_ARROW expr - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{ - &ast.ExprArrayItem{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $3), - Key: $1, - DoubleArrowTkn: $2, - Val: $3, - }, - }, - } - } - | expr - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{ - &ast.ExprArrayItem{ - Position: yylex.(*Parser).builder.NewNodePosition($1), - Val: $1, - }, - }, - } - } - | non_empty_array_pair_list ',' expr T_DOUBLE_ARROW '&' w_variable - { - arrayItem := &ast.ExprArrayItem{ - Position: yylex.(*Parser).builder.NewNodesPosition($3, $6), - Key: $3, - DoubleArrowTkn: $4, - AmpersandTkn: $5, - Val: $6, - } - - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, arrayItem) - - $$ = $1 - } - | non_empty_array_pair_list ',' '&' w_variable - { - arrayItem := &ast.ExprArrayItem{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($3, $4), - AmpersandTkn: $3, - Val: $4, - } - - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, arrayItem) - - $$ = $1 - } - | expr T_DOUBLE_ARROW '&' w_variable - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{ - &ast.ExprArrayItem{ - Position: yylex.(*Parser).builder.NewNodesPosition($1, $4), - Key: $1, - DoubleArrowTkn: $2, - AmpersandTkn: $3, - Val: $4, - }, - }, - } - } - | '&' w_variable - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{ - &ast.ExprArrayItem{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - AmpersandTkn: $1, - Val: $2, - }, - }, - } - } -; - -encaps_list: - encaps_list encaps_var - { - $$ = append($1, $2) - } - | encaps_list T_ENCAPSED_AND_WHITESPACE - { - $$ = append( - $1, - &ast.ScalarEncapsedStringPart{ - Position: yylex.(*Parser).builder.NewTokenPosition($2), - EncapsedStrTkn: $2, - Value: $2.Value, - }, - ) - } - | encaps_var - { - $$ = []ast.Vertex{$1} - } - | T_ENCAPSED_AND_WHITESPACE encaps_var - { - $$ = []ast.Vertex{ - &ast.ScalarEncapsedStringPart{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - EncapsedStrTkn: $1, - Value: $1.Value, - }, - $2, - } - } -; - -encaps_var: - T_VARIABLE - { - $$ = &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - } - } - | T_VARIABLE '[' encaps_var_offset ']' - { - $$ = &ast.ExprArrayDimFetch{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - }, - OpenBracketTkn: $2, - Dim: $3, - CloseBracketTkn: $4, - } - } - | T_VARIABLE T_OBJECT_OPERATOR T_STRING - { - $$ = &ast.ExprPropertyFetch{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - Var: &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - }, - ObjectOperatorTkn: $2, - Prop: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - } - } - | T_DOLLAR_OPEN_CURLY_BRACES expr '}' - { - $$ = &ast.ScalarEncapsedStringVar{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - DollarOpenCurlyBracketTkn: $1, - Name: $2, - CloseCurlyBracketTkn: $3, - } - } - | T_DOLLAR_OPEN_CURLY_BRACES T_STRING_VARNAME '}' - { - $$ = &ast.ScalarEncapsedStringVar{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - DollarOpenCurlyBracketTkn: $1, - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($2), - IdentifierTkn: $2, - Value: $2.Value, - }, - CloseCurlyBracketTkn: $3, - } - } - | T_DOLLAR_OPEN_CURLY_BRACES T_STRING_VARNAME '[' expr ']' '}' - { - $$ = &ast.ScalarEncapsedStringVar{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - DollarOpenCurlyBracketTkn: $1, - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($2), - IdentifierTkn: $2, - Value: $2.Value, - }, - OpenSquareBracketTkn: $3, - Dim: $4, - CloseSquareBracketTkn: $5, - CloseCurlyBracketTkn: $6, - } - } - | T_CURLY_OPEN variable '}' - { - $$ = &ast.ScalarEncapsedStringBrackets{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $3), - OpenCurlyBracketTkn: $1, - Var: $2, - CloseCurlyBracketTkn: $3, - } - } -; - -encaps_var_offset: - T_STRING - { - $$ = &ast.ScalarString{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - StringTkn: $1, - Value: $1.Value, - } - } - | T_NUM_STRING - { - // TODO: add option to handle 64 bit integer - if _, err := strconv.Atoi(string($1.Value)); err == nil { - $$ = &ast.ScalarLnumber{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - NumberTkn: $1, - Value: $1.Value, - } - } else { - $$ = &ast.ScalarString{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - StringTkn: $1, - Value: $1.Value, - } - } - } - | T_VARIABLE - { - $$ = &ast.ExprVariable{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - Name: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($1), - IdentifierTkn: $1, - Value: $1.Value, - }, - } - } -; - -internal_functions_in_yacc: - T_ISSET '(' isset_variables ')' - { - $$ = &ast.ExprIsset{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - IssetTkn: $1, - OpenParenthesisTkn: $2, - Vars: $3.(*ParserSeparatedList).Items, - SeparatorTkns: $3.(*ParserSeparatedList).SeparatorTkns, - CloseParenthesisTkn: $4, - } - } - | T_EMPTY '(' variable ')' - { - $$ = &ast.ExprEmpty{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - EmptyTkn: $1, - OpenParenthesisTkn: $2, - Expr: $3, - CloseParenthesisTkn: $4, - } - } - | T_EMPTY '(' expr ')' - { - $$ = &ast.ExprEmpty{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - EmptyTkn: $1, - OpenParenthesisTkn: $2, - Expr: $3, - CloseParenthesisTkn: $4, - } - } - | T_INCLUDE expr - { - $$ = &ast.ExprInclude{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - IncludeTkn: $1, - Expr: $2, - } - } - | T_INCLUDE_ONCE expr - { - $$ = &ast.ExprIncludeOnce{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - IncludeOnceTkn: $1, - Expr: $2, - } - } - | T_EVAL '(' expr ')' - { - $$ = &ast.ExprEval{ - Position: yylex.(*Parser).builder.NewTokensPosition($1, $4), - EvalTkn: $1, - OpenParenthesisTkn: $2, - Expr: $3, - CloseParenthesisTkn: $4, - } - } - | T_REQUIRE expr - { - $$ = &ast.ExprRequire{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - RequireTkn: $1, - Expr: $2, - } - } - | T_REQUIRE_ONCE expr - { - $$ = &ast.ExprRequireOnce{ - Position: yylex.(*Parser).builder.NewTokenNodePosition($1, $2), - RequireOnceTkn: $1, - Expr: $2, - } - } -; - -isset_variables: - isset_variable - { - $$ = &ParserSeparatedList{ - Items: []ast.Vertex{$1}, - } - } - | isset_variables ',' isset_variable - { - $1.(*ParserSeparatedList).SeparatorTkns = append($1.(*ParserSeparatedList).SeparatorTkns, $2) - $1.(*ParserSeparatedList).Items = append($1.(*ParserSeparatedList).Items, $3) - - $$ = $1 - } -; - -isset_variable: - variable - { - $$ = $1 - } - | expr_without_variable - { - $$ = $1 - } -; - -class_constant: - class_name T_PAAMAYIM_NEKUDOTAYIM T_STRING - { - $$ = &ast.ExprClassConstFetch{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $3), - Class: $1, - DoubleColonTkn: $2, - Const: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - } - } - | variable_class_name T_PAAMAYIM_NEKUDOTAYIM T_STRING - { - $$ = &ast.ExprClassConstFetch{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $3), - Class: $1, - DoubleColonTkn: $2, - Const: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - } - } -; - -static_class_name_scalar: - class_name T_PAAMAYIM_NEKUDOTAYIM T_CLASS - { - $$ = &ast.ExprClassConstFetch{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $3), - Class: $1, - DoubleColonTkn: $2, - Const: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - } - } -; - -class_name_scalar: - class_name T_PAAMAYIM_NEKUDOTAYIM T_CLASS - { - $$ = &ast.ExprClassConstFetch{ - Position: yylex.(*Parser).builder.NewNodeTokenPosition($1, $3), - Class: $1, - DoubleColonTkn: $2, - Const: &ast.Identifier{ - Position: yylex.(*Parser).builder.NewTokenPosition($3), - IdentifierTkn: $3, - Value: $3.Value, - }, - } - } -; - -%% diff --git a/internal/php5/php5_bench_test.go b/internal/php5/php5_bench_test.go deleted file mode 100644 index 42b6917..0000000 --- a/internal/php5/php5_bench_test.go +++ /dev/null @@ -1,30 +0,0 @@ -package php5_test - -import ( - "io/ioutil" - "testing" - - "github.com/VKCOM/php-parser/internal/php5" - "github.com/VKCOM/php-parser/internal/scanner" - "github.com/VKCOM/php-parser/pkg/conf" - "github.com/VKCOM/php-parser/pkg/version" -) - -func BenchmarkPhp5(b *testing.B) { - src, err := ioutil.ReadFile("test.php") - if err != nil { - b.Fatal("can not read test.php: " + err.Error()) - } - - for n := 0; n < b.N; n++ { - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer(src, config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - } -} diff --git a/internal/php5/test.php b/internal/php5/test.php deleted file mode 100644 index c811eb1..0000000 --- a/internal/php5/test.php +++ /dev/null @@ -1,381 +0,0 @@ -bar($a, ...$b); -foo::bar($a, ...$b); -$foo::bar($a, ...$b); -new foo($a, ...$b); - -function foo(bar $bar=null, baz &...$baz) {} -class foo {public function foo(bar $bar=null, baz &...$baz) {}} -function(bar $bar=null, baz &...$baz) {}; -static function(bar $bar=null, baz &...$baz) {}; - -1234567890123456789; -12345678901234567890; -0.; -0b0111111111111111111111111111111111111111111111111111111111111111; -0b1111111111111111111111111111111111111111111111111111111111111111; -0x007111111111111111; -0x8111111111111111; -__CLASS__; -__DIR__; -__FILE__; -__FUNCTION__; -__LINE__; -__NAMESPACE__; -__METHOD__; -__TRAIT__; - -"test $var"; -"test $var[1]"; -"test $var[1234567890123456789012345678901234567890]"; -"test $var[bar]"; -"test $var[$bar]"; -"$foo $bar"; -"test $foo->bar()"; -"test ${foo}"; -"test ${foo[0]}"; -"test {$foo->bar()}"; - -if ($a) : -endif; -if ($a) : -elseif ($b): -endif; -if ($a) : -else: -endif; -if ($a) : -elseif ($b): -elseif ($c): -else: -endif; - -while (1) { break; } -while (1) { break 2; } -while (1) : break(3); endwhile; -class foo{ const FOO = 1, BAR = 2; } -class foo{ function bar() {} } -class foo{ public static function &bar() {} } -class foo{ final private function bar() {} protected function baz() {} } -abstract class foo{ abstract public function bar(); } -final class foo extends bar { } -final class foo implements bar { } -final class foo implements bar, baz { } - -const FOO = 1, BAR = 2; -while (1) { continue; } -while (1) { continue 2; } -while (1) { continue(3); } -declare(ticks=1); -declare(ticks=1, strict_types=1) {} -declare(ticks=1): enddeclare; -do {} while(1); -echo $a, 1; -echo($a); -for($i = 0; $i < 10; $i++, $i++) {} -for(; $i < 10; $i++) : endfor; -foreach ($a as $v) {} -foreach ([] as $v) {} -foreach ($a as $v) : endforeach; -foreach ($a as $k => $v) {} -foreach ([] as $k => $v) {} -foreach ($a as $k => &$v) {} -foreach ($a as $k => list($v)) {} -function foo() {} - -function foo() { - function bar() {} - class Baz {} - return $a; -} - -function foo(array $a, callable $b) {return;} -function &foo() {return 1;} -function &foo() {} -global $a, $b, $$c, ${foo()}; -a: -goto a; -if ($a) {} -if ($a) {} elseif ($b) {} -if ($a) {} else {} -if ($a) {} elseif ($b) {} elseif ($c) {} else {} -if ($a) {} elseif ($b) {} else if ($c) {} else {} -?>
1, &$b,); -array(3 =>&$b); -array(&$b, 1=>1, 1, 3 =>&$b); -~$a; -!$a; - -Foo::Bar; -clone($a); -clone $a; -function(){}; -function($a, $b) use ($c, &$d) {}; -function($a, $b) use (&$c, $d) {}; -function() {}; -foo; -namespace\foo; -\foo; - -empty($a); -empty(Foo); -@$a; -eval($a); -exit; -exit($a); -die(); -die($a); -foo(); -namespace\foo(&$a); -\foo([]); -$foo(yield $a); - -$a--; -$a++; ---$a; -++$a; - -include $a; -include_once $a; -require $a; -require_once $a; - -$a instanceof Foo; -$a instanceof namespace\Foo; -$a instanceof \Foo; - -isset($a, $b); -isset(Foo); -list() = $b; -list($a, $b) = $b; -list($a[]) = $b; -list(list($a)) = $b; - -$a->foo(); -new Foo; -new namespace\Foo(); -new \Foo(); -print($a); -$a->foo; -$a->foo[1]; -$a->foo->bar->baz()->quux[0]; -$a->foo()[1][1]; -`cmd $a`; -`cmd`; -``; -[]; -[1]; -[1=>1, &$b,]; - -Foo::bar(); -namespace\Foo::bar(); -\Foo::bar(); -Foo::$bar(); -$foo::$bar(); -Foo::$bar; -namespace\Foo::$bar; -\Foo::$bar; -$a ? $b : $c; -$a ? : $c; -$a ? $b ? $c : $d : $e; -$a ? $b : $c ? $d : $e; --$a; -+$a; -$$a; -$$$a; -yield; -yield $a; -yield $a => $b; -yield Foo::class; -yield $a => Foo::class; - -(array)$a; -(boolean)$a; -(bool)$a; -(double)$a; -(float)$a; -(integer)$a; -(int)$a; -(object)$a; -(string)$a; -(unset)$a; - -$a & $b; -$a | $b; -$a ^ $b; -$a && $b; -$a || $b; -$a . $b; -$a / $b; -$a == $b; -$a >= $b; -$a > $b; -$a === $b; -$a and $b; -$a or $b; -$a xor $b; -$a - $b; -$a % $b; -$a * $b; -$a != $b; -$a !== $b; -$a + $b; -$a ** $b; -$a << $b; -$a >> $b; -$a <= $b; -$a < $b; - -$a =& $b; -$a =& new Foo; -$a =& new Foo($b); -$a = $b; -$a &= $b; -$a |= $b; -$a ^= $b; -$a .= $b; -$a /= $b; -$a -= $b; -$a %= $b; -$a *= $b; -$a += $b; -$a **= $b; -$a <<= $b; -$a >>= $b; - - -(new \Foo()); -(new \Foo())->bar()->baz; -(new \Foo())[0][0]; -(new \Foo())[0]->bar(); - -array([0])[0][0]; -"foo"[0]; -foo[0]; -static::foo; - -new $foo; -new $foo::$bar; -new $a->b[0]; -new $a->b{$b ?: null}->$c->d[0];static $a = [1][0]; - -static $a = !1; -static $a = ~1; -static $a = +1; -static $a = -1; -static $a = (1); -static $a = 1 ?: 2; -static $a = 1 ? 2 : 3; -static $a = 1 & 2; -static $a = 1 | 2; -static $a = 1 ^ 2; -static $a = 1 && 2; -static $a = 1 || 2; -static $a = 1 . 2; -static $a = 1 / 2; -static $a = 1 == 2; -static $a = 1 >= 2; -static $a = 1 > 2; -static $a = 1 === 2; -static $a = 1 and 2; -static $a = 1 or 2; -static $a = 1 xor 2; -static $a = 1 - 2; -static $a = 1 % 2; -static $a = 1 * 2; -static $a = 1 != 2; -static $a = 1 !== 2; -static $a = 1 + 2; -static $a = 1 ** 2; -static $a = 1 << 2; -static $a = 1 >> 2; -static $a = 1 <= 2; -static $a = 1 < 2; -static $a = Foo::bar; -static $a = Foo::class; -static $a = __CLASS__; -static $a = Foo; -static $a = namespace\Foo; -static $a = \Foo; -static $a = array(); -static $a = array(1 => 1, 2); -static $a = [1, 2 => 2][0]; - -if (yield 1) {} -Foo::$$bar; - -$foo(); -$foo()[0][0]; -$a{$b}; -${$a}; -$foo::{$bar}(); -$foo::bar; - -__halt_compiler(); - -parsing process must be terminated \ No newline at end of file diff --git a/pkg/parser/parser.go b/pkg/parser/parser.go index 0000eab..5f09633 100644 --- a/pkg/parser/parser.go +++ b/pkg/parser/parser.go @@ -3,10 +3,8 @@ package parser import ( "errors" - "github.com/VKCOM/php-parser/internal/php5" "github.com/VKCOM/php-parser/internal/php7" "github.com/VKCOM/php-parser/internal/php8" - "github.com/VKCOM/php-parser/internal/scanner" "github.com/VKCOM/php-parser/pkg/ast" "github.com/VKCOM/php-parser/pkg/conf" "github.com/VKCOM/php-parser/pkg/version" @@ -16,9 +14,6 @@ var ( // ErrVersionOutOfRange is returned if the version is not supported ErrVersionOutOfRange = errors.New("the version is out of supported range") - php5RangeStart = &version.Version{Major: 5} - php5RangeEnd = &version.Version{Major: 5, Minor: 6} - php7RangeStart = &version.Version{Major: 7} php7RangeEnd = &version.Version{Major: 7, Minor: 4} @@ -39,15 +34,8 @@ func Parse(src []byte, config conf.Config) (ast.Vertex, error) { config.Version = php7RangeEnd } - if config.Version.InRange(php5RangeStart, php5RangeEnd) { - lexer := scanner.NewLexer(src, config) - parser = php5.NewParser(lexer, config) - parser.Parse() - return parser.GetRootNode(), nil - } - if config.Version.InRange(php7RangeStart, php7RangeEnd) { - lexer := scanner.NewLexer(src, config) + lexer := php7.NewLexer(src, config) parser = php7.NewParser(lexer, config) parser.Parse() return parser.GetRootNode(), nil diff --git a/pkg/visitor/printer/printer_php5_test.go b/pkg/visitor/printer/printer_php5_test.go deleted file mode 100644 index 7fffe23..0000000 --- a/pkg/visitor/printer/printer_php5_test.go +++ /dev/null @@ -1,1439 +0,0 @@ -package printer_test - -import ( - "bytes" - "testing" - - "github.com/VKCOM/php-parser/internal/php5" - "github.com/VKCOM/php-parser/internal/scanner" - "github.com/VKCOM/php-parser/pkg/ast" - "github.com/VKCOM/php-parser/pkg/conf" - "github.com/VKCOM/php-parser/pkg/version" - "github.com/VKCOM/php-parser/pkg/visitor/printer" -) - -func parsePhp5(src string) ast.Vertex { - config := conf.Config{ - Version: &version.Version{ - Major: 5, - Minor: 6, - }, - } - lexer := scanner.NewLexer([]byte(src), config) - php5parser := php5.NewParser(lexer, config) - php5parser.Parse() - - return php5parser.GetRootNode() -} - -func printPhp5(n ast.Vertex) string { - o := bytes.NewBufferString("") - - p := printer.NewPrinter(o) - n.Accept(p) - - return o.String() -} - -// test node - -func TestParseAndPrintPhp5Root(t *testing.T) { - - src := `
Hello
- >= $b ; - ` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -} - -// test binary - -func TestParseAndPrintPhp5Binary(t *testing.T) { - src := `= $b ; - $a > $b ; - $a === $b ; - $a and $b ; - $a or $b ; - $a xor $b ; - $a - $b ; - $a % $b ; - $a * $b ; - $a != $b ; - $a <> $b ; - $a !== $b ; - $a + $b ; - $a ** $b ; - $a << $b ; - $a >> $b ; - $a <= $b ; - $a < $b ; - ` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -} - -// test cast - -func TestParseAndPrintPhp5Cast(t *testing.T) { - src := ` $world , - ] ; - ` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -} - -func TestParseAndPrintPhp5Array(t *testing.T) { - src := ` 2 ) ; - ` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -} - -func TestParseAndPrintPhp5BitwiseNot(t *testing.T) { - src := ` bar ( $arg ) ;` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -} - -func TestParseAndPrintPhp5New(t *testing.T) { - src := ` b ;` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -} - -func TestParseAndPrintPhp5Reference(t *testing.T) { - src := ` & $c ] ; - - $a = function ( ) use ( & $b ) { - // do nothing - } ; - - foreach ( $a as & $b ) { - // do nothing - }` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -} - -func TestParseAndPrintPhp5Require(t *testing.T) { - - src := ` & $b , // one - $c , /* two */ - ] ; - $a = [0, 1, 2] ;` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -} - -func TestParseAndPrintPhp5StaticCall(t *testing.T) { - src := ` $v ;` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -} - -// test stmt - -func TestParseAndPrintPhp5AltIf(t *testing.T) { - src := ` & $v ) : - echo $v ; - endforeach ;` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -} - -func TestParseAndPrintPhp5AltSwitch(t *testing.T) { - src := ` - - - & $v ) { - ; - }` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -} - -func TestParseAndPrintPhp5Function(t *testing.T) { - - src := `testtest call ( ) ; - $a -> { $b . 'b' } ; - $a -> $b ( ) -> { $c . 'c' } ; - ` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -} - -func TestParseAndPrintPhp5ComplexString1(t *testing.T) { - src := `bar" ; - ` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -} - -func TestParseAndPrintPhp5ComplexString2(t *testing.T) { - src := ` bar }" ; - "test ${ $foo -> bar ( ) }" ; - "test ${ $a . '' }" ; - ` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -} - -func TestParseAndPrintPhp5ComplexString3(t *testing.T) { - src := ` bar }" ; - "test ${$foo -> bar ( ) }" ; - "test ${$a . '' }" ; - ` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -} - -func TestParseAndPrintPhp5ComplexString4(t *testing.T) { - src := ` bar }" ; - "test {$foo -> bar ( ) }" ; - ` - - actual := printPhp5(parsePhp5(src)) - - if src != actual { - t.Errorf("\nexpected: %s\ngot: %s\n", src, actual) - } -}