mirror of
				https://github.com/StackExchange/dnscontrol.git
				synced 2024-05-11 05:55:12 +00:00 
			
		
		
		
	
		
			
				
	
	
		
			657 lines
		
	
	
		
			15 KiB
		
	
	
	
		
			Go
		
	
	
	
	
	
			
		
		
	
	
			657 lines
		
	
	
		
			15 KiB
		
	
	
	
		
			Go
		
	
	
	
	
	
| package otto
 | |
| 
 | |
| import (
 | |
| 	"fmt"
 | |
| 	"regexp"
 | |
| 
 | |
| 	"github.com/robertkrimen/otto/ast"
 | |
| 	"github.com/robertkrimen/otto/file"
 | |
| 	"github.com/robertkrimen/otto/token"
 | |
| )
 | |
| 
 | |
| var trueLiteral = &_nodeLiteral{value: toValue_bool(true)}
 | |
| var falseLiteral = &_nodeLiteral{value: toValue_bool(false)}
 | |
| var nullLiteral = &_nodeLiteral{value: nullValue}
 | |
| var emptyStatement = &_nodeEmptyStatement{}
 | |
| 
 | |
| func (cmpl *_compiler) parseExpression(in ast.Expression) _nodeExpression {
 | |
| 	if in == nil {
 | |
| 		return nil
 | |
| 	}
 | |
| 
 | |
| 	switch in := in.(type) {
 | |
| 
 | |
| 	case *ast.ArrayLiteral:
 | |
| 		out := &_nodeArrayLiteral{
 | |
| 			value: make([]_nodeExpression, len(in.Value)),
 | |
| 		}
 | |
| 		for i, value := range in.Value {
 | |
| 			out.value[i] = cmpl.parseExpression(value)
 | |
| 		}
 | |
| 		return out
 | |
| 
 | |
| 	case *ast.AssignExpression:
 | |
| 		return &_nodeAssignExpression{
 | |
| 			operator: in.Operator,
 | |
| 			left:     cmpl.parseExpression(in.Left),
 | |
| 			right:    cmpl.parseExpression(in.Right),
 | |
| 		}
 | |
| 
 | |
| 	case *ast.BinaryExpression:
 | |
| 		return &_nodeBinaryExpression{
 | |
| 			operator:   in.Operator,
 | |
| 			left:       cmpl.parseExpression(in.Left),
 | |
| 			right:      cmpl.parseExpression(in.Right),
 | |
| 			comparison: in.Comparison,
 | |
| 		}
 | |
| 
 | |
| 	case *ast.BooleanLiteral:
 | |
| 		if in.Value {
 | |
| 			return trueLiteral
 | |
| 		}
 | |
| 		return falseLiteral
 | |
| 
 | |
| 	case *ast.BracketExpression:
 | |
| 		return &_nodeBracketExpression{
 | |
| 			idx:    in.Left.Idx0(),
 | |
| 			left:   cmpl.parseExpression(in.Left),
 | |
| 			member: cmpl.parseExpression(in.Member),
 | |
| 		}
 | |
| 
 | |
| 	case *ast.CallExpression:
 | |
| 		out := &_nodeCallExpression{
 | |
| 			callee:       cmpl.parseExpression(in.Callee),
 | |
| 			argumentList: make([]_nodeExpression, len(in.ArgumentList)),
 | |
| 		}
 | |
| 		for i, value := range in.ArgumentList {
 | |
| 			out.argumentList[i] = cmpl.parseExpression(value)
 | |
| 		}
 | |
| 		return out
 | |
| 
 | |
| 	case *ast.ConditionalExpression:
 | |
| 		return &_nodeConditionalExpression{
 | |
| 			test:       cmpl.parseExpression(in.Test),
 | |
| 			consequent: cmpl.parseExpression(in.Consequent),
 | |
| 			alternate:  cmpl.parseExpression(in.Alternate),
 | |
| 		}
 | |
| 
 | |
| 	case *ast.DotExpression:
 | |
| 		return &_nodeDotExpression{
 | |
| 			idx:        in.Left.Idx0(),
 | |
| 			left:       cmpl.parseExpression(in.Left),
 | |
| 			identifier: in.Identifier.Name,
 | |
| 		}
 | |
| 
 | |
| 	case *ast.EmptyExpression:
 | |
| 		return nil
 | |
| 
 | |
| 	case *ast.FunctionLiteral:
 | |
| 		name := ""
 | |
| 		if in.Name != nil {
 | |
| 			name = in.Name.Name
 | |
| 		}
 | |
| 		out := &_nodeFunctionLiteral{
 | |
| 			name:   name,
 | |
| 			body:   cmpl.parseStatement(in.Body),
 | |
| 			source: in.Source,
 | |
| 			file:   cmpl.file,
 | |
| 		}
 | |
| 		if in.ParameterList != nil {
 | |
| 			list := in.ParameterList.List
 | |
| 			out.parameterList = make([]string, len(list))
 | |
| 			for i, value := range list {
 | |
| 				out.parameterList[i] = value.Name
 | |
| 			}
 | |
| 		}
 | |
| 		for _, value := range in.DeclarationList {
 | |
| 			switch value := value.(type) {
 | |
| 			case *ast.FunctionDeclaration:
 | |
| 				out.functionList = append(out.functionList, cmpl.parseExpression(value.Function).(*_nodeFunctionLiteral))
 | |
| 			case *ast.VariableDeclaration:
 | |
| 				for _, value := range value.List {
 | |
| 					out.varList = append(out.varList, value.Name)
 | |
| 				}
 | |
| 			default:
 | |
| 				panic(fmt.Errorf("Here be dragons: parseProgram.declaration(%T)", value))
 | |
| 			}
 | |
| 		}
 | |
| 		return out
 | |
| 
 | |
| 	case *ast.Identifier:
 | |
| 		return &_nodeIdentifier{
 | |
| 			idx:  in.Idx,
 | |
| 			name: in.Name,
 | |
| 		}
 | |
| 
 | |
| 	case *ast.NewExpression:
 | |
| 		out := &_nodeNewExpression{
 | |
| 			callee:       cmpl.parseExpression(in.Callee),
 | |
| 			argumentList: make([]_nodeExpression, len(in.ArgumentList)),
 | |
| 		}
 | |
| 		for i, value := range in.ArgumentList {
 | |
| 			out.argumentList[i] = cmpl.parseExpression(value)
 | |
| 		}
 | |
| 		return out
 | |
| 
 | |
| 	case *ast.NullLiteral:
 | |
| 		return nullLiteral
 | |
| 
 | |
| 	case *ast.NumberLiteral:
 | |
| 		return &_nodeLiteral{
 | |
| 			value: toValue(in.Value),
 | |
| 		}
 | |
| 
 | |
| 	case *ast.ObjectLiteral:
 | |
| 		out := &_nodeObjectLiteral{
 | |
| 			value: make([]_nodeProperty, len(in.Value)),
 | |
| 		}
 | |
| 		for i, value := range in.Value {
 | |
| 			out.value[i] = _nodeProperty{
 | |
| 				key:   value.Key,
 | |
| 				kind:  value.Kind,
 | |
| 				value: cmpl.parseExpression(value.Value),
 | |
| 			}
 | |
| 		}
 | |
| 		return out
 | |
| 
 | |
| 	case *ast.RegExpLiteral:
 | |
| 		return &_nodeRegExpLiteral{
 | |
| 			flags:   in.Flags,
 | |
| 			pattern: in.Pattern,
 | |
| 		}
 | |
| 
 | |
| 	case *ast.SequenceExpression:
 | |
| 		out := &_nodeSequenceExpression{
 | |
| 			sequence: make([]_nodeExpression, len(in.Sequence)),
 | |
| 		}
 | |
| 		for i, value := range in.Sequence {
 | |
| 			out.sequence[i] = cmpl.parseExpression(value)
 | |
| 		}
 | |
| 		return out
 | |
| 
 | |
| 	case *ast.StringLiteral:
 | |
| 		return &_nodeLiteral{
 | |
| 			value: toValue_string(in.Value),
 | |
| 		}
 | |
| 
 | |
| 	case *ast.ThisExpression:
 | |
| 		return &_nodeThisExpression{}
 | |
| 
 | |
| 	case *ast.UnaryExpression:
 | |
| 		return &_nodeUnaryExpression{
 | |
| 			operator: in.Operator,
 | |
| 			operand:  cmpl.parseExpression(in.Operand),
 | |
| 			postfix:  in.Postfix,
 | |
| 		}
 | |
| 
 | |
| 	case *ast.VariableExpression:
 | |
| 		return &_nodeVariableExpression{
 | |
| 			idx:         in.Idx0(),
 | |
| 			name:        in.Name,
 | |
| 			initializer: cmpl.parseExpression(in.Initializer),
 | |
| 		}
 | |
| 
 | |
| 	}
 | |
| 
 | |
| 	panic(fmt.Errorf("Here be dragons: cmpl.parseExpression(%T)", in))
 | |
| }
 | |
