[cfe] Handle assigned variables in for and for-in
Change-Id: I06deda7f017dcd40e5c6987c61261cf3be2be0ff Reviewed-on: https://dart-review.googlesource.com/c/sdk/+/123410 Reviewed-by: Dmitry Stefantsov <dmitryas@google.com> Commit-Queue: Johnni Winther <johnniwinther@google.com>
This commit is contained in:
committed by
commit-bot@chromium.org
parent
bb71c3eecc
commit
d76ffbc149
@@ -2524,12 +2524,12 @@ class AstBuilder extends StackListener {
|
||||
}
|
||||
|
||||
@override
|
||||
void handleForInitializerExpressionStatement(Token token) {
|
||||
void handleForInitializerExpressionStatement(Token token, bool forIn) {
|
||||
debugEvent("ForInitializerExpressionStatement");
|
||||
}
|
||||
|
||||
@override
|
||||
void handleForInitializerLocalVariableDeclaration(Token token) {
|
||||
void handleForInitializerLocalVariableDeclaration(Token token, bool forIn) {
|
||||
debugEvent("ForInitializerLocalVariableDeclaration");
|
||||
}
|
||||
|
||||
|
||||
@@ -42,6 +42,8 @@ import '../fasta_codes.dart' as fasta;
|
||||
|
||||
import '../fasta_codes.dart' show LocatedMessage, Message, noLength, Template;
|
||||
|
||||
import '../flow_analysis/flow_analysis.dart';
|
||||
|
||||
import '../identifiers.dart'
|
||||
show
|
||||
Identifier,
|
||||
@@ -2465,16 +2467,29 @@ class BodyBuilder extends ScopeListener<JumpTarget>
|
||||
void handleForInitializerEmptyStatement(Token token) {
|
||||
debugEvent("ForInitializerEmptyStatement");
|
||||
push(NullValue.Expression);
|
||||
// This is matched by the call to [deferNode] in [endForStatement] or
|
||||
// [endForControlFlow].
|
||||
typeInferrer?.assignedVariables?.beginNode();
|
||||
}
|
||||
|
||||
@override
|
||||
void handleForInitializerExpressionStatement(Token token) {
|
||||
void handleForInitializerExpressionStatement(Token token, bool forIn) {
|
||||
debugEvent("ForInitializerExpressionStatement");
|
||||
if (!forIn) {
|
||||
// This is matched by the call to [deferNode] in [endForStatement] or
|
||||
// [endForControlFlow].
|
||||
typeInferrer?.assignedVariables?.beginNode();
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
void handleForInitializerLocalVariableDeclaration(Token token) {
|
||||
void handleForInitializerLocalVariableDeclaration(Token token, bool forIn) {
|
||||
debugEvent("ForInitializerLocalVariableDeclaration");
|
||||
if (!forIn) {
|
||||
// This is matched by the call to [deferNode] in [endForStatement] or
|
||||
// [endForControlFlow].
|
||||
typeInferrer?.assignedVariables?.beginNode();
|
||||
}
|
||||
}
|
||||
|
||||
@override
|
||||
@@ -2496,10 +2511,12 @@ class BodyBuilder extends ScopeListener<JumpTarget>
|
||||
Token forToken = pop();
|
||||
List<Expression> updates = popListForEffect(updateExpressionCount);
|
||||
Statement conditionStatement = popStatement(); // condition
|
||||
Object variableOrExpression = pop();
|
||||
exitLocalScope();
|
||||
|
||||
if (constantContext != ConstantContext.none) {
|
||||
pop(); // Pop variable or expression.
|
||||
exitLocalScope();
|
||||
typeInferrer?.assignedVariables?.discardNode();
|
||||
|
||||
handleRecoverableError(
|
||||
fasta.templateCantUseControlFlowOrSpreadAsConstant
|
||||
.withArguments(forToken),
|
||||
@@ -2509,6 +2526,16 @@ class BodyBuilder extends ScopeListener<JumpTarget>
|
||||
return;
|
||||
}
|
||||
|
||||
// This is matched by the call to [beginNode] in
|
||||
// [handleForInitializerEmptyStatement],
|
||||
// [handleForInitializerExpressionStatement], and
|
||||
// [handleForInitializerLocalVariableDeclaration].
|
||||
AssignedVariablesNodeInfo<VariableDeclaration> assignedVariablesNodeInfo =
|
||||
typeInferrer?.assignedVariables?.deferNode();
|
||||
|
||||
Object variableOrExpression = pop();
|
||||
exitLocalScope();
|
||||
|
||||
transformCollections = true;
|
||||
List<VariableDeclaration> variables =
|
||||
buildVariableDeclarations(variableOrExpression);
|
||||
@@ -2519,11 +2546,17 @@ class BodyBuilder extends ScopeListener<JumpTarget>
|
||||
assert(conditionStatement is EmptyStatement);
|
||||
}
|
||||
if (entry is MapEntry) {
|
||||
push(forest.createForMapEntry(
|
||||
offsetForToken(forToken), variables, condition, updates, entry));
|
||||
ForMapEntry result = forest.createForMapEntry(
|
||||
offsetForToken(forToken), variables, condition, updates, entry);
|
||||
typeInferrer?.assignedVariables
|
||||
?.storeInfo(result, assignedVariablesNodeInfo);
|
||||
push(result);
|
||||
} else {
|
||||
push(forest.createForElement(offsetForToken(forToken), variables,
|
||||
condition, updates, toValue(entry)));
|
||||
ForElement result = forest.createForElement(offsetForToken(forToken),
|
||||
variables, condition, updates, toValue(entry));
|
||||
typeInferrer?.assignedVariables
|
||||
?.storeInfo(result, assignedVariablesNodeInfo);
|
||||
push(result);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -2560,6 +2593,13 @@ class BodyBuilder extends ScopeListener<JumpTarget>
|
||||
|
||||
List<Expression> updates = popListForEffect(updateExpressionCount);
|
||||
Statement conditionStatement = popStatement();
|
||||
// This is matched by the call to [beginNode] in
|
||||
// [handleForInitializerEmptyStatement],
|
||||
// [handleForInitializerExpressionStatement], and
|
||||
// [handleForInitializerLocalVariableDeclaration].
|
||||
AssignedVariablesNodeInfo<VariableDeclaration> assignedVariablesNodeInfo =
|
||||
typeInferrer?.assignedVariables?.deferNode();
|
||||
|
||||
Object variableOrExpression = pop();
|
||||
List<VariableDeclaration> variables =
|
||||
buildVariableDeclarations(variableOrExpression);
|
||||
@@ -2576,8 +2616,10 @@ class BodyBuilder extends ScopeListener<JumpTarget>
|
||||
} else {
|
||||
assert(conditionStatement is EmptyStatement);
|
||||
}
|
||||
Statement result = forest.createForStatement(offsetForToken(forKeyword),
|
||||
variables, condition, conditionStatement, updates, body);
|
||||
Statement result = forest.createForStatement(
|
||||
offsetForToken(forKeyword), variables, condition, updates, body);
|
||||
typeInferrer?.assignedVariables
|
||||
?.storeInfo(result, assignedVariablesNodeInfo);
|
||||
if (breakTarget.hasUsers) {
|
||||
result = forest.createLabeledStatement(result);
|
||||
breakTarget.resolveBreaks(forest, result);
|
||||
@@ -4359,6 +4401,9 @@ class BodyBuilder extends ScopeListener<JumpTarget>
|
||||
push(awaitToken ?? NullValue.AwaitToken);
|
||||
push(forToken);
|
||||
push(inKeyword);
|
||||
// This is matched by the call to [deferNode] in [endForIn] or
|
||||
// [endForInControlFlow].
|
||||
typeInferrer?.assignedVariables?.beginNode();
|
||||
}
|
||||
|
||||
@override
|
||||
@@ -4368,11 +4413,13 @@ class BodyBuilder extends ScopeListener<JumpTarget>
|
||||
Token inToken = pop();
|
||||
Token forToken = pop();
|
||||
Token awaitToken = pop(NullValue.AwaitToken);
|
||||
Expression iterable = popForValue();
|
||||
Object lvalue = pop(); // lvalue
|
||||
exitLocalScope();
|
||||
|
||||
if (constantContext != ConstantContext.none) {
|
||||
popForValue(); // Pop iterable
|
||||
pop(); // Pop lvalue
|
||||
exitLocalScope();
|
||||
typeInferrer?.assignedVariables?.discardNode();
|
||||
|
||||
handleRecoverableError(
|
||||
fasta.templateCantUseControlFlowOrSpreadAsConstant
|
||||
.withArguments(forToken),
|
||||
@@ -4382,23 +4429,45 @@ class BodyBuilder extends ScopeListener<JumpTarget>
|
||||
return;
|
||||
}
|
||||
|
||||
// This is matched by the call to [beginNode] in [handleForInLoopParts].
|
||||
AssignedVariablesNodeInfo<VariableDeclaration> assignedVariablesNodeInfo =
|
||||
typeInferrer?.assignedVariables?.deferNode();
|
||||
|
||||
Expression iterable = popForValue();
|
||||
Object lvalue = pop(); // lvalue
|
||||
exitLocalScope();
|
||||
|
||||
transformCollections = true;
|
||||
VariableDeclaration variable = buildForInVariable(forToken, lvalue);
|
||||
Expression problem = checkForInVariable(lvalue, variable, forToken);
|
||||
Statement prologue = buildForInBody(lvalue, variable, forToken, inToken);
|
||||
if (entry is MapEntry) {
|
||||
push(forest.createForInMapEntry(offsetForToken(forToken), variable,
|
||||
iterable, prologue, entry, problem,
|
||||
isAsync: awaitToken != null));
|
||||
ForInMapEntry result = forest.createForInMapEntry(
|
||||
offsetForToken(forToken),
|
||||
variable,
|
||||
iterable,
|
||||
prologue,
|
||||
entry,
|
||||
problem,
|
||||
isAsync: awaitToken != null);
|
||||
typeInferrer?.assignedVariables
|
||||
?.storeInfo(result, assignedVariablesNodeInfo);
|
||||
push(result);
|
||||
} else {
|
||||
push(forest.createForInElement(offsetForToken(forToken), variable,
|
||||
iterable, prologue, toValue(entry), problem,
|
||||
isAsync: awaitToken != null));
|
||||
ForInElement result = forest.createForInElement(offsetForToken(forToken),
|
||||
variable, iterable, prologue, toValue(entry), problem,
|
||||
isAsync: awaitToken != null);
|
||||
typeInferrer?.assignedVariables
|
||||
?.storeInfo(result, assignedVariablesNodeInfo);
|
||||
push(result);
|
||||
}
|
||||
}
|
||||
|
||||
VariableDeclaration buildForInVariable(Token token, Object lvalue) {
|
||||
if (lvalue is VariableDeclaration) return lvalue;
|
||||
if (lvalue is VariableDeclaration) {
|
||||
typeInferrer?.assignedVariables?.write(lvalue);
|
||||
return lvalue;
|
||||
}
|
||||
return forest.createVariableDeclaration(
|
||||
offsetForToken(token), null, functionNestingLevel,
|
||||
isFinal: true);
|
||||
@@ -4476,6 +4545,10 @@ class BodyBuilder extends ScopeListener<JumpTarget>
|
||||
Token forToken = pop();
|
||||
Token awaitToken = pop(NullValue.AwaitToken);
|
||||
|
||||
// This is matched by the call to [beginNode] in [handleForInLoopParts].
|
||||
AssignedVariablesNodeInfo<VariableDeclaration> assignedVariablesNodeInfo =
|
||||
typeInferrer?.assignedVariables?.deferNode();
|
||||
|
||||
Expression expression = popForValue();
|
||||
Object lvalue = pop();
|
||||
exitLocalScope();
|
||||
@@ -4506,6 +4579,8 @@ class BodyBuilder extends ScopeListener<JumpTarget>
|
||||
isAsync: awaitToken != null)
|
||||
..fileOffset = awaitToken?.charOffset ?? forToken.charOffset
|
||||
..bodyOffset = body.fileOffset; // TODO(ahe): Isn't this redundant?
|
||||
typeInferrer?.assignedVariables
|
||||
?.storeInfo(result, assignedVariablesNodeInfo);
|
||||
if (breakTarget.hasUsers) {
|
||||
result = forest.createLabeledStatement(result);
|
||||
breakTarget.resolveBreaks(forest, result);
|
||||
|
||||
@@ -383,7 +383,6 @@ class Forest {
|
||||
int fileOffset,
|
||||
List<VariableDeclaration> variables,
|
||||
Expression condition,
|
||||
Statement conditionStatement,
|
||||
List<Expression> updaters,
|
||||
Statement body) {
|
||||
assert(fileOffset != null);
|
||||
|
||||
@@ -66,7 +66,7 @@ import 'collections.dart'
|
||||
|
||||
import '../problems.dart' show getFileUri, unhandled;
|
||||
|
||||
import '../source/source_loader.dart' show SourceLoader;
|
||||
import '../source/source_loader.dart';
|
||||
|
||||
import 'redirecting_factory_body.dart' show RedirectingFactoryBody;
|
||||
|
||||
@@ -82,6 +82,7 @@ class CollectionTransformer extends Transformer {
|
||||
final Class mapEntryClass;
|
||||
final Field mapEntryKey;
|
||||
final Field mapEntryValue;
|
||||
final SourceLoaderDataForTesting dataForTesting;
|
||||
|
||||
static Procedure _findSetFactory(CoreTypes coreTypes) {
|
||||
Procedure factory = coreTypes.index.getMember('dart:core', 'Set', '');
|
||||
@@ -105,7 +106,8 @@ class CollectionTransformer extends Transformer {
|
||||
mapEntryKey =
|
||||
loader.coreTypes.index.getMember('dart:core', 'MapEntry', 'key'),
|
||||
mapEntryValue =
|
||||
loader.coreTypes.index.getMember('dart:core', 'MapEntry', 'value');
|
||||
loader.coreTypes.index.getMember('dart:core', 'MapEntry', 'value'),
|
||||
dataForTesting = loader.dataForTesting;
|
||||
|
||||
TreeNode _translateListOrSet(
|
||||
Expression node, DartType elementType, List<Expression> elements,
|
||||
@@ -208,6 +210,7 @@ class CollectionTransformer extends Transformer {
|
||||
..fileOffset = element.fileOffset;
|
||||
transformList(loop.variables, this, loop);
|
||||
transformList(loop.updates, this, loop);
|
||||
dataForTesting?.registerAlias(element, loop);
|
||||
body.add(loop);
|
||||
}
|
||||
|
||||
@@ -228,10 +231,12 @@ class CollectionTransformer extends Transformer {
|
||||
if (element.problem != null) {
|
||||
body.add(new ExpressionStatement(element.problem.accept<TreeNode>(this)));
|
||||
}
|
||||
body.add(new ForInStatement(
|
||||
ForInStatement loop = new ForInStatement(
|
||||
element.variable, element.iterable.accept<TreeNode>(this), loopBody,
|
||||
isAsync: element.isAsync)
|
||||
..fileOffset = element.fileOffset);
|
||||
..fileOffset = element.fileOffset;
|
||||
dataForTesting?.registerAlias(element, loop);
|
||||
body.add(loop);
|
||||
}
|
||||
|
||||
void _translateSpreadElement(SpreadElement element, DartType elementType,
|
||||
@@ -396,6 +401,7 @@ class CollectionTransformer extends Transformer {
|
||||
ForStatement loop = new ForStatement(entry.variables,
|
||||
entry.condition?.accept<TreeNode>(this), entry.updates, loopBody)
|
||||
..fileOffset = entry.fileOffset;
|
||||
dataForTesting?.registerAlias(entry, loop);
|
||||
transformList(loop.variables, this, loop);
|
||||
transformList(loop.updates, this, loop);
|
||||
body.add(loop);
|
||||
@@ -418,10 +424,12 @@ class CollectionTransformer extends Transformer {
|
||||
if (entry.problem != null) {
|
||||
body.add(new ExpressionStatement(entry.problem.accept<TreeNode>(this)));
|
||||
}
|
||||
body.add(new ForInStatement(
|
||||
ForInStatement loop = new ForInStatement(
|
||||
entry.variable, entry.iterable.accept<TreeNode>(this), loopBody,
|
||||
isAsync: entry.isAsync)
|
||||
..fileOffset = entry.fileOffset);
|
||||
..fileOffset = entry.fileOffset;
|
||||
dataForTesting?.registerAlias(entry, loop);
|
||||
body.add(loop);
|
||||
}
|
||||
|
||||
void _translateSpreadEntry(SpreadMapEntry entry, DartType keyType,
|
||||
|
||||
@@ -1164,13 +1164,13 @@ class ForwardingListener implements Listener {
|
||||
}
|
||||
|
||||
@override
|
||||
void handleForInitializerExpressionStatement(Token token) {
|
||||
listener?.handleForInitializerExpressionStatement(token);
|
||||
void handleForInitializerExpressionStatement(Token token, bool forIn) {
|
||||
listener?.handleForInitializerExpressionStatement(token, forIn);
|
||||
}
|
||||
|
||||
@override
|
||||
void handleForInitializerLocalVariableDeclaration(Token token) {
|
||||
listener?.handleForInitializerLocalVariableDeclaration(token);
|
||||
void handleForInitializerLocalVariableDeclaration(Token token, bool forIn) {
|
||||
listener?.handleForInitializerLocalVariableDeclaration(token, forIn);
|
||||
}
|
||||
|
||||
@override
|
||||
|
||||
@@ -407,13 +407,13 @@ class Listener implements UnescapeErrorListener {
|
||||
|
||||
/// Marks that the grammar term `forInitializerStatement` has been parsed and
|
||||
/// it was an expression statement.
|
||||
void handleForInitializerExpressionStatement(Token token) {
|
||||
void handleForInitializerExpressionStatement(Token token, bool forIn) {
|
||||
logEvent("ForInitializerExpressionStatement");
|
||||
}
|
||||
|
||||
/// Marks that the grammar term `forInitializerStatement` has been parsed and
|
||||
/// it was a `localVariableDeclaration`.
|
||||
void handleForInitializerLocalVariableDeclaration(Token token) {
|
||||
void handleForInitializerLocalVariableDeclaration(Token token, bool forIn) {
|
||||
logEvent("ForInitializerLocalVariableDeclaration");
|
||||
}
|
||||
|
||||
|
||||
@@ -5736,12 +5736,19 @@ class Parser {
|
||||
Token parseForLoopPartsMid(Token token, Token awaitToken, Token forToken) {
|
||||
if (token != forToken.next) {
|
||||
token = parseVariablesDeclarationRest(token, false);
|
||||
listener.handleForInitializerLocalVariableDeclaration(token);
|
||||
listener.handleForInitializerLocalVariableDeclaration(
|
||||
token, optional('in', token.next));
|
||||
} else if (optional(';', token.next)) {
|
||||
listener.handleForInitializerEmptyStatement(token.next);
|
||||
} else {
|
||||
token = parseExpression(token);
|
||||
listener.handleForInitializerExpressionStatement(token);
|
||||
listener.handleForInitializerExpressionStatement(
|
||||
token,
|
||||
optional('in', token.next) ||
|
||||
optional(':', token.next) ||
|
||||
// If this is an empty `await for`, we rewrite it into an
|
||||
// `await for (_ in _)`.
|
||||
(awaitToken != null && optional(')', token.next)));
|
||||
}
|
||||
Token next = token.next;
|
||||
if (optional(';', next)) {
|
||||
|
||||
@@ -10,6 +10,7 @@ import 'dart:convert' show utf8;
|
||||
|
||||
import 'dart:typed_data' show Uint8List;
|
||||
|
||||
import 'package:front_end/src/base/common.dart';
|
||||
import 'package:kernel/ast.dart'
|
||||
show
|
||||
Arguments,
|
||||
@@ -151,8 +152,12 @@ class SourceLoader extends Loader {
|
||||
|
||||
SetLiteralTransformer setLiteralTransformer;
|
||||
|
||||
final SourceLoaderDataForTesting dataForTesting;
|
||||
|
||||
SourceLoader(this.fileSystem, this.includeComments, KernelTarget target)
|
||||
: super(target);
|
||||
: dataForTesting =
|
||||
retainDataForTesting ? new SourceLoaderDataForTesting() : null,
|
||||
super(target);
|
||||
|
||||
Template<SummaryTemplate> get outlineSummaryTemplate =>
|
||||
templateSourceOutlineSummary;
|
||||
@@ -1276,3 +1281,19 @@ class AmbiguousTypesRecord {
|
||||
|
||||
const AmbiguousTypesRecord(this.cls, this.a, this.b);
|
||||
}
|
||||
|
||||
class SourceLoaderDataForTesting {
|
||||
final Map<TreeNode, TreeNode> _aliasMap = {};
|
||||
|
||||
/// Registers that [original] has been replaced by [alias] in the generated
|
||||
/// AST.
|
||||
void registerAlias(TreeNode original, TreeNode alias) {
|
||||
_aliasMap[alias] = original;
|
||||
}
|
||||
|
||||
/// Returns the original node for [alias] or [alias] if it was not registered
|
||||
/// as an alias.
|
||||
TreeNode toOriginal(TreeNode alias) {
|
||||
return _aliasMap[alias] ?? alias;
|
||||
}
|
||||
}
|
||||
|
||||
@@ -600,13 +600,13 @@ class TypePromotionLookAheadListener extends Listener {
|
||||
}
|
||||
|
||||
@override
|
||||
void handleForInitializerExpressionStatement(Token token) {
|
||||
void handleForInitializerExpressionStatement(Token token, bool forIn) {
|
||||
debugEvent("ForInitializerExpressionStatement", token);
|
||||
state.pop(); // Expression.
|
||||
}
|
||||
|
||||
@override
|
||||
void handleForInitializerLocalVariableDeclaration(Token token) {
|
||||
void handleForInitializerLocalVariableDeclaration(Token token, bool forIn) {
|
||||
debugEvent("ForInitializerLocalVariableDeclaration", token);
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,3 @@
|
||||
main() async {
|
||||
await for () {}
|
||||
}
|
||||
@@ -0,0 +1,56 @@
|
||||
Problems reported:
|
||||
|
||||
parser_test/error_recovery/empty_await_for:2:14: Expected an identifier, but got ')'.
|
||||
await for () {}
|
||||
^
|
||||
|
||||
parser_test/error_recovery/empty_await_for:2:14: Expected 'in' before this.
|
||||
await for () {}
|
||||
^
|
||||
|
||||
parser_test/error_recovery/empty_await_for:2:14: Expected an identifier, but got ')'.
|
||||
await for () {}
|
||||
^
|
||||
|
||||
parser_test/error_recovery/empty_await_for:2:14: Expected an identifier, but got ')'.
|
||||
await for () {}
|
||||
^
|
||||
|
||||
beginCompilationUnit(main)
|
||||
beginMetadataStar(main)
|
||||
endMetadataStar(0)
|
||||
beginTopLevelMember(main)
|
||||
beginTopLevelMethod(, null)
|
||||
handleNoType()
|
||||
handleIdentifier(main, topLevelFunctionDeclaration)
|
||||
handleNoTypeVariables(()
|
||||
beginFormalParameters((, MemberKind.TopLevelMethod)
|
||||
endFormalParameters(0, (, ), MemberKind.TopLevelMethod)
|
||||
handleAsyncModifier(async, null)
|
||||
beginBlockFunctionBody({)
|
||||
beginForStatement(for)
|
||||
handleRecoverableError(Message[ExpectedIdentifier, Expected an identifier, but got ')'., null, {token: )}], ), ))
|
||||
handleIdentifier(, expression)
|
||||
handleNoTypeArguments())
|
||||
handleNoArguments())
|
||||
handleSend(, ))
|
||||
handleForInitializerExpressionStatement(, true)
|
||||
handleRecoverableError(Message[ExpectedButGot, Expected 'in' before this., null, {string: in}], ), ))
|
||||
handleRecoverableError(Message[ExpectedIdentifier, Expected an identifier, but got ')'., null, {token: )}], ), ))
|
||||
beginForInExpression())
|
||||
handleRecoverableError(Message[ExpectedIdentifier, Expected an identifier, but got ')'., null, {token: )}], ), ))
|
||||
handleIdentifier(, expression)
|
||||
handleNoTypeArguments())
|
||||
handleNoArguments())
|
||||
handleSend(, ))
|
||||
endForInExpression())
|
||||
handleForInLoopParts(await, for, (, in)
|
||||
beginForInBody({)
|
||||
beginBlock({, BlockKind(statement))
|
||||
endBlock(0, {, }, BlockKind(statement))
|
||||
endForInBody(})
|
||||
endForIn(})
|
||||
endBlockFunctionBody(1, {, })
|
||||
endTopLevelMethod(main, null, })
|
||||
endTopLevelDeclaration()
|
||||
endCompilationUnit(1, )
|
||||
@@ -0,0 +1,91 @@
|
||||
parseUnit(main)
|
||||
skipErrorTokens(main)
|
||||
listener: beginCompilationUnit(main)
|
||||
syntheticPreviousToken(main)
|
||||
parseTopLevelDeclarationImpl(, Instance of 'DirectiveContext')
|
||||
parseMetadataStar()
|
||||
listener: beginMetadataStar(main)
|
||||
listener: endMetadataStar(0)
|
||||
parseTopLevelMemberImpl()
|
||||
listener: beginTopLevelMember(main)
|
||||
parseTopLevelMethod(, null, , Instance of 'NoType', null, main)
|
||||
listener: beginTopLevelMethod(, null)
|
||||
listener: handleNoType()
|
||||
ensureIdentifier(, topLevelFunctionDeclaration)
|
||||
listener: handleIdentifier(main, topLevelFunctionDeclaration)
|
||||
parseMethodTypeVar(main)
|
||||
listener: handleNoTypeVariables(()
|
||||
parseGetterOrFormalParameters(main, main, false, MemberKind.TopLevelMethod)
|
||||
parseFormalParameters(main, MemberKind.TopLevelMethod)
|
||||
parseFormalParametersRest((, MemberKind.TopLevelMethod)
|
||||
listener: beginFormalParameters((, MemberKind.TopLevelMethod)
|
||||
listener: endFormalParameters(0, (, ), MemberKind.TopLevelMethod)
|
||||
parseAsyncModifierOpt())
|
||||
listener: handleAsyncModifier(async, null)
|
||||
inPlainSync()
|
||||
parseFunctionBody(async, false, false)
|
||||
listener: beginBlockFunctionBody({)
|
||||
notEofOrValue(}, await)
|
||||
parseStatement({)
|
||||
parseStatementX({)
|
||||
parseForStatement(await, await)
|
||||
listener: beginForStatement(for)
|
||||
parseForLoopPartsStart(await, for)
|
||||
parseExpressionStatementOrDeclaration((, true)
|
||||
parseExpressionStatementOrDeclarationAfterModifiers((, (, null, null, null, true)
|
||||
parseForLoopPartsMid((, await, for)
|
||||
parseExpression(()
|
||||
parsePrecedenceExpression((, 1, true)
|
||||
parseUnaryExpression((, true)
|
||||
parsePrimary((, expression)
|
||||
parseSend((, expression)
|
||||
ensureIdentifier((, expression)
|
||||
reportRecoverableErrorWithToken(), Instance of 'Template<(Token) => Message>')
|
||||
listener: handleRecoverableError(Message[ExpectedIdentifier, Expected an identifier, but got ')'., null, {token: )}], ), ))
|
||||
rewriter()
|
||||
listener: handleIdentifier(, expression)
|
||||
listener: handleNoTypeArguments())
|
||||
parseArgumentsOpt()
|
||||
listener: handleNoArguments())
|
||||
listener: handleSend(, ))
|
||||
listener: handleForInitializerExpressionStatement(, true)
|
||||
reportRecoverableError(), Message[ExpectedButGot, Expected 'in' before this., null, {string: in}])
|
||||
listener: handleRecoverableError(Message[ExpectedButGot, Expected 'in' before this., null, {string: in}], ), ))
|
||||
parseForInRest(, await, for, ))
|
||||
parseForInLoopPartsRest(, await, for, ))
|
||||
reportRecoverableErrorWithToken(), Instance of 'Template<(Token) => Message>')
|
||||
listener: handleRecoverableError(Message[ExpectedIdentifier, Expected an identifier, but got ')'., null, {token: )}], ), ))
|
||||
listener: beginForInExpression())
|
||||
parseExpression(in)
|
||||
parsePrecedenceExpression(in, 1, true)
|
||||
parseUnaryExpression(in, true)
|
||||
parsePrimary(in, expression)
|
||||
parseSend(in, expression)
|
||||
ensureIdentifier(in, expression)
|
||||
reportRecoverableErrorWithToken(), Instance of 'Template<(Token) => Message>')
|
||||
listener: handleRecoverableError(Message[ExpectedIdentifier, Expected an identifier, but got ')'., null, {token: )}], ), ))
|
||||
rewriter()
|
||||
listener: handleIdentifier(, expression)
|
||||
listener: handleNoTypeArguments())
|
||||
parseArgumentsOpt()
|
||||
listener: handleNoArguments())
|
||||
listener: handleSend(, ))
|
||||
ensureCloseParen(, ()
|
||||
listener: endForInExpression())
|
||||
listener: handleForInLoopParts(await, for, (, in)
|
||||
listener: beginForInBody({)
|
||||
parseStatement())
|
||||
parseStatementX())
|
||||
parseBlock(), BlockKind(statement))
|
||||
ensureBlock(), null, null)
|
||||
listener: beginBlock({, BlockKind(statement))
|
||||
notEofOrValue(}, })
|
||||
listener: endBlock(0, {, }, BlockKind(statement))
|
||||
listener: endForInBody(})
|
||||
listener: endForIn(})
|
||||
notEofOrValue(}, })
|
||||
listener: endBlockFunctionBody(1, {, })
|
||||
listener: endTopLevelMethod(main, null, })
|
||||
listener: endTopLevelDeclaration()
|
||||
reportAllErrorTokens(main)
|
||||
listener: endCompilationUnit(1, )
|
||||
@@ -0,0 +1,11 @@
|
||||
NOTICE: Stream was rewritten by parser!
|
||||
|
||||
main() async {
|
||||
await for (in) {}
|
||||
}
|
||||
|
||||
|
||||
main[StringToken]([BeginToken])[SimpleToken] async[KeywordToken] {[BeginToken]
|
||||
await[KeywordToken] for[KeywordToken] ([BeginToken][SyntheticStringToken]in[SyntheticKeywordToken][SyntheticStringToken])[SimpleToken] {[BeginToken]}[SimpleToken]
|
||||
}[SimpleToken]
|
||||
[SimpleToken]
|
||||
@@ -0,0 +1,9 @@
|
||||
main() async {
|
||||
await for () {}
|
||||
}
|
||||
|
||||
|
||||
main[StringToken]([BeginToken])[SimpleToken] async[KeywordToken] {[BeginToken]
|
||||
await[KeywordToken] for[KeywordToken] ([BeginToken])[SimpleToken] {[BeginToken]}[SimpleToken]
|
||||
}[SimpleToken]
|
||||
[SimpleToken]
|
||||
@@ -0,0 +1,3 @@
|
||||
main() {
|
||||
for () {}
|
||||
}
|
||||
@@ -0,0 +1,55 @@
|
||||
Problems reported:
|
||||
|
||||
parser_test/error_recovery/empty_for:2:8: Expected an identifier, but got ')'.
|
||||
for () {}
|
||||
^
|
||||
|
||||
parser_test/error_recovery/empty_for:2:8: Expected ';' after this.
|
||||
for () {}
|
||||
^
|
||||
|
||||
parser_test/error_recovery/empty_for:2:8: Expected an identifier, but got ')'.
|
||||
for () {}
|
||||
^
|
||||
|
||||
parser_test/error_recovery/empty_for:2:8: Expected ';' after this.
|
||||
for () {}
|
||||
^
|
||||
|
||||
beginCompilationUnit(main)
|
||||
beginMetadataStar(main)
|
||||
endMetadataStar(0)
|
||||
beginTopLevelMember(main)
|
||||
beginTopLevelMethod(, null)
|
||||
handleNoType()
|
||||
handleIdentifier(main, topLevelFunctionDeclaration)
|
||||
handleNoTypeVariables(()
|
||||
beginFormalParameters((, MemberKind.TopLevelMethod)
|
||||
endFormalParameters(0, (, ), MemberKind.TopLevelMethod)
|
||||
handleAsyncModifier(null, null)
|
||||
beginBlockFunctionBody({)
|
||||
beginForStatement(for)
|
||||
handleRecoverableError(Message[ExpectedIdentifier, Expected an identifier, but got ')'., null, {token: )}], ), ))
|
||||
handleIdentifier(, expression)
|
||||
handleNoTypeArguments())
|
||||
handleNoArguments())
|
||||
handleSend(, ))
|
||||
handleForInitializerExpressionStatement(, false)
|
||||
handleRecoverableError(Message[ExpectedAfterButGot, Expected ';' after this., null, {string: ;}], ), ))
|
||||
handleRecoverableError(Message[ExpectedIdentifier, Expected an identifier, but got ')'., null, {token: )}], ), ))
|
||||
handleIdentifier(, expression)
|
||||
handleNoTypeArguments())
|
||||
handleNoArguments())
|
||||
handleSend(, ))
|
||||
handleRecoverableError(Message[ExpectedAfterButGot, Expected ';' after this., null, {string: ;}], ), ))
|
||||
handleExpressionStatement(;)
|
||||
handleForLoopParts(for, (, ;, 0)
|
||||
beginForStatementBody({)
|
||||
beginBlock({, BlockKind(statement))
|
||||
endBlock(0, {, }, BlockKind(statement))
|
||||
endForStatementBody(})
|
||||
endForStatement(})
|
||||
endBlockFunctionBody(1, {, })
|
||||
endTopLevelMethod(main, null, })
|
||||
endTopLevelDeclaration()
|
||||
endCompilationUnit(1, )
|
||||
@@ -0,0 +1,94 @@
|
||||
parseUnit(main)
|
||||
skipErrorTokens(main)
|
||||
listener: beginCompilationUnit(main)
|
||||
syntheticPreviousToken(main)
|
||||
parseTopLevelDeclarationImpl(, Instance of 'DirectiveContext')
|
||||
parseMetadataStar()
|
||||
listener: beginMetadataStar(main)
|
||||
listener: endMetadataStar(0)
|
||||
parseTopLevelMemberImpl()
|
||||
listener: beginTopLevelMember(main)
|
||||
parseTopLevelMethod(, null, , Instance of 'NoType', null, main)
|
||||
listener: beginTopLevelMethod(, null)
|
||||
listener: handleNoType()
|
||||
ensureIdentifier(, topLevelFunctionDeclaration)
|
||||
listener: handleIdentifier(main, topLevelFunctionDeclaration)
|
||||
parseMethodTypeVar(main)
|
||||
listener: handleNoTypeVariables(()
|
||||
parseGetterOrFormalParameters(main, main, false, MemberKind.TopLevelMethod)
|
||||
parseFormalParameters(main, MemberKind.TopLevelMethod)
|
||||
parseFormalParametersRest((, MemberKind.TopLevelMethod)
|
||||
listener: beginFormalParameters((, MemberKind.TopLevelMethod)
|
||||
listener: endFormalParameters(0, (, ), MemberKind.TopLevelMethod)
|
||||
parseAsyncModifierOpt())
|
||||
listener: handleAsyncModifier(null, null)
|
||||
inPlainSync()
|
||||
parseFunctionBody(), false, false)
|
||||
listener: beginBlockFunctionBody({)
|
||||
notEofOrValue(}, for)
|
||||
parseStatement({)
|
||||
parseStatementX({)
|
||||
parseForStatement({, null)
|
||||
listener: beginForStatement(for)
|
||||
parseForLoopPartsStart(null, for)
|
||||
parseExpressionStatementOrDeclaration((, true)
|
||||
parseExpressionStatementOrDeclarationAfterModifiers((, (, null, null, null, true)
|
||||
parseForLoopPartsMid((, null, for)
|
||||
parseExpression(()
|
||||
parsePrecedenceExpression((, 1, true)
|
||||
parseUnaryExpression((, true)
|
||||
parsePrimary((, expression)
|
||||
parseSend((, expression)
|
||||
ensureIdentifier((, expression)
|
||||
reportRecoverableErrorWithToken(), Instance of 'Template<(Token) => Message>')
|
||||
listener: handleRecoverableError(Message[ExpectedIdentifier, Expected an identifier, but got ')'., null, {token: )}], ), ))
|
||||
rewriter()
|
||||
listener: handleIdentifier(, expression)
|
||||
listener: handleNoTypeArguments())
|
||||
parseArgumentsOpt()
|
||||
listener: handleNoArguments())
|
||||
listener: handleSend(, ))
|
||||
listener: handleForInitializerExpressionStatement(, false)
|
||||
parseForRest(null, , for)
|
||||
parseForLoopPartsRest(, for, null)
|
||||
ensureSemicolon()
|
||||
reportRecoverableError(, Message[ExpectedAfterButGot, Expected ';' after this., null, {string: ;}])
|
||||
listener: handleRecoverableError(Message[ExpectedAfterButGot, Expected ';' after this., null, {string: ;}], ), ))
|
||||
rewriter()
|
||||
parseExpressionStatement(;)
|
||||
parseExpression(;)
|
||||
parsePrecedenceExpression(;, 1, true)
|
||||
parseUnaryExpression(;, true)
|
||||
parsePrimary(;, expression)
|
||||
parseSend(;, expression)
|
||||
ensureIdentifier(;, expression)
|
||||
reportRecoverableErrorWithToken(), Instance of 'Template<(Token) => Message>')
|
||||
listener: handleRecoverableError(Message[ExpectedIdentifier, Expected an identifier, but got ')'., null, {token: )}], ), ))
|
||||
rewriter()
|
||||
listener: handleIdentifier(, expression)
|
||||
listener: handleNoTypeArguments())
|
||||
parseArgumentsOpt()
|
||||
listener: handleNoArguments())
|
||||
listener: handleSend(, ))
|
||||
ensureSemicolon()
|
||||
reportRecoverableError(, Message[ExpectedAfterButGot, Expected ';' after this., null, {string: ;}])
|
||||
listener: handleRecoverableError(Message[ExpectedAfterButGot, Expected ';' after this., null, {string: ;}], ), ))
|
||||
rewriter()
|
||||
listener: handleExpressionStatement(;)
|
||||
listener: handleForLoopParts(for, (, ;, 0)
|
||||
listener: beginForStatementBody({)
|
||||
parseStatement())
|
||||
parseStatementX())
|
||||
parseBlock(), BlockKind(statement))
|
||||
ensureBlock(), null, null)
|
||||
listener: beginBlock({, BlockKind(statement))
|
||||
notEofOrValue(}, })
|
||||
listener: endBlock(0, {, }, BlockKind(statement))
|
||||
listener: endForStatementBody(})
|
||||
listener: endForStatement(})
|
||||
notEofOrValue(}, })
|
||||
listener: endBlockFunctionBody(1, {, })
|
||||
listener: endTopLevelMethod(main, null, })
|
||||
listener: endTopLevelDeclaration()
|
||||
reportAllErrorTokens(main)
|
||||
listener: endCompilationUnit(1, )
|
||||
@@ -0,0 +1,11 @@
|
||||
NOTICE: Stream was rewritten by parser!
|
||||
|
||||
main() {
|
||||
for (;;) {}
|
||||
}
|
||||
|
||||
|
||||
main[StringToken]([BeginToken])[SimpleToken] {[BeginToken]
|
||||
for[KeywordToken] ([BeginToken][SyntheticStringToken];[SyntheticToken][SyntheticStringToken];[SyntheticToken])[SimpleToken] {[BeginToken]}[SimpleToken]
|
||||
}[SimpleToken]
|
||||
[SimpleToken]
|
||||
@@ -0,0 +1,9 @@
|
||||
main() {
|
||||
for () {}
|
||||
}
|
||||
|
||||
|
||||
main[StringToken]([BeginToken])[SimpleToken] {[BeginToken]
|
||||
for[KeywordToken] ([BeginToken])[SimpleToken] {[BeginToken]}[SimpleToken]
|
||||
}[SimpleToken]
|
||||
[SimpleToken]
|
||||
@@ -24,7 +24,7 @@ beginCompilationUnit(main)
|
||||
endVariableInitializer(=)
|
||||
endInitializedIdentifier(i)
|
||||
endVariablesDeclaration(1, null)
|
||||
handleForInitializerLocalVariableDeclaration(0)
|
||||
handleForInitializerLocalVariableDeclaration(0, false)
|
||||
handleIdentifier(i, expression)
|
||||
handleNoTypeArguments(<)
|
||||
handleNoArguments(<)
|
||||
|
||||
@@ -56,7 +56,7 @@ parseUnit(main)
|
||||
listener: endVariableInitializer(=)
|
||||
listener: endInitializedIdentifier(i)
|
||||
listener: endVariablesDeclaration(1, null)
|
||||
listener: handleForInitializerLocalVariableDeclaration(0)
|
||||
listener: handleForInitializerLocalVariableDeclaration(0, false)
|
||||
parseForRest(null, 0, for)
|
||||
parseForLoopPartsRest(0, for, null)
|
||||
ensureSemicolon(0)
|
||||
|
||||
@@ -20,7 +20,7 @@ beginCompilationUnit(main)
|
||||
handleNoVariableInitializer(in)
|
||||
endInitializedIdentifier(i)
|
||||
endVariablesDeclaration(1, null)
|
||||
handleForInitializerLocalVariableDeclaration(i)
|
||||
handleForInitializerLocalVariableDeclaration(i, true)
|
||||
beginForInExpression([])
|
||||
handleNoTypeArguments([])
|
||||
handleLiteralList(0, [, null, ])
|
||||
|
||||
@@ -47,7 +47,7 @@ parseUnit(main)
|
||||
listener: handleNoVariableInitializer(in)
|
||||
listener: endInitializedIdentifier(i)
|
||||
listener: endVariablesDeclaration(1, null)
|
||||
listener: handleForInitializerLocalVariableDeclaration(i)
|
||||
listener: handleForInitializerLocalVariableDeclaration(i, true)
|
||||
parseForInRest(i, null, for, i)
|
||||
parseForInLoopPartsRest(i, null, for, i)
|
||||
listener: beginForInExpression([])
|
||||
|
||||
@@ -0,0 +1,4 @@
|
||||
main() {
|
||||
var i;
|
||||
for (i in []) {}
|
||||
}
|
||||
@@ -0,0 +1,41 @@
|
||||
beginCompilationUnit(main)
|
||||
beginMetadataStar(main)
|
||||
endMetadataStar(0)
|
||||
beginTopLevelMember(main)
|
||||
beginTopLevelMethod(, null)
|
||||
handleNoType()
|
||||
handleIdentifier(main, topLevelFunctionDeclaration)
|
||||
handleNoTypeVariables(()
|
||||
beginFormalParameters((, MemberKind.TopLevelMethod)
|
||||
endFormalParameters(0, (, ), MemberKind.TopLevelMethod)
|
||||
handleAsyncModifier(null, null)
|
||||
beginBlockFunctionBody({)
|
||||
beginMetadataStar(var)
|
||||
endMetadataStar(0)
|
||||
handleNoType(var)
|
||||
beginVariablesDeclaration(i, null, var)
|
||||
handleIdentifier(i, localVariableDeclaration)
|
||||
beginInitializedIdentifier(i)
|
||||
handleNoVariableInitializer(;)
|
||||
endInitializedIdentifier(i)
|
||||
endVariablesDeclaration(1, ;)
|
||||
beginForStatement(for)
|
||||
handleIdentifier(i, expression)
|
||||
handleNoTypeArguments(in)
|
||||
handleNoArguments(in)
|
||||
handleSend(i, in)
|
||||
handleForInitializerExpressionStatement(i, true)
|
||||
beginForInExpression([])
|
||||
handleNoTypeArguments([])
|
||||
handleLiteralList(0, [, null, ])
|
||||
endForInExpression())
|
||||
handleForInLoopParts(null, for, (, in)
|
||||
beginForInBody({)
|
||||
beginBlock({, BlockKind(statement))
|
||||
endBlock(0, {, }, BlockKind(statement))
|
||||
endForInBody(})
|
||||
endForIn(})
|
||||
endBlockFunctionBody(2, {, })
|
||||
endTopLevelMethod(main, null, })
|
||||
endTopLevelDeclaration()
|
||||
endCompilationUnit(1, )
|
||||
@@ -0,0 +1,100 @@
|
||||
parseUnit(main)
|
||||
skipErrorTokens(main)
|
||||
listener: beginCompilationUnit(main)
|
||||
syntheticPreviousToken(main)
|
||||
parseTopLevelDeclarationImpl(, Instance of 'DirectiveContext')
|
||||
parseMetadataStar()
|
||||
listener: beginMetadataStar(main)
|
||||
listener: endMetadataStar(0)
|
||||
parseTopLevelMemberImpl()
|
||||
listener: beginTopLevelMember(main)
|
||||
parseTopLevelMethod(, null, , Instance of 'NoType', null, main)
|
||||
listener: beginTopLevelMethod(, null)
|
||||
listener: handleNoType()
|
||||
ensureIdentifier(, topLevelFunctionDeclaration)
|
||||
listener: handleIdentifier(main, topLevelFunctionDeclaration)
|
||||
parseMethodTypeVar(main)
|
||||
listener: handleNoTypeVariables(()
|
||||
parseGetterOrFormalParameters(main, main, false, MemberKind.TopLevelMethod)
|
||||
parseFormalParameters(main, MemberKind.TopLevelMethod)
|
||||
parseFormalParametersRest((, MemberKind.TopLevelMethod)
|
||||
listener: beginFormalParameters((, MemberKind.TopLevelMethod)
|
||||
listener: endFormalParameters(0, (, ), MemberKind.TopLevelMethod)
|
||||
parseAsyncModifierOpt())
|
||||
listener: handleAsyncModifier(null, null)
|
||||
inPlainSync()
|
||||
parseFunctionBody(), false, false)
|
||||
listener: beginBlockFunctionBody({)
|
||||
notEofOrValue(}, var)
|
||||
parseStatement({)
|
||||
parseStatementX({)
|
||||
parseExpressionStatementOrDeclarationAfterModifiers(var, {, null, var, null, false)
|
||||
looksLikeLocalFunction(i)
|
||||
listener: beginMetadataStar(var)
|
||||
listener: endMetadataStar(0)
|
||||
listener: handleNoType(var)
|
||||
listener: beginVariablesDeclaration(i, null, var)
|
||||
parseVariablesDeclarationRest(var, true)
|
||||
parseOptionallyInitializedIdentifier(var)
|
||||
ensureIdentifier(var, localVariableDeclaration)
|
||||
listener: handleIdentifier(i, localVariableDeclaration)
|
||||
listener: beginInitializedIdentifier(i)
|
||||
parseVariableInitializerOpt(i)
|
||||
listener: handleNoVariableInitializer(;)
|
||||
listener: endInitializedIdentifier(i)
|
||||
ensureSemicolon(i)
|
||||
listener: endVariablesDeclaration(1, ;)
|
||||
notEofOrValue(}, for)
|
||||
parseStatement(;)
|
||||
parseStatementX(;)
|
||||
parseForStatement(;, null)
|
||||
listener: beginForStatement(for)
|
||||
parseForLoopPartsStart(null, for)
|
||||
parseExpressionStatementOrDeclaration((, true)
|
||||
parseExpressionStatementOrDeclarationAfterModifiers((, (, null, null, null, true)
|
||||
parseForLoopPartsMid((, null, for)
|
||||
parseExpression(()
|
||||
parsePrecedenceExpression((, 1, true)
|
||||
parseUnaryExpression((, true)
|
||||
parsePrimary((, expression)
|
||||
parseSendOrFunctionLiteral((, expression)
|
||||
parseSend((, expression)
|
||||
ensureIdentifier((, expression)
|
||||
listener: handleIdentifier(i, expression)
|
||||
listener: handleNoTypeArguments(in)
|
||||
parseArgumentsOpt(i)
|
||||
listener: handleNoArguments(in)
|
||||
listener: handleSend(i, in)
|
||||
listener: handleForInitializerExpressionStatement(i, true)
|
||||
parseForInRest(i, null, for, i)
|
||||
parseForInLoopPartsRest(i, null, for, i)
|
||||
listener: beginForInExpression([])
|
||||
parseExpression(in)
|
||||
parsePrecedenceExpression(in, 1, true)
|
||||
parseUnaryExpression(in, true)
|
||||
parsePrimary(in, expression)
|
||||
listener: handleNoTypeArguments([])
|
||||
parseLiteralListSuffix(in, null)
|
||||
rewriteSquareBrackets(in)
|
||||
link([, ])
|
||||
rewriter()
|
||||
listener: handleLiteralList(0, [, null, ])
|
||||
ensureCloseParen(], ()
|
||||
listener: endForInExpression())
|
||||
listener: handleForInLoopParts(null, for, (, in)
|
||||
listener: beginForInBody({)
|
||||
parseStatement())
|
||||
parseStatementX())
|
||||
parseBlock(), BlockKind(statement))
|
||||
ensureBlock(), null, null)
|
||||
listener: beginBlock({, BlockKind(statement))
|
||||
notEofOrValue(}, })
|
||||
listener: endBlock(0, {, }, BlockKind(statement))
|
||||
listener: endForInBody(})
|
||||
listener: endForIn(})
|
||||
notEofOrValue(}, })
|
||||
listener: endBlockFunctionBody(2, {, })
|
||||
listener: endTopLevelMethod(main, null, })
|
||||
listener: endTopLevelDeclaration()
|
||||
reportAllErrorTokens(main)
|
||||
listener: endCompilationUnit(1, )
|
||||
@@ -0,0 +1,11 @@
|
||||
main() {
|
||||
var i;
|
||||
for (i in []) {}
|
||||
}
|
||||
|
||||
|
||||
main[StringToken]([BeginToken])[SimpleToken] {[BeginToken]
|
||||
var[KeywordToken] i[StringToken];[SimpleToken]
|
||||
for[KeywordToken] ([BeginToken]i[StringToken] in[KeywordToken] [[BeginToken]][SimpleToken])[SimpleToken] {[BeginToken]}[SimpleToken]
|
||||
}[SimpleToken]
|
||||
[SimpleToken]
|
||||
@@ -0,0 +1,11 @@
|
||||
main() {
|
||||
var i;
|
||||
for (i in []) {}
|
||||
}
|
||||
|
||||
|
||||
main[StringToken]([BeginToken])[SimpleToken] {[BeginToken]
|
||||
var[KeywordToken] i[StringToken];[SimpleToken]
|
||||
for[KeywordToken] ([BeginToken]i[StringToken] in[KeywordToken] [][SimpleToken])[SimpleToken] {[BeginToken]}[SimpleToken]
|
||||
}[SimpleToken]
|
||||
[SimpleToken]
|
||||
@@ -0,0 +1,4 @@
|
||||
main() {
|
||||
int i;
|
||||
for (i = 0; i < 10; i++) {}
|
||||
}
|
||||
@@ -0,0 +1,54 @@
|
||||
beginCompilationUnit(main)
|
||||
beginMetadataStar(main)
|
||||
endMetadataStar(0)
|
||||
beginTopLevelMember(main)
|
||||
beginTopLevelMethod(, null)
|
||||
handleNoType()
|
||||
handleIdentifier(main, topLevelFunctionDeclaration)
|
||||
handleNoTypeVariables(()
|
||||
beginFormalParameters((, MemberKind.TopLevelMethod)
|
||||
endFormalParameters(0, (, ), MemberKind.TopLevelMethod)
|
||||
handleAsyncModifier(null, null)
|
||||
beginBlockFunctionBody({)
|
||||
beginMetadataStar(int)
|
||||
endMetadataStar(0)
|
||||
handleIdentifier(int, typeReference)
|
||||
handleNoTypeArguments(i)
|
||||
handleType(int, null)
|
||||
beginVariablesDeclaration(i, null, null)
|
||||
handleIdentifier(i, localVariableDeclaration)
|
||||
beginInitializedIdentifier(i)
|
||||
handleNoVariableInitializer(;)
|
||||
endInitializedIdentifier(i)
|
||||
endVariablesDeclaration(1, ;)
|
||||
beginForStatement(for)
|
||||
handleIdentifier(i, expression)
|
||||
handleNoTypeArguments(=)
|
||||
handleNoArguments(=)
|
||||
handleSend(i, =)
|
||||
handleLiteralInt(0)
|
||||
handleAssignmentExpression(=)
|
||||
handleForInitializerExpressionStatement(0, false)
|
||||
handleIdentifier(i, expression)
|
||||
handleNoTypeArguments(<)
|
||||
handleNoArguments(<)
|
||||
handleSend(i, <)
|
||||
beginBinaryExpression(<)
|
||||
handleLiteralInt(10)
|
||||
endBinaryExpression(<)
|
||||
handleExpressionStatement(;)
|
||||
handleIdentifier(i, expression)
|
||||
handleNoTypeArguments(++)
|
||||
handleNoArguments(++)
|
||||
handleSend(i, ++)
|
||||
handleUnaryPostfixAssignmentExpression(++)
|
||||
handleForLoopParts(for, (, ;, 1)
|
||||
beginForStatementBody({)
|
||||
beginBlock({, BlockKind(statement))
|
||||
endBlock(0, {, }, BlockKind(statement))
|
||||
endForStatementBody(})
|
||||
endForStatement(})
|
||||
endBlockFunctionBody(2, {, })
|
||||
endTopLevelMethod(main, null, })
|
||||
endTopLevelDeclaration()
|
||||
endCompilationUnit(1, )
|
||||
@@ -0,0 +1,131 @@
|
||||
parseUnit(main)
|
||||
skipErrorTokens(main)
|
||||
listener: beginCompilationUnit(main)
|
||||
syntheticPreviousToken(main)
|
||||
parseTopLevelDeclarationImpl(, Instance of 'DirectiveContext')
|
||||
parseMetadataStar()
|
||||
listener: beginMetadataStar(main)
|
||||
listener: endMetadataStar(0)
|
||||
parseTopLevelMemberImpl()
|
||||
listener: beginTopLevelMember(main)
|
||||
parseTopLevelMethod(, null, , Instance of 'NoType', null, main)
|
||||
listener: beginTopLevelMethod(, null)
|
||||
listener: handleNoType()
|
||||
ensureIdentifier(, topLevelFunctionDeclaration)
|
||||
listener: handleIdentifier(main, topLevelFunctionDeclaration)
|
||||
parseMethodTypeVar(main)
|
||||
listener: handleNoTypeVariables(()
|
||||
parseGetterOrFormalParameters(main, main, false, MemberKind.TopLevelMethod)
|
||||
parseFormalParameters(main, MemberKind.TopLevelMethod)
|
||||
parseFormalParametersRest((, MemberKind.TopLevelMethod)
|
||||
listener: beginFormalParameters((, MemberKind.TopLevelMethod)
|
||||
listener: endFormalParameters(0, (, ), MemberKind.TopLevelMethod)
|
||||
parseAsyncModifierOpt())
|
||||
listener: handleAsyncModifier(null, null)
|
||||
inPlainSync()
|
||||
parseFunctionBody(), false, false)
|
||||
listener: beginBlockFunctionBody({)
|
||||
notEofOrValue(}, int)
|
||||
parseStatement({)
|
||||
parseStatementX({)
|
||||
parseExpressionStatementOrDeclarationAfterModifiers({, {, null, null, null, false)
|
||||
looksLikeLocalFunction(i)
|
||||
listener: beginMetadataStar(int)
|
||||
listener: endMetadataStar(0)
|
||||
listener: handleIdentifier(int, typeReference)
|
||||
listener: handleNoTypeArguments(i)
|
||||
listener: handleType(int, null)
|
||||
listener: beginVariablesDeclaration(i, null, null)
|
||||
parseVariablesDeclarationRest(int, true)
|
||||
parseOptionallyInitializedIdentifier(int)
|
||||
ensureIdentifier(int, localVariableDeclaration)
|
||||
listener: handleIdentifier(i, localVariableDeclaration)
|
||||
listener: beginInitializedIdentifier(i)
|
||||
parseVariableInitializerOpt(i)
|
||||
listener: handleNoVariableInitializer(;)
|
||||
listener: endInitializedIdentifier(i)
|
||||
ensureSemicolon(i)
|
||||
listener: endVariablesDeclaration(1, ;)
|
||||
notEofOrValue(}, for)
|
||||
parseStatement(;)
|
||||
parseStatementX(;)
|
||||
parseForStatement(;, null)
|
||||
listener: beginForStatement(for)
|
||||
parseForLoopPartsStart(null, for)
|
||||
parseExpressionStatementOrDeclaration((, true)
|
||||
parseExpressionStatementOrDeclarationAfterModifiers((, (, null, null, null, true)
|
||||
parseForLoopPartsMid((, null, for)
|
||||
parseExpression(()
|
||||
parsePrecedenceExpression((, 1, true)
|
||||
parseUnaryExpression((, true)
|
||||
parsePrimary((, expression)
|
||||
parseSendOrFunctionLiteral((, expression)
|
||||
parseSend((, expression)
|
||||
ensureIdentifier((, expression)
|
||||
listener: handleIdentifier(i, expression)
|
||||
listener: handleNoTypeArguments(=)
|
||||
parseArgumentsOpt(i)
|
||||
listener: handleNoArguments(=)
|
||||
listener: handleSend(i, =)
|
||||
parsePrecedenceExpression(=, 1, true)
|
||||
parseUnaryExpression(=, true)
|
||||
parsePrimary(=, expression)
|
||||
parseLiteralInt(=)
|
||||
listener: handleLiteralInt(0)
|
||||
listener: handleAssignmentExpression(=)
|
||||
listener: handleForInitializerExpressionStatement(0, false)
|
||||
parseForRest(null, 0, for)
|
||||
parseForLoopPartsRest(0, for, null)
|
||||
ensureSemicolon(0)
|
||||
parseExpressionStatement(;)
|
||||
parseExpression(;)
|
||||
parsePrecedenceExpression(;, 1, true)
|
||||
parseUnaryExpression(;, true)
|
||||
parsePrimary(;, expression)
|
||||
parseSendOrFunctionLiteral(;, expression)
|
||||
parseSend(;, expression)
|
||||
ensureIdentifier(;, expression)
|
||||
listener: handleIdentifier(i, expression)
|
||||
listener: handleNoTypeArguments(<)
|
||||
parseArgumentsOpt(i)
|
||||
listener: handleNoArguments(<)
|
||||
listener: handleSend(i, <)
|
||||
listener: beginBinaryExpression(<)
|
||||
parsePrecedenceExpression(<, 9, true)
|
||||
parseUnaryExpression(<, true)
|
||||
parsePrimary(<, expression)
|
||||
parseLiteralInt(<)
|
||||
listener: handleLiteralInt(10)
|
||||
listener: endBinaryExpression(<)
|
||||
ensureSemicolon(10)
|
||||
listener: handleExpressionStatement(;)
|
||||
parseExpression(;)
|
||||
parsePrecedenceExpression(;, 1, true)
|
||||
parseUnaryExpression(;, true)
|
||||
parsePrimary(;, expression)
|
||||
parseSendOrFunctionLiteral(;, expression)
|
||||
parseSend(;, expression)
|
||||
ensureIdentifier(;, expression)
|
||||
listener: handleIdentifier(i, expression)
|
||||
listener: handleNoTypeArguments(++)
|
||||
parseArgumentsOpt(i)
|
||||
listener: handleNoArguments(++)
|
||||
listener: handleSend(i, ++)
|
||||
listener: handleUnaryPostfixAssignmentExpression(++)
|
||||
listener: handleForLoopParts(for, (, ;, 1)
|
||||
listener: beginForStatementBody({)
|
||||
parseStatement())
|
||||
parseStatementX())
|
||||
parseBlock(), BlockKind(statement))
|
||||
ensureBlock(), null, null)
|
||||
listener: beginBlock({, BlockKind(statement))
|
||||
notEofOrValue(}, })
|
||||
listener: endBlock(0, {, }, BlockKind(statement))
|
||||
listener: endForStatementBody(})
|
||||
listener: endForStatement(})
|
||||
notEofOrValue(}, })
|
||||
listener: endBlockFunctionBody(2, {, })
|
||||
listener: endTopLevelMethod(main, null, })
|
||||
listener: endTopLevelDeclaration()
|
||||
reportAllErrorTokens(main)
|
||||
listener: endCompilationUnit(1, )
|
||||
@@ -0,0 +1,11 @@
|
||||
main() {
|
||||
int i;
|
||||
for (i = 0; i < 10; i++) {}
|
||||
}
|
||||
|
||||
|
||||
main[StringToken]([BeginToken])[SimpleToken] {[BeginToken]
|
||||
int[StringToken] i[StringToken];[SimpleToken]
|
||||
for[KeywordToken] ([BeginToken]i[StringToken] =[SimpleToken] 0[StringToken];[SimpleToken] i[StringToken] <[BeginToken] 10[StringToken];[SimpleToken] i[StringToken]++[SimpleToken])[SimpleToken] {[BeginToken]}[SimpleToken]
|
||||
}[SimpleToken]
|
||||
[SimpleToken]
|
||||
@@ -0,0 +1,11 @@
|
||||
main() {
|
||||
int i;
|
||||
for (i = 0; i < 10; i++) {}
|
||||
}
|
||||
|
||||
|
||||
main[StringToken]([BeginToken])[SimpleToken] {[BeginToken]
|
||||
int[StringToken] i[StringToken];[SimpleToken]
|
||||
for[KeywordToken] ([BeginToken]i[StringToken] =[SimpleToken] 0[StringToken];[SimpleToken] i[StringToken] <[BeginToken] 10[StringToken];[SimpleToken] i[StringToken]++[SimpleToken])[SimpleToken] {[BeginToken]}[SimpleToken]
|
||||
}[SimpleToken]
|
||||
[SimpleToken]
|
||||
@@ -984,12 +984,12 @@ class TestInfoListener implements Listener {
|
||||
}
|
||||
|
||||
@override
|
||||
void handleForInitializerExpressionStatement(Token token) {
|
||||
void handleForInitializerExpressionStatement(Token token, bool forIn) {
|
||||
calls.add('handleForInitializerExpressionStatement $token');
|
||||
}
|
||||
|
||||
@override
|
||||
void handleForInitializerLocalVariableDeclaration(Token token) {
|
||||
void handleForInitializerLocalVariableDeclaration(Token token, bool forIn) {
|
||||
calls.add('handleForInitializerLocalVariableDeclaration $token');
|
||||
}
|
||||
|
||||
|
||||
@@ -6,8 +6,9 @@ import 'dart:io' show Directory, Platform;
|
||||
import 'package:front_end/src/api_prototype/experimental_flags.dart'
|
||||
show ExperimentalFlag;
|
||||
import 'package:front_end/src/fasta/flow_analysis/flow_analysis.dart';
|
||||
import 'package:front_end/src/fasta/source/source_loader.dart';
|
||||
|
||||
import 'package:front_end/src/testing/id.dart' show ActualData, Id;
|
||||
import 'package:front_end/src/testing/id.dart' show ActualData, Id, IdKind;
|
||||
import 'package:front_end/src/testing/id_testing.dart'
|
||||
show DataInterpreter, runTests;
|
||||
import 'package:front_end/src/testing/id_testing.dart';
|
||||
@@ -58,12 +59,15 @@ class AssignedVariablesDataComputer extends DataComputer<_Data> {
|
||||
}
|
||||
|
||||
class AssignedVariablesDataExtractor extends CfeDataExtractor<_Data> {
|
||||
final SourceLoaderDataForTesting _sourceLoaderDataForTesting;
|
||||
final AssignedVariablesForTesting<TreeNode, VariableDeclaration>
|
||||
_assignedVariables;
|
||||
|
||||
AssignedVariablesDataExtractor(InternalCompilerResult compilerResult,
|
||||
Map<Id, ActualData<_Data>> actualMap, this._assignedVariables)
|
||||
: super(compilerResult, actualMap);
|
||||
: _sourceLoaderDataForTesting =
|
||||
compilerResult.kernelTargetForTesting.loader.dataForTesting,
|
||||
super(compilerResult, actualMap);
|
||||
|
||||
@override
|
||||
_Data computeMemberValue(Id id, Member member) {
|
||||
@@ -78,11 +82,19 @@ class AssignedVariablesDataExtractor extends CfeDataExtractor<_Data> {
|
||||
|
||||
@override
|
||||
_Data computeNodeValue(Id id, TreeNode node) {
|
||||
if (!_assignedVariables.isTracked(node)) return null;
|
||||
switch (id.kind) {
|
||||
case IdKind.iterator:
|
||||
case IdKind.current:
|
||||
case IdKind.moveNext:
|
||||
return null;
|
||||
default:
|
||||
}
|
||||
TreeNode alias = _sourceLoaderDataForTesting.toOriginal(node);
|
||||
if (!_assignedVariables.isTracked(alias)) return null;
|
||||
return new _Data(
|
||||
_convertVars(_assignedVariables.declaredInNode(node)),
|
||||
_convertVars(_assignedVariables.writtenInNode(node)),
|
||||
_convertVars(_assignedVariables.capturedInNode(node)));
|
||||
_convertVars(_assignedVariables.declaredInNode(alias)),
|
||||
_convertVars(_assignedVariables.writtenInNode(alias)),
|
||||
_convertVars(_assignedVariables.capturedInNode(alias)));
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
@@ -450,12 +450,13 @@ class ParserTestListener implements Listener {
|
||||
doPrint('handleForInitializerEmptyStatement(' '$token)');
|
||||
}
|
||||
|
||||
void handleForInitializerExpressionStatement(Token token) {
|
||||
doPrint('handleForInitializerExpressionStatement(' '$token)');
|
||||
void handleForInitializerExpressionStatement(Token token, bool forIn) {
|
||||
doPrint('handleForInitializerExpressionStatement(' '$token, ' '$forIn)');
|
||||
}
|
||||
|
||||
void handleForInitializerLocalVariableDeclaration(Token token) {
|
||||
doPrint('handleForInitializerLocalVariableDeclaration(' '$token)');
|
||||
void handleForInitializerLocalVariableDeclaration(Token token, bool forIn) {
|
||||
doPrint(
|
||||
'handleForInitializerLocalVariableDeclaration(' '$token, ' '$forIn)');
|
||||
}
|
||||
|
||||
void beginForStatement(Token token) {
|
||||
|
||||
Reference in New Issue
Block a user