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

Side by Side Diff: pkg/front_end/lib/src/fasta/kernel/body_builder.dart

Issue 2841863002: Change accessors and AstFactory to use tokens rather than file offsets. (Closed)
Patch Set: Created 3 years, 7 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 unified diff | Download patch
OLDNEW
1 // Copyright (c) 2016, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2016, 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 fasta.body_builder; 5 library fasta.body_builder;
6 6
7 import '../fasta_codes.dart' 7 import '../fasta_codes.dart'
8 show FastaMessage, codeExpectedButGot, codeExpectedFunctionBody; 8 show FastaMessage, codeExpectedButGot, codeExpectedFunctionBody;
9 9
10 import '../parser/parser.dart' show FormalParameterType, optional; 10 import '../parser/parser.dart' show FormalParameterType, optional;
(...skipping 19 matching lines...) Expand all
30 30
31 import 'package:kernel/class_hierarchy.dart' show ClassHierarchy; 31 import 'package:kernel/class_hierarchy.dart' show ClassHierarchy;
32 32
33 import 'package:kernel/core_types.dart' show CoreTypes; 33 import 'package:kernel/core_types.dart' show CoreTypes;
34 34
35 import 'frontend_accessors.dart' show buildIsNull, makeBinary, makeLet; 35 import 'frontend_accessors.dart' show buildIsNull, makeBinary, makeLet;
36 36
37 import '../parser/dart_vm_native.dart' show skipNativeClause; 37 import '../parser/dart_vm_native.dart' show skipNativeClause;
38 38
39 import '../scanner/token.dart' 39 import '../scanner/token.dart'
40 show BeginGroupToken, Token, isBinaryOperator, isMinusOperator; 40 show
41 BeginGroupToken,
42 Token,
43 isBinaryOperator,
44 isMinusOperator,
45 offsetForToken;
41 46
42 import '../errors.dart' show formatUnexpected, internalError; 47 import '../errors.dart' show formatUnexpected, internalError;
43 48
44 import '../source/scope_listener.dart' 49 import '../source/scope_listener.dart'
45 show JumpTargetKind, NullValue, ScopeListener; 50 show JumpTargetKind, NullValue, ScopeListener;
46 51
47 import '../scope.dart' show ProblemBuilder; 52 import '../scope.dart' show ProblemBuilder;
48 53
49 import '../source/outline_builder.dart' show asyncMarkerFromTokens; 54 import '../source/outline_builder.dart' show asyncMarkerFromTokens;
50 55
(...skipping 178 matching lines...) Expand 10 before | Expand all | Expand 10 after
229 234
230 List<Expression> popListForEffect(int n) { 235 List<Expression> popListForEffect(int n) {
231 List<Expression> list = 236 List<Expression> list =
232 new List<Expression>.filled(n, null, growable: true); 237 new List<Expression>.filled(n, null, growable: true);
233 for (int i = n - 1; i >= 0; i--) { 238 for (int i = n - 1; i >= 0; i--) {
234 list[i] = popForEffect(); 239 list[i] = popForEffect();
235 } 240 }
236 return list; 241 return list;
237 } 242 }
238 243
239 Block popBlock(int count, int charOffset) { 244 Block popBlock(int count, Token beginToken) {
240 List<dynamic /*Statement | List<Statement>*/ > statements = 245 List<dynamic /*Statement | List<Statement>*/ > statements =
241 popList(count) ?? <Statement>[]; 246 popList(count) ?? <Statement>[];
242 List<Statement> copy; 247 List<Statement> copy;
243 for (int i = 0; i < statements.length; i++) { 248 for (int i = 0; i < statements.length; i++) {
244 var statement = statements[i]; 249 var statement = statements[i];
245 if (statement is List) { 250 if (statement is List) {
246 copy ??= new List<Statement>.from(statements.getRange(0, i)); 251 copy ??= new List<Statement>.from(statements.getRange(0, i));
247 // TODO(sigmund): remove this assignment (issue #28651) 252 // TODO(sigmund): remove this assignment (issue #28651)
248 Iterable subStatements = statement; 253 Iterable subStatements = statement;
249 copy.addAll(subStatements); 254 copy.addAll(subStatements);
250 } else if (copy != null) { 255 } else if (copy != null) {
251 copy.add(statement); 256 copy.add(statement);
252 } 257 }
253 } 258 }
254 return astFactory.block(copy ?? statements, charOffset); 259 return astFactory.block(copy ?? statements, beginToken);
255 } 260 }
256 261
257 Statement popStatementIfNotNull(Object value) { 262 Statement popStatementIfNotNull(Object value) {
258 return value == null ? null : popStatement(); 263 return value == null ? null : popStatement();
259 } 264 }
260 265
261 Statement popStatement() { 266 Statement popStatement() {
262 var statement = pop(); 267 var statement = pop();
263 if (statement is List) { 268 if (statement is List) {
264 return new Block(new List<Statement>.from(statement)); 269 return new Block(new List<Statement>.from(statement));
(...skipping 97 matching lines...) Expand 10 before | Expand all | Expand 10 after
362 checkEmpty(-1); 367 checkEmpty(-1);
363 } 368 }
364 369
365 @override 370 @override
366 void endBlockFunctionBody(int count, Token beginToken, Token endToken) { 371 void endBlockFunctionBody(int count, Token beginToken, Token endToken) {
367 debugEvent("BlockFunctionBody"); 372 debugEvent("BlockFunctionBody");
368 if (beginToken == null) { 373 if (beginToken == null) {
369 assert(count == 0); 374 assert(count == 0);
370 push(NullValue.Block); 375 push(NullValue.Block);
371 } else { 376 } else {
372 Block block = popBlock(count, beginToken.charOffset); 377 Block block = popBlock(count, beginToken);
373 exitLocalScope(); 378 exitLocalScope();
374 push(block); 379 push(block);
375 } 380 }
376 } 381 }
377 382
378 @override 383 @override
379 void prepareInitializers() { 384 void prepareInitializers() {
380 scope = formalParameterScope; 385 scope = formalParameterScope;
381 assert(fieldInitializers.isEmpty); 386 assert(fieldInitializers.isEmpty);
382 final member = this.member; 387 final member = this.member;
(...skipping 176 matching lines...) Expand 10 before | Expand all | Expand 10 after
559 arguments.getRange(firstNamedArgumentIndex, arguments.length)); 564 arguments.getRange(firstNamedArgumentIndex, arguments.length));
560 push(new Arguments(positional, named: named)); 565 push(new Arguments(positional, named: named));
561 } else { 566 } else {
562 push(new Arguments(arguments)); 567 push(new Arguments(arguments));
563 } 568 }
564 } 569 }
565 570
566 @override 571 @override
567 void handleParenthesizedExpression(BeginGroupToken token) { 572 void handleParenthesizedExpression(BeginGroupToken token) {
568 debugEvent("ParenthesizedExpression"); 573 debugEvent("ParenthesizedExpression");
569 push(new ParenthesizedExpression( 574 push(new ParenthesizedExpression(this, popForValue(), token.endGroup));
570 this, popForValue(), token.endGroup.charOffset));
571 } 575 }
572 576
573 @override 577 @override
574 void endSend(Token beginToken, Token endToken) { 578 void endSend(Token beginToken, Token endToken) {
575 debugEvent("Send"); 579 debugEvent("Send");
576 Arguments arguments = pop(); 580 Arguments arguments = pop();
577 List<DartType> typeArguments = pop(); 581 List<DartType> typeArguments = pop();
578 Object receiver = pop(); 582 Object receiver = pop();
579 if (arguments != null && typeArguments != null) { 583 if (arguments != null && typeArguments != null) {
580 arguments.types.addAll(typeArguments); 584 arguments.types.addAll(typeArguments);
581 } else { 585 } else {
582 assert(typeArguments == null); 586 assert(typeArguments == null);
583 } 587 }
584 if (receiver is Identifier) { 588 if (receiver is Identifier) {
585 Name name = new Name(receiver.name, library.library); 589 Name name = new Name(receiver.name, library.library);
586 if (arguments == null) { 590 if (arguments == null) {
587 push(new IncompletePropertyAccessor(this, beginToken.charOffset, name)); 591 push(new IncompletePropertyAccessor(this, beginToken, name));
588 } else { 592 } else {
589 push(new SendAccessor(this, beginToken.charOffset, name, arguments)); 593 push(new SendAccessor(this, beginToken, name, arguments));
590 } 594 }
591 } else if (arguments == null) { 595 } else if (arguments == null) {
592 push(receiver); 596 push(receiver);
593 } else { 597 } else {
594 push(finishSend(receiver, arguments, beginToken.charOffset)); 598 push(finishSend(receiver, arguments, beginToken.charOffset));
595 } 599 }
596 } 600 }
597 601
598 @override 602 @override
599 finishSend(Object receiver, Arguments arguments, int charOffset) { 603 finishSend(Object receiver, Arguments arguments, int charOffset) {
(...skipping 15 matching lines...) Expand all
615 toValue(receiver), callName, arguments, charOffset); 619 toValue(receiver), callName, arguments, charOffset);
616 } 620 }
617 } 621 }
618 622
619 @override 623 @override
620 void beginCascade(Token token) { 624 void beginCascade(Token token) {
621 debugEvent("beginCascade"); 625 debugEvent("beginCascade");
622 Expression expression = popForValue(); 626 Expression expression = popForValue();
623 if (expression is CascadeReceiver) { 627 if (expression is CascadeReceiver) {
624 push(expression); 628 push(expression);
625 push(new VariableAccessor( 629 // TODO(paulberry): Previously we used expression.fileOffset; now we are
626 this, expression.fileOffset, expression.variable)); 630 // using token. Is that a problem?
ahe 2017/04/25 17:39:59 I think so. Try running the service tests: nice .
Paul Berry 2017/04/25 22:00:55 Thanks! I've verified that these tests pass and I
631 push(new VariableAccessor(this, token, expression.variable));
627 expression.extend(); 632 expression.extend();
628 } else { 633 } else {
629 VariableDeclaration variable = 634 VariableDeclaration variable =
630 new VariableDeclaration.forValue(expression); 635 new VariableDeclaration.forValue(expression);
631 push(new CascadeReceiver(variable)); 636 push(new CascadeReceiver(variable));
632 push(new VariableAccessor(this, expression.fileOffset, variable)); 637 // TODO(paulberry): Previously we used expression.fileOffset; now we are
638 // using token. Is that a problem?
639 push(new VariableAccessor(this, token, variable));
633 } 640 }
634 } 641 }
635 642
636 @override 643 @override
637 void endCascade() { 644 void endCascade() {
638 debugEvent("endCascade"); 645 debugEvent("endCascade");
639 Expression expression = popForEffect(); 646 Expression expression = popForEffect();
640 CascadeReceiver cascadeReceiver = pop(); 647 CascadeReceiver cascadeReceiver = pop();
641 cascadeReceiver.finalize(expression); 648 cascadeReceiver.finalize(expression);
642 push(cascadeReceiver); 649 push(cascadeReceiver);
(...skipping 165 matching lines...) Expand 10 before | Expand all | Expand 10 after
808 @override 815 @override
809 void handleIdentifier(Token token, IdentifierContext context) { 816 void handleIdentifier(Token token, IdentifierContext context) {
810 debugEvent("handleIdentifier"); 817 debugEvent("handleIdentifier");
811 String name = token.lexeme; 818 String name = token.lexeme;
812 if (context.isScopeReference) { 819 if (context.isScopeReference) {
813 assert(!inInitializer || 820 assert(!inInitializer ||
814 this.scope == enclosingScope || 821 this.scope == enclosingScope ||
815 this.scope.parent == enclosingScope); 822 this.scope.parent == enclosingScope);
816 // This deals with this kind of initializer: `C(a) : a = a;` 823 // This deals with this kind of initializer: `C(a) : a = a;`
817 Scope scope = inInitializer ? enclosingScope : this.scope; 824 Scope scope = inInitializer ? enclosingScope : this.scope;
818 push(scopeLookup(scope, name, token.charOffset)); 825 push(scopeLookup(scope, name, token));
819 return; 826 return;
820 } else if (context.inDeclaration) { 827 } else if (context.inDeclaration) {
821 if (context == IdentifierContext.topLevelVariableDeclaration || 828 if (context == IdentifierContext.topLevelVariableDeclaration ||
822 context == IdentifierContext.fieldDeclaration) { 829 context == IdentifierContext.fieldDeclaration) {
823 constantExpressionRequired = member.isConst; 830 constantExpressionRequired = member.isConst;
824 } 831 }
825 } else if (constantExpressionRequired && 832 } else if (constantExpressionRequired &&
826 !context.allowedInConstantExpression) { 833 !context.allowedInConstantExpression) {
827 addCompileTimeError( 834 addCompileTimeError(
828 token.charOffset, "Not a constant expression: $context"); 835 token.charOffset, "Not a constant expression: $context");
829 } 836 }
830 push(new Identifier(name, token.charOffset)); 837 push(new Identifier(token));
831 } 838 }
832 839
833 /// Look up [name] in [scope] using [charOffset] to report any 840 /// Look up [name] in [scope] using [token] to report any
834 /// problems. [isQualified] should be true if [name] is a qualified access 841 /// problems. [isQualified] should be true if [name] is a qualified access
ahe 2017/04/25 17:39:59 Perhaps this documentation of charOffset/token isn
Paul Berry 2017/04/25 22:00:55 Good point. Fixed.
835 /// (which implies that it shouldn't be turned into a [ThisPropertyAccessor] 842 /// (which implies that it shouldn't be turned into a [ThisPropertyAccessor]
836 /// if the name doesn't resolve in the scope). 843 /// if the name doesn't resolve in the scope).
837 @override 844 @override
838 scopeLookup(Scope scope, String name, int charOffset, 845 scopeLookup(Scope scope, String name, Token token,
839 {bool isQualified: false, PrefixBuilder prefix}) { 846 {bool isQualified: false, PrefixBuilder prefix}) {
840 Builder builder = scope.lookup(name, charOffset, uri); 847 Builder builder = scope.lookup(name, offsetForToken(token), uri);
841 if (builder == null || (!isInstanceContext && builder.isInstanceMember)) { 848 if (builder == null || (!isInstanceContext && builder.isInstanceMember)) {
842 Name n = new Name(name, library.library); 849 Name n = new Name(name, library.library);
843 if (prefix != null && 850 if (prefix != null &&
844 prefix.deferred && 851 prefix.deferred &&
845 builder == null && 852 builder == null &&
846 "loadLibrary" == name) { 853 "loadLibrary" == name) {
847 return buildCompileTimeError( 854 return buildCompileTimeError(
848 "Deferred loading isn't implemented yet.", charOffset); 855 "Deferred loading isn't implemented yet.", offsetForToken(token));
849 } else if (!isQualified && isInstanceContext) { 856 } else if (!isQualified && isInstanceContext) {
850 assert(builder == null); 857 assert(builder == null);
851 if (constantExpressionRequired) { 858 if (constantExpressionRequired) {
852 return new UnresolvedAccessor(this, n, charOffset); 859 return new UnresolvedAccessor(this, n, token);
853 } 860 }
854 return new ThisPropertyAccessor(this, charOffset, n, null, null); 861 return new ThisPropertyAccessor(this, token, n, null, null);
855 } else if (isDartLibrary && 862 } else if (isDartLibrary &&
856 name == "main" && 863 name == "main" &&
857 library.uri.path == "_builtin" && 864 library.uri.path == "_builtin" &&
858 member?.name == "_getMainClosure") { 865 member?.name == "_getMainClosure") {
859 // TODO(ahe): https://github.com/dart-lang/sdk/issues/28989 866 // TODO(ahe): https://github.com/dart-lang/sdk/issues/28989
860 return new NullLiteral()..fileOffset = charOffset; 867 return new NullLiteral()..fileOffset = offsetForToken(token);
861 } else { 868 } else {
862 return new UnresolvedAccessor(this, n, charOffset); 869 return new UnresolvedAccessor(this, n, token);
863 } 870 }
864 } else if (builder.isTypeDeclaration) { 871 } else if (builder.isTypeDeclaration) {
865 if (constantExpressionRequired && 872 if (constantExpressionRequired &&
866 builder.isTypeVariable && 873 builder.isTypeVariable &&
867 !member.isConstructor) { 874 !member.isConstructor) {
868 addCompileTimeError(charOffset, "Not a constant expression."); 875 addCompileTimeError(
876 offsetForToken(token), "Not a constant expression.");
869 } 877 }
870 return builder; 878 return builder;
871 } else if (builder.isLocal) { 879 } else if (builder.isLocal) {
872 if (constantExpressionRequired && 880 if (constantExpressionRequired &&
873 !builder.isConst && 881 !builder.isConst &&
874 !member.isConstructor) { 882 !member.isConstructor) {
875 addCompileTimeError(charOffset, "Not a constant expression."); 883 addCompileTimeError(
884 offsetForToken(token), "Not a constant expression.");
876 } 885 }
877 return new VariableAccessor(this, charOffset, builder.target); 886 return new VariableAccessor(this, token, builder.target);
878 } else if (builder.isInstanceMember) { 887 } else if (builder.isInstanceMember) {
879 if (constantExpressionRequired && 888 if (constantExpressionRequired &&
880 !inInitializer && 889 !inInitializer &&
881 // TODO(ahe): This is a hack because Fasta sets up the scope 890 // TODO(ahe): This is a hack because Fasta sets up the scope
882 // "this.field" parameters according to old semantics. Under the new 891 // "this.field" parameters according to old semantics. Under the new
883 // semantics, such parameters introduces a new parameter with that 892 // semantics, such parameters introduces a new parameter with that
884 // name that should be resolved here. 893 // name that should be resolved here.
885 !member.isConstructor) { 894 !member.isConstructor) {
886 addCompileTimeError(charOffset, "Not a constant expression."); 895 addCompileTimeError(
896 offsetForToken(token), "Not a constant expression.");
887 } 897 }
888 return new ThisPropertyAccessor( 898 return new ThisPropertyAccessor(
889 this, charOffset, new Name(name, library.library), null, null); 899 this, token, new Name(name, library.library), null, null);
890 } else if (builder.isRegularMethod) { 900 } else if (builder.isRegularMethod) {
891 assert(builder.isStatic || builder.isTopLevel); 901 assert(builder.isStatic || builder.isTopLevel);
892 return new StaticAccessor(this, charOffset, builder.target, null); 902 return new StaticAccessor(this, token, builder.target, null);
893 } else if (builder is PrefixBuilder) { 903 } else if (builder is PrefixBuilder) {
894 if (constantExpressionRequired && builder.deferred) { 904 if (constantExpressionRequired && builder.deferred) {
895 addCompileTimeError( 905 addCompileTimeError(
896 charOffset, 906 offsetForToken(token),
897 "'$name' can't be used in a constant expression because it's " 907 "'$name' can't be used in a constant expression because it's "
898 "marked as 'deferred' which means it isn't available until " 908 "marked as 'deferred' which means it isn't available until "
899 "loaded.\n" 909 "loaded.\n"
900 "You might try moving the constant to the deferred library, " 910 "You might try moving the constant to the deferred library, "
901 "or removing 'deferred' from the import."); 911 "or removing 'deferred' from the import.");
902 } 912 }
903 return builder; 913 return builder;
904 } else { 914 } else {
905 if (builder.hasProblem && builder is! AccessErrorBuilder) return builder; 915 if (builder.hasProblem && builder is! AccessErrorBuilder) return builder;
906 Builder setter; 916 Builder setter;
907 if (builder.isSetter) { 917 if (builder.isSetter) {
908 setter = builder; 918 setter = builder;
909 } else if (builder.isGetter) { 919 } else if (builder.isGetter) {
910 setter = scope.lookupSetter(name, charOffset, uri); 920 setter = scope.lookupSetter(name, offsetForToken(token), uri);
911 } else if (builder.isField && !builder.isFinal) { 921 } else if (builder.isField && !builder.isFinal) {
912 setter = builder; 922 setter = builder;
913 } 923 }
914 StaticAccessor accessor = 924 StaticAccessor accessor =
915 new StaticAccessor.fromBuilder(this, builder, charOffset, setter); 925 new StaticAccessor.fromBuilder(this, builder, token, setter);
916 if (constantExpressionRequired) { 926 if (constantExpressionRequired) {
917 Member readTarget = accessor.readTarget; 927 Member readTarget = accessor.readTarget;
918 if (!(readTarget is Field && readTarget.isConst || 928 if (!(readTarget is Field && readTarget.isConst ||
919 // Static tear-offs are also compile time constants. 929 // Static tear-offs are also compile time constants.
920 readTarget is Procedure)) { 930 readTarget is Procedure)) {
921 addCompileTimeError(charOffset, "Not a constant expression."); 931 addCompileTimeError(
932 offsetForToken(token), "Not a constant expression.");
922 } 933 }
923 } 934 }
924 return accessor; 935 return accessor;
925 } 936 }
926 } 937 }
927 938
928 @override 939 @override
929 void handleQualified(Token period) { 940 void handleQualified(Token period) {
930 debugEvent("Qualified"); 941 debugEvent("Qualified");
931 Identifier name = pop(); 942 Identifier name = pop();
(...skipping 74 matching lines...) Expand 10 before | Expand all | Expand 10 after
1006 expressions.add(part); 1017 expressions.add(part);
1007 } 1018 }
1008 } 1019 }
1009 } 1020 }
1010 push(new StringConcatenation(expressions ?? parts)); 1021 push(new StringConcatenation(expressions ?? parts));
1011 } 1022 }
1012 1023
1013 @override 1024 @override
1014 void handleLiteralInt(Token token) { 1025 void handleLiteralInt(Token token) {
1015 debugEvent("LiteralInt"); 1026 debugEvent("LiteralInt");
1016 push(astFactory.intLiteral(int.parse(token.lexeme), token.charOffset)); 1027 push(astFactory.intLiteral(int.parse(token.lexeme), token));
1017 } 1028 }
1018 1029
1019 @override 1030 @override
1020 void handleEmptyFunctionBody(Token semicolon) { 1031 void handleEmptyFunctionBody(Token semicolon) {
1021 debugEvent("ExpressionFunctionBody"); 1032 debugEvent("ExpressionFunctionBody");
1022 endBlockFunctionBody(0, null, semicolon); 1033 endBlockFunctionBody(0, null, semicolon);
1023 } 1034 }
1024 1035
1025 @override 1036 @override
1026 void handleExpressionFunctionBody(Token arrowToken, Token endToken) { 1037 void handleExpressionFunctionBody(Token arrowToken, Token endToken) {
(...skipping 19 matching lines...) Expand all
1046 Statement elsePart = popStatementIfNotNull(elseToken); 1057 Statement elsePart = popStatementIfNotNull(elseToken);
1047 Statement thenPart = popStatement(); 1058 Statement thenPart = popStatement();
1048 Expression condition = popForValue(); 1059 Expression condition = popForValue();
1049 push(new IfStatement(condition, thenPart, elsePart)); 1060 push(new IfStatement(condition, thenPart, elsePart));
1050 } 1061 }
1051 1062
1052 @override 1063 @override
1053 void endVariableInitializer(Token assignmentOperator) { 1064 void endVariableInitializer(Token assignmentOperator) {
1054 debugEvent("VariableInitializer"); 1065 debugEvent("VariableInitializer");
1055 assert(assignmentOperator.stringValue == "="); 1066 assert(assignmentOperator.stringValue == "=");
1056 pushNewLocalVariable(popForValue(), 1067 pushNewLocalVariable(popForValue(), equalsToken: assignmentOperator);
1057 equalsCharOffset: assignmentOperator.charOffset);
1058 } 1068 }
1059 1069
1060 @override 1070 @override
1061 void handleNoVariableInitializer(Token token) { 1071 void handleNoVariableInitializer(Token token) {
1062 debugEvent("NoVariableInitializer"); 1072 debugEvent("NoVariableInitializer");
1063 pushNewLocalVariable(null); 1073 pushNewLocalVariable(null);
1064 } 1074 }
1065 1075
1066 void pushNewLocalVariable(Expression initializer, 1076 void pushNewLocalVariable(Expression initializer, {Token equalsToken}) {
1067 {int equalsCharOffset: TreeNode.noOffset}) {
1068 Identifier identifier = pop(); 1077 Identifier identifier = pop();
1069 assert(currentLocalVariableModifiers != -1); 1078 assert(currentLocalVariableModifiers != -1);
1070 bool isConst = (currentLocalVariableModifiers & constMask) != 0; 1079 bool isConst = (currentLocalVariableModifiers & constMask) != 0;
1071 bool isFinal = (currentLocalVariableModifiers & finalMask) != 0; 1080 bool isFinal = (currentLocalVariableModifiers & finalMask) != 0;
1072 assert(isConst == constantExpressionRequired); 1081 assert(isConst == constantExpressionRequired);
1073 push(astFactory.variableDeclaration(identifier.name, identifier.fileOffset, 1082 push(astFactory.variableDeclaration(identifier.name, identifier.token,
1074 initializer: initializer, 1083 initializer: initializer,
1075 type: currentLocalVariableType, 1084 type: currentLocalVariableType,
1076 isFinal: isFinal, 1085 isFinal: isFinal,
1077 isConst: isConst, 1086 isConst: isConst,
1078 equalsCharOffset: equalsCharOffset)); 1087 equalsToken: equalsToken));
1079 } 1088 }
1080 1089
1081 @override 1090 @override
1082 void endFieldInitializer(Token assignmentOperator, Token token) { 1091 void endFieldInitializer(Token assignmentOperator, Token token) {
1083 debugEvent("FieldInitializer"); 1092 debugEvent("FieldInitializer");
1084 assert(assignmentOperator.stringValue == "="); 1093 assert(assignmentOperator.stringValue == "=");
1085 push(popForValue()); 1094 push(popForValue());
1086 } 1095 }
1087 1096
1088 @override 1097 @override
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after
1133 if (variables.length != 1) { 1142 if (variables.length != 1) {
1134 push(variables); 1143 push(variables);
1135 } else { 1144 } else {
1136 push(variables.single); 1145 push(variables.single);
1137 } 1146 }
1138 } 1147 }
1139 1148
1140 @override 1149 @override
1141 void endBlock(int count, Token beginToken, Token endToken) { 1150 void endBlock(int count, Token beginToken, Token endToken) {
1142 debugEvent("Block"); 1151 debugEvent("Block");
1143 Block block = popBlock(count, beginToken.charOffset); 1152 Block block = popBlock(count, beginToken);
1144 exitLocalScope(); 1153 exitLocalScope();
1145 push(block); 1154 push(block);
1146 } 1155 }
1147 1156
1148 @override 1157 @override
1149 void handleAssignmentExpression(Token token) { 1158 void handleAssignmentExpression(Token token) {
1150 debugEvent("AssignmentExpression"); 1159 debugEvent("AssignmentExpression");
1151 Expression value = popForValue(); 1160 Expression value = popForValue();
1152 var accessor = pop(); 1161 var accessor = pop();
1153 if (accessor is TypeDeclarationBuilder) { 1162 if (accessor is TypeDeclarationBuilder) {
1154 push(wrapInvalid(new TypeLiteral( 1163 push(wrapInvalid(new TypeLiteral(
1155 accessor.buildTypesWithBuiltArguments(library, null)))); 1164 accessor.buildTypesWithBuiltArguments(library, null))));
1156 } else if (accessor is! FastaAccessor) { 1165 } else if (accessor is! FastaAccessor) {
1157 push(buildCompileTimeError("Can't assign to this.", token.charOffset)); 1166 push(buildCompileTimeError("Can't assign to this.", token.charOffset));
1158 } else { 1167 } else {
1159 push(new DelayedAssignment( 1168 push(new DelayedAssignment(
1160 this, token.charOffset, accessor, value, token.stringValue)); 1169 this, token, accessor, value, token.stringValue));
1161 } 1170 }
1162 } 1171 }
1163 1172
1164 @override 1173 @override
1165 void enterLoop(int charOffset) { 1174 void enterLoop(int charOffset) {
1166 if (peek() is LabelTarget) { 1175 if (peek() is LabelTarget) {
1167 LabelTarget target = peek(); 1176 LabelTarget target = peek();
1168 enterBreakTarget(charOffset, target.breakTarget); 1177 enterBreakTarget(charOffset, target.breakTarget);
1169 enterContinueTarget(charOffset, target.continueTarget); 1178 enterContinueTarget(charOffset, target.continueTarget);
1170 } else { 1179 } else {
(...skipping 155 matching lines...) Expand 10 before | Expand all | Expand 10 after
1326 } else { 1335 } else {
1327 return internalError("Unhandled: ${name.runtimeType}"); 1336 return internalError("Unhandled: ${name.runtimeType}");
1328 } 1337 }
1329 } 1338 }
1330 1339
1331 @override 1340 @override
1332 void endLiteralSymbol(Token hashToken, int identifierCount) { 1341 void endLiteralSymbol(Token hashToken, int identifierCount) {
1333 debugEvent("LiteralSymbol"); 1342 debugEvent("LiteralSymbol");
1334 String value; 1343 String value;
1335 if (identifierCount == 1) { 1344 if (identifierCount == 1) {
1336 value = symbolPartToString(popForValue()); 1345 value = symbolPartToString(pop());
ahe 2017/04/25 17:39:59 Why this change?
Paul Berry 2017/04/25 22:00:55 This is necessary in order to decouple Identifier
1337 } else { 1346 } else {
1338 List parts = popList(identifierCount); 1347 List parts = popList(identifierCount);
1339 value = symbolPartToString(parts.first); 1348 value = symbolPartToString(parts.first);
1340 for (int i = 1; i < parts.length; i++) { 1349 for (int i = 1; i < parts.length; i++) {
1341 value += ".${symbolPartToString(parts[i])}"; 1350 value += ".${symbolPartToString(parts[i])}";
1342 } 1351 }
1343 } 1352 }
1344 push(new SymbolLiteral(value)); 1353 push(new SymbolLiteral(value));
1345 } 1354 }
1346 1355
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after
1391 if (suffix is Identifier) { 1400 if (suffix is Identifier) {
1392 suffix = suffix.name; 1401 suffix = suffix.name;
1393 } 1402 }
1394 Builder builder; 1403 Builder builder;
1395 if (prefix is Builder) { 1404 if (prefix is Builder) {
1396 builder = prefix; 1405 builder = prefix;
1397 } else { 1406 } else {
1398 builder = scope.lookup(prefix, beginToken.charOffset, uri); 1407 builder = scope.lookup(prefix, beginToken.charOffset, uri);
1399 } 1408 }
1400 if (builder is PrefixBuilder) { 1409 if (builder is PrefixBuilder) {
1401 name = scopeLookup(builder.exports, suffix, beginToken.charOffset, 1410 name = scopeLookup(builder.exports, suffix, beginToken,
1402 isQualified: true, prefix: builder); 1411 isQualified: true, prefix: builder);
1403 } else { 1412 } else {
1404 push(const DynamicType()); 1413 push(const DynamicType());
1405 addCompileTimeError(beginToken.charOffset, 1414 addCompileTimeError(beginToken.charOffset,
1406 "Can't be used as a type: '${debugName(prefix, suffix)}'."); 1415 "Can't be used as a type: '${debugName(prefix, suffix)}'.");
1407 return; 1416 return;
1408 } 1417 }
1409 } 1418 }
1410 if (name is Identifier) { 1419 if (name is Identifier) {
1411 name = name.name; 1420 name = name.name;
(...skipping 115 matching lines...) Expand 10 before | Expand all | Expand 10 after
1527 } else if (thisKeyword == null) { 1536 } else if (thisKeyword == null) {
1528 variable = builder.build(library); 1537 variable = builder.build(library);
1529 variable.initializer = name.initializer; 1538 variable.initializer = name.initializer;
1530 } else if (builder.isField && builder.parent == classBuilder) { 1539 } else if (builder.isField && builder.parent == classBuilder) {
1531 FieldBuilder field = builder; 1540 FieldBuilder field = builder;
1532 if (type != null) { 1541 if (type != null) {
1533 nit("Ignoring type on 'this' parameter '${name.name}'.", 1542 nit("Ignoring type on 'this' parameter '${name.name}'.",
1534 thisKeyword.charOffset); 1543 thisKeyword.charOffset);
1535 } 1544 }
1536 type = field.target.type ?? const DynamicType(); 1545 type = field.target.type ?? const DynamicType();
1537 variable = astFactory.variableDeclaration(name.name, name.fileOffset, 1546 variable = astFactory.variableDeclaration(name.name, name.token,
1538 type: type, 1547 type: type,
1539 initializer: name.initializer, 1548 initializer: name.initializer,
1540 isFinal: isFinal, 1549 isFinal: isFinal,
1541 isConst: isConst); 1550 isConst: isConst);
1542 } else { 1551 } else {
1543 addCompileTimeError( 1552 addCompileTimeError(offsetForToken(name.token),
1544 name.fileOffset, "'${name.name}' isn't a field in this class."); 1553 "'${name.name}' isn't a field in this class.");
1545 } 1554 }
1546 } 1555 }
1547 variable ??= astFactory.variableDeclaration(name.name, name.fileOffset, 1556 variable ??= astFactory.variableDeclaration(name.name, name.token,
1548 type: type ?? const DynamicType(), 1557 type: type ?? const DynamicType(),
1549 initializer: name.initializer, 1558 initializer: name.initializer,
1550 isFinal: isFinal, 1559 isFinal: isFinal,
1551 isConst: isConst); 1560 isConst: isConst);
1552 push(variable); 1561 push(variable);
1553 } 1562 }
1554 1563
1555 @override 1564 @override
1556 void endOptionalFormalParameters( 1565 void endOptionalFormalParameters(
1557 int count, Token beginToken, Token endToken) { 1566 int count, Token beginToken, Token endToken) {
(...skipping 24 matching lines...) Expand all
1582 push(formals.toFunctionType(returnType)); 1591 push(formals.toFunctionType(returnType));
1583 push(name); 1592 push(name);
1584 functionNestingLevel--; 1593 functionNestingLevel--;
1585 } 1594 }
1586 1595
1587 @override 1596 @override
1588 void handleValuedFormalParameter(Token equals, Token token) { 1597 void handleValuedFormalParameter(Token equals, Token token) {
1589 debugEvent("ValuedFormalParameter"); 1598 debugEvent("ValuedFormalParameter");
1590 Expression initializer = popForValue(); 1599 Expression initializer = popForValue();
1591 Identifier name = pop(); 1600 Identifier name = pop();
1592 push(new InitializedIdentifier(name.name, initializer, name.fileOffset)); 1601 push(new InitializedIdentifier(name.token, initializer));
1593 } 1602 }
1594 1603
1595 @override 1604 @override
1596 void handleFormalParameterWithoutValue(Token token) { 1605 void handleFormalParameterWithoutValue(Token token) {
1597 debugEvent("FormalParameterWithoutValue"); 1606 debugEvent("FormalParameterWithoutValue");
1598 } 1607 }
1599 1608
1600 @override 1609 @override
1601 void endFormalParameters(int count, Token beginToken, Token endToken) { 1610 void endFormalParameters(int count, Token beginToken, Token endToken) {
1602 debugEvent("FormalParameters"); 1611 debugEvent("FormalParameters");
(...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after
1684 push(NullValue.Expression); 1693 push(NullValue.Expression);
1685 } 1694 }
1686 1695
1687 @override 1696 @override
1688 void handleIndexedExpression( 1697 void handleIndexedExpression(
1689 Token openCurlyBracket, Token closeCurlyBracket) { 1698 Token openCurlyBracket, Token closeCurlyBracket) {
1690 debugEvent("IndexedExpression"); 1699 debugEvent("IndexedExpression");
1691 Expression index = popForValue(); 1700 Expression index = popForValue();
1692 var receiver = pop(); 1701 var receiver = pop();
1693 if (receiver is ThisAccessor && receiver.isSuper) { 1702 if (receiver is ThisAccessor && receiver.isSuper) {
1694 push(new SuperIndexAccessor(this, receiver.offset, index, 1703 push(new SuperIndexAccessor(this, receiver.token, index,
1695 lookupSuperMember(indexGetName), lookupSuperMember(indexSetName))); 1704 lookupSuperMember(indexGetName), lookupSuperMember(indexSetName)));
1696 } else { 1705 } else {
1697 push(IndexAccessor.make(this, openCurlyBracket.charOffset, 1706 push(IndexAccessor.make(
1698 toValue(receiver), index, null, null)); 1707 this, openCurlyBracket, toValue(receiver), index, null, null));
1699 } 1708 }
1700 } 1709 }
1701 1710
1702 @override 1711 @override
1703 void handleUnaryPrefixExpression(Token token) { 1712 void handleUnaryPrefixExpression(Token token) {
1704 debugEvent("UnaryPrefixExpression"); 1713 debugEvent("UnaryPrefixExpression");
1705 var receiver = pop(); 1714 var receiver = pop();
1706 if (optional("!", token)) { 1715 if (optional("!", token)) {
1707 push(new Not(toValue(receiver))); 1716 push(new Not(toValue(receiver)));
1708 } else { 1717 } else {
1709 String operator = token.stringValue; 1718 String operator = token.stringValue;
1710 if (optional("-", token)) { 1719 if (optional("-", token)) {
1711 operator = "unary-"; 1720 operator = "unary-";
1712 } 1721 }
1713 if (receiver is ThisAccessor && receiver.isSuper) { 1722 if (receiver is ThisAccessor && receiver.isSuper) {
1714 push(toSuperMethodInvocation(buildMethodInvocation( 1723 push(toSuperMethodInvocation(buildMethodInvocation(
1715 new ThisExpression()..fileOffset = receiver.offset, 1724 new ThisExpression()..fileOffset = offsetForToken(receiver.token),
1716 new Name(operator), 1725 new Name(operator),
1717 new Arguments.empty(), 1726 new Arguments.empty(),
1718 token.charOffset))); 1727 token.charOffset)));
1719 } else { 1728 } else {
1720 push(buildMethodInvocation(toValue(receiver), new Name(operator), 1729 push(buildMethodInvocation(toValue(receiver), new Name(operator),
1721 new Arguments.empty(), token.charOffset)); 1730 new Arguments.empty(), token.charOffset));
1722 } 1731 }
1723 } 1732 }
1724 } 1733 }
1725 1734
(...skipping 14 matching lines...) Expand all
1740 push(wrapInvalid(toValue(accessor))); 1749 push(wrapInvalid(toValue(accessor)));
1741 } 1750 }
1742 } 1751 }
1743 1752
1744 @override 1753 @override
1745 void handleUnaryPostfixAssignmentExpression(Token token) { 1754 void handleUnaryPostfixAssignmentExpression(Token token) {
1746 debugEvent("UnaryPostfixAssignmentExpression"); 1755 debugEvent("UnaryPostfixAssignmentExpression");
1747 var accessor = pop(); 1756 var accessor = pop();
1748 if (accessor is FastaAccessor) { 1757 if (accessor is FastaAccessor) {
1749 push(new DelayedPostfixIncrement( 1758 push(new DelayedPostfixIncrement(
1750 this, token.charOffset, accessor, incrementOperator(token), null)); 1759 this, token, accessor, incrementOperator(token), null));
1751 } else { 1760 } else {
1752 push(wrapInvalid(toValue(accessor))); 1761 push(wrapInvalid(toValue(accessor)));
1753 } 1762 }
1754 } 1763 }
1755 1764
1756 @override 1765 @override
1757 void endConstructorReference( 1766 void endConstructorReference(
1758 Token start, Token periodBeforeName, Token endToken) { 1767 Token start, Token periodBeforeName, Token endToken) {
1759 debugEvent("ConstructorReference"); 1768 debugEvent("ConstructorReference");
1760 // A constructor reference can contain up to three identifiers: 1769 // A constructor reference can contain up to three identifiers:
(...skipping 16 matching lines...) Expand all
1777 // ClassBuilder, or a ThisPropertyAccessor. Otherwise, it's an error that 1786 // ClassBuilder, or a ThisPropertyAccessor. Otherwise, it's an error that
1778 // should be handled later. 1787 // should be handled later.
1779 Identifier suffix = popIfNotNull(periodBeforeName); 1788 Identifier suffix = popIfNotNull(periodBeforeName);
1780 Identifier identifier; 1789 Identifier identifier;
1781 List<DartType> typeArguments = pop(); 1790 List<DartType> typeArguments = pop();
1782 dynamic type = pop(); 1791 dynamic type = pop();
1783 if (type is List) { 1792 if (type is List) {
1784 var prefix = type[0]; 1793 var prefix = type[0];
1785 identifier = type[1]; 1794 identifier = type[1];
1786 if (prefix is PrefixBuilder) { 1795 if (prefix is PrefixBuilder) {
1787 type = scopeLookup(prefix.exports, identifier.name, start.charOffset, 1796 type = scopeLookup(prefix.exports, identifier.name, start,
1788 isQualified: true, prefix: prefix); 1797 isQualified: true, prefix: prefix);
1789 identifier = null; 1798 identifier = null;
1790 } else if (prefix is ClassBuilder) { 1799 } else if (prefix is ClassBuilder) {
1791 type = prefix; 1800 type = prefix;
1792 } else { 1801 } else {
1793 type = new Identifier(start.lexeme, start.charOffset); 1802 type = new Identifier(start);
1794 } 1803 }
1795 } 1804 }
1796 String name; 1805 String name;
1797 if (identifier != null && suffix != null) { 1806 if (identifier != null && suffix != null) {
1798 name = "${identifier.name}.${suffix.name}"; 1807 name = "${identifier.name}.${suffix.name}";
1799 } else if (identifier != null) { 1808 } else if (identifier != null) {
1800 name = identifier.name; 1809 name = identifier.name;
1801 } else if (suffix != null) { 1810 } else if (suffix != null) {
1802 name = suffix.name; 1811 name = suffix.name;
1803 } else { 1812 } else {
(...skipping 163 matching lines...) Expand 10 before | Expand all | Expand 10 after
1967 @override 1976 @override
1968 void endTypeArguments(int count, Token beginToken, Token endToken) { 1977 void endTypeArguments(int count, Token beginToken, Token endToken) {
1969 debugEvent("TypeArguments"); 1978 debugEvent("TypeArguments");
1970 push(popList(count)); 1979 push(popList(count));
1971 } 1980 }
1972 1981
1973 @override 1982 @override
1974 void handleThisExpression(Token token, IdentifierContext context) { 1983 void handleThisExpression(Token token, IdentifierContext context) {
1975 debugEvent("ThisExpression"); 1984 debugEvent("ThisExpression");
1976 if (context.isScopeReference && isInstanceContext) { 1985 if (context.isScopeReference && isInstanceContext) {
1977 push(new ThisAccessor(this, token.charOffset, inInitializer)); 1986 push(new ThisAccessor(this, token, inInitializer));
1978 } else { 1987 } else {
1979 push(new IncompleteError( 1988 push(new IncompleteError(
1980 this, token.charOffset, "Expected identifier, but got 'this'.")); 1989 this, token, "Expected identifier, but got 'this'."));
1981 } 1990 }
1982 } 1991 }
1983 1992
1984 @override 1993 @override
1985 void handleSuperExpression(Token token, IdentifierContext context) { 1994 void handleSuperExpression(Token token, IdentifierContext context) {
1986 debugEvent("SuperExpression"); 1995 debugEvent("SuperExpression");
1987 if (context.isScopeReference && isInstanceContext) { 1996 if (context.isScopeReference && isInstanceContext) {
1988 Member member = this.member.target; 1997 Member member = this.member.target;
1989 member.transformerFlags |= TransformerFlag.superCalls; 1998 member.transformerFlags |= TransformerFlag.superCalls;
1990 push(new ThisAccessor(this, token.charOffset, inInitializer, 1999 push(new ThisAccessor(this, token, inInitializer, isSuper: true));
1991 isSuper: true));
1992 } else { 2000 } else {
1993 push(new IncompleteError( 2001 push(new IncompleteError(
1994 this, token.charOffset, "Expected identifier, but got 'super'.")); 2002 this, token, "Expected identifier, but got 'super'."));
1995 } 2003 }
1996 } 2004 }
1997 2005
1998 @override 2006 @override
1999 void handleNamedArgument(Token colon) { 2007 void handleNamedArgument(Token colon) {
2000 debugEvent("NamedArgument"); 2008 debugEvent("NamedArgument");
2001 Expression value = popForValue(); 2009 Expression value = popForValue();
2002 Identifier identifier = pop(); 2010 Identifier identifier = pop();
2003 push(new NamedExpression(identifier.name, value)); 2011 push(new NamedExpression(identifier.name, value));
2004 } 2012 }
2005 2013
2006 @override 2014 @override
2007 void endFunctionName(Token beginToken, Token token) { 2015 void endFunctionName(Token beginToken, Token token) {
2008 debugEvent("FunctionName"); 2016 debugEvent("FunctionName");
2009 Identifier name = pop(); 2017 Identifier name = pop();
2010 VariableDeclaration variable = astFactory 2018 VariableDeclaration variable =
2011 .variableDeclaration(name.name, name.fileOffset, isFinal: true); 2019 astFactory.variableDeclaration(name.name, name.token, isFinal: true);
2012 push(new FunctionDeclaration( 2020 push(new FunctionDeclaration(
2013 variable, new FunctionNode(new InvalidStatement())) 2021 variable, new FunctionNode(new InvalidStatement()))
2014 ..fileOffset = beginToken.charOffset); 2022 ..fileOffset = beginToken.charOffset);
2015 scope[variable.name] = new KernelVariableBuilder( 2023 scope[variable.name] = new KernelVariableBuilder(
2016 variable, member ?? classBuilder ?? library, uri); 2024 variable, member ?? classBuilder ?? library, uri);
2017 enterLocalScope(); 2025 enterLocalScope();
2018 } 2026 }
2019 2027
2020 void enterFunction() { 2028 void enterFunction() {
2021 debugEvent("enterFunction"); 2029 debugEvent("enterFunction");
(...skipping 289 matching lines...) Expand 10 before | Expand all | Expand 10 after
2311 2319
2312 @override 2320 @override
2313 void handleSwitchCase( 2321 void handleSwitchCase(
2314 int labelCount, 2322 int labelCount,
2315 int expressionCount, 2323 int expressionCount,
2316 Token defaultKeyword, 2324 Token defaultKeyword,
2317 int statementCount, 2325 int statementCount,
2318 Token firstToken, 2326 Token firstToken,
2319 Token endToken) { 2327 Token endToken) {
2320 debugEvent("SwitchCase"); 2328 debugEvent("SwitchCase");
2321 Block block = popBlock(statementCount, firstToken.charOffset); 2329 Block block = popBlock(statementCount, firstToken);
2322 exitLocalScope(); 2330 exitLocalScope();
2323 List<Label> labels = pop(); 2331 List<Label> labels = pop();
2324 List<Expression> expressions = pop(); 2332 List<Expression> expressions = pop();
2325 List<int> expressionOffsets = <int>[]; 2333 List<int> expressionOffsets = <int>[];
2326 for (Expression expression in expressions) { 2334 for (Expression expression in expressions) {
2327 expressionOffsets.add(expression.fileOffset); 2335 expressionOffsets.add(expression.fileOffset);
2328 } 2336 }
2329 push(new SwitchCase(expressions, expressionOffsets, block, 2337 push(new SwitchCase(expressions, expressionOffsets, block,
2330 isDefault: defaultKeyword != null) 2338 isDefault: defaultKeyword != null)
2331 ..fileOffset = firstToken.charOffset); 2339 ..fileOffset = firstToken.charOffset);
(...skipping 85 matching lines...) Expand 10 before | Expand all | Expand 10 after
2417 push(compileTimeErrorInLoopOrSwitch = buildCompileTimeErrorStatement( 2425 push(compileTimeErrorInLoopOrSwitch = buildCompileTimeErrorStatement(
2418 "Target of continue must be a label.", continueKeyword.charOffset)); 2426 "Target of continue must be a label.", continueKeyword.charOffset));
2419 return; 2427 return;
2420 } 2428 }
2421 if (target == null) { 2429 if (target == null) {
2422 if (switchScope == null) { 2430 if (switchScope == null) {
2423 push(buildCompileTimeErrorStatement( 2431 push(buildCompileTimeErrorStatement(
2424 "Can't find label '$name'.", continueKeyword.next.charOffset)); 2432 "Can't find label '$name'.", continueKeyword.next.charOffset));
2425 return; 2433 return;
2426 } 2434 }
2427 switchScope.forwardDeclareLabel( 2435 switchScope.forwardDeclareLabel(identifier.name,
2428 identifier.name, target = createGotoTarget(identifier.fileOffset)); 2436 target = createGotoTarget(offsetForToken(identifier.token)));
2429 } 2437 }
2430 if (target.isGotoTarget && 2438 if (target.isGotoTarget &&
2431 target.functionNestingLevel == functionNestingLevel) { 2439 target.functionNestingLevel == functionNestingLevel) {
2432 ContinueSwitchStatement statement = new ContinueSwitchStatement(null); 2440 ContinueSwitchStatement statement = new ContinueSwitchStatement(null);
2433 target.addGoto(statement); 2441 target.addGoto(statement);
2434 push(statement); 2442 push(statement);
2435 return; 2443 return;
2436 } 2444 }
2437 } 2445 }
2438 if (target == null) { 2446 if (target == null) {
(...skipping 122 matching lines...) Expand 10 before | Expand all | Expand 10 after
2561 2569
2562 @override 2570 @override
2563 void handleOperator(Token token) { 2571 void handleOperator(Token token) {
2564 debugEvent("Operator"); 2572 debugEvent("Operator");
2565 push(new Operator(token.stringValue)..fileOffset = token.charOffset); 2573 push(new Operator(token.stringValue)..fileOffset = token.charOffset);
2566 } 2574 }
2567 2575
2568 @override 2576 @override
2569 void handleSymbolVoid(Token token) { 2577 void handleSymbolVoid(Token token) {
2570 debugEvent("SymbolVoid"); 2578 debugEvent("SymbolVoid");
2571 push(new Identifier(token.stringValue, token.charOffset)); 2579 push(new Identifier(token));
2572 } 2580 }
2573 2581
2574 dynamic addCompileTimeError(int charOffset, String message, 2582 dynamic addCompileTimeError(int charOffset, String message,
2575 {bool silent: false}) { 2583 {bool silent: false}) {
2576 // TODO(ahe): If constantExpressionRequired is set, set it to false to 2584 // TODO(ahe): If constantExpressionRequired is set, set it to false to
2577 // avoid a long list of errors. 2585 // avoid a long list of errors.
2578 return library.addCompileTimeError(charOffset, message, fileUri: uri); 2586 return library.addCompileTimeError(charOffset, message, fileUri: uri);
2579 } 2587 }
2580 2588
2581 @override 2589 @override
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after
2615 } 2623 }
2616 return expression; 2624 return expression;
2617 } 2625 }
2618 2626
2619 @override 2627 @override
2620 void debugEvent(String name) { 2628 void debugEvent(String name) {
2621 // printEvent(name); 2629 // printEvent(name);
2622 } 2630 }
2623 2631
2624 @override 2632 @override
2625 StaticGet makeStaticGet(Member readTarget, int offset) { 2633 StaticGet makeStaticGet(Member readTarget, Token token) {
2626 // TODO(paulberry): only record the dependencies mandated by the top level 2634 // TODO(paulberry): only record the dependencies mandated by the top level
2627 // type inference spec. 2635 // type inference spec.
2628 if (fieldDependencies != null && readTarget is KernelField) { 2636 if (fieldDependencies != null && readTarget is KernelField) {
2629 var fieldNode = _typeInferrer.getFieldNodeForReadTarget(readTarget); 2637 var fieldNode = _typeInferrer.getFieldNodeForReadTarget(readTarget);
2630 if (fieldNode != null) { 2638 if (fieldNode != null) {
2631 fieldDependencies.add(fieldNode); 2639 fieldDependencies.add(fieldNode);
2632 } 2640 }
2633 } 2641 }
2634 return astFactory.staticGet(readTarget, offset); 2642 return astFactory.staticGet(readTarget, token);
2635 } 2643 }
2636 } 2644 }
2637 2645
2638 // TODO(ahe): Shouldn't need to be an expression. 2646 class Identifier {
ahe 2017/04/25 17:39:59 Could remove the superclass in a separate CL?
Paul Berry 2017/04/25 22:00:55 Ok, I will do so before landing this CL.
2639 class Identifier extends InvalidExpression { 2647 final Token token;
2640 final String name; 2648 String get name => token.lexeme;
2641 2649
2642 Identifier(this.name, int charOffset) { 2650 Identifier(this.token);
2643 fileOffset = charOffset;
2644 }
2645 2651
2646 Expression get initializer => null; 2652 Expression get initializer => null;
2647 2653
2648 String toString() => "identifier($name)"; 2654 String toString() => "identifier($name)";
2649 } 2655 }
2650 2656
2651 // TODO(ahe): Shouldn't need to be an expression. 2657 // TODO(ahe): Shouldn't need to be an expression.
2652 class Operator extends InvalidExpression { 2658 class Operator extends InvalidExpression {
2653 final String name; 2659 final String name;
2654 2660
2655 Operator(this.name); 2661 Operator(this.name);
2656 2662
2657 String toString() => "operator($name)"; 2663 String toString() => "operator($name)";
2658 } 2664 }
2659 2665
2660 class InitializedIdentifier extends Identifier { 2666 class InitializedIdentifier extends Identifier {
2661 final Expression initializer; 2667 final Expression initializer;
2662 2668
2663 InitializedIdentifier(String name, this.initializer, int charOffset) 2669 InitializedIdentifier(Token token, this.initializer) : super(token);
2664 : super(name, charOffset);
2665 2670
2666 String toString() => "initialized-identifier($name, $initializer)"; 2671 String toString() => "initialized-identifier($name, $initializer)";
2667 } 2672 }
2668 2673
2669 // TODO(ahe): Shouldn't need to be an expression. 2674 // TODO(ahe): Shouldn't need to be an expression.
2670 class Label extends InvalidExpression { 2675 class Label extends InvalidExpression {
2671 String name; 2676 String name;
2672 2677
2673 Label(this.name); 2678 Label(this.name);
2674 2679
(...skipping 26 matching lines...) Expand all
2701 nextCascade.variable.initializer = expression; 2706 nextCascade.variable.initializer = expression;
2702 expression.parent = nextCascade.variable; 2707 expression.parent = nextCascade.variable;
2703 } 2708 }
2704 } 2709 }
2705 2710
2706 abstract class ContextAccessor extends FastaAccessor { 2711 abstract class ContextAccessor extends FastaAccessor {
2707 final BuilderHelper helper; 2712 final BuilderHelper helper;
2708 2713
2709 final FastaAccessor accessor; 2714 final FastaAccessor accessor;
2710 2715
2711 final int offset; 2716 final Token token;
2712 2717
2713 ContextAccessor(this.helper, this.offset, this.accessor); 2718 ContextAccessor(this.helper, this.token, this.accessor);
2714 2719
2715 @override 2720 @override
2716 Expression get builtBinary => internalError("Unsupported operation."); 2721 Expression get builtBinary => internalError("Unsupported operation.");
2717 2722
2718 @override 2723 @override
2719 void set builtBinary(Expression expression) { 2724 void set builtBinary(Expression expression) {
2720 internalError("Unsupported operation."); 2725 internalError("Unsupported operation.");
2721 } 2726 }
2722 2727
2723 @override 2728 @override
(...skipping 41 matching lines...) Expand 10 before | Expand all | Expand 10 after
2765 {int offset: TreeNode.noOffset, 2770 {int offset: TreeNode.noOffset,
2766 bool voidContext: false, 2771 bool voidContext: false,
2767 Procedure interfaceTarget}) { 2772 Procedure interfaceTarget}) {
2768 return makeInvalidWrite(null); 2773 return makeInvalidWrite(null);
2769 } 2774 }
2770 2775
2771 makeInvalidRead() => internalError("not supported"); 2776 makeInvalidRead() => internalError("not supported");
2772 2777
2773 Expression makeInvalidWrite(Expression value) { 2778 Expression makeInvalidWrite(Expression value) {
2774 return helper.buildCompileTimeError( 2779 return helper.buildCompileTimeError(
2775 "Can't be used as left-hand side of assignment.", offset); 2780 "Can't be used as left-hand side of assignment.",
2781 offsetForToken(token));
2776 } 2782 }
2777 } 2783 }
2778 2784
2779 class DelayedAssignment extends ContextAccessor { 2785 class DelayedAssignment extends ContextAccessor {
2780 final Expression value; 2786 final Expression value;
2781 2787
2782 final String assignmentOperator; 2788 final String assignmentOperator;
2783 2789
2784 DelayedAssignment(BuilderHelper helper, int charOffset, 2790 DelayedAssignment(BuilderHelper helper, Token token, FastaAccessor accessor,
2785 FastaAccessor accessor, this.value, this.assignmentOperator) 2791 this.value, this.assignmentOperator)
2786 : super(helper, charOffset, accessor); 2792 : super(helper, token, accessor);
2787 2793
2788 Expression buildSimpleRead() { 2794 Expression buildSimpleRead() {
2789 return handleAssignment(false); 2795 return handleAssignment(false);
2790 } 2796 }
2791 2797
2792 Expression buildForEffect() { 2798 Expression buildForEffect() {
2793 return handleAssignment(true); 2799 return handleAssignment(true);
2794 } 2800 }
2795 2801
2796 Expression handleAssignment(bool voidContext) { 2802 Expression handleAssignment(bool voidContext) {
2797 if (identical("=", assignmentOperator)) { 2803 if (identical("=", assignmentOperator)) {
2798 return accessor.buildAssignment(value, voidContext: voidContext); 2804 return accessor.buildAssignment(value, voidContext: voidContext);
2799 } else if (identical("+=", assignmentOperator)) { 2805 } else if (identical("+=", assignmentOperator)) {
2800 return accessor.buildCompoundAssignment(plusName, value, 2806 return accessor.buildCompoundAssignment(plusName, value,
2801 offset: offset, voidContext: voidContext); 2807 offset: offsetForToken(token), voidContext: voidContext);
2802 } else if (identical("-=", assignmentOperator)) { 2808 } else if (identical("-=", assignmentOperator)) {
2803 return accessor.buildCompoundAssignment(minusName, value, 2809 return accessor.buildCompoundAssignment(minusName, value,
2804 offset: offset, voidContext: voidContext); 2810 offset: offsetForToken(token), voidContext: voidContext);
2805 } else if (identical("*=", assignmentOperator)) { 2811 } else if (identical("*=", assignmentOperator)) {
2806 return accessor.buildCompoundAssignment(multiplyName, value, 2812 return accessor.buildCompoundAssignment(multiplyName, value,
2807 offset: offset, voidContext: voidContext); 2813 offset: offsetForToken(token), voidContext: voidContext);
2808 } else if (identical("%=", assignmentOperator)) { 2814 } else if (identical("%=", assignmentOperator)) {
2809 return accessor.buildCompoundAssignment(percentName, value, 2815 return accessor.buildCompoundAssignment(percentName, value,
2810 offset: offset, voidContext: voidContext); 2816 offset: offsetForToken(token), voidContext: voidContext);
2811 } else if (identical("&=", assignmentOperator)) { 2817 } else if (identical("&=", assignmentOperator)) {
2812 return accessor.buildCompoundAssignment(ampersandName, value, 2818 return accessor.buildCompoundAssignment(ampersandName, value,
2813 offset: offset, voidContext: voidContext); 2819 offset: offsetForToken(token), voidContext: voidContext);
2814 } else if (identical("/=", assignmentOperator)) { 2820 } else if (identical("/=", assignmentOperator)) {
2815 return accessor.buildCompoundAssignment(divisionName, value, 2821 return accessor.buildCompoundAssignment(divisionName, value,
2816 offset: offset, voidContext: voidContext); 2822 offset: offsetForToken(token), voidContext: voidContext);
2817 } else if (identical("<<=", assignmentOperator)) { 2823 } else if (identical("<<=", assignmentOperator)) {
2818 return accessor.buildCompoundAssignment(leftShiftName, value, 2824 return accessor.buildCompoundAssignment(leftShiftName, value,
2819 offset: offset, voidContext: voidContext); 2825 offset: offsetForToken(token), voidContext: voidContext);
2820 } else if (identical(">>=", assignmentOperator)) { 2826 } else if (identical(">>=", assignmentOperator)) {
2821 return accessor.buildCompoundAssignment(rightShiftName, value, 2827 return accessor.buildCompoundAssignment(rightShiftName, value,
2822 offset: offset, voidContext: voidContext); 2828 offset: offsetForToken(token), voidContext: voidContext);
2823 } else if (identical("??=", assignmentOperator)) { 2829 } else if (identical("??=", assignmentOperator)) {
2824 return accessor.buildNullAwareAssignment(value, const DynamicType(), 2830 return accessor.buildNullAwareAssignment(value, const DynamicType(),
2825 voidContext: voidContext); 2831 voidContext: voidContext);
2826 } else if (identical("^=", assignmentOperator)) { 2832 } else if (identical("^=", assignmentOperator)) {
2827 return accessor.buildCompoundAssignment(caretName, value, 2833 return accessor.buildCompoundAssignment(caretName, value,
2828 offset: offset, voidContext: voidContext); 2834 offset: offsetForToken(token), voidContext: voidContext);
2829 } else if (identical("|=", assignmentOperator)) { 2835 } else if (identical("|=", assignmentOperator)) {
2830 return accessor.buildCompoundAssignment(barName, value, 2836 return accessor.buildCompoundAssignment(barName, value,
2831 offset: offset, voidContext: voidContext); 2837 offset: offsetForToken(token), voidContext: voidContext);
2832 } else if (identical("~/=", assignmentOperator)) { 2838 } else if (identical("~/=", assignmentOperator)) {
2833 return accessor.buildCompoundAssignment(mustacheName, value, 2839 return accessor.buildCompoundAssignment(mustacheName, value,
2834 offset: offset, voidContext: voidContext); 2840 offset: offsetForToken(token), voidContext: voidContext);
2835 } else { 2841 } else {
2836 return internalError("Unhandled: $assignmentOperator"); 2842 return internalError("Unhandled: $assignmentOperator");
2837 } 2843 }
2838 } 2844 }
2839 2845
2840 Initializer buildFieldInitializer( 2846 Initializer buildFieldInitializer(
2841 Map<String, FieldInitializer> initializers) { 2847 Map<String, FieldInitializer> initializers) {
2842 if (!identical("=", assignmentOperator) || 2848 if (!identical("=", assignmentOperator) ||
2843 !accessor.isThisPropertyAccessor) { 2849 !accessor.isThisPropertyAccessor) {
2844 return accessor.buildFieldInitializer(initializers); 2850 return accessor.buildFieldInitializer(initializers);
2845 } 2851 }
2846 String name = accessor.plainNameForRead; 2852 String name = accessor.plainNameForRead;
2847 FieldInitializer initializer = initializers[name]; 2853 FieldInitializer initializer = initializers[name];
2848 if (initializer != null && initializer.value == null) { 2854 if (initializer != null && initializer.value == null) {
2849 initializers.remove(name); 2855 initializers.remove(name);
2850 initializer.value = value..parent = initializer; 2856 initializer.value = value..parent = initializer;
2851 return initializer; 2857 return initializer;
2852 } 2858 }
2853 return accessor.buildFieldInitializer(initializers); 2859 return accessor.buildFieldInitializer(initializers);
2854 } 2860 }
2855 } 2861 }
2856 2862
2857 class DelayedPostfixIncrement extends ContextAccessor { 2863 class DelayedPostfixIncrement extends ContextAccessor {
2858 final Name binaryOperator; 2864 final Name binaryOperator;
2859 2865
2860 final Procedure interfaceTarget; 2866 final Procedure interfaceTarget;
2861 2867
2862 DelayedPostfixIncrement(BuilderHelper helper, int offset, 2868 DelayedPostfixIncrement(BuilderHelper helper, Token token,
2863 FastaAccessor accessor, this.binaryOperator, this.interfaceTarget) 2869 FastaAccessor accessor, this.binaryOperator, this.interfaceTarget)
2864 : super(helper, offset, accessor); 2870 : super(helper, token, accessor);
2865 2871
2866 Expression buildSimpleRead() { 2872 Expression buildSimpleRead() {
2867 return accessor.buildPostfixIncrement(binaryOperator, 2873 return accessor.buildPostfixIncrement(binaryOperator,
2868 offset: offset, voidContext: false, interfaceTarget: interfaceTarget); 2874 offset: offsetForToken(token),
2875 voidContext: false,
2876 interfaceTarget: interfaceTarget);
2869 } 2877 }
2870 2878
2871 Expression buildForEffect() { 2879 Expression buildForEffect() {
2872 return accessor.buildPostfixIncrement(binaryOperator, 2880 return accessor.buildPostfixIncrement(binaryOperator,
2873 offset: offset, voidContext: true, interfaceTarget: interfaceTarget); 2881 offset: offsetForToken(token),
2882 voidContext: true,
2883 interfaceTarget: interfaceTarget);
2874 } 2884 }
2875 } 2885 }
2876 2886
2877 class JumpTarget extends Builder { 2887 class JumpTarget extends Builder {
2878 final List<Statement> users = <Statement>[]; 2888 final List<Statement> users = <Statement>[];
2879 2889
2880 final JumpTargetKind kind; 2890 final JumpTargetKind kind;
2881 2891
2882 final int functionNestingLevel; 2892 final int functionNestingLevel;
2883 2893
(...skipping 210 matching lines...) Expand 10 before | Expand all | Expand 10 after
3094 } else if (node is PrefixBuilder) { 3104 } else if (node is PrefixBuilder) {
3095 return node.name; 3105 return node.name;
3096 } else if (node is ThisAccessor) { 3106 } else if (node is ThisAccessor) {
3097 return node.isSuper ? "super" : "this"; 3107 return node.isSuper ? "super" : "this";
3098 } else if (node is FastaAccessor) { 3108 } else if (node is FastaAccessor) {
3099 return node.plainNameForRead; 3109 return node.plainNameForRead;
3100 } else { 3110 } else {
3101 return internalError("Unhandled: ${node.runtimeType}"); 3111 return internalError("Unhandled: ${node.runtimeType}");
3102 } 3112 }
3103 } 3113 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698