| 
 | |
| func (cmpl *_compiler) parseStatement(in ast.Statement) _nodeStatement {
 | |
| 	if in == nil {
 | |
| 		return nil
 | |
| 	}
 | |
| 
 | |
| 	switch in := in.(type) {
 | |
| 
 | |
| 	case *ast.BlockStatement:
 | |
| 		out := &_nodeBlockStatement{
 | |
| 			list: make([]_nodeStatement, len(in.List)),
 | |
| 		}
 | |
| 		for i, value := range in.List {
 | |
| 			out.list[i] = cmpl.parseStatement(value)
 | |
| 		}
 | |
| 		return out
 | |
| 
 | |
| 	case *ast.BranchStatement:
 | |
| 		out := &_nodeBranchStatement{
 | |
| 			branch: in.Token,
 | |
| 		}
 | |
| 		if in.Label != nil {
 | |
| 			out.label = in.Label.Name
 | |
| 		}
 | |
| 		return out
 | |
| 
 | |
| 	case *ast.DebuggerStatement:
 | |
| 		return &_nodeDebuggerStatement{}
 | |
| 
 | |
| 	case *ast.DoWhileStatement:
 | |
| 		out := &_nodeDoWhileStatement{
 | |
| 			test: cmpl.parseExpression(in.Test),
 | |
| 		}
 | |
| 		body := cmpl.parseStatement(in.Body)
 | |
| 		if block, ok := body.(*_nodeBlockStatement); ok {
 | |
| 			out.body = block.list
 | |
| 		} else {
 | |
| 			out.body = append(out.body, body)
 | |
| 		}
 | |
| 		return out
 | |
| 
 | |
| 	case *ast.EmptyStatement:
 | |
| 		return emptyStatement
 | |
| 
 | |
| 	case *ast.ExpressionStatement:
 | |
| 		return &_nodeExpressionStatement{
 | |
| 			expression: cmpl.parseExpression(in.Expression),
 | |
| 		}
 | |
| 
 | |
| 	case *ast.ForInStatement:
 | |
| 		out := &_nodeForInStatement{
 | |
| 			into:   cmpl.parseExpression(in.Into),
 | |
| 			source: cmpl.parseExpression(in.Source),
 | |
| 		}
 | |
| 		body := cmpl.parseStatement(in.Body)
 | |
| 		if block, ok := body.(*_nodeBlockStatement); ok {
 | |
| 			out.body = block.list
 | |
| 		} else {
 | |
| 			out.body = append(out.body, body)
 | |
| 		}
 | |
| 		return out
 | |
| 
 | |
| 	case *ast.ForStatement:
 | |
| 		out := &_nodeForStatement{
 | |
| 			initializer: cmpl.parseExpression(in.Initializer),
 | |
| 			update:      cmpl.parseExpression(in.Update),
 | |
| 			test:        cmpl.parseExpression(in.Test),
 | |
| 		}
 | |
| 		body := cmpl.parseStatement(in.Body)
 | |
| 		if block, ok := body.(*_nodeBlockStatement); ok {
 | |
| 			out.body = block.list
 | |
| 		} else {
 | |
| 			out.body = append(out.body, body)
 | |
| 		}
 | |
| 		return out
 | |
| 
 | |
| 	case *ast.FunctionStatement:
 | |
| 		return emptyStatement
 | |
| 
 | |
| 	case *ast.IfStatement:
 | |
| 		return &_nodeIfStatement{
 | |
| 			test:       cmpl.parseExpression(in.Test),
 | |
| 			consequent: cmpl.parseStatement(in.Consequent),
 | |
| 			alternate:  cmpl.parseStatement(in.Alternate),
 | |
| 		}
 | |
| 
 | |
| 	case *ast.LabelledStatement:
 | |
| 		return &_nodeLabelledStatement{
 | |
| 			label:     in.Label.Name,
 | |
| 			statement: cmpl.parseStatement(in.Statement),
 | |
| 		}
 | |
| 
 | |
| 	case *ast.ReturnStatement:
 | |
| 		return &_nodeReturnStatement{
 | |
| 			argument: cmpl.parseExpression(in.Argument),
 | |
| 		}
 | |
| 
 | |
| 	case *ast.SwitchStatement:
 | |
| 		out := &_nodeSwitchStatement{
 | |
| 			discriminant: cmpl.parseExpression(in.Discriminant),
 | |
| 			default_:     in.Default,
 | |
| 			body:         make([]*_nodeCaseStatement, len(in.Body)),
 | |
| 		}
 | |
| 		for i, clause := range in.Body {
 | |
| 			out.body[i] = &_nodeCaseStatement{
 | |
| 				test:       cmpl.parseExpression(clause.Test),
 | |
| 				consequent: make([]_nodeStatement, len(clause.Consequent)),
 | |
| 			}
 | |
| 			for j, value := range clause.Consequent {
 | |
| 				out.body[i].consequent[j] = cmpl.parseStatement(value)
 | |
| 			}
 | |
| 		}
 | |
| 		return out
 | |
| 
 | |
| 	case *ast.ThrowStatement:
 | |
| 		return &_nodeThrowStatement{
 | |
| 			argument: cmpl.parseExpression(in.Argument),
 | |
| 		}
 | |
| 
 | |
| 	case *ast.TryStatement:
 | |
| 		out := &_nodeTryStatement{
 | |
| 			body:    cmpl.parseStatement(in.Body),
 | |
| 			finally: cmpl.parseStatement(in.Finally),
 | |
| 		}
 | |
| 		if in.Catch != nil {
 | |
| 			out.catch = &_nodeCatchStatement{
 | |
| 				parameter: in.Catch.Parameter.Name,
 | |
| 				body:      cmpl.parseStatement(in.Catch.Body),
 | |
| 			}
 | |
| 		}
 | |
| 		return out
 | |
| 
 | |
| 	case *ast.VariableStatement:
 | |
| 		out := &_nodeVariableStatement{
 | |
| 			list: make([]_nodeExpression, len(in.List)),
 | |
| 		}
 | |
| 		for i, value := range in.List {
 | |
| 			out.list[i] = cmpl.parseExpression(value)
 | |
| 		}
 | |
| 		return out
 | |
| 
 | |
| 	case *ast.WhileStatement:
 | |
| 		out := &_nodeWhileStatement{
 | |
| 			test: cmpl.parseExpression(in.Test),
 | |
| 		}
 | |
| 		body := cmpl.parseStatement(in.Body)
 | |
| 		if block, ok := body.(*_nodeBlockStatement); ok {
 | |
| 			out.body = block.list
 | |
| 		} else {
 | |
| 			out.body = append(out.body, body)
 | |
| 		}
 | |
| 		return out
 | |
| 
 | |
| 	case *ast.WithStatement:
 | |
| 		return &_nodeWithStatement{
 | |
| 			object: cmpl.parseExpression(in.Object),
 | |
| 			body:   cmpl.parseStatement(in.Body),
 | |
| 		}
 | |
| 
 | |
| 	}
 | |
| 
 | |
| 	panic(fmt.Errorf("Here be dragons: cmpl.parseStatement(%T)", in))
 | |
| }
 | |
