Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(76)

Unified Diff: pkg/compiler/lib/src/parser/parser.dart

Issue 1878253002: Adds support for remaining generic method syntax constructs. (Closed) Base URL: https://github.com/dart-lang/sdk.git@master
Patch Set: Added comment at a tricky point Created 4 years, 8 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
Index: pkg/compiler/lib/src/parser/parser.dart
diff --git a/pkg/compiler/lib/src/parser/parser.dart b/pkg/compiler/lib/src/parser/parser.dart
index 0a8d68d77a76cdf7aefdbda26dade47234441bb1..df576076fd9251eb0154b935c569e8079be4ba8b 100644
--- a/pkg/compiler/lib/src/parser/parser.dart
+++ b/pkg/compiler/lib/src/parser/parser.dart
@@ -463,6 +463,11 @@ class Parser {
}
token = parseIdentifier(token);
if (optional('(', token)) {
+ listener.handleNoTypeVariables(token);
+ token = parseFormalParameters(token);
+ listener.handleFunctionTypedFormalParameter(token);
+ } else if (enableGenericMethodSyntax && optional('<', token)) {
+ token = parseTypeVariablesOpt(token);
token = parseFormalParameters(token);
listener.handleFunctionTypedFormalParameter(token);
}
@@ -767,9 +772,12 @@ class Parser {
Token parseTypeVariable(Token token) {
listener.beginTypeVariable(token);
token = parseIdentifier(token);
- if (optional('extends', token)) {
+ if (optional('extends', token) ||
+ (enableGenericMethodSyntax && optional('super', token))) {
+ listener.handleExtendsOrSuper(token);
token = parseType(token.next);
} else {
+ listener.handleNoExtendsNorSuper(token);
listener.handleNoType(token);
}
listener.endTypeVariable(token);
Johnni Winther 2016/04/13 11:50:19 Remove 'handleExtendsOrSuper' and 'handleNoExtends
eernst 2016/04/13 17:08:26 Done.
@@ -1845,15 +1853,37 @@ class Parser {
// We are looking at "type identifier '('".
BeginGroupToken beginParen = afterId;
Token endParen = beginParen.endGroup;
karlklose 2016/04/13 12:26:55 Consider creating an issue for this and change the
eernst 2016/04/13 17:08:26 Done.
+ // TODO(eernst): Check this, looks like an NPE with unbalanced parens.
Johnni Winther 2016/04/13 11:50:19 Do you have examples that trigger this (and others
eernst 2016/04/13 17:08:26 No, I hoped to get a quick confirmation like "That
Token afterParens = endParen.next;
if (optional('{', afterParens) ||
optional('=>', afterParens) ||
optional('async', afterParens) ||
optional('sync', afterParens)) {
// We are looking at "type identifier '(' ... ')'" followed
- // by '=>' or '{'.
+ // by '{', '=>', 'async', or 'sync'.
return parseFunctionDeclaration(token);
}
+ } else if (enableGenericMethodSyntax &&
+ identical(afterIdKind, LT_TOKEN)) {
+ // We are looking at "type identifier '<'".
+ BeginGroupToken beginAngle = afterId;
+ Token endAngle = beginAngle.endGroup;
+ if (endAngle != null &&
+ identical(endAngle.next.kind, OPEN_PAREN_TOKEN)) {
+ BeginGroupToken beginParen = endAngle.next;
+ Token endParen = beginParen.endGroup;
+ if (endParen != null) {
+ Token afterParens = endParen.next;
+ if (optional('{', afterParens) ||
+ optional('=>', afterParens) ||
+ optional('async', afterParens) ||
+ optional('sync', afterParens)) {
+ // We are looking at "type identifier '<' ... '>' '(' ... ')'"
+ // followed by '{', '=>', 'async', or 'sync'.
+ return parseFunctionDeclaration(token);
+ }
+ }
+ }
}
// Fall-through to expression statement.
} else {
@@ -1861,6 +1891,7 @@ class Parser {
return parseLabeledStatement(token);
} else if (optional('(', token.next)) {
BeginGroupToken begin = token.next;
+ // TODO(eernst): Check this, looks like an NPE with unbalanced parens.
String afterParens = begin.endGroup.next.stringValue;
if (identical(afterParens, '{') ||
identical(afterParens, '=>') ||
@@ -1868,6 +1899,24 @@ class Parser {
identical(afterParens, 'sync')) {
return parseFunctionDeclaration(token);
}
+ } else if (enableGenericMethodSyntax && optional('<', token.next)) {
+ BeginGroupToken beginAngle = token.next;
+ Token endAngle = beginAngle.endGroup;
+ if (endAngle != null &&
+ identical(endAngle.next.kind, OPEN_PAREN_TOKEN)) {
+ BeginGroupToken beginParen = endAngle.next;
+ Token endParen = beginParen.endGroup;
+ if (endParen != null) {
+ String afterParens = endParen.next.stringValue;
+ if (identical(afterParens, '{') ||
+ identical(afterParens, '=>') ||
+ identical(afterParens, 'async') ||
+ identical(afterParens, 'sync')) {
+ return parseFunctionDeclaration(token);
+ }
+ }
+ }
+ // Fall through to expression statement.
}
}
return parseExpressionStatement(token);
@@ -2139,7 +2188,7 @@ class Parser {
(kind == OPEN_SQUARE_BRACKET_TOKEN) ||
(kind == OPEN_CURLY_BRACKET_TOKEN) ||
token.stringValue == '[]') {
- return parseLiteralListOrMap(token);
+ return parseLiteralListOrMapOrFunction(token);
} else {
return listener.expectedExpression(token);
}
@@ -2147,6 +2196,7 @@ class Parser {
Token parseParenthesizedExpressionOrFunctionLiteral(Token token) {
BeginGroupToken beginGroup = token;
+ // TODO(eernst): Check this, looks like an NPE with unbalanced parens.
Token nextToken = beginGroup.endGroup.next;
int kind = nextToken.kind;
if (mayParseFunctionExpressions &&
@@ -2154,6 +2204,7 @@ class Parser {
identical(kind, OPEN_CURLY_BRACKET_TOKEN) ||
(identical(kind, KEYWORD_TOKEN) &&
(nextToken.value == 'async' || nextToken.value == 'sync')))) {
+ listener.handleNoTypeVariables(token);
return parseUnnamedFunction(token);
} else {
bool old = mayParseFunctionExpressions;
@@ -2203,13 +2254,27 @@ class Parser {
return token;
}
- Token parseLiteralListOrMap(Token token) {
+ Token parseLiteralListOrMapOrFunction(Token token) {
Token constKeyword = null;
if (optional('const', token)) {
constKeyword = token;
token = token.next;
}
- token = parseTypeArgumentsOpt(token);
+ if (enableGenericMethodSyntax &&
+ constKeyword == null &&
+ optional('<', token) &&
+ token is BeginGroupToken &&
+ token.endGroup != null &&
+ identical(token.endGroup.next.kind, OPEN_PAREN_TOKEN)) {
+ token = parseTypeVariablesOpt(token);
+ } else {
+ // [parseLiteralListOrMapOrFunction] is only called when [token] is one
+ // of `<`, '{', `[`, so we are not looking at a non-generic literal
+ // function, so we are looking at a map or list literal, and they may
+ // or may not have a `<..>` part, but if it is present it contains type
+ // arguments.
+ token = parseTypeArgumentsOpt(token);
+ }
Token beginToken = token;
int count = 0;
if (optional('{', token)) {
@@ -2243,10 +2308,22 @@ class Parser {
} else if (optional('[]', token)) {
listener.handleLiteralList(0, token, constKeyword, token);
return token.next;
- } else {
- listener.unexpected(token);
- return null;
+ } else if (optional('(',token)) {
+ BeginGroupToken beginGroup = token;
+ if (beginGroup.endGroup != null) {
+ Token nextToken = beginGroup.endGroup.next;
+ int kind = nextToken.kind;
+ if (identical(kind, FUNCTION_TOKEN) ||
+ identical(kind, OPEN_CURLY_BRACKET_TOKEN) ||
+ (identical(kind, KEYWORD_TOKEN) &&
+ (nextToken.value == 'async' || nextToken.value == 'sync'))) {
+ return parseUnnamedFunction(token);
+ }
+ // Fall through.
+ }
}
+ listener.unexpected(token);
+ return null;
}
Token parseMapLiteralEntry(Token token) {
@@ -2275,8 +2352,14 @@ class Parser {
}
bool isFunctionDeclaration(Token token) {
+ if (enableGenericMethodSyntax && optional('<', token)) {
+ BeginGroupToken begin = token;
+ if (begin.endGroup == null) return false;
+ token = begin.endGroup.next;
+ }
if (optional('(', token)) {
BeginGroupToken begin = token;
+ // TODO(eernst): Check this, looks like an NPE with unbalanced parens.
String afterParens = begin.endGroup.next.stringValue;
if (identical(afterParens, '{') ||
identical(afterParens, '=>') ||
@@ -2315,7 +2398,7 @@ class Parser {
(identical(value, '[')) ||
(identical(value, '[]')) ||
(identical(value, '{'))) {
- return parseLiteralListOrMap(constKeyword);
+ return parseLiteralListOrMapOrFunction(constKeyword);
}
token = parseConstructorReference(token);
token = parseRequiredArguments(token);
« no previous file with comments | « pkg/compiler/lib/src/parser/node_listener.dart ('k') | pkg/compiler/lib/src/scanner/array_based_scanner.dart » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698