Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Fetching contributors…

Cannot retrieve contributors at this time

1183 lines (976 sloc) 57.165 kb
{
module Language.JavaScript.Parser.Grammar5 (
parseProgram
, parseLiteral
, parsePrimaryExpression
, parseStatement
-- debug
, fp
) where
-- import Control.Monad.Error.Class (throwError)
import Data.Char
import Language.JavaScript.Parser.Lexer
import Language.JavaScript.Parser.ParseError
import Language.JavaScript.Parser.ParserMonad
import Language.JavaScript.Parser.SrcLocation
import Language.JavaScript.Parser.Token
import qualified Language.JavaScript.Parser.AST as AST
}
-- The name of the generated function to be exported from the module
%name parseProgram Program
%name parseLiteral LiteralMain
%name parsePrimaryExpression PrimaryExpressionMain
%name parseStatement StatementMain
%tokentype { Token }
%error { parseError }
%monad { Alex } { >>= } { return }
%lexer { lexCont } { EOFToken {} }
%token
';' { SemiColonToken {} }
',' { CommaToken {} }
'?' { HookToken {} }
':' { ColonToken {} }
'||' { OrToken {} }
'&&' { AndToken {} }
'|' { BitwiseOrToken {} }
'^' { BitwiseXorToken {} }
'&' { BitwiseAndToken {} }
'===' { StrictEqToken {} }
'==' { EqToken {} }
'=' { SimpleAssignToken {} }
'!==' { StrictNeToken {} }
'!=' { NeToken {} }
'<<' { LshToken {} }
'<=' { LeToken {} }
'<' { LtToken {} }
'>>>' { UrshToken {} }
'>>' { RshToken {} }
'>=' { GeToken {} }
'>' { GtToken {} }
'++' { IncrementToken {} }
'--' { DecrementToken {} }
'+' { PlusToken {} }
'-' { MinusToken {} }
'*' { MulToken {} }
'/' { DivToken {} }
'%' { ModToken {} }
'!' { NotToken {} }
'~' { BitwiseNotToken {} }
'.' { DotToken {} }
'[' { LeftBracketToken {} }
']' { RightBracketToken {} }
'{' { LeftCurlyToken {} }
'}' { RightCurlyToken {} }
'(' { LeftParenToken {} }
')' { RightParenToken {} }
'@*/' { CondcommentEndToken {} }
'break' { BreakToken {} }
'case' { CaseToken {} }
'catch' { CatchToken {} }
'const' { ConstToken {} }
'continue' { ContinueToken {} }
'debugger' { DebuggerToken {} }
'default' { DefaultToken {} }
'delete' { DeleteToken {} }
'do' { DoToken {} }
'else' { ElseToken {} }
'enum' { EnumToken {} }
'false' { FalseToken {} }
'finally' { FinallyToken {} }
'for' { ForToken {} }
'function' { FunctionToken {} }
'get' { GetToken {} }
'if' { IfToken {} }
'in' { InToken {} }
'instanceof' { InstanceofToken {} }
'new' { NewToken {} }
'null' { NullToken {} }
'return' { ReturnToken {} }
'set' { SetToken {} }
'switch' { SwitchToken {} }
'this' { ThisToken {} }
'throw' { ThrowToken {} }
'true' { TrueToken {} }
'try' { TryToken {} }
'typeof' { TypeofToken {} }
'var' { VarToken {} }
'void' { VoidToken {} }
'while' { WhileToken {} }
'with' { WithToken {} }
'ident' { IdentifierToken {} }
'decimal' { DecimalToken {} }
'hexinteger' { HexIntegerToken {} }
'string' { StringToken {} }
'regex' { RegExToken {} }
'assign' { AssignToken {} }
'future' { FutureToken {} }
'tail' { TailToken {} }
'eof' { EOFToken {} }
%%
-- ---------------------------------------------------------------------
-- Sort out automatically inserted semi-colons
AutoSemi :: { AST.JSNode }
AutoSemi : ';' { AST.NT (AST.JSLiteral ";") (ss $1) (gc $1)}
| { AST.NT (AST.JSLiteral "") tokenPosnEmpty []}
-- ---------------------------------------------------------------------
-- Helpers
LParen :: { AST.JSNode }
LParen : '(' { fp (AST.NT (AST.JSLiteral "(") (ss $1) (gc $1))}
RParen :: { AST.JSNode }
RParen : ')' { fp (AST.NT (AST.JSLiteral ")") (ss $1) (gc $1))}
LBrace :: { AST.JSNode }
LBrace : '{' { fp (AST.NT (AST.JSLiteral "{") (ss $1) (gc $1))}
RBrace :: { AST.JSNode }
RBrace : '}' { fp (AST.NT (AST.JSLiteral "}") (ss $1) (gc $1))}
LSquare :: { AST.JSNode }
LSquare : '[' { fp (AST.NT (AST.JSLiteral "[") (ss $1) (gc $1))}
RSquare :: { AST.JSNode }
RSquare : ']' { fp (AST.NT (AST.JSLiteral "]") (ss $1) (gc $1))}
Comma :: { AST.JSNode }
Comma : ',' { fp (AST.NT (AST.JSLiteral ",") (ss $1) (gc $1))}
Colon :: { AST.JSNode }
Colon : ':' { fp (AST.NT (AST.JSLiteral ":") (ss $1) (gc $1))}
Semi :: { AST.JSNode }
Semi : ';' { fp (AST.NT (AST.JSLiteral ";") (ss $1) (gc $1))}
Dot :: { AST.JSNode }
Dot : '.' { fp (AST.NT (AST.JSLiteral ".") (ss $1) (gc $1))}
Increment :: { AST.JSNode }
Increment : '++' { fp (AST.NT (AST.JSLiteral "++") (ss $1) (gc $1))}
Decrement :: { AST.JSNode }
Decrement : '--' { fp (AST.NT (AST.JSLiteral "--") (ss $1) (gc $1))}
Delete :: { AST.JSNode }
Delete : 'delete' { fp (AST.NT (AST.JSLiteral "delete") (ss $1) (gc $1))}
Void :: { AST.JSNode }
Void : 'void' { fp (AST.NT (AST.JSLiteral "void") (ss $1) (gc $1))}
Typeof :: { AST.JSNode }
Typeof : 'typeof' { fp (AST.NT (AST.JSLiteral "typeof") (ss $1) (gc $1))}
Plus :: { AST.JSNode }
Plus : '+' { fp (AST.NT (AST.JSLiteral "+") (ss $1) (gc $1))}
Minus :: { AST.JSNode }
Minus : '-' { fp (AST.NT (AST.JSLiteral "-") (ss $1) (gc $1))}
Tilde :: { AST.JSNode }
Tilde : '~' { fp (AST.NT (AST.JSLiteral "~") (ss $1) (gc $1))}
Not :: { AST.JSNode }
Not : '!' { fp (AST.NT (AST.JSLiteral "!") (ss $1) (gc $1))}
Mul :: { AST.JSNode }
Mul : '*' { fp (AST.NT (AST.JSLiteral "*") (ss $1) (gc $1))}
Div :: { AST.JSNode }
Div : '/' { fp (AST.NT (AST.JSLiteral "/") (ss $1) (gc $1))}
Mod :: { AST.JSNode }
Mod : '%' { fp (AST.NT (AST.JSLiteral "%") (ss $1) (gc $1))}
Lsh :: { AST.JSNode }
Lsh : '<<' { fp (AST.NT (AST.JSLiteral "<<") (ss $1) (gc $1))}
Rsh :: { AST.JSNode }
Rsh : '>>' { fp (AST.NT (AST.JSLiteral ">>") (ss $1) (gc $1))}
Ursh :: { AST.JSNode }
Ursh : '>>>' { fp (AST.NT (AST.JSLiteral ">>>") (ss $1) (gc $1))}
Le :: { AST.JSNode }
Le : '<=' { fp (AST.NT (AST.JSLiteral "<=") (ss $1) (gc $1))}
Lt :: { AST.JSNode }
Lt : '<' { fp (AST.NT (AST.JSLiteral "<") (ss $1) (gc $1))}
Ge :: { AST.JSNode }
Ge : '>=' { fp (AST.NT (AST.JSLiteral ">=") (ss $1) (gc $1))}
Gt :: { AST.JSNode }
Gt : '>' { fp (AST.NT (AST.JSLiteral ">") (ss $1) (gc $1))}
In :: { AST.JSNode }
In : 'in' { fp (AST.NT (AST.JSLiteral "in") (ss $1) (gc $1))}
Instanceof :: { AST.JSNode }
Instanceof : 'instanceof' { fp (AST.NT (AST.JSLiteral "instanceof") (ss $1) (gc $1))}
StrictEq :: { AST.JSNode }
StrictEq : '===' { fp (AST.NT (AST.JSLiteral "===") (ss $1) (gc $1))}
Equal :: { AST.JSNode }
Equal : '==' { fp (AST.NT (AST.JSLiteral "==") (ss $1) (gc $1))}
StrictNe :: { AST.JSNode }
StrictNe : '!==' { fp (AST.NT (AST.JSLiteral "!==") (ss $1) (gc $1))}
Ne :: { AST.JSNode }
Ne : '!=' { fp (AST.NT (AST.JSLiteral "!=") (ss $1) (gc $1))}
Or :: { AST.JSNode }
Or : '||' { fp (AST.NT (AST.JSLiteral "||") (ss $1) (gc $1))}
And :: { AST.JSNode }
And : '&&' { fp (AST.NT (AST.JSLiteral "&&") (ss $1) (gc $1))}
BitOr :: { AST.JSNode }
BitOr : '|' { fp (AST.NT (AST.JSLiteral "|") (ss $1) (gc $1))}
BitAnd :: { AST.JSNode }
BitAnd : '&' { fp (AST.NT (AST.JSLiteral "&") (ss $1) (gc $1))}
BitXor :: { AST.JSNode }
BitXor : '^' { fp (AST.NT (AST.JSLiteral "^") (ss $1) (gc $1))}
Hook :: { AST.JSNode }
Hook : '?' { fp (AST.NT (AST.JSLiteral "?") (ss $1) (gc $1))}
SimpleAssign :: { AST.JSNode }
SimpleAssign : '=' { fp (AST.NT (AST.JSLiteral "=") (ss $1) (gc $1))}
Assign :: { AST.JSNode }
Assign : 'assign' { fp (AST.NT (AST.JSLiteral (token_literal $1)) (ss $1) (gc $1))}
Var :: { AST.JSNode }
Var : 'var' { fp (AST.NT (AST.JSLiteral "var") (ss $1) (gc $1))}
Const :: { AST.JSNode }
Const : 'const' { fp (AST.NT (AST.JSLiteral "const") (ss $1) (gc $1))}
If :: { AST.JSNode }
If : 'if' { fp (AST.NT (AST.JSLiteral "if") (ss $1) (gc $1))}
Else :: { AST.JSNode }
Else : 'else' { fp (AST.NT (AST.JSLiteral "else") (ss $1) (gc $1))}
Do :: { AST.JSNode }
Do : 'do' { fp (AST.NT (AST.JSLiteral "do") (ss $1) (gc $1))}
While :: { AST.JSNode }
While : 'while' { fp (AST.NT (AST.JSLiteral "while") (ss $1) (gc $1))}
For :: { AST.JSNode }
For : 'for' { fp (AST.NT (AST.JSLiteral "for") (ss $1) (gc $1))}
Continue :: { AST.JSNode }
Continue : 'continue' { fp (AST.NT (AST.JSLiteral "continue") (ss $1) (gc $1))}
Break :: { AST.JSNode }
Break : 'break' { fp (AST.NT (AST.JSLiteral "break") (ss $1) (gc $1))}
Return :: { AST.JSNode }
Return : 'return' { fp (AST.NT (AST.JSLiteral "return") (ss $1) (gc $1))}
With :: { AST.JSNode }
With : 'with' { fp (AST.NT (AST.JSLiteral "with") (ss $1) (gc $1))}
Switch :: { AST.JSNode }
Switch : 'switch' { fp (AST.NT (AST.JSLiteral "switch") (ss $1) (gc $1))}
Case :: { AST.JSNode }
Case : 'case' { fp (AST.NT (AST.JSLiteral "case") (ss $1) (gc $1))}
Default :: { AST.JSNode }
Default : 'default' { fp (AST.NT (AST.JSLiteral "default") (ss $1) (gc $1))}
Throw :: { AST.JSNode }
Throw : 'throw' { fp (AST.NT (AST.JSLiteral "throw") (ss $1) (gc $1))}
Try :: { AST.JSNode }
Try : 'try' { fp (AST.NT (AST.JSLiteral "try") (ss $1) (gc $1))}
CatchL :: { AST.JSNode }
CatchL : 'catch' { fp (AST.NT (AST.JSLiteral "catch") (ss $1) (gc $1))}
FinallyL :: { AST.JSNode }
FinallyL : 'finally' { fp (AST.NT (AST.JSLiteral "finally") (ss $1) (gc $1))}
Function :: { AST.JSNode }
Function : 'function' { fp (AST.NT (AST.JSLiteral "function") (ss $1) (gc $1))}
Eof :: { AST.JSNode }
Eof : 'tail' { fp (AST.NT (AST.JSLiteral "") (ss $1) (gc $1))}
-- Literal :: See 7.8
-- NullLiteral
-- BooleanLiteral
-- NumericLiteral
-- StringLiteral
Literal :: { AST.JSNode }
Literal : NullLiteral {$1}
| BooleanLiteral {$1}
| NumericLiteral {$1}
| StringLiteral {$1}
| RegularExpressionLiteral {$1}
NullLiteral :: { AST.JSNode }
NullLiteral : 'null' { fp (AST.NT (AST.JSLiteral "null") (ss $1) (gc $1))}
BooleanLiteral :: { AST.JSNode }
BooleanLiteral : 'true' { fp (AST.NT (AST.JSLiteral "true") (ss $1) (gc $1)) }
| 'false' { fp (AST.NT (AST.JSLiteral "false") (ss $1) (gc $1)) }
-- <Numeric Literal> ::= DecimalLiteral
-- | HexIntegerLiteral
NumericLiteral :: { AST.JSNode }
NumericLiteral : 'decimal' { fp (AST.NT (AST.JSDecimal (token_literal $1)) (ss $1) (gc $1))}
| 'hexinteger' { fp (AST.NT (AST.JSHexInteger (token_literal $1)) (ss $1) (gc $1)) }
StringLiteral :: { AST.JSNode }
StringLiteral : 'string' { fp (AST.NT (AST.JSStringLiteral (token_delimiter $1) (token_literal $1)) (ss $1) (gc $1)) }
-- <Regular Expression Literal> ::= RegExp
RegularExpressionLiteral :: { AST.JSNode }
RegularExpressionLiteral : 'regex' { fp (AST.NT (AST.JSRegEx (token_literal $1)) (ss $1) (gc $1)) }
-- PrimaryExpression : See 11.1
-- this
-- Identifier
-- Literal
-- ArrayLiteral
-- ObjectLiteral
-- ( Expression )
PrimaryExpression :: { AST.JSNode }
PrimaryExpression : 'this' { fp (AST.NT (AST.JSLiteral "this") (ss $1) (gc $1))}
| Identifier { $1 {- PrimaryExpression1 -}}
| Literal { $1 {- PrimaryExpression2 -}}
| ArrayLiteral { $1 {- PrimaryExpression3 -}}
| ObjectLiteral { $1 {- PrimaryExpression4 -}}
| LParen Expression RParen { fp (AST.NN (AST.JSExpressionParen $1 $2 $3)) }
-- Identifier :: See 7.6
-- IdentifierName but not ReservedWord
-- IdentifierName :: See 7.6
-- IdentifierStart
-- IdentifierName IdentifierPart
Identifier :: { AST.JSNode }
Identifier : 'ident' { (AST.NT (AST.JSIdentifier (token_literal $1)) (ss $1) (gc $1))}
| 'get' { (AST.NT (AST.JSIdentifier "get") (ss $1) (gc $1))}
| 'set' { (AST.NT (AST.JSIdentifier "set") (ss $1) (gc $1))}
-- TODO: make this include any reserved word too, including future ones
IdentifierName :: { AST.JSNode }
IdentifierName : Identifier {$1}
| 'break' { fp (AST.NT (AST.JSIdentifier "break") (ss $1) (gc $1))}
| 'case' { fp (AST.NT (AST.JSIdentifier "case") (ss $1) (gc $1))}
| 'catch' { fp (AST.NT (AST.JSIdentifier "catch") (ss $1) (gc $1))}
| 'const' { fp (AST.NT (AST.JSIdentifier "const") (ss $1) (gc $1))}
| 'continue' { fp (AST.NT (AST.JSIdentifier "continue") (ss $1) (gc $1))}
| 'debugger' { fp (AST.NT (AST.JSIdentifier "debugger") (ss $1) (gc $1))}
| 'default' { fp (AST.NT (AST.JSIdentifier "default") (ss $1) (gc $1))}
| 'delete' { fp (AST.NT (AST.JSIdentifier "delete") (ss $1) (gc $1))}
| 'do' { fp (AST.NT (AST.JSIdentifier "do") (ss $1) (gc $1))}
| 'else' { fp (AST.NT (AST.JSIdentifier "else") (ss $1) (gc $1))}
| 'enum' { fp (AST.NT (AST.JSIdentifier "enum") (ss $1) (gc $1))}
| 'false' { fp (AST.NT (AST.JSIdentifier "false") (ss $1) (gc $1))}
| 'finally' { fp (AST.NT (AST.JSIdentifier "finally") (ss $1) (gc $1))}
| 'for' { fp (AST.NT (AST.JSIdentifier "for") (ss $1) (gc $1))}
| 'function' { fp (AST.NT (AST.JSIdentifier "function") (ss $1) (gc $1))}
| 'get' { fp (AST.NT (AST.JSIdentifier "get") (ss $1) (gc $1))}
| 'if' { fp (AST.NT (AST.JSIdentifier "if") (ss $1) (gc $1))}
| 'in' { fp (AST.NT (AST.JSIdentifier "in") (ss $1) (gc $1))}
| 'instanceof' { fp (AST.NT (AST.JSIdentifier "instanceof") (ss $1) (gc $1))}
| 'new' { fp (AST.NT (AST.JSIdentifier "new") (ss $1) (gc $1))}
| 'null' { fp (AST.NT (AST.JSIdentifier "null") (ss $1) (gc $1))}
| 'return' { fp (AST.NT (AST.JSIdentifier "return") (ss $1) (gc $1))}
| 'set' { fp (AST.NT (AST.JSIdentifier "set") (ss $1) (gc $1))}
| 'switch' { fp (AST.NT (AST.JSIdentifier "switch") (ss $1) (gc $1))}
| 'this' { fp (AST.NT (AST.JSIdentifier "this") (ss $1) (gc $1))}
| 'throw' { fp (AST.NT (AST.JSIdentifier "throw") (ss $1) (gc $1))}
| 'true' { fp (AST.NT (AST.JSIdentifier "true") (ss $1) (gc $1))}
| 'try' { fp (AST.NT (AST.JSIdentifier "try") (ss $1) (gc $1))}
| 'typeof' { fp (AST.NT (AST.JSIdentifier "typeof") (ss $1) (gc $1))}
| 'var' { fp (AST.NT (AST.JSIdentifier "var") (ss $1) (gc $1))}
| 'void' { fp (AST.NT (AST.JSIdentifier "void") (ss $1) (gc $1))}
| 'while' { fp (AST.NT (AST.JSIdentifier "while") (ss $1) (gc $1))}
| 'with' { fp (AST.NT (AST.JSIdentifier "with") (ss $1) (gc $1))}
| 'future' { fp (AST.NT (AST.JSIdentifier (token_literal $1)) (ss $1) (gc $1))}
-- ArrayLiteral : See 11.1.4
-- [ Elisionopt ]
-- [ ElementList ]
-- [ ElementList , Elisionopt ]
ArrayLiteral :: { AST.JSNode }
ArrayLiteral : LSquare RSquare { fp (AST.NN (AST.JSArrayLiteral $1 [] $2))}
| LSquare Elision RSquare { fp (AST.NN (AST.JSArrayLiteral $1 $2 $3))}
| LSquare ElementList RSquare { fp (AST.NN (AST.JSArrayLiteral $1 $2 $3))}
| LSquare ElementList Comma Elision RSquare { fp (AST.NN (AST.JSArrayLiteral $1 ($2++[$3]++$4) $5))}
| LSquare ElementList Comma RSquare { fp (AST.NN (AST.JSArrayLiteral $1 ($2++[$3]) $4))}
-- ElementList : See 11.1.4
-- Elisionopt AssignmentExpression
-- ElementList , Elisionopt AssignmentExpression
ElementList :: { [AST.JSNode] }
ElementList : Elision AssignmentExpression { (($1)++($2)) {- ElementList -}}
| AssignmentExpression { $1 {- ElementList -}}
| ElementList Comma Elision AssignmentExpression { (($1)++[fp (AST.NN (AST.JSElision $2))]++($3)++($4)) {- ElementList -}}
| ElementList Comma AssignmentExpression { (($1)++[fp (AST.NN (AST.JSElision $2))]++($3)) {- ElementList -}}
-- Elision : See 11.1.4
-- ,
-- Elision ,
Elision :: { [AST.JSNode] }
Elision : Comma { [ fp (AST.NN (AST.JSElision $1))] }
| Elision Comma { ($1 ++ [fp (AST.NN (AST.JSElision $2))]) }
-- ObjectLiteral : See 11.1.5
-- { }
-- { PropertyNameAndValueList }
-- { PropertyNameAndValueList , }
ObjectLiteral :: { AST.JSNode }
ObjectLiteral : LBrace RBrace { fp (AST.NN (AST.JSObjectLiteral $1 [] $2) )}
| LBrace PropertyNameandValueList RBrace { fp (AST.NN (AST.JSObjectLiteral $1 $2 $3) )}
| LBrace PropertyNameandValueList Comma RBrace { fp (AST.NN (AST.JSObjectLiteral $1 ($2++[$3]) $4) )}
-- <Property Name and Value List> ::= <Property Name> ':' <Assignment Expression>
-- | <Property Name and Value List> ',' <Property Name> ':' <Assignment Expression>
-- Seems we can have function declarations in the value part too
-- PropertyNameAndValueList : See 11.1.5
-- PropertyAssignment
-- PropertyNameAndValueList , PropertyAssignment
PropertyNameandValueList :: { [ AST.JSNode ] }
PropertyNameandValueList : PropertyAssignment { [$1] {- PropertyNameandValueList1 -} }
| PropertyNameandValueList Comma PropertyAssignment { ($1++[$2]++[$3]) {- PropertyNameandValueList2 -} }
-- PropertyAssignment : See 11.1.5
-- PropertyName : AssignmentExpression
-- get PropertyName() { FunctionBody }
-- set PropertyName( PropertySetParameterList ) { FunctionBody }
-- TODO: not clear if get/set are keywords, or just used in a specific context. Puzzling.
PropertyAssignment :: { AST.JSNode }
PropertyAssignment : PropertyName Colon AssignmentExpression { fp (AST.NN (AST.JSPropertyNameandValue $1 $2 $3)) }
-- Should be "get" in next, but is not a Token
| 'get' PropertyName LParen RParen FunctionBody
{ fp (AST.NN (AST.JSPropertyAccessor (AST.NT (AST.JSLiteral "get") (ss $1) (gc $1)) $2 $3 [] $4 $5)) }
-- Should be "set" in next, but is not a Token
| 'set' PropertyName LParen PropertySetParameterList RParen FunctionBody
{ fp (AST.NN (AST.JSPropertyAccessor (AST.NT (AST.JSLiteral "set") (ss $1) (gc $1)) $2 $3 [$4] $5 $6)) }
-- PropertyName : See 11.1.5
-- IdentifierName
-- StringLiteral
-- NumericLiteral
PropertyName :: { AST.JSNode }
PropertyName : IdentifierName { $1 {- PropertyName1 -}}
| StringLiteral { $1 {- PropertyName2 -}}
| NumericLiteral { $1 {- PropertyName3 -}}
-- PropertySetParameterList : See 11.1.5
-- Identifier
PropertySetParameterList :: { AST.JSNode }
PropertySetParameterList : Identifier { $1 {- PropertySetParameterList -}}
-- MemberExpression : See 11.2
-- PrimaryExpression
-- FunctionExpression
-- MemberExpression [ Expression ]
-- MemberExpression . IdentifierName
-- new MemberExpression Arguments
MemberExpression :: { [AST.JSNode] }
MemberExpression : PrimaryExpression { [$1] {- MemberExpression -}}
| FunctionExpression { [$1] {- MemberExpression -}}
| MemberExpression LSquare Expression RSquare { [fp (AST.NN (AST.JSMemberSquare $1 $2 $3 $4))] }
| MemberExpression Dot IdentifierName { [fp (AST.NN (AST.JSMemberDot $1 $2 $3))] }
| 'new' MemberExpression Arguments { (((fp (AST.NT (AST.JSLiteral "new") (ss $1) (gc $1))):$2)++[$3])}
-- NewExpression : See 11.2
-- MemberExpression
-- new NewExpression
NewExpression :: { [AST.JSNode] }
NewExpression : MemberExpression { $1 {- NewExpression -}}
| 'new' NewExpression { (fp (AST.NT (AST.JSLiteral "new") (ss $1) (gc $1))):$2 }
-- CallExpression : See 11.2
-- MemberExpression Arguments
-- CallExpression Arguments
-- CallExpression [ Expression ]
-- CallExpression . IdentifierName
CallExpression :: { [AST.JSNode] }
CallExpression : MemberExpression Arguments { $1++[$2] {- CallExpression -} }
| CallExpression Arguments { ($1++[fp (AST.NN (AST.JSCallExpression "()" [] [$2] []))]) }
| CallExpression LSquare Expression RSquare { ($1++[fp (AST.NN (AST.JSCallExpression "[]" [$2] [$3] [$4]))]) }
| CallExpression Dot IdentifierName { ($1++[fp (AST.NN (AST.JSCallExpression "." [$2] [$3] []))]) }
-- Arguments : See 11.2
-- ()
-- ( ArgumentList )
Arguments :: { AST.JSNode }
Arguments : LParen RParen { fp (AST.NN (AST.JSArguments $1 [] $2)) }
| LParen ArgumentList RParen { fp (AST.NN (AST.JSArguments $1 $2 $3)) }
-- ArgumentList : See 11.2
-- AssignmentExpression
-- ArgumentList , AssignmentExpression
ArgumentList :: { [AST.JSNode] }
ArgumentList : AssignmentExpression { $1 {- ArgumentList -}}
| ArgumentList Comma AssignmentExpression { $1++[$2]++$3 {- ArgumentList2 -} }
-- LeftHandSideExpression : See 11.2
-- NewExpression
-- CallExpression
LeftHandSideExpression :: { [AST.JSNode] }
LeftHandSideExpression : NewExpression { $1 {- LeftHandSideExpression1 -}}
| CallExpression { $1 {- LeftHandSideExpression12 -}}
-- PostfixExpression : See 11.3
-- LeftHandSideExpression
-- [no LineTerminator here]
-- LeftHandSideExpression ++
-- [no LineTerminator here]
-- LeftHandSideExpression --
PostfixExpression :: { [AST.JSNode] }
PostfixExpression : LeftHandSideExpression { $1 {- PostfixExpression -} }
| PostfixExpression Increment {[fp (AST.NN (AST.JSExpressionPostfix "++" $1 $2))]}
| PostfixExpression Decrement {[fp (AST.NN (AST.JSExpressionPostfix "--" $1 $2))]}
-- UnaryExpression : See 11.4
-- PostfixExpression
-- delete UnaryExpression
-- void UnaryExpression
-- typeof UnaryExpression
-- ++ UnaryExpression
-- -- UnaryExpression
-- + UnaryExpression
-- - UnaryExpression
-- ~ UnaryExpression
-- ! UnaryExpression
UnaryExpression :: { [AST.JSNode] }
UnaryExpression : PostfixExpression { $1 {- UnaryExpression -} }
| Delete UnaryExpression { ((fp (AST.NN (AST.JSUnary "delete " $1))):$2)}
| Void UnaryExpression { ((fp (AST.NN (AST.JSUnary "void " $1))):$2)}
| Typeof UnaryExpression { ((fp (AST.NN (AST.JSUnary "typeof " $1))):$2)}
| Increment UnaryExpression { ((fp (AST.NN (AST.JSUnary "++" $1))):$2) }
| Decrement UnaryExpression { ((fp (AST.NN (AST.JSUnary "--" $1))):$2)}
| Plus UnaryExpression { ((fp (AST.NN (AST.JSUnary "+" $1))):$2)}
| Minus UnaryExpression { ((fp (AST.NN (AST.JSUnary "-" $1))):$2)}
| Tilde UnaryExpression { ((fp (AST.NN (AST.JSUnary "~" $1))):$2)}
| Not UnaryExpression { ((fp (AST.NN (AST.JSUnary "!" $1))):$2)}
-- MultiplicativeExpression : See 11.5
-- UnaryExpression
-- MultiplicativeExpression * UnaryExpression
-- MultiplicativeExpression / UnaryExpression
-- MultiplicativeExpression % UnaryExpression
MultiplicativeExpression :: { [AST.JSNode] }
MultiplicativeExpression : UnaryExpression { $1 {- MultiplicativeExpression -}}
| MultiplicativeExpression Mul UnaryExpression { [fp (AST.NN (AST.JSExpressionBinary "*" $1 $2 $3))]}
| MultiplicativeExpression Div UnaryExpression { [fp (AST.NN (AST.JSExpressionBinary "/" $1 $2 $3))]}
| MultiplicativeExpression Mod UnaryExpression { [fp (AST.NN (AST.JSExpressionBinary "%" $1 $2 $3))]}
-- AdditiveExpression : See 11.6
-- MultiplicativeExpression
-- AdditiveExpression + MultiplicativeExpression
-- AdditiveExpression - MultiplicativeExpression
AdditiveExpression :: { [AST.JSNode] }
AdditiveExpression : AdditiveExpression Plus MultiplicativeExpression { [fp (AST.NN (AST.JSExpressionBinary "+" $1 $2 $3))]}
| AdditiveExpression Minus MultiplicativeExpression { [fp (AST.NN (AST.JSExpressionBinary "-" $1 $2 $3))]}
| MultiplicativeExpression { $1 {- (goRegExp $1)-} {- AdditiveExpression -} }
-- ShiftExpression : See 11.7
-- AdditiveExpression
-- ShiftExpression << AdditiveExpression
-- ShiftExpression >> AdditiveExpression
-- ShiftExpression >>> AdditiveExpression
ShiftExpression :: { [AST.JSNode] }
ShiftExpression : ShiftExpression Lsh AdditiveExpression { [fp (AST.NN (AST.JSExpressionBinary "<<" $1 $2 $3))]}
| ShiftExpression Rsh AdditiveExpression { [fp (AST.NN (AST.JSExpressionBinary ">>" $1 $2 $3))]}
| ShiftExpression Ursh AdditiveExpression { [fp (AST.NN (AST.JSExpressionBinary ">>>" $1 $2 $3))]}
| AdditiveExpression { $1 {- ShiftExpression -}}
-- RelationalExpression : See 11.8
-- ShiftExpression
-- RelationalExpression < ShiftExpression
-- RelationalExpression > ShiftExpression
-- RelationalExpression <= ShiftExpression
-- RelationalExpression >= ShiftExpression
-- RelationalExpression instanceof ShiftExpression
-- RelationalExpression in ShiftExpression
RelationalExpression :: { [AST.JSNode] }
RelationalExpression : ShiftExpression { $1 {- RelationalExpression -}}
| RelationalExpression Lt ShiftExpression { [fp (AST.NN (AST.JSExpressionBinary "<" $1 $2 $3))]}
| RelationalExpression Gt ShiftExpression { [fp (AST.NN (AST.JSExpressionBinary ">" $1 $2 $3))]}
| RelationalExpression Le ShiftExpression { [fp (AST.NN (AST.JSExpressionBinary "<=" $1 $2 $3))]}
| RelationalExpression Ge ShiftExpression { [fp (AST.NN (AST.JSExpressionBinary ">=" $1 $2 $3))]}
| RelationalExpression Instanceof ShiftExpression { [fp (AST.NN (AST.JSExpressionBinary " instanceof " $1 $2 $3))]}
| RelationalExpression In ShiftExpression { [fp (AST.NN (AST.JSExpressionBinary " in " $1 $2 $3))]}
-- RelationalExpressionNoIn : See 11.8
-- ShiftExpression
-- RelationalExpressionNoIn < ShiftExpression
-- RelationalExpressionNoIn > ShiftExpression
-- RelationalExpressionNoIn <= ShiftExpression
-- RelationalExpressionNoIn >= ShiftExpression
-- RelationalExpressionNoIn instanceof ShiftExpression
RelationalExpressionNoIn :: { [AST.JSNode] }
RelationalExpressionNoIn : ShiftExpression { $1 {- RelationalExpressionNoIn -}}
| RelationalExpressionNoIn Lt ShiftExpression { [fp (AST.NN (AST.JSExpressionBinary "<" $1 $2 $3))]}
| RelationalExpressionNoIn Gt ShiftExpression { [fp (AST.NN (AST.JSExpressionBinary ">" $1 $2 $3))]}
| RelationalExpressionNoIn Le ShiftExpression { [fp (AST.NN (AST.JSExpressionBinary "<=" $1 $2 $3))]}
| RelationalExpressionNoIn Ge ShiftExpression { [fp (AST.NN (AST.JSExpressionBinary ">=" $1 $2 $3))]}
| RelationalExpressionNoIn Instanceof ShiftExpression { [fp (AST.NN (AST.JSExpressionBinary " instanceof " $1 $2 $3))]}
-- EqualityExpression : See 11.9
-- RelationalExpression
-- EqualityExpression == RelationalExpression
-- EqualityExpression != RelationalExpression
-- EqualityExpression === RelationalExpression
-- EqualityExpression !== RelationalExpression
EqualityExpression :: { [AST.JSNode] }
EqualityExpression : RelationalExpression { $1 {- EqualityExpression -} }
| EqualityExpression Equal RelationalExpression { [fp (AST.NN (AST.JSExpressionBinary "==" $1 $2 $3))]}
| EqualityExpression Ne RelationalExpression { [fp (AST.NN (AST.JSExpressionBinary "!=" $1 $2 $3))]}
| EqualityExpression StrictEq RelationalExpression { [fp (AST.NN (AST.JSExpressionBinary "===" $1 $2 $3))]}
| EqualityExpression StrictNe RelationalExpression { [fp (AST.NN (AST.JSExpressionBinary "!==" $1 $2 $3))]}
-- EqualityExpressionNoIn : See 11.9
-- RelationalExpressionNoIn
-- EqualityExpressionNoIn == RelationalExpressionNoIn
-- EqualityExpressionNoIn != RelationalExpressionNoIn
-- EqualityExpressionNoIn === RelationalExpressionNoIn
-- EqualityExpressionNoIn !== RelationalExpressionNoIn
EqualityExpressionNoIn :: { [AST.JSNode] }
EqualityExpressionNoIn : RelationalExpressionNoIn { $1 {- EqualityExpressionNoIn -} }
| EqualityExpressionNoIn Equal RelationalExpression { [fp (AST.NN (AST.JSExpressionBinary "==" $1 $2 $3))]}
| EqualityExpressionNoIn Ne RelationalExpression { [fp (AST.NN (AST.JSExpressionBinary "!=" $1 $2 $3))]}
| EqualityExpressionNoIn StrictEq RelationalExpression { [fp (AST.NN (AST.JSExpressionBinary "===" $1 $2 $3))]}
| EqualityExpressionNoIn StrictNe RelationalExpression { [fp (AST.NN (AST.JSExpressionBinary "!==" $1 $2 $3))]}
-- BitwiseANDExpression : See 11.10
-- EqualityExpression
-- BitwiseANDExpression & EqualityExpression
BitwiseAndExpression :: { [AST.JSNode] }
BitwiseAndExpression : EqualityExpression { $1 {- BitwiseAndExpression -} }
| BitwiseAndExpression BitAnd EqualityExpression { [fp (AST.NN (AST.JSExpressionBinary "&" $1 $2 $3))]}
-- BitwiseANDExpressionNoIn : See 11.10
-- EqualityExpressionNoIn
-- BitwiseANDExpressionNoIn & EqualityExpressionNoIn
BitwiseAndExpressionNoIn :: { [AST.JSNode] }
BitwiseAndExpressionNoIn : EqualityExpressionNoIn { $1 {- BitwiseAndExpression -} }
| BitwiseAndExpressionNoIn BitAnd EqualityExpressionNoIn { [fp (AST.NN (AST.JSExpressionBinary "&" $1 $2 $3))]}
-- BitwiseXORExpression : See 11.10
-- BitwiseANDExpression
-- BitwiseXORExpression ^ BitwiseANDExpression
BitwiseXOrExpression :: { [AST.JSNode] }
BitwiseXOrExpression : BitwiseAndExpression { $1 {- BitwiseXOrExpression -} }
| BitwiseXOrExpression BitXor BitwiseAndExpression { [fp (AST.NN (AST.JSExpressionBinary "^" $1 $2 $3))]}
-- BitwiseXORExpressionNoIn : See 11.10
-- BitwiseANDExpressionNoIn
-- BitwiseXORExpressionNoIn ^ BitwiseANDExpressionNoIn
BitwiseXOrExpressionNoIn :: { [AST.JSNode] }
BitwiseXOrExpressionNoIn : BitwiseAndExpressionNoIn { $1 {- BitwiseXOrExpression -} }
| BitwiseXOrExpressionNoIn BitXor BitwiseAndExpressionNoIn { [fp (AST.NN (AST.JSExpressionBinary "^" $1 $2 $3))]}
-- BitwiseORExpression : See 11.10
-- BitwiseXORExpression
-- BitwiseORExpression | BitwiseXORExpression
BitwiseOrExpression :: { [AST.JSNode] }
BitwiseOrExpression : BitwiseXOrExpression { $1 {- BitwiseOrExpression -} }
| BitwiseOrExpression BitOr BitwiseXOrExpression { [fp (AST.NN (AST.JSExpressionBinary "|" $1 $2 $3))]}
-- BitwiseORExpressionNoIn : See 11.10
-- BitwiseXORExpressionNoIn
-- BitwiseORExpressionNoIn | BitwiseXORExpressionNoIn
BitwiseOrExpressionNoIn :: { [AST.JSNode] }
BitwiseOrExpressionNoIn : BitwiseXOrExpressionNoIn { $1 {- BitwiseOrExpression -} }
| BitwiseOrExpressionNoIn BitOr BitwiseXOrExpressionNoIn { [fp (AST.NN (AST.JSExpressionBinary "|" $1 $2 $3))]}
-- LogicalANDExpression : See 11.11
-- BitwiseORExpression
-- LogicalANDExpression && BitwiseORExpression
LogicalAndExpression :: { [AST.JSNode] }
LogicalAndExpression : BitwiseOrExpression { $1 {- LogicalAndExpression -} }
| LogicalAndExpression And BitwiseOrExpression { [fp (AST.NN (AST.JSExpressionBinary "&&" $1 $2 $3))]}
-- LogicalANDExpressionNoIn : See 11.11
-- BitwiseORExpressionNoIn
-- LogicalANDExpressionNoIn && BitwiseORExpressionNoIn
LogicalAndExpressionNoIn :: { [AST.JSNode] }
LogicalAndExpressionNoIn : BitwiseOrExpressionNoIn { $1 {- LogicalAndExpression -} }
| LogicalAndExpressionNoIn And BitwiseOrExpressionNoIn { [fp (AST.NN (AST.JSExpressionBinary "&&" $1 $2 $3))]}
-- LogicalORExpression : See 11.11
-- LogicalANDExpression
-- LogicalORExpression || LogicalANDExpression
LogicalOrExpression :: { [AST.JSNode] }
LogicalOrExpression : LogicalAndExpression { $1 {- LogicalOrExpression -} }
| LogicalOrExpression Or LogicalAndExpression { [fp (AST.NN (AST.JSExpressionBinary "||" $1 $2 $3))]}
-- LogicalORExpressionNoIn : See 11.11
-- LogicalANDExpressionNoIn
-- LogicalORExpressionNoIn || LogicalANDExpressionNoIn
LogicalOrExpressionNoIn :: { [AST.JSNode] }
LogicalOrExpressionNoIn : LogicalAndExpressionNoIn { $1 {- LogicalOrExpression -} }
| LogicalOrExpressionNoIn Or LogicalAndExpressionNoIn { [fp (AST.NN (AST.JSExpressionBinary "||" $1 $2 $3))]}
-- ConditionalExpression : See 11.12
-- LogicalORExpression
-- LogicalORExpression ? AssignmentExpression : AssignmentExpression
ConditionalExpression :: { [AST.JSNode] }
ConditionalExpression : LogicalOrExpression { $1 {- ConditionalExpression -} }
| LogicalOrExpression Hook AssignmentExpression Colon AssignmentExpression
{ [fp (AST.NN (AST.JSExpressionTernary $1 $2 $3 $4 $5))] }
-- ConditionalExpressionNoIn : See 11.12
-- LogicalORExpressionNoIn
-- LogicalORExpressionNoIn ? AssignmentExpressionNoIn : AssignmentExpressionNoIn
ConditionalExpressionNoIn :: { [AST.JSNode] }
ConditionalExpressionNoIn : LogicalOrExpressionNoIn { $1 {- ConditionalExpression -} }
| LogicalOrExpressionNoIn Hook AssignmentExpressionNoIn Colon AssignmentExpressionNoIn
{ [fp (AST.NN (AST.JSExpressionTernary $1 $2 $3 $4 $5))] }
-- AssignmentExpression : See 11.13
-- ConditionalExpression
-- LeftHandSideExpression AssignmentOperator AssignmentExpression
AssignmentExpression :: { [AST.JSNode] }
AssignmentExpression : ConditionalExpression { $1 {- AssignmentExpression -}}
| LeftHandSideExpression AssignmentOperator AssignmentExpression
{ ($1++[$2]++$3) }
-- AssignmentExpressionNoIn : See 11.13
-- ConditionalExpressionNoIn
-- LeftHandSideExpression AssignmentOperator AssignmentExpressionNoIn
AssignmentExpressionNoIn :: { [AST.JSNode] }
AssignmentExpressionNoIn : ConditionalExpressionNoIn { $1 {- AssignmentExpression -}}
| LeftHandSideExpression AssignmentOperator AssignmentExpressionNoIn
{ ($1++[$2]++$3) }
-- AssignmentOperator : one of See 11.13
-- '=' | '*=' | '/=' | '%=' | '+=' | '-=' | '<<=' | '>>=' | '>>>=' | '&=' | '^=' | '|='
AssignmentOperator :: { AST.JSNode }
AssignmentOperator : Assign { fp (AST.NN (AST.JSOperator $1))}
| SimpleAssign { fp (AST.NN (AST.JSOperator $1))}
-- Expression : See 11.14
-- AssignmentExpression
-- Expression , AssignmentExpression
Expression :: { AST.JSNode }
Expression : AssignmentExpression { fp (AST.NN (AST.JSExpression $1)) {- Expression -} }
| Expression Comma AssignmentExpression { fp (AST.NN (AST.JSExpression ($1:[$2]++$3))) {- Expression2 -} }
-- ExpressionNoIn : See 11.14
-- AssignmentExpressionNoIn
-- ExpressionNoIn , AssignmentExpressionNoIn
ExpressionNoIn :: { AST.JSNode }
ExpressionNoIn : AssignmentExpressionNoIn { fp (AST.NN (AST.JSExpression $1)) {- ExpressionNoIn -} }
| ExpressionNoIn Comma AssignmentExpressionNoIn { fp (AST.NN (AST.JSExpression ($1:[$2]++$3))) {- ExpressionNoIn2 -} }
-- TODO: still required?
ExpressionOpt :: { [AST.JSNode] }
ExpressionOpt : Expression { [$1] {- ExpressionOpt -}}
| { [] {- ExpressionOpt -}}
ExpressionNoInOpt :: { [AST.JSNode] }
ExpressionNoInOpt : ExpressionNoIn { [$1] {- ExpressionOpt -}}
| { [] {- ExpressionOpt -}}
-- Statement : See clause 12
-- Block
-- VariableStatement
-- EmptyStatement
-- ExpressionStatement
-- IfStatement
-- IterationStatement
-- ContinueStatement
-- BreakStatement
-- ReturnStatement
-- WithStatement
-- LabelledStatement
-- SwitchStatement
-- ThrowStatement
-- TryStatement
-- DebuggerStatement
Statement :: { AST.JSNode }
Statement : StatementNoEmpty { $1 {- Statement1 -}}
| EmptyStatement { $1 {- Statement3 -}}
StatementNoEmpty :: { AST.JSNode }
StatementNoEmpty : StatementBlock { $1 {- StatementNoEmpty1 -}}
| VariableStatement { $1 {- StatementNoEmpty2 -}}
| ExpressionStatement { $1 {- StatementNoEmpty4 -}}
| IfStatement { $1 {- StatementNoEmpty5 -}}
| IterationStatement { $1 {- StatementNoEmpty6 -}}
| ContinueStatement { $1 {- StatementNoEmpty7 -}}
| BreakStatement { $1 {- StatementNoEmpty8 -}}
| ReturnStatement { $1 {- StatementNoEmpty9 -}}
| WithStatement { $1 {- StatementNoEmpty10 -}}
| LabelledStatement { $1 {- StatementNoEmpty11 -}}
| SwitchStatement { $1 {- StatementNoEmpty12 -}}
| ThrowStatement { $1 {- StatementNoEmpty13 -}}
| TryStatement { $1 {- StatementNoEmpty14 -}}
| DebuggerStatement { $1 {- StatementNoEmpty15 -}}
StatementBlock :: { AST.JSNode }
StatementBlock : LBrace RBrace { fp (AST.NN (AST.JSBlock [$1] [] [$2])) }
| LBrace StatementList RBrace { fp (AST.NN (AST.JSBlock [$1] $2 [$3])) }
-- Block : See 12.1
-- { StatementListopt }
Block :: { AST.JSNode }
Block : LBrace RBrace { fp (AST.NN (AST.JSBlock [$1] [] [$2])) }
| LBrace StatementList RBrace { fp (AST.NN (AST.JSBlock [$1] $2 [$3])) }
-- StatementList : See 12.1
-- Statement
-- StatementList Statement
StatementList :: { [AST.JSNode] }
StatementList : Statement { [$1] {- StatementList1 -} }
| StatementList Statement { ($1++[$2]) {- StatementList2 -} }
-- VariableStatement : See 12.2
-- var VariableDeclarationList ;
VariableStatement :: { AST.JSNode }
VariableStatement : Var VariableDeclarationList AutoSemi { fp (AST.NN (AST.JSVariables $1 $2 $3))}
| Const VariableDeclarationList AutoSemi { fp (AST.NN (AST.JSVariables $1 $2 $3))}
-- VariableDeclarationList : See 12.2
-- VariableDeclaration
-- VariableDeclarationList , VariableDeclaration
VariableDeclarationList :: { [AST.JSNode] }
VariableDeclarationList : VariableDeclaration { [$1] {- VariableDeclarationList -}}
| VariableDeclarationList Comma VariableDeclaration { ($1++[$2]++[$3]) {- VariableDeclarationList -}}
-- VariableDeclarationListNoIn : See 12.2
-- VariableDeclarationNoIn
-- VariableDeclarationListNoIn , VariableDeclarationNoIn
VariableDeclarationListNoIn :: { [AST.JSNode] }
VariableDeclarationListNoIn : VariableDeclarationNoIn { [$1] {- VariableDeclarationList -}}
| VariableDeclarationListNoIn Comma VariableDeclarationNoIn { ($1++[$2]++[$3]) {- VariableDeclarationListNoIn -}}
-- VariableDeclaration : See 12.2
-- Identifier Initialiseropt
VariableDeclaration :: { AST.JSNode }
VariableDeclaration : Identifier { fp (AST.NN (AST.JSVarDecl $1 []))}
| Identifier Initializer { fp (AST.NN (AST.JSVarDecl $1 $2))}
-- VariableDeclarationNoIn : See 12.2
-- Identifier InitialiserNoInopt
VariableDeclarationNoIn :: { AST.JSNode }
VariableDeclarationNoIn : Identifier InitializerNoIn { fp (AST.NN (AST.JSVarDecl $1 $2)) }
| Identifier { fp (AST.NN (AST.JSVarDecl $1 [])) }
-- Initialiser : See 12.2
-- = AssignmentExpression
Initializer :: { [AST.JSNode] }
Initializer : SimpleAssign AssignmentExpression { $1:$2 {- Initializer -} }
-- InitialiserNoIn : See 12.2
-- = AssignmentExpressionNoIn
InitializerNoIn :: { [AST.JSNode] }
InitializerNoIn : SimpleAssign AssignmentExpressionNoIn { $1:$2 {- InitializerNoIn -}}
-- EmptyStatement : See 12.3
-- ;
EmptyStatement :: { AST.JSNode }
EmptyStatement : Semi { $1 }
-- ExpressionStatement : See 12.4
-- [lookahead ∉ {{, function}] Expression ;
-- TODO: Sort out lookahead issue. Maybe by just putting production lower to set reduce/reduce conflict
-- According to http://sideshowbarker.github.com/es5-spec/#x12.4, the ambiguity is with
-- Block or FunctionDeclaration
ExpressionStatement :: { AST.JSNode }
ExpressionStatement : Expression { $1 {- ExpressionStatement -} }
-- IfStatement : See 12.5
-- if ( Expression ) Statement else Statement
-- if ( Expression ) Statement
IfStatement :: { AST.JSNode } -- +++XXXX++
IfStatement : If LParen Expression RParen StatementSemi IfElseRest
{ (fp (AST.NN (AST.JSIf $1 $2 $3 $4 $5 $6)) ) }
IfElseRest :: { [AST.JSNode] }
IfElseRest : Else Statement { [$1,$2] }
| { [] }
StatementSemi :: { [AST.JSNode] }
StatementSemi : StatementNoEmpty Semi { [$1,$2] {- StatementSemi1 -}}
| StatementNoEmpty { [$1] {- StatementSemi2 -}}
| Semi { [$1] {- StatementSemi3 -}}
-- IterationStatement : See 12.6
-- do Statement while ( Expression );
-- while ( Expression ) Statement
-- for (ExpressionNoInopt; Expressionopt ; Expressionopt ) Statement
-- for ( var VariableDeclarationListNoIn; Expressionopt ; Expressionopt ) Statement
-- for ( LeftHandSideExpression in Expression ) Statement
-- for ( var VariableDeclarationNoIn in Expression ) Statement
IterationStatement :: { AST.JSNode }
IterationStatement : Do Statement While LParen Expression RParen AutoSemi
{ fp (AST.NN (AST.JSDoWhile $1 $2 $3 $4 $5 $6 $7)) }
| While LParen Expression RParen Statement
{ fp (AST.NN (AST.JSWhile $1 $2 $3 $4 $5)) }
| For LParen ExpressionNoInOpt Semi ExpressionOpt Semi ExpressionOpt RParen Statement
{ fp (AST.NN (AST.JSFor $1 $2 $3 $4 $5 $6 $7 $8 $9)) }
| For LParen Var VariableDeclarationListNoIn Semi ExpressionOpt Semi ExpressionOpt RParen Statement
{ fp (AST.NN (AST.JSForVar $1 $2 $3 $4 $5 $6 $7 $8 $9 $10)) }
| For LParen LeftHandSideExpression In Expression RParen Statement
{ fp (AST.NN (AST.JSForIn $1 $2 $3 $4 $5 $6 $7)) }
| For LParen Var VariableDeclarationNoIn In Expression RParen Statement
{ fp (AST.NN (AST.JSForVarIn $1 $2 $3 $4 $5 $6 $7 $8)) }
-- ContinueStatement : See 12.7
-- continue [no LineTerminator here] Identifieropt ;
-- TODO: deal with [no LineTerminator here]
ContinueStatement :: { AST.JSNode }
ContinueStatement : Continue AutoSemi { fp (AST.NN (AST.JSContinue $1 [] $2)) }
| Continue Identifier AutoSemi { fp (AST.NN (AST.JSContinue $1 [$2] $3)) }
-- BreakStatement : See 12.8
-- break [no LineTerminator here] Identifieropt ;
-- TODO: deal with [no LineTerminator here]
BreakStatement :: { AST.JSNode }
BreakStatement : Break AutoSemi { fp (AST.NN (AST.JSBreak $1 [] $2)) }
| Break Identifier AutoSemi { fp (AST.NN (AST.JSBreak $1 [$2] $3)) }
-- ReturnStatement : See 12.9
-- return [no LineTerminator here] Expressionopt ;
-- TODO: deal with [no LineTerminator here]
ReturnStatement :: { AST.JSNode }
ReturnStatement : Return AutoSemi { fp (AST.NN (AST.JSReturn $1 [] $2)) }
| Return Expression AutoSemi { fp (AST.NN (AST.JSReturn $1 [$2] $3)) }
-- WithStatement : See 12.10
-- with ( Expression ) Statement
WithStatement :: { AST.JSNode }
WithStatement : With LParen Expression RParen Statement AutoSemi { fp (AST.NN (AST.JSWith $1 $2 $3 $4 [$5,$6])) }
-- SwitchStatement : See 12.11
-- switch ( Expression ) CaseBlock
SwitchStatement :: { AST.JSNode }
SwitchStatement : Switch LParen Expression RParen CaseBlock { (AST.NN (AST.JSSwitch $1 $2 $3 $4 $5)) }
-- CaseBlock : See 12.11
-- { CaseClausesopt }
-- { CaseClausesopt DefaultClause CaseClausesopt }
CaseBlock :: { AST.JSNode }
CaseBlock : LBrace CaseClausesOpt RBrace { fp (AST.NN (AST.JSBlock [$1] $2 [$3])){- CaseBlock1 -}}
| LBrace CaseClausesOpt DefaultClause CaseClausesOpt RBrace { fp (AST.NN (AST.JSBlock [$1] ($2++[$3]++$4) [$5])){- CaseBlock2 -}}
-- CaseClauses : See 12.11
-- CaseClause
-- CaseClauses CaseClause
CaseClausesOpt :: { [AST.JSNode] }
CaseClausesOpt : CaseClause { [$1] {- CaseClauses1 -}}
| CaseClausesOpt CaseClause { ($1++[$2]) {- CaseClauses2 -}}
| { [fp (AST.NT (AST.JSLiteral "") tokenPosnEmpty []) ] } -- { [] }
-- CaseClause : See 12.11
-- case Expression : StatementListopt
CaseClause :: { AST.JSNode }
CaseClause : Case Expression Colon StatementList { fp (AST.NN (AST.JSCase $1 $2 $3 $4)) }
| Case Expression Colon { fp (AST.NN (AST.JSCase $1 $2 $3 [])) }
-- DefaultClause : See 12.11
-- default : StatementListopt
DefaultClause :: { AST.JSNode }
DefaultClause : Default Colon { fp (AST.NN (AST.JSDefault $1 $2 [])) }
| Default Colon StatementList { fp (AST.NN (AST.JSDefault $1 $2 $3)) }
-- LabelledStatement : See 12.12
-- Identifier : Statement
LabelledStatement :: { AST.JSNode }
LabelledStatement : Identifier Colon Statement { fp (AST.NN (AST.JSLabelled $1 $2 $3)) }
-- ThrowStatement : See 12.13
-- throw [no LineTerminator here] Expression ;
-- TODO : sort out no LineTerminator here
-- Does it need a semi at the end?
ThrowStatement :: { AST.JSNode }
ThrowStatement : Throw Expression { fp (AST.NN (AST.JSThrow $1 $2)) }
-- Note: worked in updated syntax as per https://developer.mozilla.org/en/JavaScript/Reference/Statements/try...catch
-- i.e., 0 or more catches, then an optional finally
-- TryStatement : See 12.14
-- try Block Catch
-- try Block Finally
-- try Block Catch Finally
TryStatement :: { AST.JSNode }
TryStatement : Try Block Catches { fp (AST.NN (AST.JSTry $1 $2 $3) ) {- TryStatement1 -} }
| Try Block Finally { fp (AST.NN (AST.JSTry $1 $2 [$3]) ) {- TryStatement2 -} }
| Try Block Catches Finally { fp (AST.NN (AST.JSTry $1 $2 ($3++[$4])) ) {- TryStatement3 -} }
Catches :: { [AST.JSNode] }
Catches : Catch { [$1] {- Catches 1 -} }
| Catches Catch { ($1++[$2]) {- Catches 2 -} }
-- Note: worked in updated syntax as per https://developer.mozilla.org/en/JavaScript/Reference/Statements/try...catch
-- <Catch> ::= 'catch' '(' Identifier ')' <Block>
-- becomes
-- <Catch> ::= 'catch' '(' Identifier ')' <Block>
-- | 'catch' '(' Identifier 'if' ConditionalExpression ')' <Block>
Catch :: { AST.JSNode }
Catch : CatchL LParen Identifier RParen Block { fp (AST.NN (AST.JSCatch $1 $2 $3 [ ] $4 $5)) }
| CatchL LParen Identifier If ConditionalExpression RParen Block { fp (AST.NN (AST.JSCatch $1 $2 $3 ($4:$5) $6 $7)) }
-- Finally : See 12.14
-- finally Block
Finally :: { AST.JSNode }
Finally : FinallyL Block { fp (AST.NN (AST.JSFinally $1 $2)) }
-- DebuggerStatement : See 12.15
-- debugger ;
DebuggerStatement :: { AST.JSNode }
DebuggerStatement : 'debugger' AutoSemi { fp (AST.NT (AST.JSLiteral "debugger") (ss $1) (gc $1)) }
-- FunctionDeclaration : See clause 13
-- function Identifier ( FormalParameterListopt ) { FunctionBody }
FunctionDeclaration :: { AST.JSNode }
FunctionDeclaration : Function Identifier LParen FormalParameterList RParen FunctionBody
{ fp (AST.NN (AST.JSFunction $1 $2 $3 $4 $5 $6) ) }
| Function Identifier LParen RParen FunctionBody
{ fp (AST.NN (AST.JSFunction $1 $2 $3 [] $4 $5) ) }
-- FunctionExpression : See clause 13
-- function Identifieropt ( FormalParameterListopt ) { FunctionBody }
FunctionExpression :: { AST.JSNode }
FunctionExpression : Function IdentifierOpt LParen RParen FunctionBody
{ fp (AST.NN (AST.JSFunctionExpression $1 $2 $3 [] $4 $5) ) }
| Function IdentifierOpt LParen FormalParameterList RParen FunctionBody
{ fp (AST.NN (AST.JSFunctionExpression $1 $2 $3 $4 $5 $6) ) }
IdentifierOpt :: { [AST.JSNode] }
IdentifierOpt : Identifier { [$1] {- IdentifierOpt -}}
| { [] {- IdentifierOpt -}}
-- FormalParameterList : See clause 13
-- Identifier
-- FormalParameterList , Identifier
FormalParameterList :: { [AST.JSNode] }
FormalParameterList : Identifier { [$1] {- FormalParameterList -}}
| FormalParameterList Comma Identifier { ($1++[$2]++[$3]) }
-- FunctionBody : See clause 13
-- SourceElementsopt
FunctionBody :: { AST.JSNode }
FunctionBody : LBrace SourceElements RBrace { (AST.NN (AST.JSBlock [$1] $2 [$3]) ) }
| LBrace RBrace { (AST.NN (AST.JSBlock [$1] [] [$2]) ) }
-- Program : See clause 14
-- SourceElementsopt
Program :: { AST.JSNode }
Program : SourceElementsTop Eof { (combineTop $1 $2) {- Program -}}
-- For debugging/other entry points
LiteralMain :: { AST.JSNode }
LiteralMain : Literal Eof { $1 }
PrimaryExpressionMain :: { AST.JSNode }
PrimaryExpressionMain : PrimaryExpression Eof { $1 }
StatementMain :: { AST.JSNode }
StatementMain : Statement Eof { $1 }
-- SourceElements : See clause 14
-- SourceElement
-- SourceElements SourceElement
SourceElements :: { [AST.JSNode] }
SourceElements : SourceElement { [$1] {- SourceElements -} }
| SourceElements SourceElement { $1++[$2] {- SourceElements -} }
SourceElementsTop :: { AST.JSNode }
SourceElementsTop : SourceElement { fp (AST.NN (AST.JSSourceElementsTop [$1]) ) }
| SourceElementsTop SourceElement { (combineSourceElementsTop $1 $2) }
-- SourceElement :
-- Statement
-- FunctionDeclaration
SourceElement :: { AST.JSNode }
SourceElement : Statement { $1 {- SourceElement1 -} }
| FunctionDeclaration { $1 {- SourceElement2 -} }
{
combineSourceElementsTop :: AST.JSNode -> AST.JSNode -> AST.JSNode
combineSourceElementsTop (AST.NN (AST.JSSourceElementsTop xs)) x1 = fp (AST.NN (AST.JSSourceElementsTop (xs++[x1])))
combineTop :: AST.JSNode -> AST.JSNode -> AST.JSNode
combineTop (AST.NN (AST.JSSourceElementsTop xs)) x1 = fp (AST.NN (AST.JSSourceElementsTop (xs++[x1])))
parseError :: Token -> Alex a
-- parseError = throwError . UnexpectedToken
parseError tok = alexError (show tok)
-- --------------------------------
{-
mex :: [AST.JSNode] -> TokenPosn
mex [] = tokenPosnEmpty
mex xs = ex (head xs)
ex :: AST.JSNode -> TokenPosn
ex (AST.NN _node span _c) = span
-}
--ss token = toSrcSpan (token_span token)
ss :: Token -> TokenPosn
ss token = token_span token
-- ------------------------------
gc :: Token -> [CommentAnnotation]
gc token = token_comment token
mgc :: [Token] -> [CommentAnnotation]
mgc xs = concatMap gc xs
-- ---------------------------------------------------------------------
fp :: AST.JSNode -> AST.JSNode
fp (AST.NN x) = (AST.NN x)
fp (AST.NT x p cs) = (AST.NT x p cs)
{-
fp (AST.NN x p cs) = (AST.NN x p' cs)
where
p' = case (filter (/= NoComment) cs) of
[] -> p
[(CommentA posn _)] -> posn
((CommentA posn _):_) -> posn
-}
}
-- Set emacs mode
-- Local Variables:
-- mode:haskell
-- End:
Jump to Line
Something went wrong with that request. Please try again.