| 
 | |
| func cmpl_parse(in *ast.Program) *_nodeProgram {
 | |
| 	cmpl := _compiler{
 | |
| 		program: in,
 | |
| 	}
 | |
| 	return cmpl.parse()
 | |
| }
 | |
| 
 | |
| func (cmpl *_compiler) _parse(in *ast.Program) *_nodeProgram {
 | |
| 	out := &_nodeProgram{
 | |
| 		body: make([]_nodeStatement, len(in.Body)),
 | |
| 		file: in.File,
 | |
| 	}
 | |
| 	for i, value := range in.Body {
 | |
| 		out.body[i] = cmpl.parseStatement(value)
 | |
| 	}
 | |
| 	for _, value := range in.DeclarationList {
 | |
| 		switch value := value.(type) {
 | |
| 		case *ast.FunctionDeclaration:
 | |
| 			out.functionList = append(out.functionList, cmpl.parseExpression(value.Function).(*_nodeFunctionLiteral))
 | |
| 		case *ast.VariableDeclaration:
 | |
| 			for _, value := range value.List {
 | |
| 				out.varList = append(out.varList, value.Name)
 | |
| 			}
 | |
| 		default:
 | |
| 			panic(fmt.Errorf("Here be dragons: cmpl.parseProgram.DeclarationList(%T)", value))
 | |
| 		}
 | |
| 	}
 | |
| 	return out
 | |
| }
 | |
