addExpression:
       mulExpression
     | addExpression ('+' | '-' | '~') mulExpression
     ;
 aliasDeclaration:
       'alias' aliasInitializer (',' aliasInitializer)* ';'
     | 'alias' storageClass* type declaratorIdentifierList ';'
     | 'alias' storageClass* type identifier '(') parameters '' * ';'
     ;
 aliasInitializer:
       Identifier templateParameters? '=' storageClass* type
     | Identifier templateParameters? '=' functionLiteralExpression
     ;
 aliasThisDeclaration:
     'alias' Identifier 'this' ';'
     ;
 alignAttribute:
     'align' ('(' assignExpression ')')?
     ;
 andAndExpression:
       orExpression
     | andAndExpression '&&' orExpression
     ;
 andExpression:
       cmpExpression
     | andExpression '&' cmpExpression
     ;
 argumentList:
     assignExpression (',' assignExpression?)*
     ;
 arguments:
     '(' argumentList? ')'
     ;
 arrayInitializer:
       '[' ']'
     | '[' arrayMemberInitialization (',' arrayMemberInitialization?)* ']'
     ;
 arrayLiteral:
     '[' argumentList? ']'
     ;
 arrayMemberInitialization:
     (assignExpression ':')? nonVoidInitializer
     ;
 asmAddExp:
       asmMulExp
     | asmAddExp ('+' | '-') asmMulExp
     ;
 asmAndExp:
       asmEqualExp
     | asmAndExp '&' asmEqualExp
     ;
 asmBrExp:
       asmUnaExp
     | asmBrExp? '[' asmExp ']'
     ;
 asmEqualExp:
       asmRelExp
     | asmEqualExp ('==' | '!=') asmRelExp
     ;
 asmExp:
     asmLogOrExp ('?' asmExp ':' asmExp)?
     ;
 asmInstruction:
       Identifier
     | 'align' IntegerLiteral
     | 'align' Identifier
     | Identifier ':' asmInstruction
     | Identifier operands
     | 'in' operands
     | 'out' operands
     | 'int' operands
     | ';'
     ;
 asmLogAndExp:
     asmOrExp
     asmLogAndExp '&&' asmOrExp
     ;
 asmLogOrExp:
       asmLogAndExp
     | asmLogOrExp '||' asmLogAndExp
     ;
 asmMulExp:
       asmBrExp
     | asmMulExp ('*' | '/' | '%') asmBrExp
     ;
 asmOrExp:
       asmXorExp
     | asmOrExp '|' asmXorExp
     ;
 asmPrimaryExp:
       IntegerLiteral
     | FloatLiteral
     | StringLiteral
     | register
     | register : AsmExp
     | identifierChain
     | '$'
     ;
 asmRelExp:
       asmShiftExp
     | asmRelExp (('<' | '<=' | '>' | '>=') asmShiftExp)?
     ;
 asmShiftExp:
     asmAddExp
     asmShiftExp ('<<' | '>>' | '>>>') asmAddExp
     ;
 asmStatement:
     'asm' functionAttributes? '{' asmInstruction+ '}'
     ;
 asmTypePrefix:
       Identifier Identifier?
     | 'byte' Identifier?
     | 'short' Identifier?
     | 'int' Identifier?
     | 'float' Identifier?
     | 'double' Identifier?
     | 'real' Identifier?
     ;
 asmUnaExp:
       asmTypePrefix asmExp
     | Identifier asmExp
     | '+' asmUnaExp
     | '-' asmUnaExp
     | '!' asmUnaExp
     | '~' asmUnaExp
     | asmPrimaryExp
     ;
 asmXorExp:
       asmAndExp
     | asmXorExp '^' asmAndExp
     ;
 assertArguments:
     assignExpression (',' assignExpression)? ','?
     ;
 assertExpression:
     'assert' '(' assertArguments ')'
     ;
 assignExpression:
     ternaryExpression (assignOperator assignExpression)?
     ;
 assignOperator:
       '='
     | '>>>='
     | '>>='
     | '<<='
     | '+='
     | '-='
     | '*='
     | '%='
     | '&='
     | '/='
     | '|='
     | '^^='
     | '^='
     | '~='
     ;
 assocArrayLiteral:
     '[' keyValuePairs ']'
     ;
 atAttribute:
       '@' Identifier
     | '@' Identifier '(' argumentList? ')'
     | '@' '(' argumentList ')'
     | '@' templateInstance
     ;
 attribute:
       pragmaExpression
     | alignAttribute
     | deprecated
     | atAttribute
     | linkageAttribute
     | 'export'
     | 'package' ("(") identifierChain "")?
     | 'private'
     | 'protected'
     | 'public'
     | 'static'
     | 'extern'
     | 'abstract'
     | 'final'
     | 'override'
     | 'synchronized'
     | 'auto'
     | 'scope'
     | 'const'
     | 'immutable'
     | 'inout'
     | 'shared'
     | '_gshared'
     | 'nothrow'
     | 'pure'
     | 'ref'
     ;
 attributeDeclaration:
     attribute ':'
     ;
 autoDeclaration:
     storageClass+  autoDeclarationPart (',' autoDeclarationPart)* ';'
     ;
 autoDeclarationPart:
     Identifier templateParameters? '=' initializer
     ;
 blockStatement:
     '{' declarationsAndStatements? '}'
     ;
 breakStatement:
     'break' Identifier? ';'
     ;
 baseClass:
     type2
     ;
 baseClassList:
     baseClass (',' baseClass)*
     ;
 builtinType:
       'bool'
     | 'byte'
     | 'ubyte'
     | 'short'
     | 'ushort'
     | 'int'
     | 'uint'
     | 'long'
     | 'ulong'
     | 'char'
     | 'wchar'
     | 'dchar'
     | 'float'
     | 'double'
     | 'real'
     | 'ifloat'
     | 'idouble'
     | 'ireal'
     | 'cfloat'
     | 'cdouble'
     | 'creal'
     | 'void'
     ;
 caseRangeStatement:
     'case' assignExpression ':' '...' 'case' assignExpression ':' declarationsAndStatements
     ;
 caseStatement:
     'case' argumentList ':' declarationsAndStatements
     ;
 castExpression:
     'cast' '(' (type | castQualifier)? ')' unaryExpression
     ;
 castQualifier:
       'const'
     | 'const' 'shared'
     | 'immutable'
     | 'inout'
     | 'inout' 'shared'
     | 'shared'
     | 'shared' 'const'
     | 'shared' 'inout'
     ;
 catch:
     'catch' '(' type Identifier? ')' declarationOrStatement
     ;
 catches:
       catch+
     | catch* lastCatch
     ;
 classDeclaration:
       'class' Identifier ';'
     | 'class' Identifier (':' baseClassList)? structBody
     | 'class' Identifier templateParameters constraint? (structBody | ';')
     | 'class' Identifier templateParameters constraint? (':' baseClassList)? structBody
     | 'class' Identifier templateParameters (':' baseClassList)? constraint? structBody
     ;
 cmpExpression:
       shiftExpression
     | equalExpression
     | identityExpression
     | relExpression
     | inExpression
     ;
 compileCondition:
       versionCondition
     | debugCondition
     | staticIfCondition
     ;
 conditionalDeclaration:
       compileCondition declaration
     | compileCondition '{' declaration* '}'
     | compileCondition ':' declaration+
     | compileCondition declaration 'else' ':' declaration*
     | compileCondition declaration 'else' declaration
     | compileCondition declaration 'else' '{' declaration* '}'
     | compileCondition '{' declaration* '}' 'else' declaration
     | compileCondition '{' declaration* '}' 'else' '{' declaration* '}'
     | compileCondition '{' declaration* '}' 'else' ':' declaration*
     | compileCondition ':' declaration+ 'else' declaration
     | compileCondition ':' declaration+ 'else' '{' declaration* '}'
     | compileCondition ':' declaration+ 'else' ':' declaration*
     ;
 conditionalStatement:
     compileCondition declarationOrStatement ('else' declarationOrStatement)?
     ;
 constraint:
     'if' '(' expression ')'
     ;
 constructor:
     'this' templateParameters? parameters memberFunctionAttribute* constraint? (functionBody | ';')
     ;
 continueStatement:
     'continue' Identifier? ';'
     ;
 debugCondition:
     'debug' ('(' (IntegerLiteral | Identifier) ')')?
     ;
 debugSpecification:
     'debug' '=' (Identifier | IntegerLiteral) ';'
     ;
 declaration:
       attribute* declaration2
     | attribute+ '{' declaration* '}'
     ;
  declaration2:
       aliasDeclaration
     | aliasThisDeclaration
     | anonymousEnumDeclaration
     | attributeDeclaration
     | classDeclaration
     | conditionalDeclaration
     | constructor
     | debugSpecification
     | destructor
     | enumDeclaration
     | eponymousTemplateDeclaration
     | functionDeclaration
     | importDeclaration
     | interfaceDeclaration
     | invariant
     | mixinDeclaration
     | mixinTemplateDeclaration
     | pragmaDeclaration
     | sharedStaticConstructor
     | sharedStaticDestructor
     | staticAssertDeclaration
     | staticConstructor
     | staticDestructor
     | structDeclaration
     | templateDeclaration
     | unionDeclaration
     | unittest
     | variableDeclaration
     | versionSpecification
     ;
 declarationsAndStatements:
     declarationOrStatement+
     ;
 declarationOrStatement:
       declaration
     | statement
     ;
 declarator:
       Identifier
     | Identifier '=' initializer
     | Identifier templateParameters '=' initializer
     ;
 declaratorIdentifierList:
     Identifier (',' Identifier)*
     ;
 defaultStatement:
     'default' ':' declarationsAndStatements
     ;
 deleteExpression:
     'delete' unaryExpression
     ;
 deprecated:
     'deprecated' ('(' StringLiteral+ ')')?
     ;
 destructor:
     '~' 'this' '(' ')' memberFunctionAttribute* (functionBody | ';')
     ;
 doStatement:
     'do' statementNoCaseNoDefault 'while' '(' expression ')' ';'
     ;
 enumBody:
     '{' enumMember (',' enumMember?)* '}'
     ;
 anonymousEnumMember:
       type identifier '=' assignExpression
     | identifier '=' assignExpression
     | identifier
     ;
 anonymousEnumDeclaration:
     'enum' (':' type)? '{' anonymousEnumMember+ '}'
     ;
 enumDeclaration:
       'enum' Identifier (':' type)? ';'
     | 'enum' Identifier (':' type)? enumBody
     ;
 enumMemberAttribute:
       atAttribute
     | deprecated
     ;
 enumMember:
     (enumMemberAttribute)* Identifier ('=' assignExpression)?
     ;
 eponymousTemplateDeclaration:
     'enum' Identifier templateParameters '=' assignExpression ';'
     ;
 equalExpression:
     shiftExpression ('==' | '!=') shiftExpression
     ;
 expression:
     assignExpression (',' assignExpression)*
     ;
 expressionStatement:
     expression ';'
     ;
 finalSwitchStatement:
     'final' switchStatement
     ;
 finally:
     'finally' declarationOrStatement
     ;
 forStatement:
     'for' '(' (declaration | statementNoCaseNoDefault) expression? ';' expression? ')' declarationOrStatement
     ;
 staticForeachDeclaration:
       'static' ('foreach' | 'foreach_reverse') '(' foreachTypeList ';' expression ')' (declaration | '{' declaration* '}')
     | 'static' ('foreach' | 'foreach_reverse') '(' foreachType ';' expression '..' expression ')' (declaration | '{' declaration* '}')
     ;
 staticForeachStatement:
     'static' foreachStatement
     ;
 foreachStatement:
       ('foreach' | 'foreach_reverse') '(' foreachTypeList ';' expression ')' declarationOrStatement
     | ('foreach' | 'foreach_reverse') '(' foreachType ';' expression '..' expression ')' declarationOrStatement
     ;
 foreachType:
       ('ref' | 'alias' | 'enum' | typeConstructor)* type? Identifier
     ;
 foreachTypeList:
     foreachType (',' foreachType)*
     ;
 functionAttribute:
       atAttribute
     | 'pure'
     | 'nothrow'
     ;
 functionBody:
       specifiedFunctionBody
     | missingFunctionBody
     ;
 functionCallExpression:
       symbol arguments
     | unaryExpression arguments
     | type arguments
     ;
 functionContract:
       inOutContractExpression
     | inOutStatement
     ;
 functionDeclaration:
       (storageClass+ | type) Identifier parameters memberFunctionAttribute* (functionBody | ';')
     | (storageClass+ | type) Identifier templateParameters parameters memberFunctionAttribute* constraint? (functionBody | ';')
     ;
 functionLiteralExpression:
     | 'delegate' type? (parameters functionAttribute*)? specifiedFunctionBody
     | 'function' type? (parameters functionAttribute*)? specifiedFunctionBody
     | parameters functionAttribute* specifiedFunctionBody
     | specifiedFunctionBody
     | Identifier '=>' assignExpression
     | 'function' type? parameters functionAttribute* '=>' assignExpression
     | 'delegate' type? parameters functionAttribute* '=>' assignExpression
     | parameters functionAttribute* '=>' assignExpression
     ;
 gotoStatement:
     'goto' (Identifier | 'default' | 'case' expression?) ';'
     ;
 identifierChain:
     Identifier ('.' Identifier)*
     ;
 typeIdentifierPart:
       identifierOrTemplateInstance
     | identifierOrTemplateInstance '.' typeIdentifierPart
     | identifierOrTemplateInstance '[' assignExpression ']' '.' typeIdentifierPart
     ;
 identifierOrTemplateChain:
     identifierOrTemplateInstance ('.' identifierOrTemplateInstance)*
     ;
 identifierOrTemplateInstance:
       Identifier
     | templateInstance
     ;
 identityExpression:
     shiftExpression ('is' | ('!' 'is')) shiftExpression
     ;
 ifStatement:
     'if' '(' ifCondition ')' declarationOrStatement ('else' declarationOrStatement)?
 ifCondition:
       'auto' Identifier '=' expression
     | typeConstructors Identifier '=' expression
     | typeConstructors? type Identifier '=' expression
     | expression
     ;
 importBind:
     Identifier ('=' Identifier)?
     ;
 importBindings:
     singleImport ':' importBind (',' importBind)*
     ;
 importDeclaration:
       'import' singleImport (',' singleImport)* (',' importBindings)? ';'
     | 'import' importBindings ';'
     ;
 importExpression:
     'import' '(' assignExpression ')'
     ;
 index:
     assignExpression ('..' assignExpression)?
     ;
 
 indexExpression:
       unaryExpression '[' ']'
     | unaryExpression '[' index (',' index)* ']'
     ;
 
 inContractExpression:
     'in' '(' assertArguments ')'
     ;
 inExpression:
     shiftExpression ('in' | ('!' 'in')) shiftExpression
     ;
 inOutContractExpression:
       inContractExpression
     | outContractExpression
     ;
 inOutStatement:
       inStatement
     | outStatement
     ;
 inStatement:
     'in' blockStatement
     ;
 initializer:
       'void'
     | nonVoidInitializer
     ;
 interfaceDeclaration:
       'interface' Identifier ';'
     | 'interface' Identifier (':' baseClassList)? structBody
     | 'interface' Identifier templateParameters constraint? (':' baseClassList)? structBody
     | 'interface' Identifier templateParameters (':' baseClassList)? constraint? structBody
     ;
 invariant:
       'invariant' ('(' '(')? blockStatement
     | 'invariant' '(' assertArguments ')' ';'
     ;
 isExpression:
       'is' '(' type identifier? ')'
     | 'is' '(' type identifier? ':' typeSpecialization ')'
     | 'is' '(' type identifier? '=' typeSpecialization ')'
     | 'is' '(' type identifier? ':' typeSpecialization ',' templateParameterList ')'
     | 'is' '(' type identifier? '=' typeSpecialization ',' templateParameterList ')'
     ;
 keyValuePair:
     assignExpression ':' assignExpression
     ;
 keyValuePairs:
     keyValuePair (',' keyValuePair)* ','?
     ;
 labeledStatement:
     Identifier ':' declarationOrStatement?
     ;
 lastCatch:
     'catch' statementNoCaseNoDefault
     ;
 linkageAttribute:
       'extern' '(' Identifier ')'
     | 'extern' '(' Identifier '-' Identifier ')'
     | 'extern' '(' Identifier '++' (',' typeIdentifierPart | 'struct' | 'class')? ')'
     ;
 memberFunctionAttribute:
       functionAttribute
     | 'immutable'
     | 'inout'
     | 'shared'
     | 'const'
     | 'return'
     | 'scope'
     ;
 missingFunctionBody:
       ';'
     | functionContract* ';'
     ;
 mixinDeclaration:
       mixinExpression ';'
     | templateMixinExpression ';'
     ;
 mixinExpression:
     'mixin' '(' argumentList ')'
     ;
 mixinTemplateDeclaration:
     'mixin' templateDeclaration
     ;
 mixinTemplateName:
       symbol
     | typeofExpression '.' identifierOrTemplateChain
     ;
 module:
     moduleDeclaration? declaration*
     ;
 moduleDeclaration:
     deprecated? 'module' identifierChain ';'
     ;
 mulExpression:
       powExpression
     | mulExpression ('*' | '/' | '%') powExpression
     ;
 newAnonClassExpression:
     'new' arguments? 'class' arguments? baseClassList? structBody
     ;
 newExpression:
       'new' type (('[' assignExpression ']') | arguments)?
     | newAnonClassExpression
     ;
 nonVoidInitializer:
       assignExpression
     | arrayInitializer
     | structInitializer
     ;
 operands:
       asmExp
     | asmExp ',' operands
     ;
 orExpression:
       xorExpression
     | orExpression '|' xorExpression
     ;
 orOrExpression:
       andAndExpression
     | orOrExpression '||' andAndExpression
     ;
 outContractExpression:
     'out' '(' Identifier? ';' assertArguments ')'
     ;
 outStatement:
     'out' ('(' Identifier ')')? blockStatement
     ;
 parameter:
       parameterAttribute* type
     | parameterAttribute* type Identifier? '...'
     | parameterAttribute* type Identifier? ('=' assignExpression)?
     ;
 parameterAttribute:
       atAttribute
     | typeConstructor
     | 'final'
     | 'in'
     | 'lazy'
     | 'out'
     | 'ref'
     | 'scope'
     | 'auto'
     | 'return'
     ;
 parameters:
       '(' parameter (',' parameter)* (',' '...')? ')'
     | '(' '...' ')'
     | '(' ')'
     ;
 postblit:
     'this' '(' 'this' ')' memberFunctionAttribute* (functionBody | ';')
     ;
 powExpression:
       unaryExpression
     | powExpression '^^' unaryExpression
     ;
 pragmaDeclaration:
     pragmaExpression ';'
     ;
 pragmaExpression:
     'pragma' '(' Identifier (',' argumentList)? ')'
     ;
 pragmaStatement:
       pragmaExpression statement
     | pragmaExpression blockStatement
     | pragmaExpression ';'
     ;
 primaryExpression:
       identifierOrTemplateInstance
     | '.' identifierOrTemplateInstance
     | typeConstructor '(' basicType ')' '.' Identifier
     | basicType '.' Identifier
     | basicType arguments
     | typeofExpression
     | typeidExpression
     | vector
     | arrayLiteral
     | assocArrayLiteral
     | '(' expression ')'
     | isExpression
     | functionLiteralExpression
     | traitsExpression
     | mixinExpression
     | importExpression
     | '$'
     | 'this'
     | 'super'
     | 'null'
     | 'true'
     | 'false'
     | '__DATE__'
     | '__FILE__'
     | '__FILE_FULL_PATH__'
     | '__FUNCTION__'
     | '__LINE__'
     | '__MODULE__'
     | '__PRETTY_FUNCTION__'
     | '__TIME__'
     | '__TIMESTAMP__'
     | '__VENDOR__'
     | '__VERSION__'
     | IntegerLiteral
     | FloatLiteral
     | StringLiteral+
     | CharacterLiteral
     ;
 register:
       Identifier
     | Identifier '(' IntegerLiteral ')'
     ;
 relExpression:
       shiftExpression
     | relExpression relOperator shiftExpression
     ;
 relOperator:
       '<'
     | '<='
     | '>'
     | '>='
     | '!<>='
     | '!<>'
     | '<>'
     | '<>='
     | '!>'
     | '!>='
     | '!<'
     | '!<='
     ;
 returnStatement:
     'return' expression? ';'
     ;
 scopeGuardStatement:
     'scope' '(' Identifier ')' statementNoCaseNoDefault
     ;
 sharedStaticConstructor:
     'shared' 'static' 'this' '(' ')' memberFunctionAttribute* (functionBody | ";")
     ;
 sharedStaticDestructor:
     'shared' 'static' '~' 'this' '(' ')' memberFunctionAttribute* (functionBody | ";")
     ;
 shiftExpression:
       addExpression
     | shiftExpression ('<<' | '>>' | '>>>') addExpression
     ;
 singleImport:
     (Identifier '=')? identifierChain
     ;
 specifiedFunctionBody:
       'do'? blockStatement
     | functionContract* inOutContractExpression 'do'? blockStatement
     | functionContract* inOutStatement 'do' blockStatement
     ;
 statement:
       statementNoCaseNoDefault
     | caseStatement
     | caseRangeStatement
     | defaultStatement
     ;
 statementNoCaseNoDefault:
       labeledStatement
     | blockStatement
     | ifStatement
     | whileStatement
     | doStatement
     | forStatement
     | foreachStatement
     | switchStatement
     | finalSwitchStatement
     | continueStatement
     | breakStatement
     | returnStatement
     | gotoStatement
     | withStatement
     | synchronizedStatement
     | tryStatement
     | throwStatement
     | scopeGuardStatement
     | pragmaStatement
     | asmStatement
     | conditionalStatement
     | staticAssertStatement
     | versionSpecification
     | debugSpecification
     | expressionStatement
     ;
 staticAssertDeclaration:
     staticAssertStatement
     ;
 staticAssertStatement:
     'static' assertExpression ';'
     ;
 staticConstructor:
     'static' 'this' '(' ')' memberFunctionAttribute* (functionBody | ";")
     ;
 staticDestructor:
     'static' '~' 'this' '(' ')' memberFunctionAttribute* (functionBody | ";")
     ;
 staticIfCondition:
     'static' 'if' '(' assignExpression ')'
     ;
 storageClass:
       alignAttribute
     | linkageAttribute
     | atAttribute
     | typeConstructor
     | deprecated
     | 'abstract'
     | 'auto'
     | 'enum'
     | 'extern'
     | 'final'
     | 'nothrow'
     | 'override'
     | 'pure'
     | 'ref'
     | '__gshared'
     | 'scope'
     | 'static'
     | 'synchronized'
     ;
 structBody:
     '{' declaration* '}'
     ;
 structDeclaration:
       'struct' Identifier (templateParameters constraint?)? (structBody | ';')
     | 'struct' structBody
     ;
 structInitializer:
     '{' structMemberInitializers? '}'
     ;
 structMemberInitializer:
     (Identifier ':')? nonVoidInitializer
     ;
 structMemberInitializers:
     structMemberInitializer (',' structMemberInitializer?)*
     ;
 switchStatement:
     'switch' '(' expression ')' statement
     ;
 symbol:
     '.'? identifierOrTemplateChain
     ;
 synchronizedStatement:
     'synchronized' ('(' expression ')')? statementNoCaseNoDefault
     ;
 templateAliasParameter:
     'alias' type? Identifier (':' (type | assignExpression))? ('=' (type | assignExpression))?
     ;
 templateArgument:
       type
     | assignExpression
     ;
 templateArgumentList:
     templateArgument (',' templateArgument?)*
     ;
 templateArguments:
     '!' ('(' templateArgumentList? ')') | templateSingleArgument
     ;
 templateDeclaration:
       'template' Identifier templateParameters constraint? '{' declaration* '}'
     ;
 templateInstance:
     Identifier templateArguments
     ;
 templateMixinExpression:
     'mixin' mixinTemplateName templateArguments? Identifier?
     ;
 templateParameter:
       templateTypeParameter
     | templateValueParameter
     | templateAliasParameter
     | templateTupleParameter
     | templateThisParameter
     ;
 templateParameterList:
     templateParameter (',' templateParameter?)* ','?
     ;
 templateParameters:
     '(' templateParameterList? ')'
     ;
 templateSingleArgument:
       builtinType
     | Identifier
     | CharacterLiteral
     | StringLiteral
     | IntegerLiteral
     | FloatLiteral
     | 'true'
     | 'false'
     | 'null'
     | 'this'
     | '__DATE__'
     | '__FILE__'
     | '__FILE_FULL_PATH__'
     | '__FUNCTION__'
     | '__LINE__'
     | '__MODULE__'
     | '__PRETTY_FUNCTION__'
     | '__TIME__'
     | '__TIMESTAMP__'
     | '__VENDOR__'
     | '__VERSION__'
     ;
 templateThisParameter:
     'this' templateTypeParameter
     ;
 templateTupleParameter:
     Identifier '...'
     ;
 templateTypeParameter:
     Identifier (':' type)? ('=' type)?
     ;
 templateValueParameter:
     type Identifier (':' assignExpression)? templateValueParameterDefault?
     ;
 templateValueParameterDefault:
       '=' '__DATE__'
     | '=' '__FILE__'
     | '=' '__FILE_FULL_PATH__'
     | '=' '__FUNCTION__'
     | '=' '__LINE__'
     | '=' '__MODULE__'
     | '=' '__PRETTY_FUNCTION__'
     | '=' '__TIME__'
     | '=' '__TIMESTAMP__'
     | '=' '__VENDOR__'
     | '=' '__VERSION__'
     | '=' assignExpression
     ;
 ternaryExpression:
     orOrExpression ('?' expression ':' ternaryExpression)?
     ;
 throwStatement:
     'throw' expression ';'
     ;
 traitsExpression:
     '__traits' '(' Identifier ',' templateArgumentList ')'
     ;
 tryStatement:
     'try' declarationOrStatement (catches | catches finally | finally)
     ;
 type:
     typeConstructors? type2 typeSuffix*
     ;
 type2:
       builtinType
     | typeIdentifierPart
     | 'super' '.' typeIdentifierPart
     | 'this' '.' typeIdentifierPart
     | typeofExpression ('.' typeIdentifierPart)?
     | typeConstructor '(' type ')'
     | traitsExpression
     | vector
     ;
 typeConstructor:
       'const'
     | 'immutable'
     | 'inout'
     | 'shared'
     ;
 typeConstructors:
     typeConstructor+
     ;
 typeSpecialization:
       type
     | 'struct'
     | 'union'
     | 'class'
     | 'interface'
     | 'enum'
     | 'function'
     | 'delegate'
     | 'super'
     | 'const'
     | 'immutable'
     | 'inout'
     | 'shared'
     | 'return'
     | 'typedef'
     | '__parameters'
     ;
 typeSuffix:
       '*'
     | '[' type? ']'
     | '[' assignExpression ']'
     | '[' assignExpression '..'  assignExpression ']'
     | ('delegate' | 'function') parameters memberFunctionAttribute*
     ;
 typeidExpression:
     'typeid' '(' (type | expression) ')'
     ;
 typeofExpression:
     'typeof' '(' (expression | 'return') ')'
     ;
 unaryExpression:
       primaryExpression
     | '&' unaryExpression
     | '!' unaryExpression
     | '*' unaryExpression
     | '+' unaryExpression
     | '-' unaryExpression
     | '~' unaryExpression
     | '++' unaryExpression
     | '--' unaryExpression
     | newExpression
     | deleteExpression
     | castExpression
     | assertExpression
     | functionCallExpression
     | indexExpression
     | '(' type ')' '.' identifierOrTemplateInstance
     | unaryExpression '.' newExpression
     | unaryExpression '.' identifierOrTemplateInstance
     | unaryExpression '--'
     | unaryExpression '++'
     ;
 unionDeclaration:
       'union' Identifier (templateParameters constraint?)? (structBody | ';')
     | 'union' structBody
     ;
 unittest:
     'unittest' blockStatement
     ;
 variableDeclaration:
       storageClass* type declarator (',' declarator)* ';'
     | storageClass* type identifier '=' functionBody ';'
     | autoDeclaration
     ;
 vector:
     '__vector' ('(' type ')')?
     ;
 versionCondition:
     'version' '(' (IntegerLiteral | Identifier | 'unittest' | 'assert') ')'
     ;
 versionSpecification:
     'version' '=' (Identifier | IntegerLiteral) ';'
     ;
 whileStatement:
     'while' '(' expression ')' declarationOrStatement
     ;
 withStatement:
     'with' '(' expression ')' declarationOrStatement
     ;
 xorExpression:
       andExpression
     | xorExpression '^' andExpression
     ;