| OLD | NEW | 
|     1 // Copyright (c) 2012, the Dart project authors.  Please see the AUTHORS file |     1 // Copyright (c) 2012, the Dart project authors.  Please see the AUTHORS file | 
|     2 // for details. All rights reserved. Use of this source code is governed by a |     2 // for details. All rights reserved. Use of this source code is governed by a | 
|     3 // BSD-style license that can be found in the LICENSE file. |     3 // BSD-style license that can be found in the LICENSE file. | 
|     4  |     4  | 
|     5 library dart2js.parser; |     5 library dart2js.parser; | 
|     6  |     6  | 
|     7 import '../common.dart'; |     7 import '../common.dart'; | 
|     8 import '../options.dart' show ParserOptions; |  | 
|     9 import '../tokens/keyword.dart' show Keyword; |     8 import '../tokens/keyword.dart' show Keyword; | 
|    10 import '../tokens/precedence.dart' show PrecedenceInfo; |     9 import '../tokens/precedence.dart' show PrecedenceInfo; | 
|    11 import '../tokens/precedence_constants.dart' |    10 import '../tokens/precedence_constants.dart' | 
|    12     show |    11     show | 
|    13         AS_INFO, |    12         AS_INFO, | 
|    14         ASSIGNMENT_PRECEDENCE, |    13         ASSIGNMENT_PRECEDENCE, | 
|    15         CASCADE_PRECEDENCE, |    14         CASCADE_PRECEDENCE, | 
|    16         EQUALITY_PRECEDENCE, |    15         EQUALITY_PRECEDENCE, | 
|    17         GT_INFO, |    16         GT_INFO, | 
|    18         IS_INFO, |    17         IS_INFO, | 
| (...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|    89  * events (except for errors) and may return null. |    88  * events (except for errors) and may return null. | 
|    90  * |    89  * | 
|    91  * Parse methods are generally named parseGrammarProductionSuffix. The |    90  * Parse methods are generally named parseGrammarProductionSuffix. The | 
|    92  * suffix can be one of "opt", or "star". "opt" means zero or one |    91  * suffix can be one of "opt", or "star". "opt" means zero or one | 
|    93  * matches, "star" means zero or more matches. For example, |    92  * matches, "star" means zero or more matches. For example, | 
|    94  * [parseMetadataStar] corresponds to this grammar snippet: [: |    93  * [parseMetadataStar] corresponds to this grammar snippet: [: | 
|    95  * metadata* :], and [parseTypeOpt] corresponds to: [: type? :]. |    94  * metadata* :], and [parseTypeOpt] corresponds to: [: type? :]. | 
|    96  */ |    95  */ | 
|    97 class Parser { |    96 class Parser { | 
|    98   final Listener listener; |    97   final Listener listener; | 
|    99   final ParserOptions parserOptions; |  | 
|   100   bool mayParseFunctionExpressions = true; |    98   bool mayParseFunctionExpressions = true; | 
|   101   bool asyncAwaitKeywordsEnabled; |    99   bool asyncAwaitKeywordsEnabled; | 
|   102  |   100  | 
|   103   final bool enableGenericMethodSyntax; |   101   Parser(this.listener, {this.asyncAwaitKeywordsEnabled: false}); | 
|   104  |  | 
|   105   Parser(this.listener, ParserOptions parserOptions, |  | 
|   106       {this.asyncAwaitKeywordsEnabled: false}) |  | 
|   107       : parserOptions = parserOptions, |  | 
|   108         enableGenericMethodSyntax = parserOptions.enableGenericMethodSyntax; |  | 
|   109  |   102  | 
|   110   Token parseUnit(Token token) { |   103   Token parseUnit(Token token) { | 
|   111     listener.beginCompilationUnit(token); |   104     listener.beginCompilationUnit(token); | 
|   112     int count = 0; |   105     int count = 0; | 
|   113     while (!identical(token.kind, EOF_TOKEN)) { |   106     while (!identical(token.kind, EOF_TOKEN)) { | 
|   114       token = parseTopLevelDeclaration(token); |   107       token = parseTopLevelDeclaration(token); | 
|   115       count++; |   108       count++; | 
|   116     } |   109     } | 
|   117     listener.endCompilationUnit(count, token); |   110     listener.endCompilationUnit(count, token); | 
|   118     return token; |   111     return token; | 
| (...skipping 340 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|   459       thisKeyword = token; |   452       thisKeyword = token; | 
|   460       // TODO(ahe): Validate field initializers are only used in |   453       // TODO(ahe): Validate field initializers are only used in | 
|   461       // constructors, and not for function-typed arguments. |   454       // constructors, and not for function-typed arguments. | 
|   462       token = expect('.', token.next); |   455       token = expect('.', token.next); | 
|   463     } |   456     } | 
|   464     token = parseIdentifier(token); |   457     token = parseIdentifier(token); | 
|   465     if (optional('(', token)) { |   458     if (optional('(', token)) { | 
|   466       listener.handleNoTypeVariables(token); |   459       listener.handleNoTypeVariables(token); | 
|   467       token = parseFormalParameters(token); |   460       token = parseFormalParameters(token); | 
|   468       listener.handleFunctionTypedFormalParameter(token); |   461       listener.handleFunctionTypedFormalParameter(token); | 
|   469     } else if (enableGenericMethodSyntax && optional('<', token)) { |   462     } else if (optional('<', token)) { | 
|   470       token = parseTypeVariablesOpt(token); |   463       token = parseTypeVariablesOpt(token); | 
|   471       token = parseFormalParameters(token); |   464       token = parseFormalParameters(token); | 
|   472       listener.handleFunctionTypedFormalParameter(token); |   465       listener.handleFunctionTypedFormalParameter(token); | 
|   473     } |   466     } | 
|   474     String value = token.stringValue; |   467     String value = token.stringValue; | 
|   475     if ((identical('=', value)) || (identical(':', value))) { |   468     if ((identical('=', value)) || (identical(':', value))) { | 
|   476       // TODO(ahe): Validate that these are only used for optional parameters. |   469       // TODO(ahe): Validate that these are only used for optional parameters. | 
|   477       Token equal = token; |   470       Token equal = token; | 
|   478       token = parseExpression(token.next); |   471       token = parseExpression(token.next); | 
|   479       listener.handleValuedFormalParameter(equal, token); |   472       listener.handleValuedFormalParameter(equal, token); | 
| (...skipping 296 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|   776     if (!identical(string, token.stringValue)) { |   769     if (!identical(string, token.stringValue)) { | 
|   777       return listener.expected(string, token); |   770       return listener.expected(string, token); | 
|   778     } |   771     } | 
|   779     return token.next; |   772     return token.next; | 
|   780   } |   773   } | 
|   781  |   774  | 
|   782   Token parseTypeVariable(Token token) { |   775   Token parseTypeVariable(Token token) { | 
|   783     listener.beginTypeVariable(token); |   776     listener.beginTypeVariable(token); | 
|   784     token = parseIdentifier(token); |   777     token = parseIdentifier(token); | 
|   785     Token extendsOrSuper = null; |   778     Token extendsOrSuper = null; | 
|   786     if (optional('extends', token) || |   779     if (optional('extends', token) || optional('super', token)) { | 
|   787         (enableGenericMethodSyntax && optional('super', token))) { |  | 
|   788       extendsOrSuper = token; |   780       extendsOrSuper = token; | 
|   789       token = parseType(token.next); |   781       token = parseType(token.next); | 
|   790     } else { |   782     } else { | 
|   791       listener.handleNoType(token); |   783       listener.handleNoType(token); | 
|   792     } |   784     } | 
|   793     listener.endTypeVariable(token, extendsOrSuper); |   785     listener.endTypeVariable(token, extendsOrSuper); | 
|   794     return token; |   786     return token; | 
|   795   } |   787   } | 
|   796  |   788  | 
|   797   /** |   789   /** | 
| (...skipping 294 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  1092       listener.handleModifiers(0); |  1084       listener.handleModifiers(0); | 
|  1093     } |  1085     } | 
|  1094  |  1086  | 
|  1095     if (type == null) { |  1087     if (type == null) { | 
|  1096       listener.handleNoType(name); |  1088       listener.handleNoType(name); | 
|  1097     } else { |  1089     } else { | 
|  1098       parseReturnTypeOpt(type); |  1090       parseReturnTypeOpt(type); | 
|  1099     } |  1091     } | 
|  1100     Token token = parseIdentifier(name); |  1092     Token token = parseIdentifier(name); | 
|  1101  |  1093  | 
|  1102     if (enableGenericMethodSyntax && getOrSet == null) { |  1094     if (getOrSet == null) { | 
|  1103       token = parseTypeVariablesOpt(token); |  1095       token = parseTypeVariablesOpt(token); | 
|  1104     } else { |  1096     } else { | 
|  1105       listener.handleNoTypeVariables(token); |  1097       listener.handleNoTypeVariables(token); | 
|  1106     } |  1098     } | 
|  1107     token = parseFormalParametersOpt(token); |  1099     token = parseFormalParametersOpt(token); | 
|  1108     bool previousAsyncAwaitKeywordsEnabled = asyncAwaitKeywordsEnabled; |  1100     bool previousAsyncAwaitKeywordsEnabled = asyncAwaitKeywordsEnabled; | 
|  1109     token = parseAsyncModifier(token); |  1101     token = parseAsyncModifier(token); | 
|  1110     token = parseFunctionBody(token, false, externalModifier != null); |  1102     token = parseFunctionBody(token, false, externalModifier != null); | 
|  1111     asyncAwaitKeywordsEnabled = previousAsyncAwaitKeywordsEnabled; |  1103     asyncAwaitKeywordsEnabled = previousAsyncAwaitKeywordsEnabled; | 
|  1112     Token endToken = token; |  1104     Token endToken = token; | 
| (...skipping 292 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  1405     token = afterName; |  1397     token = afterName; | 
|  1406     bool isField; |  1398     bool isField; | 
|  1407     while (true) { |  1399     while (true) { | 
|  1408       // Loop to allow the listener to rewrite the token stream for |  1400       // Loop to allow the listener to rewrite the token stream for | 
|  1409       // error handling. |  1401       // error handling. | 
|  1410       final String value = token.stringValue; |  1402       final String value = token.stringValue; | 
|  1411       if ((identical(value, '(')) || |  1403       if ((identical(value, '(')) || | 
|  1412           (identical(value, '.')) || |  1404           (identical(value, '.')) || | 
|  1413           (identical(value, '{')) || |  1405           (identical(value, '{')) || | 
|  1414           (identical(value, '=>')) || |  1406           (identical(value, '=>')) || | 
|  1415           (enableGenericMethodSyntax && identical(value, '<'))) { |  1407           (identical(value, '<'))) { | 
|  1416         isField = false; |  1408         isField = false; | 
|  1417         break; |  1409         break; | 
|  1418       } else if (identical(value, ';')) { |  1410       } else if (identical(value, ';')) { | 
|  1419         if (getOrSet != null) { |  1411         if (getOrSet != null) { | 
|  1420           // If we found a "get" keyword, this must be an abstract |  1412           // If we found a "get" keyword, this must be an abstract | 
|  1421           // getter. |  1413           // getter. | 
|  1422           isField = (!identical(getOrSet.stringValue, 'get')); |  1414           isField = (!identical(getOrSet.stringValue, 'get')); | 
|  1423           // TODO(ahe): This feels like a hack. |  1415           // TODO(ahe): This feels like a hack. | 
|  1424         } else { |  1416         } else { | 
|  1425           isField = true; |  1417           isField = true; | 
| (...skipping 74 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  1500       token = parseOperatorName(name); |  1492       token = parseOperatorName(name); | 
|  1501       if (staticModifier != null) { |  1493       if (staticModifier != null) { | 
|  1502         listener.reportError(staticModifier, MessageKind.EXTRANEOUS_MODIFIER, |  1494         listener.reportError(staticModifier, MessageKind.EXTRANEOUS_MODIFIER, | 
|  1503             {'modifier': staticModifier}); |  1495             {'modifier': staticModifier}); | 
|  1504       } |  1496       } | 
|  1505     } else { |  1497     } else { | 
|  1506       token = parseIdentifier(name); |  1498       token = parseIdentifier(name); | 
|  1507     } |  1499     } | 
|  1508  |  1500  | 
|  1509     token = parseQualifiedRestOpt(token); |  1501     token = parseQualifiedRestOpt(token); | 
|  1510     if (enableGenericMethodSyntax && getOrSet == null) { |  1502     if (getOrSet == null) { | 
|  1511       token = parseTypeVariablesOpt(token); |  1503       token = parseTypeVariablesOpt(token); | 
|  1512     } else { |  1504     } else { | 
|  1513       listener.handleNoTypeVariables(token); |  1505       listener.handleNoTypeVariables(token); | 
|  1514     } |  1506     } | 
|  1515     token = parseFormalParametersOpt(token); |  1507     token = parseFormalParametersOpt(token); | 
|  1516     token = parseInitializersOpt(token); |  1508     token = parseInitializersOpt(token); | 
|  1517     bool previousAsyncAwaitKeywordsEnabled = asyncAwaitKeywordsEnabled; |  1509     bool previousAsyncAwaitKeywordsEnabled = asyncAwaitKeywordsEnabled; | 
|  1518     token = parseAsyncModifier(token); |  1510     token = parseAsyncModifier(token); | 
|  1519     if (optional('=', token)) { |  1511     if (optional('=', token)) { | 
|  1520       token = parseRedirectingFactoryBody(token); |  1512       token = parseRedirectingFactoryBody(token); | 
| (...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  1591       } |  1583       } | 
|  1592       listener.beginFunctionName(token); |  1584       listener.beginFunctionName(token); | 
|  1593       if (optional('operator', token)) { |  1585       if (optional('operator', token)) { | 
|  1594         token = parseOperatorName(token); |  1586         token = parseOperatorName(token); | 
|  1595       } else { |  1587       } else { | 
|  1596         token = parseIdentifier(token); |  1588         token = parseIdentifier(token); | 
|  1597       } |  1589       } | 
|  1598     } |  1590     } | 
|  1599     token = parseQualifiedRestOpt(token); |  1591     token = parseQualifiedRestOpt(token); | 
|  1600     listener.endFunctionName(token); |  1592     listener.endFunctionName(token); | 
|  1601     if (enableGenericMethodSyntax && getOrSet == null) { |  1593     if (getOrSet == null) { | 
|  1602       token = parseTypeVariablesOpt(token); |  1594       token = parseTypeVariablesOpt(token); | 
|  1603     } else { |  1595     } else { | 
|  1604       listener.handleNoTypeVariables(token); |  1596       listener.handleNoTypeVariables(token); | 
|  1605     } |  1597     } | 
|  1606     token = parseFormalParametersOpt(token); |  1598     token = parseFormalParametersOpt(token); | 
|  1607     token = parseInitializersOpt(token); |  1599     token = parseInitializersOpt(token); | 
|  1608     bool previousAsyncAwaitKeywordsEnabled = asyncAwaitKeywordsEnabled; |  1600     bool previousAsyncAwaitKeywordsEnabled = asyncAwaitKeywordsEnabled; | 
|  1609     token = parseAsyncModifier(token); |  1601     token = parseAsyncModifier(token); | 
|  1610     if (optional('=', token)) { |  1602     if (optional('=', token)) { | 
|  1611       token = parseRedirectingFactoryBody(token); |  1603       token = parseRedirectingFactoryBody(token); | 
| (...skipping 24 matching lines...) Expand all  Loading... | 
|  1636     return token; |  1628     return token; | 
|  1637   } |  1629   } | 
|  1638  |  1630  | 
|  1639   Token parseFunctionExpression(Token token) { |  1631   Token parseFunctionExpression(Token token) { | 
|  1640     listener.beginFunction(token); |  1632     listener.beginFunction(token); | 
|  1641     listener.handleModifiers(0); |  1633     listener.handleModifiers(0); | 
|  1642     token = parseReturnTypeOpt(token); |  1634     token = parseReturnTypeOpt(token); | 
|  1643     listener.beginFunctionName(token); |  1635     listener.beginFunctionName(token); | 
|  1644     token = parseIdentifier(token); |  1636     token = parseIdentifier(token); | 
|  1645     listener.endFunctionName(token); |  1637     listener.endFunctionName(token); | 
|  1646     if (enableGenericMethodSyntax) { |  1638     token = parseTypeVariablesOpt(token); | 
|  1647       token = parseTypeVariablesOpt(token); |  | 
|  1648     } else { |  | 
|  1649       listener.handleNoTypeVariables(token); |  | 
|  1650     } |  | 
|  1651     token = parseFormalParameters(token); |  1639     token = parseFormalParameters(token); | 
|  1652     listener.handleNoInitializers(); |  1640     listener.handleNoInitializers(); | 
|  1653     bool previousAsyncAwaitKeywordsEnabled = asyncAwaitKeywordsEnabled; |  1641     bool previousAsyncAwaitKeywordsEnabled = asyncAwaitKeywordsEnabled; | 
|  1654     token = parseAsyncModifier(token); |  1642     token = parseAsyncModifier(token); | 
|  1655     bool isBlock = optional('{', token); |  1643     bool isBlock = optional('{', token); | 
|  1656     token = parseFunctionBody(token, true, false); |  1644     token = parseFunctionBody(token, true, false); | 
|  1657     asyncAwaitKeywordsEnabled = previousAsyncAwaitKeywordsEnabled; |  1645     asyncAwaitKeywordsEnabled = previousAsyncAwaitKeywordsEnabled; | 
|  1658     listener.endFunction(null, token); |  1646     listener.endFunction(null, token); | 
|  1659     return isBlock ? token.next : token; |  1647     return isBlock ? token.next : token; | 
|  1660   } |  1648   } | 
| (...skipping 211 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  1872         // TODO(eernst): Check for NPE as described in issue 26252. |  1860         // TODO(eernst): Check for NPE as described in issue 26252. | 
|  1873         Token afterParens = endParen.next; |  1861         Token afterParens = endParen.next; | 
|  1874         if (optional('{', afterParens) || |  1862         if (optional('{', afterParens) || | 
|  1875             optional('=>', afterParens) || |  1863             optional('=>', afterParens) || | 
|  1876             optional('async', afterParens) || |  1864             optional('async', afterParens) || | 
|  1877             optional('sync', afterParens)) { |  1865             optional('sync', afterParens)) { | 
|  1878           // We are looking at "type identifier '(' ... ')'" followed |  1866           // We are looking at "type identifier '(' ... ')'" followed | 
|  1879           // by '{', '=>', 'async', or 'sync'. |  1867           // by '{', '=>', 'async', or 'sync'. | 
|  1880           return parseFunctionDeclaration(token); |  1868           return parseFunctionDeclaration(token); | 
|  1881         } |  1869         } | 
|  1882       } else if (enableGenericMethodSyntax && |  1870       } else if (identical(afterIdKind, LT_TOKEN)) { | 
|  1883           identical(afterIdKind, LT_TOKEN)) { |  | 
|  1884         // We are looking at "type identifier '<'". |  1871         // We are looking at "type identifier '<'". | 
|  1885         BeginGroupToken beginAngle = afterId; |  1872         BeginGroupToken beginAngle = afterId; | 
|  1886         Token endAngle = beginAngle.endGroup; |  1873         Token endAngle = beginAngle.endGroup; | 
|  1887         if (endAngle != null && |  1874         if (endAngle != null && | 
|  1888             identical(endAngle.next.kind, OPEN_PAREN_TOKEN)) { |  1875             identical(endAngle.next.kind, OPEN_PAREN_TOKEN)) { | 
|  1889           BeginGroupToken beginParen = endAngle.next; |  1876           BeginGroupToken beginParen = endAngle.next; | 
|  1890           Token endParen = beginParen.endGroup; |  1877           Token endParen = beginParen.endGroup; | 
|  1891           if (endParen != null) { |  1878           if (endParen != null) { | 
|  1892             Token afterParens = endParen.next; |  1879             Token afterParens = endParen.next; | 
|  1893             if (optional('{', afterParens) || |  1880             if (optional('{', afterParens) || | 
| (...skipping 14 matching lines...) Expand all  Loading... | 
|  1908       } else if (optional('(', token.next)) { |  1895       } else if (optional('(', token.next)) { | 
|  1909         BeginGroupToken begin = token.next; |  1896         BeginGroupToken begin = token.next; | 
|  1910         // TODO(eernst): Check for NPE as described in issue 26252. |  1897         // TODO(eernst): Check for NPE as described in issue 26252. | 
|  1911         String afterParens = begin.endGroup.next.stringValue; |  1898         String afterParens = begin.endGroup.next.stringValue; | 
|  1912         if (identical(afterParens, '{') || |  1899         if (identical(afterParens, '{') || | 
|  1913             identical(afterParens, '=>') || |  1900             identical(afterParens, '=>') || | 
|  1914             identical(afterParens, 'async') || |  1901             identical(afterParens, 'async') || | 
|  1915             identical(afterParens, 'sync')) { |  1902             identical(afterParens, 'sync')) { | 
|  1916           return parseFunctionDeclaration(token); |  1903           return parseFunctionDeclaration(token); | 
|  1917         } |  1904         } | 
|  1918       } else if (enableGenericMethodSyntax && optional('<', token.next)) { |  1905       } else if (optional('<', token.next)) { | 
|  1919         BeginGroupToken beginAngle = token.next; |  1906         BeginGroupToken beginAngle = token.next; | 
|  1920         Token endAngle = beginAngle.endGroup; |  1907         Token endAngle = beginAngle.endGroup; | 
|  1921         if (endAngle != null && |  1908         if (endAngle != null && | 
|  1922             identical(endAngle.next.kind, OPEN_PAREN_TOKEN)) { |  1909             identical(endAngle.next.kind, OPEN_PAREN_TOKEN)) { | 
|  1923           BeginGroupToken beginParen = endAngle.next; |  1910           BeginGroupToken beginParen = endAngle.next; | 
|  1924           Token endParen = beginParen.endGroup; |  1911           Token endParen = beginParen.endGroup; | 
|  1925           if (endParen != null) { |  1912           if (endParen != null) { | 
|  1926             String afterParens = endParen.next.stringValue; |  1913             String afterParens = endParen.next.stringValue; | 
|  1927             if (identical(afterParens, '{') || |  1914             if (identical(afterParens, '{') || | 
|  1928                 identical(afterParens, '=>') || |  1915                 identical(afterParens, '=>') || | 
| (...skipping 424 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  2353   /// Where |  2340   /// Where | 
|  2354   ///   genericListLiteral ::= typeArguments '[' (expressionList ','?)? ']' |  2341   ///   genericListLiteral ::= typeArguments '[' (expressionList ','?)? ']' | 
|  2355   ///   genericMapLiteral ::= |  2342   ///   genericMapLiteral ::= | 
|  2356   ///       typeArguments '{' (mapLiteralEntry (',' mapLiteralEntry)* ','?)? '}' |  2343   ///       typeArguments '{' (mapLiteralEntry (',' mapLiteralEntry)* ','?)? '}' | 
|  2357   ///   genericFunctionLiteral ::= |  2344   ///   genericFunctionLiteral ::= | 
|  2358   ///       typeParameters formalParameterList functionBody |  2345   ///       typeParameters formalParameterList functionBody | 
|  2359   /// Provide token for [constKeyword] if preceded by 'const', null if not. |  2346   /// Provide token for [constKeyword] if preceded by 'const', null if not. | 
|  2360   Token parseLiteralListOrMapOrFunction(Token token, Token constKeyword) { |  2347   Token parseLiteralListOrMapOrFunction(Token token, Token constKeyword) { | 
|  2361     assert(optional('<', token)); |  2348     assert(optional('<', token)); | 
|  2362     BeginGroupToken begin = token; |  2349     BeginGroupToken begin = token; | 
|  2363     if (enableGenericMethodSyntax && |  2350     if (constKeyword == null && | 
|  2364         constKeyword == null && |  | 
|  2365         begin.endGroup != null && |  2351         begin.endGroup != null && | 
|  2366         identical(begin.endGroup.next.kind, OPEN_PAREN_TOKEN)) { |  2352         identical(begin.endGroup.next.kind, OPEN_PAREN_TOKEN)) { | 
|  2367       token = parseTypeVariablesOpt(token); |  2353       token = parseTypeVariablesOpt(token); | 
|  2368       return parseLiteralFunctionSuffix(token); |  2354       return parseLiteralFunctionSuffix(token); | 
|  2369     } else { |  2355     } else { | 
|  2370       token = parseTypeArgumentsOpt(token); |  2356       token = parseTypeArgumentsOpt(token); | 
|  2371       if (optional('{', token)) { |  2357       if (optional('{', token)) { | 
|  2372         return parseLiteralMapSuffix(token, constKeyword); |  2358         return parseLiteralMapSuffix(token, constKeyword); | 
|  2373       } else if ((optional('[', token)) || (optional('[]', token))) { |  2359       } else if ((optional('[', token)) || (optional('[]', token))) { | 
|  2374         return parseLiteralListSuffix(token, constKeyword); |  2360         return parseLiteralListSuffix(token, constKeyword); | 
| (...skipping 22 matching lines...) Expand all  Loading... | 
|  2397         isFunctionDeclaration(peek.next)) { |  2383         isFunctionDeclaration(peek.next)) { | 
|  2398       return parseFunctionExpression(token); |  2384       return parseFunctionExpression(token); | 
|  2399     } else if (isFunctionDeclaration(token.next)) { |  2385     } else if (isFunctionDeclaration(token.next)) { | 
|  2400       return parseFunctionExpression(token); |  2386       return parseFunctionExpression(token); | 
|  2401     } else { |  2387     } else { | 
|  2402       return parseSend(token); |  2388       return parseSend(token); | 
|  2403     } |  2389     } | 
|  2404   } |  2390   } | 
|  2405  |  2391  | 
|  2406   bool isFunctionDeclaration(Token token) { |  2392   bool isFunctionDeclaration(Token token) { | 
|  2407     if (enableGenericMethodSyntax && optional('<', token)) { |  2393     if (optional('<', token)) { | 
|  2408       BeginGroupToken begin = token; |  2394       BeginGroupToken begin = token; | 
|  2409       if (begin.endGroup == null) return false; |  2395       if (begin.endGroup == null) return false; | 
|  2410       token = begin.endGroup.next; |  2396       token = begin.endGroup.next; | 
|  2411     } |  2397     } | 
|  2412     if (optional('(', token)) { |  2398     if (optional('(', token)) { | 
|  2413       BeginGroupToken begin = token; |  2399       BeginGroupToken begin = token; | 
|  2414       // TODO(eernst): Check for NPE as described in issue 26252. |  2400       // TODO(eernst): Check for NPE as described in issue 26252. | 
|  2415       String afterParens = begin.endGroup.next.stringValue; |  2401       String afterParens = begin.endGroup.next.stringValue; | 
|  2416       if (identical(afterParens, '{') || |  2402       if (identical(afterParens, '{') || | 
|  2417           identical(afterParens, '=>') || |  2403           identical(afterParens, '=>') || | 
| (...skipping 128 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  2546   } |  2532   } | 
|  2547  |  2533  | 
|  2548   Token parseLiteralNull(Token token) { |  2534   Token parseLiteralNull(Token token) { | 
|  2549     listener.handleLiteralNull(token); |  2535     listener.handleLiteralNull(token); | 
|  2550     return token.next; |  2536     return token.next; | 
|  2551   } |  2537   } | 
|  2552  |  2538  | 
|  2553   Token parseSend(Token token) { |  2539   Token parseSend(Token token) { | 
|  2554     listener.beginSend(token); |  2540     listener.beginSend(token); | 
|  2555     token = parseIdentifier(token); |  2541     token = parseIdentifier(token); | 
|  2556     if (enableGenericMethodSyntax && isValidMethodTypeArguments(token)) { |  2542     if (isValidMethodTypeArguments(token)) { | 
|  2557       token = parseTypeArgumentsOpt(token); |  2543       token = parseTypeArgumentsOpt(token); | 
|  2558     } else { |  2544     } else { | 
|  2559       listener.handleNoTypeArguments(token); |  2545       listener.handleNoTypeArguments(token); | 
|  2560     } |  2546     } | 
|  2561     token = parseArgumentsOpt(token); |  2547     token = parseArgumentsOpt(token); | 
|  2562     listener.endSend(token); |  2548     listener.endSend(token); | 
|  2563     return token; |  2549     return token; | 
|  2564   } |  2550   } | 
|  2565  |  2551  | 
|  2566   Token parseArgumentsOpt(Token token) { |  2552   Token parseArgumentsOpt(Token token) { | 
| (...skipping 438 matching lines...) Expand 10 before | Expand all | Expand 10 after  Loading... | 
|  3005     } |  2991     } | 
|  3006     listener.handleContinueStatement(hasTarget, continueKeyword, token); |  2992     listener.handleContinueStatement(hasTarget, continueKeyword, token); | 
|  3007     return expectSemicolon(token); |  2993     return expectSemicolon(token); | 
|  3008   } |  2994   } | 
|  3009  |  2995  | 
|  3010   Token parseEmptyStatement(Token token) { |  2996   Token parseEmptyStatement(Token token) { | 
|  3011     listener.handleEmptyStatement(token); |  2997     listener.handleEmptyStatement(token); | 
|  3012     return expectSemicolon(token); |  2998     return expectSemicolon(token); | 
|  3013   } |  2999   } | 
|  3014 } |  3000 } | 
| OLD | NEW |