| 
 | |
| type _nodeProgram struct {
 | |
| 	body []_nodeStatement
 | |
| 
 | |
| 	varList      []string
 | |
| 	functionList []*_nodeFunctionLiteral
 | |
| 
 | |
| 	variableList []_nodeDeclaration
 | |
| 
 | |
| 	file *file.File
 | |
| }
 | |
| 
 | |
| type _nodeDeclaration struct {
 | |
| 	name       string
 | |
| 	definition _node
 | |
| }
 | |
| 
 | |
| type _node interface {
 | |
| }
 | |
| 
 | |
| type (
 | |
| 	_nodeExpression interface {
 | |
| 		_node
 | |
| 		_expressionNode()
 | |
| 	}
 | |
| 
 | |
| 	_nodeArrayLiteral struct {
 | |
| 		value []_nodeExpression
 | |
| 	}
 | |
| 
 | |
| 	_nodeAssignExpression struct {
 | |
| 		operator token.Token
 | |
| 		left     _nodeExpression
 | |
| 		right    _nodeExpression
 | |
| 	}
 | |
| 
 | |
| 	_nodeBinaryExpression struct {
 | |
| 		operator   token.Token
 | |
| 		left       _nodeExpression
 | |
| 		right      _nodeExpression
 | |
| 		comparison bool
 | |
| 	}
 | |
| 
 | |
| 	_nodeBracketExpression struct {
 | |
| 		idx    file.Idx
 | |
| 		left   _nodeExpression
 | |
| 		member _nodeExpression
 | |
| 	}
 | |
| 
 | |
| 	_nodeCallExpression struct {
 | |
| 		callee       _nodeExpression
 | |
| 		argumentList []_nodeExpression
 | |
| 	}
 | |
| 
 | |
| 	_nodeConditionalExpression struct {
 | |
| 		test       _nodeExpression
 | |
| 		consequent _nodeExpression
 | |
| 		alternate  _nodeExpression
 | |
| 	}
 | |
| 
 | |
| 	_nodeDotExpression struct {
 | |
| 		idx        file.Idx
 | |
| 		left       _nodeExpression
 | |
| 		identifier string
 | |
| 	}
 | |
| 
 | |
| 	_nodeFunctionLiteral struct {
 | |
| 		name          string
 | |
| 		body          _nodeStatement
 | |
| 		source        string
 | |
| 		parameterList []string
 | |
| 		varList       []string
 | |
| 		functionList  []*_nodeFunctionLiteral
 | |
| 		file          *file.File
 | |
| 	}
 | |
| 
 | |
| 	_nodeIdentifier struct {
 | |
| 		idx  file.Idx
 | |
| 		name string
 | |
| 	}
 | |
| 
 | |
| 	_nodeLiteral struct {
 | |
| 		value Value
 | |
| 	}
 | |
| 
 | |
| 	_nodeNewExpression struct {
 | |
| 		callee       _nodeExpression
 | |
| 		argumentList []_nodeExpression
 | |
| 	}
 | |
| 
 | |
| 	_nodeObjectLiteral struct {
 | |
| 		value []_nodeProperty
 | |
| 	}
 | |
| 
 | |
| 	_nodeProperty struct {
 | |
| 		key   string
 | |
| 		kind  string
 | |
| 		value _nodeExpression
 | |
| 	}
 | |
| 
 | |
| 	_nodeRegExpLiteral struct {
 | |
| 		flags   string
 | |
| 		pattern string // Value?
 | |
| 		regexp  *regexp.Regexp
 | |
| 	}
 | |
| 
 | |
| 	_nodeSequenceExpression struct {
 | |
| 		sequence []_nodeExpression
 | |
| 	}
 | |
| 
 | |
| 	_nodeThisExpression struct {
 | |
| 	}
 | |
| 
 | |
| 	_nodeUnaryExpression struct {
 | |
| 		operator token.Token
 | |
| 		operand  _nodeExpression
 | |
| 		postfix  bool
 | |
| 	}
 | |
| 
 | |
| 	_nodeVariableExpression struct {
 | |
| 		idx         file.Idx
 | |
| 		name        string
 | |
| 		initializer _nodeExpression
 | |
| 	}
 | |
| )
 | |
| 
 | |
| type (
 | |
| 	_nodeStatement interface {
 | |
| 		_node
 | |
| 		_statementNode()
 | |
| 	}
 | |
| 
 | |
| 	_nodeBlockStatement struct {
 | |
| 		list []_nodeStatement
 | |
| 	}
 | |
| 
 | |
| 	_nodeBranchStatement struct {
 | |
| 		branch token.Token
 | |
| 		label  string
 | |
| 	}
 | |
| 
 | |
| 	_nodeCaseStatement struct {
 | |
| 		test       _nodeExpression
 | |
| 		consequent []_nodeStatement
 | |
| 	}
 | |
| 
 | |
| 	_nodeCatchStatement struct {
 | |
| 		parameter string
 | |
| 		body      _nodeStatement
 | |
| 	}
 | |
| 
 | |
| 	_nodeDebuggerStatement struct {
 | |
| 	}
 | |
| 
 | |
| 	_nodeDoWhileStatement struct {
 | |
| 		test _nodeExpression
 | |
| 		body []_nodeStatement
 | |
| 	}
 | |
| 
 | |
| 	_nodeEmptyStatement struct {
 | |
| 	}
 | |
| 
 | |
| 	_nodeExpressionStatement struct {
 | |
| 		expression _nodeExpression
 | |
| 	}
 | |
| 
 | |
| 	_nodeForInStatement struct {
 | |
| 		into   _nodeExpression
 | |
| 		source _nodeExpression
 | |
| 		body   []_nodeStatement
 | |
| 	}
 | |
| 
 | |
| 	_nodeForStatement struct {
 | |
| 		initializer _nodeExpression
 | |
| 		update      _nodeExpression
 | |
| 		test        _nodeExpression
 | |
| 		body        []_nodeStatement
 | |
| 	}
 | |
| 
 | |
| 	_nodeIfStatement struct {
 | |
| 		test       _nodeExpression
 | |
| 		consequent _nodeStatement
 | |
| 		alternate  _nodeStatement
 | |
| 	}
 | |
| 
 | |
| 	_nodeLabelledStatement struct {
 | |
| 		label     string
 | |
| 		statement _nodeStatement
 | |
| 	}
 | |
| 
 | |
| 	_nodeReturnStatement struct {
 | |
| 		argument _nodeExpression
 | |
| 	}
 | |
| 
 | |
| 	_nodeSwitchStatement struct {
 | |
| 		discriminant _nodeExpression
 | |
| 		default_     int
 | |
| 		body         []*_nodeCaseStatement
 | |
| 	}
 | |
| 
 | |
| 	_nodeThrowStatement struct {
 | |
| 		argument _nodeExpression
 | |
| 	}
 | |
| 
 | |
| 	_nodeTryStatement struct {
 | |
| 		body    _nodeStatement
 | |
| 		catch   *_nodeCatchStatement
 | |
| 		finally _nodeStatement
 | |
| 	}
 | |
| 
 | |
| 	_nodeVariableStatement struct {
 | |
| 		list []_nodeExpression
 | |
| 	}
 | |
| 
 | |
| 	_nodeWhileStatement struct {
 | |
| 		test _nodeExpression
 | |
| 		body []_nodeStatement
 | |
| 	}
 | |
| 
 | |
| 	_nodeWithStatement struct {
 | |
| 		object _nodeExpression
 | |
| 		body   _nodeStatement
 | |
| 	}
 | |
| )
 | |
| 
 | |
| // _expressionNode
 | |
| 
 | |
| func (*_nodeArrayLiteral) _expressionNode()          {}
 | |
| func (*_nodeAssignExpression) _expressionNode()      {}
 | |
| func (*_nodeBinaryExpression) _expressionNode()      {}
 | |
| func (*_nodeBracketExpression) _expressionNode()     {}
 | |
| func (*_nodeCallExpression) _expressionNode()        {}
 | |
| func (*_nodeConditionalExpression) _expressionNode() {}
 | |
| func (*_nodeDotExpression) _expressionNode()         {}
 | |
| func (*_nodeFunctionLiteral) _expressionNode()       {}
 | |
| func (*_nodeIdentifier) _expressionNode()            {}
 | |
| func (*_nodeLiteral) _expressionNode()               {}
 | |
| func (*_nodeNewExpression) _expressionNode()         {}
 | |
| func (*_nodeObjectLiteral) _expressionNode()         {}
 | |
| func (*_nodeRegExpLiteral) _expressionNode()         {}
 | |
| func (*_nodeSequenceExpression) _expressionNode()    {}
 | |
| func (*_nodeThisExpression) _expressionNode()        {}
 | |
| func (*_nodeUnaryExpression) _expressionNode()       {}
 | |
| func (*_nodeVariableExpression) _expressionNode()    {}
 | |
| 
 | |
| // _statementNode
 | |
| 
 | |
| func (*_nodeBlockStatement) _statementNode()      {}
 | |
| func (*_nodeBranchStatement) _statementNode()     {}
 | |
| func (*_nodeCaseStatement) _statementNode()       {}
 | |
| func (*_nodeCatchStatement) _statementNode()      {}
 | |
| func (*_nodeDebuggerStatement) _statementNode()   {}
 | |
| func (*_nodeDoWhileStatement) _statementNode()    {}
 | |
| func (*_nodeEmptyStatement) _statementNode()      {}
 | |
| func (*_nodeExpressionStatement) _statementNode() {}
 | |
| func (*_nodeForInStatement) _statementNode()      {}
 | |
| func (*_nodeForStatement) _statementNode()        {}
 | |
| func (*_nodeIfStatement) _statementNode()         {}
 | |
| func (*_nodeLabelledStatement) _statementNode()   {}
 | |
| func (*_nodeReturnStatement) _statementNode()     {}
 | |
| func (*_nodeSwitchStatement) _statementNode()     {}
 | |
| func (*_nodeThrowStatement) _statementNode()      {}
 | |
| func (*_nodeTryStatement) _statementNode()        {}
 | |
| func (*_nodeVariableStatement) _statementNode()   {}
 | |
| func (*_nodeWhileStatement) _statementNode()      {}
 | |
| func (*_nodeWithStatement) _statementNode()       {}
 |