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

Side by Side Diff: pkg/analyzer/lib/src/generated/error_verifier.dart

Issue 1021083002: Clean up comments in error verifier (Closed) Base URL: https://dart.googlecode.com/svn/branches/bleeding_edge/dart
Patch Set: Created 5 years, 9 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 | Annotate | Revision Log
« no previous file with comments | « no previous file | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright (c) 2014, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2014, 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 engine.resolver.error_verifier; 5 library engine.resolver.error_verifier;
6 6
7 import "dart:math" as math; 7 import "dart:math" as math;
8 import 'dart:collection'; 8 import 'dart:collection';
9 9
10 import 'package:analyzer/src/generated/static_type_analyzer.dart'; 10 import 'package:analyzer/src/generated/static_type_analyzer.dart';
11 11
12 import 'ast.dart'; 12 import 'ast.dart';
13 import 'constant.dart'; 13 import 'constant.dart';
14 import 'element.dart'; 14 import 'element.dart';
15 import 'element_resolver.dart'; 15 import 'element_resolver.dart';
16 import 'error.dart'; 16 import 'error.dart';
17 import 'java_engine.dart'; 17 import 'java_engine.dart';
18 import 'parser.dart' show Parser, ParserErrorCode; 18 import 'parser.dart' show Parser, ParserErrorCode;
19 import 'resolver.dart'; 19 import 'resolver.dart';
20 import 'scanner.dart' as sc; 20 import 'scanner.dart' as sc;
21 import 'sdk.dart' show DartSdk, SdkLibrary; 21 import 'sdk.dart' show DartSdk, SdkLibrary;
22 import 'utilities_dart.dart'; 22 import 'utilities_dart.dart';
23 23
24 /** 24 /**
25 * Instances of the class `ErrorVerifier` traverse an AST structure looking for additional 25 * A visitor used to traverse an AST structure looking for additional errors and
26 * errors and warnings not covered by the parser and resolver. 26 * warnings not covered by the parser and resolver.
27 */ 27 */
28 class ErrorVerifier extends RecursiveAstVisitor<Object> { 28 class ErrorVerifier extends RecursiveAstVisitor<Object> {
29 /** 29 /**
30 * Static final string with value `"getter "` used in the construction of the 30 * Static final string with value `"getter "` used in the construction of the
31 * [StaticWarningCode.NON_ABSTRACT_CLASS_INHERITS_ABSTRACT_MEMBER_ONE], and si milar, error 31 * [StaticWarningCode.NON_ABSTRACT_CLASS_INHERITS_ABSTRACT_MEMBER_ONE], and
32 * code messages. 32 * similar, error code messages.
33 * 33 *
34 * See [_checkForNonAbstractClassInheritsAbstractMember]. 34 * See [_checkForNonAbstractClassInheritsAbstractMember].
35 */ 35 */
36 static String _GETTER_SPACE = "getter "; 36 static String _GETTER_SPACE = "getter ";
37 37
38 /** 38 /**
39 * Static final string with value `"setter "` used in the construction of the 39 * Static final string with value `"setter "` used in the construction of the
40 * [StaticWarningCode.NON_ABSTRACT_CLASS_INHERITS_ABSTRACT_MEMBER_ONE], and si milar, error 40 * [StaticWarningCode.NON_ABSTRACT_CLASS_INHERITS_ABSTRACT_MEMBER_ONE], and
41 * code messages. 41 * similar, error code messages.
42 * 42 *
43 * See [_checkForNonAbstractClassInheritsAbstractMember]. 43 * See [_checkForNonAbstractClassInheritsAbstractMember].
44 */ 44 */
45 static String _SETTER_SPACE = "setter "; 45 static String _SETTER_SPACE = "setter ";
46 46
47 /** 47 /**
48 * The error reporter by which errors will be reported. 48 * The error reporter by which errors will be reported.
49 */ 49 */
50 final ErrorReporter _errorReporter; 50 final ErrorReporter _errorReporter;
51 51
(...skipping 16 matching lines...) Expand all
68 * The object providing access to the types defined by the language. 68 * The object providing access to the types defined by the language.
69 */ 69 */
70 final TypeProvider _typeProvider; 70 final TypeProvider _typeProvider;
71 71
72 /** 72 /**
73 * The manager for the inheritance mappings. 73 * The manager for the inheritance mappings.
74 */ 74 */
75 final InheritanceManager _inheritanceManager; 75 final InheritanceManager _inheritanceManager;
76 76
77 /** 77 /**
78 * This is set to `true` iff the visitor is currently visiting children nodes of a 78 * A flag indicating whether the visitor is currently within a constructor
79 * [ConstructorDeclaration] and the constructor is 'const'. 79 * declaration that is 'const'.
80 * 80 *
81 * See [visitConstructorDeclaration]. 81 * See [visitConstructorDeclaration].
82 */ 82 */
83 bool _isEnclosingConstructorConst = false; 83 bool _isEnclosingConstructorConst = false;
84 84
85 /** 85 /**
86 * A flag indicating whether we are currently within a function body marked as being asynchronous. 86 * A flag indicating whether we are currently within a function body marked as
87 * being asynchronous.
87 */ 88 */
88 bool _inAsync = false; 89 bool _inAsync = false;
89 90
90 /** 91 /**
91 * A flag indicating whether we are currently within a function body marked as being a generator. 92 * A flag indicating whether we are currently within a function body marked a
93 * being a generator.
92 */ 94 */
93 bool _inGenerator = false; 95 bool _inGenerator = false;
94 96
95 /** 97 /**
96 * This is set to `true` iff the visitor is currently visiting children nodes of a 98 * A flag indicating whether the visitor is currently within a catch clause.
97 * [CatchClause].
98 * 99 *
99 * See [visitCatchClause]. 100 * See [visitCatchClause].
100 */ 101 */
101 bool _isInCatchClause = false; 102 bool _isInCatchClause = false;
102 103
103 /** 104 /**
104 * This is set to `true` iff the visitor is currently visiting children nodes of an 105 * A flag indicating whether the visitor is currently within a comment.
105 * [Comment].
106 */ 106 */
107 bool _isInComment = false; 107 bool _isInComment = false;
108 108
109 /** 109 /**
110 * This is set to `true` iff the visitor is currently visiting children nodes of an 110 * A flag indicating whether the visitor is currently within an instance
111 * [InstanceCreationExpression]. 111 * creation expression.
112 */ 112 */
113 bool _isInConstInstanceCreation = false; 113 bool _isInConstInstanceCreation = false;
114 114
115 /** 115 /**
116 * This is set to `true` iff the visitor is currently visiting children nodes of a native 116 * A flag indicating whether the visitor is currently within a native class
117 * [ClassDeclaration]. 117 * declaration.
118 */ 118 */
119 bool _isInNativeClass = false; 119 bool _isInNativeClass = false;
120 120
121 /** 121 /**
122 * This is set to `true` iff the visitor is currently visiting a static variab le 122 * A flag indicating whether the visitor is currently within a static variable
123 * declaration. 123 * declaration.
124 */ 124 */
125 bool _isInStaticVariableDeclaration = false; 125 bool _isInStaticVariableDeclaration = false;
126 126
127 /** 127 /**
128 * This is set to `true` iff the visitor is currently visiting an instance var iable 128 * A flag indicating whether the visitor is currently within an instance
129 * declaration. 129 * variable declaration.
130 */ 130 */
131 bool _isInInstanceVariableDeclaration = false; 131 bool _isInInstanceVariableDeclaration = false;
132 132
133 /** 133 /**
134 * This is set to `true` iff the visitor is currently visiting an instance var iable 134 * A flag indicating whether the visitor is currently within an instance
135 * initializer. 135 * variable initializer.
136 */ 136 */
137 bool _isInInstanceVariableInitializer = false; 137 bool _isInInstanceVariableInitializer = false;
138 138
139 /** 139 /**
140 * This is set to `true` iff the visitor is currently visiting a 140 * A flag indicating whether the visitor is currently within a constructor
141 * [ConstructorInitializer]. 141 * initializer.
142 */ 142 */
143 bool _isInConstructorInitializer = false; 143 bool _isInConstructorInitializer = false;
144 144
145 /** 145 /**
146 * This is set to `true` iff the visitor is currently visiting a 146 * This is set to `true` iff the visitor is currently within a function typed
147 * [FunctionTypedFormalParameter]. 147 * formal parameter.
148 */ 148 */
149 bool _isInFunctionTypedFormalParameter = false; 149 bool _isInFunctionTypedFormalParameter = false;
150 150
151 /** 151 /**
152 * This is set to `true` iff the visitor is currently visiting a static method . By "method" 152 * A flag indicating whether the visitor is currently within a static method.
153 * here getter, setter and operator declarations are also implied since they a re all represented 153 * By "method" here getter, setter and operator declarations are also implied
154 * with a [MethodDeclaration] in the AST structure. 154 * since they are all represented with a [MethodDeclaration] in the AST
155 * structure.
155 */ 156 */
156 bool _isInStaticMethod = false; 157 bool _isInStaticMethod = false;
157 158
158 /** 159 /**
159 * This is set to `true` iff the visitor is currently visiting a factory const ructor. 160 * A flag indicating whether the visitor is currently within a factory
161 * constructor.
160 */ 162 */
161 bool _isInFactory = false; 163 bool _isInFactory = false;
162 164
163 /** 165 /**
164 * This is set to `true` iff the visitor is currently visiting code in the SDK . 166 * A flag indicating whether the visitor is currently within code in the SDK.
165 */ 167 */
166 bool _isInSystemLibrary = false; 168 bool _isInSystemLibrary = false;
167 169
168 /** 170 /**
169 * A flag indicating whether the current library contains at least one import directive with a URI 171 * A flag indicating whether the current library contains at least one import
170 * that uses the "dart-ext" scheme. 172 * directive with a URI that uses the "dart-ext" scheme.
171 */ 173 */
172 bool _hasExtUri = false; 174 bool _hasExtUri = false;
173 175
174 /** 176 /**
175 * This is set to `false` on the entry of every [BlockFunctionBody], and is re stored 177 * This is set to `false` on the entry of every [BlockFunctionBody], and is
176 * to the enclosing value on exit. The value is used in 178 * restored to the enclosing value on exit. The value is used in
177 * [checkForMixedReturns] to prevent both 179 * [_checkForMixedReturns] to prevent both
178 * [StaticWarningCode.MIXED_RETURN_TYPES] and [StaticWarningCode.RETURN_WITHOU T_VALUE] 180 * [StaticWarningCode.MIXED_RETURN_TYPES] and
179 * from being generated in the same function body. 181 * [StaticWarningCode.RETURN_WITHOUT_VALUE] from being generated in the same
182 * function body.
180 */ 183 */
181 bool _hasReturnWithoutValue = false; 184 bool _hasReturnWithoutValue = false;
182 185
183 /** 186 /**
184 * The class containing the AST nodes being visited, or `null` if we are not i n the scope of 187 * The class containing the AST nodes being visited, or `null` if we are not
185 * a class. 188 * in the scope of a class.
186 */ 189 */
187 ClassElement _enclosingClass; 190 ClassElement _enclosingClass;
188 191
189 /** 192 /**
190 * The method or function that we are currently visiting, or `null` if we are not inside a 193 * The method or function that we are currently visiting, or `null` if we are
191 * method or function. 194 * not inside a method or function.
192 */ 195 */
193 ExecutableElement _enclosingFunction; 196 ExecutableElement _enclosingFunction;
194 197
195 /** 198 /**
196 * The return statements found in the method or function that we are currently visiting that have 199 * The return statements found in the method or function that we are currently
197 * a return value. 200 * visiting that have a return value.
198 */ 201 */
199 List<ReturnStatement> _returnsWith = new List<ReturnStatement>(); 202 List<ReturnStatement> _returnsWith = new List<ReturnStatement>();
200 203
201 /** 204 /**
202 * The return statements found in the method or function that we are currently visiting that do 205 * The return statements found in the method or function that we are currently
203 * not have a return value. 206 * visiting that do not have a return value.
204 */ 207 */
205 List<ReturnStatement> _returnsWithout = new List<ReturnStatement>(); 208 List<ReturnStatement> _returnsWithout = new List<ReturnStatement>();
206 209
207 /** 210 /**
208 * This map is initialized when visiting the contents of a class declaration. If the visitor is 211 * This map is initialized when visiting the contents of a class declaration.
209 * not in an enclosing class declaration, then the map is set to `null`. 212 * If the visitor is not in an enclosing class declaration, then the map is
213 * set to `null`.
210 * 214 *
211 * When set the map maps the set of [FieldElement]s in the class to an 215 * When set the map maps the set of [FieldElement]s in the class to an
212 * [INIT_STATE.NOT_INIT] or [INIT_STATE.INIT_IN_DECLARATION]. <code>checkFor*< /code> 216 * [INIT_STATE.NOT_INIT] or [INIT_STATE.INIT_IN_DECLARATION]. The `checkFor*`
213 * methods, specifically [checkForAllFinalInitializedErrorCodes], 217 * methods, specifically [_checkForAllFinalInitializedErrorCodes], can make a
214 * can make a copy of the map to compute error code states. <code>checkFor*</c ode> methods should 218 * copy of the map to compute error code states. The `checkFor*` methods
215 * only ever make a copy, or read from this map after it has been set in 219 * should only ever make a copy, or read from this map after it has been set
216 * [visitClassDeclaration]. 220 * in [visitClassDeclaration].
217 * 221 *
218 * See [visitClassDeclaration], and [_checkForAllFinalInitializedErrorCodes]. 222 * See [visitClassDeclaration], and [_checkForAllFinalInitializedErrorCodes].
219 */ 223 */
220 HashMap<FieldElement, INIT_STATE> _initialFieldElementsMap; 224 HashMap<FieldElement, INIT_STATE> _initialFieldElementsMap;
221 225
222 /** 226 /**
223 * A table mapping name of the library to the export directive which export th is library. 227 * A table mapping name of the library to the export directive which export
228 * this library.
224 */ 229 */
225 HashMap<String, LibraryElement> _nameToExportElement = 230 HashMap<String, LibraryElement> _nameToExportElement =
226 new HashMap<String, LibraryElement>(); 231 new HashMap<String, LibraryElement>();
227 232
228 /** 233 /**
229 * A table mapping name of the library to the import directive which import th is library. 234 * A table mapping name of the library to the import directive which import
235 * this library.
230 */ 236 */
231 HashMap<String, LibraryElement> _nameToImportElement = 237 HashMap<String, LibraryElement> _nameToImportElement =
232 new HashMap<String, LibraryElement>(); 238 new HashMap<String, LibraryElement>();
233 239
234 /** 240 /**
235 * A table mapping names to the exported elements. 241 * A table mapping names to the exported elements.
236 */ 242 */
237 HashMap<String, Element> _exportedElements = new HashMap<String, Element>(); 243 HashMap<String, Element> _exportedElements = new HashMap<String, Element>();
238 244
239 /** 245 /**
240 * A set of the names of the variable initializers we are visiting now. 246 * A set of the names of the variable initializers we are visiting now.
241 */ 247 */
242 HashSet<String> _namesForReferenceToDeclaredVariableInInitializer = 248 HashSet<String> _namesForReferenceToDeclaredVariableInInitializer =
243 new HashSet<String>(); 249 new HashSet<String>();
244 250
245 /** 251 /**
246 * A list of types used by the [CompileTimeErrorCode.EXTENDS_DISALLOWED_CLASS] and 252 * A list of types used by the [CompileTimeErrorCode.EXTENDS_DISALLOWED_CLASS]
247 * [CompileTimeErrorCode.IMPLEMENTS_DISALLOWED_CLASS] error codes. 253 * and [CompileTimeErrorCode.IMPLEMENTS_DISALLOWED_CLASS] error codes.
248 */ 254 */
249 List<InterfaceType> _DISALLOWED_TYPES_TO_EXTEND_OR_IMPLEMENT; 255 List<InterfaceType> _DISALLOWED_TYPES_TO_EXTEND_OR_IMPLEMENT;
250 256
251 /** 257 /**
252 * Initialize the [ErrorVerifier] visitor. 258 * Initialize a newly created error verifier.
253 */ 259 */
254 ErrorVerifier(this._errorReporter, this._currentLibrary, this._typeProvider, 260 ErrorVerifier(this._errorReporter, this._currentLibrary, this._typeProvider,
255 this._inheritanceManager) { 261 this._inheritanceManager) {
256 this._isInSystemLibrary = _currentLibrary.source.isInSystemLibrary; 262 this._isInSystemLibrary = _currentLibrary.source.isInSystemLibrary;
257 this._hasExtUri = _currentLibrary.hasExtUri; 263 this._hasExtUri = _currentLibrary.hasExtUri;
258 _isEnclosingConstructorConst = false; 264 _isEnclosingConstructorConst = false;
259 _isInCatchClause = false; 265 _isInCatchClause = false;
260 _isInStaticVariableDeclaration = false; 266 _isInStaticVariableDeclaration = false;
261 _isInInstanceVariableDeclaration = false; 267 _isInInstanceVariableDeclaration = false;
262 _isInInstanceVariableInitializer = false; 268 _isInInstanceVariableInitializer = false;
(...skipping 170 matching lines...) Expand 10 before | Expand all | Expand 10 after
433 _isInNativeClass = false; 439 _isInNativeClass = false;
434 _initialFieldElementsMap = null; 440 _initialFieldElementsMap = null;
435 _enclosingClass = outerClass; 441 _enclosingClass = outerClass;
436 } 442 }
437 } 443 }
438 444
439 /** 445 /**
440 * Implementation of this method should be synchronized with 446 * Implementation of this method should be synchronized with
441 * [visitClassDeclaration]. 447 * [visitClassDeclaration].
442 */ 448 */
443 visitClassDeclarationIncrementally(ClassDeclaration node) { 449 void visitClassDeclarationIncrementally(ClassDeclaration node) {
444 _isInNativeClass = node.nativeClause != null; 450 _isInNativeClass = node.nativeClause != null;
445 _enclosingClass = node.element; 451 _enclosingClass = node.element;
446 // initialize initialFieldElementsMap 452 // initialize initialFieldElementsMap
447 if (_enclosingClass != null) { 453 if (_enclosingClass != null) {
448 List<FieldElement> fieldElements = _enclosingClass.fields; 454 List<FieldElement> fieldElements = _enclosingClass.fields;
449 _initialFieldElementsMap = new HashMap<FieldElement, INIT_STATE>(); 455 _initialFieldElementsMap = new HashMap<FieldElement, INIT_STATE>();
450 for (FieldElement fieldElement in fieldElements) { 456 for (FieldElement fieldElement in fieldElements) {
451 if (!fieldElement.isSynthetic) { 457 if (!fieldElement.isSynthetic) {
452 _initialFieldElementsMap[fieldElement] = fieldElement.initializer == 458 _initialFieldElementsMap[fieldElement] = fieldElement.initializer ==
453 null ? INIT_STATE.NOT_INIT : INIT_STATE.INIT_IN_DECLARATION; 459 null ? INIT_STATE.NOT_INIT : INIT_STATE.INIT_IN_DECLARATION;
(...skipping 630 matching lines...) Expand 10 before | Expand all | Expand 10 after
1084 errorCode = CompileTimeErrorCode.YIELD_EACH_IN_NON_GENERATOR; 1090 errorCode = CompileTimeErrorCode.YIELD_EACH_IN_NON_GENERATOR;
1085 } else { 1091 } else {
1086 errorCode = CompileTimeErrorCode.YIELD_IN_NON_GENERATOR; 1092 errorCode = CompileTimeErrorCode.YIELD_IN_NON_GENERATOR;
1087 } 1093 }
1088 _errorReporter.reportErrorForNode(errorCode, node); 1094 _errorReporter.reportErrorForNode(errorCode, node);
1089 } 1095 }
1090 return super.visitYieldStatement(node); 1096 return super.visitYieldStatement(node);
1091 } 1097 }
1092 1098
1093 /** 1099 /**
1094 * This verifies if the passed map literal has type arguments then there is ex actly two. 1100 * Verify that the given list of [typeArguments] contains exactly two
1101 * elements.
1095 * 1102 *
1096 * @param typeArguments the type arguments, always non-`null`
1097 * @return `true` if and only if an error code is generated on the passed node
1098 * See [StaticTypeWarningCode.EXPECTED_TWO_MAP_TYPE_ARGUMENTS]. 1103 * See [StaticTypeWarningCode.EXPECTED_TWO_MAP_TYPE_ARGUMENTS].
1099 */ 1104 */
1100 bool _checkExpectedTwoMapTypeArguments(TypeArgumentList typeArguments) { 1105 bool _checkExpectedTwoMapTypeArguments(TypeArgumentList typeArguments) {
1101 // check number of type arguments 1106 // check number of type arguments
1102 int num = typeArguments.arguments.length; 1107 int num = typeArguments.arguments.length;
1103 if (num == 2) { 1108 if (num == 2) {
1104 return false; 1109 return false;
1105 } 1110 }
1106 // report problem 1111 // report problem
1107 _errorReporter.reportErrorForNode( 1112 _errorReporter.reportErrorForNode(
1108 StaticTypeWarningCode.EXPECTED_TWO_MAP_TYPE_ARGUMENTS, typeArguments, 1113 StaticTypeWarningCode.EXPECTED_TWO_MAP_TYPE_ARGUMENTS, typeArguments,
1109 [num]); 1114 [num]);
1110 return true; 1115 return true;
1111 } 1116 }
1112 1117
1113 /** 1118 /**
1114 * This verifies that the passed constructor declaration does not violate any of the error codes 1119 * Verify that the given [constructor] declaration does not violate any of the
1115 * relating to the initialization of fields in the enclosing class. 1120 * error codes relating to the initialization of fields in the enclosing
1121 * class.
1116 * 1122 *
1117 * @param node the [ConstructorDeclaration] to evaluate
1118 * @return `true` if and only if an error code is generated on the passed node
1119 * See [_initialFieldElementsMap], 1123 * See [_initialFieldElementsMap],
1120 * [StaticWarningCode.FINAL_INITIALIZED_IN_DECLARATION_AND_CONSTRUCTOR], 1124 * [StaticWarningCode.FINAL_INITIALIZED_IN_DECLARATION_AND_CONSTRUCTOR], and
1121 * and [CompileTimeErrorCode.FINAL_INITIALIZED_MULTIPLE_TIMES]. 1125 * [CompileTimeErrorCode.FINAL_INITIALIZED_MULTIPLE_TIMES].
1122 */ 1126 */
1123 bool _checkForAllFinalInitializedErrorCodes(ConstructorDeclaration node) { 1127 bool _checkForAllFinalInitializedErrorCodes(ConstructorDeclaration node) {
1124 if (node.factoryKeyword != null || 1128 if (node.factoryKeyword != null ||
1125 node.redirectedConstructor != null || 1129 node.redirectedConstructor != null ||
1126 node.externalKeyword != null) { 1130 node.externalKeyword != null) {
1127 return false; 1131 return false;
1128 } 1132 }
1129 // Ignore if native class. 1133 // Ignore if native class.
1130 if (_isInNativeClass) { 1134 if (_isInNativeClass) {
1131 return false; 1135 return false;
(...skipping 113 matching lines...) Expand 10 before | Expand all | Expand 10 after
1245 ]); 1249 ]);
1246 } 1250 }
1247 analysisError.setProperty( 1251 analysisError.setProperty(
1248 ErrorProperty.NOT_INITIALIZED_FIELDS, notInitFinalFields); 1252 ErrorProperty.NOT_INITIALIZED_FIELDS, notInitFinalFields);
1249 _errorReporter.reportError(analysisError); 1253 _errorReporter.reportError(analysisError);
1250 } 1254 }
1251 return foundError; 1255 return foundError;
1252 } 1256 }
1253 1257
1254 /** 1258 /**
1255 * This checks the passed executable element against override-error codes. 1259 * Check the given [executableElement] against override-error codes. The
1260 * [overriddenExecutable] is the element that the executable element is
1261 * overriding. The [parameters] is the parameters of the executable element.
1262 * The [errorNameTarget] is the node to report problems on.
1256 * 1263 *
1257 * @param executableElement a non-null [ExecutableElement] to evaluate
1258 * @param overriddenExecutable the element that the executableElement is overr iding
1259 * @param parameters the parameters of the executable element
1260 * @param errorNameTarget the node to report problems on
1261 * @return `true` if and only if an error code is generated on the passed node
1262 * See [StaticWarningCode.INSTANCE_METHOD_NAME_COLLIDES_WITH_SUPERCLASS_STATIC ], 1264 * See [StaticWarningCode.INSTANCE_METHOD_NAME_COLLIDES_WITH_SUPERCLASS_STATIC ],
1263 * [CompileTimeErrorCode.INVALID_OVERRIDE_REQUIRED], 1265 * [CompileTimeErrorCode.INVALID_OVERRIDE_REQUIRED],
1264 * [CompileTimeErrorCode.INVALID_OVERRIDE_POSITIONAL], 1266 * [CompileTimeErrorCode.INVALID_OVERRIDE_POSITIONAL],
1265 * [CompileTimeErrorCode.INVALID_OVERRIDE_NAMED], 1267 * [CompileTimeErrorCode.INVALID_OVERRIDE_NAMED],
1266 * [StaticWarningCode.INVALID_GETTER_OVERRIDE_RETURN_TYPE], 1268 * [StaticWarningCode.INVALID_GETTER_OVERRIDE_RETURN_TYPE],
1267 * [StaticWarningCode.INVALID_METHOD_OVERRIDE_RETURN_TYPE], 1269 * [StaticWarningCode.INVALID_METHOD_OVERRIDE_RETURN_TYPE],
1268 * [StaticWarningCode.INVALID_METHOD_OVERRIDE_NORMAL_PARAM_TYPE], 1270 * [StaticWarningCode.INVALID_METHOD_OVERRIDE_NORMAL_PARAM_TYPE],
1269 * [StaticWarningCode.INVALID_SETTER_OVERRIDE_NORMAL_PARAM_TYPE], 1271 * [StaticWarningCode.INVALID_SETTER_OVERRIDE_NORMAL_PARAM_TYPE],
1270 * [StaticWarningCode.INVALID_METHOD_OVERRIDE_OPTIONAL_PARAM_TYPE], 1272 * [StaticWarningCode.INVALID_METHOD_OVERRIDE_OPTIONAL_PARAM_TYPE],
1271 * [StaticWarningCode.INVALID_METHOD_OVERRIDE_NAMED_PARAM_TYPE], and 1273 * [StaticWarningCode.INVALID_METHOD_OVERRIDE_NAMED_PARAM_TYPE], and
(...skipping 138 matching lines...) Expand 10 before | Expand all | Expand 10 after
1410 overridingType, 1412 overridingType,
1411 overriddenType, 1413 overriddenType,
1412 overriddenExecutable.enclosingElement.displayName 1414 overriddenExecutable.enclosingElement.displayName
1413 ]); 1415 ]);
1414 return true; 1416 return true;
1415 } 1417 }
1416 } 1418 }
1417 } 1419 }
1418 // SWC.INVALID_OVERRIDE_DIFFERENT_DEFAULT_VALUES 1420 // SWC.INVALID_OVERRIDE_DIFFERENT_DEFAULT_VALUES
1419 // 1421 //
1420 // Create three arrays: an array of the optional parameter ASTs 1422 // Create three lists: a list of the optional parameter ASTs
1421 // (FormalParameters), an array of the optional parameters elements from our 1423 // (FormalParameters), a list of the optional parameters elements from our
1422 // method, and finally an array of the optional parameter elements from the 1424 // method, and finally a list of the optional parameter elements from the
1423 // method we are overriding. 1425 // method we are overriding.
1424 // 1426 //
1425 bool foundError = false; 1427 bool foundError = false;
1426 List<AstNode> formalParameters = new List<AstNode>(); 1428 List<AstNode> formalParameters = new List<AstNode>();
1427 List<ParameterElementImpl> parameterElts = new List<ParameterElementImpl>(); 1429 List<ParameterElementImpl> parameterElts = new List<ParameterElementImpl>();
1428 List<ParameterElementImpl> overriddenParameterElts = 1430 List<ParameterElementImpl> overriddenParameterElts =
1429 new List<ParameterElementImpl>(); 1431 new List<ParameterElementImpl>();
1430 List<ParameterElement> overriddenPEs = overriddenExecutable.parameters; 1432 List<ParameterElement> overriddenPEs = overriddenExecutable.parameters;
1431 for (int i = 0; i < parameters.length; i++) { 1433 for (int i = 0; i < parameters.length; i++) {
1432 ParameterElement parameter = parameters[i]; 1434 ParameterElement parameter = parameters[i];
(...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after
1520 ]); 1522 ]);
1521 foundError = true; 1523 foundError = true;
1522 } 1524 }
1523 } 1525 }
1524 } 1526 }
1525 } 1527 }
1526 return foundError; 1528 return foundError;
1527 } 1529 }
1528 1530
1529 /** 1531 /**
1530 * This checks the passed executable element against override-error codes. Thi s method computes 1532 * Check the given [executableElement] against override-error codes. This
1531 * the passed executableElement is overriding and calls 1533 * method computes the given executableElement is overriding and calls
1532 * [checkForAllInvalidOverrideErrorCodes] 1534 * [_checkForAllInvalidOverrideErrorCodes] when the [InheritanceManager]
1533 * when the [InheritanceManager] returns a [MultiplyInheritedExecutableElement ], this 1535 * returns a [MultiplyInheritedExecutableElement], this method loops through
1534 * method loops through the array in the [MultiplyInheritedExecutableElement]. 1536 * the list in the [MultiplyInheritedExecutableElement]. The [parameters] are
1535 * 1537 * the parameters of the executable element. The [errorNameTarget] is the node
1536 * @param executableElement a non-null [ExecutableElement] to evaluate 1538 * to report problems on.
1537 * @param parameters the parameters of the executable element
1538 * @param errorNameTarget the node to report problems on
1539 * @return `true` if and only if an error code is generated on the passed node
1540 */ 1539 */
1541 bool _checkForAllInvalidOverrideErrorCodesForExecutable( 1540 bool _checkForAllInvalidOverrideErrorCodesForExecutable(
1542 ExecutableElement executableElement, List<ParameterElement> parameters, 1541 ExecutableElement executableElement, List<ParameterElement> parameters,
1543 List<AstNode> parameterLocations, SimpleIdentifier errorNameTarget) { 1542 List<AstNode> parameterLocations, SimpleIdentifier errorNameTarget) {
1544 // 1543 //
1545 // Compute the overridden executable from the InheritanceManager 1544 // Compute the overridden executable from the InheritanceManager
1546 // 1545 //
1547 List<ExecutableElement> overriddenExecutables = _inheritanceManager 1546 List<ExecutableElement> overriddenExecutables = _inheritanceManager
1548 .lookupOverrides(_enclosingClass, executableElement.name); 1547 .lookupOverrides(_enclosingClass, executableElement.name);
1549 if (_checkForInstanceMethodNameCollidesWithSuperclassStatic( 1548 if (_checkForInstanceMethodNameCollidesWithSuperclassStatic(
1550 executableElement, errorNameTarget)) { 1549 executableElement, errorNameTarget)) {
1551 return true; 1550 return true;
1552 } 1551 }
1553 for (ExecutableElement overriddenElement in overriddenExecutables) { 1552 for (ExecutableElement overriddenElement in overriddenExecutables) {
1554 if (_checkForAllInvalidOverrideErrorCodes(executableElement, 1553 if (_checkForAllInvalidOverrideErrorCodes(executableElement,
1555 overriddenElement, parameters, parameterLocations, errorNameTarget)) { 1554 overriddenElement, parameters, parameterLocations, errorNameTarget)) {
1556 return true; 1555 return true;
1557 } 1556 }
1558 } 1557 }
1559 return false; 1558 return false;
1560 } 1559 }
1561 1560
1562 /** 1561 /**
1563 * This checks the passed field declaration against override-error codes. 1562 * Check the given [field] declaration against override-error codes.
1564 * 1563 *
1565 * @param node the [MethodDeclaration] to evaluate
1566 * @return `true` if and only if an error code is generated on the passed node
1567 * See [_checkForAllInvalidOverrideErrorCodes]. 1564 * See [_checkForAllInvalidOverrideErrorCodes].
1568 */ 1565 */
1569 bool _checkForAllInvalidOverrideErrorCodesForField(FieldDeclaration node) { 1566 bool _checkForAllInvalidOverrideErrorCodesForField(FieldDeclaration node) {
1570 if (_enclosingClass == null || node.isStatic) { 1567 if (_enclosingClass == null || node.isStatic) {
1571 return false; 1568 return false;
1572 } 1569 }
1573 bool hasProblems = false; 1570 bool hasProblems = false;
1574 VariableDeclarationList fields = node.fields; 1571 VariableDeclarationList fields = node.fields;
1575 for (VariableDeclaration field in fields.variables) { 1572 for (VariableDeclaration field in fields.variables) {
1576 FieldElement element = field.element as FieldElement; 1573 FieldElement element = field.element as FieldElement;
(...skipping 13 matching lines...) Expand all
1590 if (_checkForAllInvalidOverrideErrorCodesForExecutable( 1587 if (_checkForAllInvalidOverrideErrorCodesForExecutable(
1591 setter, setter.parameters, <AstNode>[fieldName], fieldName)) { 1588 setter, setter.parameters, <AstNode>[fieldName], fieldName)) {
1592 hasProblems = true; 1589 hasProblems = true;
1593 } 1590 }
1594 } 1591 }
1595 } 1592 }
1596 return hasProblems; 1593 return hasProblems;
1597 } 1594 }
1598 1595
1599 /** 1596 /**
1600 * This checks the passed method declaration against override-error codes. 1597 * Check the given [method] declaration against override-error codes.
1601 * 1598 *
1602 * @param node the [MethodDeclaration] to evaluate
1603 * @return `true` if and only if an error code is generated on the passed node
1604 * See [_checkForAllInvalidOverrideErrorCodes]. 1599 * See [_checkForAllInvalidOverrideErrorCodes].
1605 */ 1600 */
1606 bool _checkForAllInvalidOverrideErrorCodesForMethod(MethodDeclaration node) { 1601 bool _checkForAllInvalidOverrideErrorCodesForMethod(MethodDeclaration node) {
1607 if (_enclosingClass == null || 1602 if (_enclosingClass == null ||
1608 node.isStatic || 1603 node.isStatic ||
1609 node.body is NativeFunctionBody) { 1604 node.body is NativeFunctionBody) {
1610 return false; 1605 return false;
1611 } 1606 }
1612 ExecutableElement executableElement = node.element; 1607 ExecutableElement executableElement = node.element;
1613 if (executableElement == null) { 1608 if (executableElement == null) {
1614 return false; 1609 return false;
1615 } 1610 }
1616 SimpleIdentifier methodName = node.name; 1611 SimpleIdentifier methodName = node.name;
1617 if (methodName.isSynthetic) { 1612 if (methodName.isSynthetic) {
1618 return false; 1613 return false;
1619 } 1614 }
1620 FormalParameterList formalParameterList = node.parameters; 1615 FormalParameterList formalParameterList = node.parameters;
1621 NodeList<FormalParameter> parameterList = 1616 NodeList<FormalParameter> parameterList =
1622 formalParameterList != null ? formalParameterList.parameters : null; 1617 formalParameterList != null ? formalParameterList.parameters : null;
1623 List<AstNode> parameters = 1618 List<AstNode> parameters =
1624 parameterList != null ? new List.from(parameterList) : null; 1619 parameterList != null ? new List.from(parameterList) : null;
1625 return _checkForAllInvalidOverrideErrorCodesForExecutable(executableElement, 1620 return _checkForAllInvalidOverrideErrorCodesForExecutable(executableElement,
1626 executableElement.parameters, parameters, methodName); 1621 executableElement.parameters, parameters, methodName);
1627 } 1622 }
1628 1623
1629 /** 1624 /**
1630 * This verifies that all classes of the passed 'with' clause are valid. 1625 * Verify that all classes of the given [withClause] are valid.
1631 * 1626 *
1632 * @param node the 'with' clause to evaluate
1633 * @return `true` if and only if an error code is generated on the passed node
1634 * See [CompileTimeErrorCode.MIXIN_DECLARES_CONSTRUCTOR], 1627 * See [CompileTimeErrorCode.MIXIN_DECLARES_CONSTRUCTOR],
1635 * [CompileTimeErrorCode.MIXIN_INHERITS_FROM_NOT_OBJECT], and 1628 * [CompileTimeErrorCode.MIXIN_INHERITS_FROM_NOT_OBJECT], and
1636 * [CompileTimeErrorCode.MIXIN_REFERENCES_SUPER]. 1629 * [CompileTimeErrorCode.MIXIN_REFERENCES_SUPER].
1637 */ 1630 */
1638 bool _checkForAllMixinErrorCodes(WithClause withClause) { 1631 bool _checkForAllMixinErrorCodes(WithClause withClause) {
1639 if (withClause == null) { 1632 if (withClause == null) {
1640 return false; 1633 return false;
1641 } 1634 }
1642 bool problemReported = false; 1635 bool problemReported = false;
1643 for (TypeName mixinName in withClause.mixinTypes) { 1636 for (TypeName mixinName in withClause.mixinTypes) {
(...skipping 18 matching lines...) Expand all
1662 } 1655 }
1663 if (_checkForMixinReferencesSuper(mixinName, mixinElement)) { 1656 if (_checkForMixinReferencesSuper(mixinName, mixinElement)) {
1664 problemReported = true; 1657 problemReported = true;
1665 } 1658 }
1666 } 1659 }
1667 } 1660 }
1668 return problemReported; 1661 return problemReported;
1669 } 1662 }
1670 1663
1671 /** 1664 /**
1672 * This checks error related to the redirected constructors. 1665 * Check for errors related to the redirected constructors.
1673 * 1666 *
1674 * @param node the constructor declaration to evaluate
1675 * @return `true` if and only if an error code is generated on the passed node
1676 * See [StaticWarningCode.REDIRECT_TO_INVALID_RETURN_TYPE], 1667 * See [StaticWarningCode.REDIRECT_TO_INVALID_RETURN_TYPE],
1677 * [StaticWarningCode.REDIRECT_TO_INVALID_FUNCTION_TYPE], and 1668 * [StaticWarningCode.REDIRECT_TO_INVALID_FUNCTION_TYPE], and
1678 * [StaticWarningCode.REDIRECT_TO_MISSING_CONSTRUCTOR]. 1669 * [StaticWarningCode.REDIRECT_TO_MISSING_CONSTRUCTOR].
1679 */ 1670 */
1680 bool _checkForAllRedirectConstructorErrorCodes(ConstructorDeclaration node) { 1671 bool _checkForAllRedirectConstructorErrorCodes(ConstructorDeclaration node) {
1681 // 1672 //
1682 // Prepare redirected constructor node 1673 // Prepare redirected constructor node
1683 // 1674 //
1684 ConstructorName redirectedConstructor = node.redirectedConstructor; 1675 ConstructorName redirectedConstructor = node.redirectedConstructor;
1685 if (redirectedConstructor == null) { 1676 if (redirectedConstructor == null) {
(...skipping 50 matching lines...) Expand 10 before | Expand all | Expand 10 after
1736 if (!redirectedType.isSubtypeOf(constructorType)) { 1727 if (!redirectedType.isSubtypeOf(constructorType)) {
1737 _errorReporter.reportErrorForNode( 1728 _errorReporter.reportErrorForNode(
1738 StaticWarningCode.REDIRECT_TO_INVALID_FUNCTION_TYPE, 1729 StaticWarningCode.REDIRECT_TO_INVALID_FUNCTION_TYPE,
1739 redirectedConstructor, [redirectedType, constructorType]); 1730 redirectedConstructor, [redirectedType, constructorType]);
1740 return true; 1731 return true;
1741 } 1732 }
1742 return false; 1733 return false;
1743 } 1734 }
1744 1735
1745 /** 1736 /**
1746 * This checks that the return statement of the form <i>return e;</i> is not i n a generative 1737 * Check that the return [statement] of the form <i>return e;</i> is not in a
1747 * constructor. 1738 * generative constructor.
1748 * 1739 *
1749 * This checks that return statements without expressions are not in a generat ive constructor and 1740 * Check that return statements without expressions are not in a generative
1750 * the return type is not assignable to `null`; that is, we don't have `return ;` if 1741 * constructor and the return type is not assignable to `null`; that is, we
1751 * the enclosing method has a return type. 1742 * don't have `return;` if the enclosing method has a return type.
1752 * 1743 *
1753 * This checks that the return type matches the type of the declared return ty pe in the enclosing 1744 * Check that the return type matches the type of the declared return type in
1754 * method or function. 1745 * the enclosing method or function.
1755 * 1746 *
1756 * @param node the return statement to evaluate
1757 * @return `true` if and only if an error code is generated on the passed node
1758 * See [CompileTimeErrorCode.RETURN_IN_GENERATIVE_CONSTRUCTOR], 1747 * See [CompileTimeErrorCode.RETURN_IN_GENERATIVE_CONSTRUCTOR],
1759 * [StaticWarningCode.RETURN_WITHOUT_VALUE], and 1748 * [StaticWarningCode.RETURN_WITHOUT_VALUE], and
1760 * [StaticTypeWarningCode.RETURN_OF_INVALID_TYPE]. 1749 * [StaticTypeWarningCode.RETURN_OF_INVALID_TYPE].
1761 */ 1750 */
1762 bool _checkForAllReturnStatementErrorCodes(ReturnStatement node) { 1751 bool _checkForAllReturnStatementErrorCodes(ReturnStatement node) {
1763 FunctionType functionType = 1752 FunctionType functionType =
1764 _enclosingFunction == null ? null : _enclosingFunction.type; 1753 _enclosingFunction == null ? null : _enclosingFunction.type;
1765 DartType expectedReturnType = functionType == null 1754 DartType expectedReturnType = functionType == null
1766 ? DynamicTypeImpl.instance 1755 ? DynamicTypeImpl.instance
1767 : functionType.returnType; 1756 : functionType.returnType;
(...skipping 24 matching lines...) Expand all
1792 } else if (_inGenerator) { 1781 } else if (_inGenerator) {
1793 // RETURN_IN_GENERATOR 1782 // RETURN_IN_GENERATOR
1794 _errorReporter.reportErrorForNode( 1783 _errorReporter.reportErrorForNode(
1795 CompileTimeErrorCode.RETURN_IN_GENERATOR, node); 1784 CompileTimeErrorCode.RETURN_IN_GENERATOR, node);
1796 } 1785 }
1797 // RETURN_OF_INVALID_TYPE 1786 // RETURN_OF_INVALID_TYPE
1798 return _checkForReturnOfInvalidType(returnExpression, expectedReturnType); 1787 return _checkForReturnOfInvalidType(returnExpression, expectedReturnType);
1799 } 1788 }
1800 1789
1801 /** 1790 /**
1802 * This verifies that the export namespace of the passed export directive does not export any name 1791 * Verify that the export namespace of the given export [directive] does not
1803 * already exported by other export directive. 1792 * export any name already exported by another export directive. The
1793 * [exportElement] is the [ExportElement] retrieved from the node. If the
1794 * element in the node was `null`, then this method is not called. The
1795 * [exportedLibrary] is the library element containing the exported element.
1804 * 1796 *
1805 * @param node the export directive node to report problem on
1806 * @param exportElement the [ExportElement] retrieved from the node, if the el ement in the
1807 * node was `null`, then this method is not called
1808 * @param exportedLibrary the library element containing the exported element
1809 * @return `true` if and only if an error code is generated on the passed node
1810 * See [CompileTimeErrorCode.AMBIGUOUS_EXPORT]. 1797 * See [CompileTimeErrorCode.AMBIGUOUS_EXPORT].
1811 */ 1798 */
1812 bool _checkForAmbiguousExport(ExportDirective node, 1799 bool _checkForAmbiguousExport(ExportDirective node,
1813 ExportElement exportElement, LibraryElement exportedLibrary) { 1800 ExportElement exportElement, LibraryElement exportedLibrary) {
1814 if (exportedLibrary == null) { 1801 if (exportedLibrary == null) {
1815 return false; 1802 return false;
1816 } 1803 }
1817 // check exported names 1804 // check exported names
1818 Namespace namespace = 1805 Namespace namespace =
1819 new NamespaceBuilder().createExportNamespaceForDirective(exportElement); 1806 new NamespaceBuilder().createExportNamespaceForDirective(exportElement);
(...skipping 10 matching lines...) Expand all
1830 ]); 1817 ]);
1831 return true; 1818 return true;
1832 } else { 1819 } else {
1833 _exportedElements[name] = element; 1820 _exportedElements[name] = element;
1834 } 1821 }
1835 } 1822 }
1836 return false; 1823 return false;
1837 } 1824 }
1838 1825
1839 /** 1826 /**
1840 * This verifies that the passed expression can be assigned to its correspondi ng parameters. 1827 * Verify that the given [expression] can be assigned to its corresponding
1828 * parameters. The [expectedStaticType] is the expected static type of the
1829 * parameter. The [actualStaticType] is the actual static type of the
1830 * argument. The [expectedPropagatedType] is the expected propagated type of
1831 * the parameter, may be `null`. The [actualPropagatedType] is the expected
1832 * propagated type of the parameter, may be `null`.
1841 * 1833 *
1842 * This method corresponds to BestPracticesVerifier.checkForArgumentTypeNotAss ignable. 1834 * This method corresponds to
1835 * [BestPracticesVerifier.checkForArgumentTypeNotAssignable].
1843 * 1836 *
1844 * @param expression the expression to evaluate
1845 * @param expectedStaticType the expected static type of the parameter
1846 * @param actualStaticType the actual static type of the argument
1847 * @param expectedPropagatedType the expected propagated type of the parameter , may be
1848 * `null`
1849 * @param actualPropagatedType the expected propagated type of the parameter, may be `null`
1850 * @return `true` if and only if an error code is generated on the passed node
1851 * See [StaticWarningCode.ARGUMENT_TYPE_NOT_ASSIGNABLE], 1837 * See [StaticWarningCode.ARGUMENT_TYPE_NOT_ASSIGNABLE],
1852 * [CompileTimeErrorCode.LIST_ELEMENT_TYPE_NOT_ASSIGNABLE], 1838 * [CompileTimeErrorCode.LIST_ELEMENT_TYPE_NOT_ASSIGNABLE],
1853 * [StaticWarningCode.LIST_ELEMENT_TYPE_NOT_ASSIGNABLE], 1839 * [StaticWarningCode.LIST_ELEMENT_TYPE_NOT_ASSIGNABLE],
1854 * [CompileTimeErrorCode.MAP_KEY_TYPE_NOT_ASSIGNABLE], 1840 * [CompileTimeErrorCode.MAP_KEY_TYPE_NOT_ASSIGNABLE],
1855 * [CompileTimeErrorCode.MAP_VALUE_TYPE_NOT_ASSIGNABLE], 1841 * [CompileTimeErrorCode.MAP_VALUE_TYPE_NOT_ASSIGNABLE],
1856 * [StaticWarningCode.MAP_KEY_TYPE_NOT_ASSIGNABLE], and 1842 * [StaticWarningCode.MAP_KEY_TYPE_NOT_ASSIGNABLE], and
1857 * [StaticWarningCode.MAP_VALUE_TYPE_NOT_ASSIGNABLE]. 1843 * [StaticWarningCode.MAP_VALUE_TYPE_NOT_ASSIGNABLE].
1858 */ 1844 */
1859 bool _checkForArgumentTypeNotAssignable(Expression expression, 1845 bool _checkForArgumentTypeNotAssignable(Expression expression,
1860 DartType expectedStaticType, DartType actualStaticType, 1846 DartType expectedStaticType, DartType actualStaticType,
1861 ErrorCode errorCode) { 1847 ErrorCode errorCode) {
1862 // 1848 //
1863 // Warning case: test static type information 1849 // Warning case: test static type information
1864 // 1850 //
1865 if (actualStaticType != null && expectedStaticType != null) { 1851 if (actualStaticType != null && expectedStaticType != null) {
1866 if (!actualStaticType.isAssignableTo(expectedStaticType)) { 1852 if (!actualStaticType.isAssignableTo(expectedStaticType)) {
1867 _errorReporter.reportTypeErrorForNode( 1853 _errorReporter.reportTypeErrorForNode(
1868 errorCode, expression, [actualStaticType, expectedStaticType]); 1854 errorCode, expression, [actualStaticType, expectedStaticType]);
1869 return true; 1855 return true;
1870 } 1856 }
1871 } 1857 }
1872 return false; 1858 return false;
1873 } 1859 }
1874 1860
1875 /** 1861 /**
1876 * This verifies that the passed argument can be assigned to its corresponding parameter. 1862 * Verify that the given [argument] can be assigned to its corresponding
1863 * parameter.
1877 * 1864 *
1878 * This method corresponds to BestPracticesVerifier.checkForArgumentTypeNotAss ignableForArgument. 1865 * This method corresponds to
1866 * [BestPracticesVerifier.checkForArgumentTypeNotAssignableForArgument].
1879 * 1867 *
1880 * @param argument the argument to evaluate
1881 * @return `true` if and only if an error code is generated on the passed node
1882 * See [StaticWarningCode.ARGUMENT_TYPE_NOT_ASSIGNABLE]. 1868 * See [StaticWarningCode.ARGUMENT_TYPE_NOT_ASSIGNABLE].
1883 */ 1869 */
1884 bool _checkForArgumentTypeNotAssignableForArgument(Expression argument) { 1870 bool _checkForArgumentTypeNotAssignableForArgument(Expression argument) {
1885 if (argument == null) { 1871 if (argument == null) {
1886 return false; 1872 return false;
1887 } 1873 }
1888 ParameterElement staticParameterElement = argument.staticParameterElement; 1874 ParameterElement staticParameterElement = argument.staticParameterElement;
1889 DartType staticParameterType = 1875 DartType staticParameterType =
1890 staticParameterElement == null ? null : staticParameterElement.type; 1876 staticParameterElement == null ? null : staticParameterElement.type;
1891 return _checkForArgumentTypeNotAssignableWithExpectedTypes(argument, 1877 return _checkForArgumentTypeNotAssignableWithExpectedTypes(argument,
1892 staticParameterType, StaticWarningCode.ARGUMENT_TYPE_NOT_ASSIGNABLE); 1878 staticParameterType, StaticWarningCode.ARGUMENT_TYPE_NOT_ASSIGNABLE);
1893 } 1879 }
1894 1880
1895 /** 1881 /**
1896 * This verifies that the passed expression can be assigned to its correspondi ng parameters. 1882 * Verify that the given [expression] can be assigned to its corresponding
1883 * parameters. The [expectedStaticType] is the expected static type. The
1884 * [expectedPropagatedType] is the expected propagated type, may be `null`.
1897 * 1885 *
1898 * This method corresponds to 1886 * This method corresponds to
1899 * BestPracticesVerifier.checkForArgumentTypeNotAssignableWithExpectedTypes. 1887 * [BestPracticesVerifier.checkForArgumentTypeNotAssignableWithExpectedTypes].
1900 * 1888 *
1901 * @param expression the expression to evaluate
1902 * @param expectedStaticType the expected static type
1903 * @param expectedPropagatedType the expected propagated type, may be `null`
1904 * @return `true` if and only if an error code is generated on the passed node
1905 * See [StaticWarningCode.ARGUMENT_TYPE_NOT_ASSIGNABLE], 1889 * See [StaticWarningCode.ARGUMENT_TYPE_NOT_ASSIGNABLE],
1906 * [CompileTimeErrorCode.LIST_ELEMENT_TYPE_NOT_ASSIGNABLE], 1890 * [CompileTimeErrorCode.LIST_ELEMENT_TYPE_NOT_ASSIGNABLE],
1907 * [StaticWarningCode.LIST_ELEMENT_TYPE_NOT_ASSIGNABLE], 1891 * [StaticWarningCode.LIST_ELEMENT_TYPE_NOT_ASSIGNABLE],
1908 * [CompileTimeErrorCode.MAP_KEY_TYPE_NOT_ASSIGNABLE], 1892 * [CompileTimeErrorCode.MAP_KEY_TYPE_NOT_ASSIGNABLE],
1909 * [CompileTimeErrorCode.MAP_VALUE_TYPE_NOT_ASSIGNABLE], 1893 * [CompileTimeErrorCode.MAP_VALUE_TYPE_NOT_ASSIGNABLE],
1910 * [StaticWarningCode.MAP_KEY_TYPE_NOT_ASSIGNABLE], and 1894 * [StaticWarningCode.MAP_KEY_TYPE_NOT_ASSIGNABLE], and
1911 * [StaticWarningCode.MAP_VALUE_TYPE_NOT_ASSIGNABLE]. 1895 * [StaticWarningCode.MAP_VALUE_TYPE_NOT_ASSIGNABLE].
1912 */ 1896 */
1913 bool _checkForArgumentTypeNotAssignableWithExpectedTypes( 1897 bool _checkForArgumentTypeNotAssignableWithExpectedTypes(
1914 Expression expression, DartType expectedStaticType, 1898 Expression expression, DartType expectedStaticType,
1915 ErrorCode errorCode) => _checkForArgumentTypeNotAssignable( 1899 ErrorCode errorCode) => _checkForArgumentTypeNotAssignable(
1916 expression, expectedStaticType, getStaticType(expression), errorCode); 1900 expression, expectedStaticType, getStaticType(expression), errorCode);
1917 1901
1918 /** 1902 /**
1919 * This verifies that the passed arguments can be assigned to their correspond ing parameters. 1903 * Verify that the arguments in the given [argumentList] can be assigned to
1904 * their corresponding parameters.
1920 * 1905 *
1921 * This method corresponds to BestPracticesVerifier.checkForArgumentTypesNotAs signableInList. 1906 * This method corresponds to
1907 * [BestPracticesVerifier.checkForArgumentTypesNotAssignableInList].
1922 * 1908 *
1923 * @param node the arguments to evaluate
1924 * @return `true` if and only if an error code is generated on the passed node
1925 * See [StaticWarningCode.ARGUMENT_TYPE_NOT_ASSIGNABLE]. 1909 * See [StaticWarningCode.ARGUMENT_TYPE_NOT_ASSIGNABLE].
1926 */ 1910 */
1927 bool _checkForArgumentTypesNotAssignableInList(ArgumentList argumentList) { 1911 bool _checkForArgumentTypesNotAssignableInList(ArgumentList argumentList) {
1928 if (argumentList == null) { 1912 if (argumentList == null) {
1929 return false; 1913 return false;
1930 } 1914 }
1931 bool problemReported = false; 1915 bool problemReported = false;
1932 for (Expression argument in argumentList.arguments) { 1916 for (Expression argument in argumentList.arguments) {
1933 if (_checkForArgumentTypeNotAssignableForArgument(argument)) { 1917 if (_checkForArgumentTypeNotAssignableForArgument(argument)) {
1934 problemReported = true; 1918 problemReported = true;
1935 } 1919 }
1936 } 1920 }
1937 return problemReported; 1921 return problemReported;
1938 } 1922 }
1939 1923
1940 /** 1924 /**
1941 * Check that the static type of the given expression is assignable to the giv en type. If it 1925 * Check that the static type of the given expression is assignable to the
1942 * isn't, report an error with the given error code. 1926 * given type. If it isn't, report an error with the given error code. The
1943 * 1927 * [type] is the type that the expression must be assignable to. The
1944 * @param expression the expression being tested 1928 * [errorCode] is the error code to be reported. The [arguments] are the
1945 * @param type the type that the expression must be assignable to 1929 * arguments to pass in when creating the error.
1946 * @param errorCode the error code to be reported
1947 * @param arguments the arguments to pass in when creating the error
1948 * @return `true` if an error was reported
1949 */ 1930 */
1950 bool _checkForAssignability(Expression expression, InterfaceType type, 1931 bool _checkForAssignability(Expression expression, InterfaceType type,
1951 ErrorCode errorCode, List<Object> arguments) { 1932 ErrorCode errorCode, List<Object> arguments) {
1952 if (expression == null) { 1933 if (expression == null) {
1953 return false; 1934 return false;
1954 } 1935 }
1955 DartType expressionType = expression.staticType; 1936 DartType expressionType = expression.staticType;
1956 if (expressionType == null) { 1937 if (expressionType == null) {
1957 return false; 1938 return false;
1958 } 1939 }
1959 if (expressionType.isAssignableTo(type)) { 1940 if (expressionType.isAssignableTo(type)) {
1960 return false; 1941 return false;
1961 } 1942 }
1962 _errorReporter.reportErrorForNode(errorCode, expression, arguments); 1943 _errorReporter.reportErrorForNode(errorCode, expression, arguments);
1963 return true; 1944 return true;
1964 } 1945 }
1965 1946
1966 /** 1947 /**
1967 * This verifies that the passed expression is not final. 1948 * Verify that the given [expression] is not final.
1968 * 1949 *
1969 * @param node the expression to evaluate
1970 * @return `true` if and only if an error code is generated on the passed node
1971 * See [StaticWarningCode.ASSIGNMENT_TO_CONST], 1950 * See [StaticWarningCode.ASSIGNMENT_TO_CONST],
1972 * [StaticWarningCode.ASSIGNMENT_TO_FINAL], and 1951 * [StaticWarningCode.ASSIGNMENT_TO_FINAL], and
1973 * [StaticWarningCode.ASSIGNMENT_TO_METHOD]. 1952 * [StaticWarningCode.ASSIGNMENT_TO_METHOD].
1974 */ 1953 */
1975 bool _checkForAssignmentToFinal(Expression expression) { 1954 bool _checkForAssignmentToFinal(Expression expression) {
1976 // prepare element 1955 // prepare element
1977 Element element = null; 1956 Element element = null;
1978 AstNode highlightedNode = expression; 1957 AstNode highlightedNode = expression;
1979 if (expression is Identifier) { 1958 if (expression is Identifier) {
1980 element = expression.staticElement; 1959 element = expression.staticElement;
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after
2019 } 1998 }
2020 if (element is MethodElement) { 1999 if (element is MethodElement) {
2021 _errorReporter.reportErrorForNode( 2000 _errorReporter.reportErrorForNode(
2022 StaticWarningCode.ASSIGNMENT_TO_METHOD, expression); 2001 StaticWarningCode.ASSIGNMENT_TO_METHOD, expression);
2023 return true; 2002 return true;
2024 } 2003 }
2025 return false; 2004 return false;
2026 } 2005 }
2027 2006
2028 /** 2007 /**
2029 * This verifies that the passed identifier is not a keyword, and generates th e passed error code 2008 * Verify that the given [identifier] is not a keyword, and generates the
2030 * on the identifier if it is a keyword. 2009 * given [errorCode] on the identifier if it is a keyword.
2031 * 2010 *
2032 * @param identifier the identifier to check to ensure that it is not a keywor d
2033 * @param errorCode if the passed identifier is a keyword then this error code is created on the
2034 * identifier, the error code will be one of
2035 * [CompileTimeErrorCode.BUILT_IN_IDENTIFIER_AS_TYPE_NAME],
2036 * [CompileTimeErrorCode.BUILT_IN_IDENTIFIER_AS_TYPE_PARAMETER_NAME] or
2037 * [CompileTimeErrorCode.BUILT_IN_IDENTIFIER_AS_TYPEDEF_NAME]
2038 * @return `true` if and only if an error code is generated on the passed node
2039 * See [CompileTimeErrorCode.BUILT_IN_IDENTIFIER_AS_TYPE_NAME], 2011 * See [CompileTimeErrorCode.BUILT_IN_IDENTIFIER_AS_TYPE_NAME],
2040 * [CompileTimeErrorCode.BUILT_IN_IDENTIFIER_AS_TYPE_PARAMETER_NAME], and 2012 * [CompileTimeErrorCode.BUILT_IN_IDENTIFIER_AS_TYPE_PARAMETER_NAME], and
2041 * [CompileTimeErrorCode.BUILT_IN_IDENTIFIER_AS_TYPEDEF_NAME]. 2013 * [CompileTimeErrorCode.BUILT_IN_IDENTIFIER_AS_TYPEDEF_NAME].
2042 */ 2014 */
2043 bool _checkForBuiltInIdentifierAsName( 2015 bool _checkForBuiltInIdentifierAsName(
2044 SimpleIdentifier identifier, ErrorCode errorCode) { 2016 SimpleIdentifier identifier, ErrorCode errorCode) {
2045 sc.Token token = identifier.token; 2017 sc.Token token = identifier.token;
2046 if (token.type == sc.TokenType.KEYWORD) { 2018 if (token.type == sc.TokenType.KEYWORD) {
2047 _errorReporter.reportErrorForNode( 2019 _errorReporter.reportErrorForNode(
2048 errorCode, identifier, [identifier.name]); 2020 errorCode, identifier, [identifier.name]);
2049 return true; 2021 return true;
2050 } 2022 }
2051 return false; 2023 return false;
2052 } 2024 }
2053 2025
2054 /** 2026 /**
2055 * This verifies that the given switch case is terminated with 'break', 'conti nue', 'return' or 2027 * Verify that the given [switchCase] is terminated with 'break', 'continue',
2056 * 'throw'. 2028 * 'return' or 'throw'.
2057 * 2029 *
2058 * @param node the switch case to evaluate
2059 * @return `true` if and only if an error code is generated on the passed node
2060 * see [StaticWarningCode.CASE_BLOCK_NOT_TERMINATED]. 2030 * see [StaticWarningCode.CASE_BLOCK_NOT_TERMINATED].
2061 */ 2031 */
2062 bool _checkForCaseBlockNotTerminated(SwitchCase node) { 2032 bool _checkForCaseBlockNotTerminated(SwitchCase node) {
2063 NodeList<Statement> statements = node.statements; 2033 NodeList<Statement> statements = node.statements;
2064 if (statements.isEmpty) { 2034 if (statements.isEmpty) {
2065 // fall-through without statements at all 2035 // fall-through without statements at all
2066 AstNode parent = node.parent; 2036 AstNode parent = node.parent;
2067 if (parent is SwitchStatement) { 2037 if (parent is SwitchStatement) {
2068 SwitchStatement switchStatement = parent; 2038 SwitchStatement switchStatement = parent;
2069 NodeList<SwitchMember> members = switchStatement.members; 2039 NodeList<SwitchMember> members = switchStatement.members;
(...skipping 19 matching lines...) Expand all
2089 } 2059 }
2090 } 2060 }
2091 } 2061 }
2092 // report error 2062 // report error
2093 _errorReporter.reportErrorForToken( 2063 _errorReporter.reportErrorForToken(
2094 StaticWarningCode.CASE_BLOCK_NOT_TERMINATED, node.keyword); 2064 StaticWarningCode.CASE_BLOCK_NOT_TERMINATED, node.keyword);
2095 return true; 2065 return true;
2096 } 2066 }
2097 2067
2098 /** 2068 /**
2099 * This verifies that the switch cases in the given switch statement is termin ated with 'break', 2069 * Verify that the switch cases in the given switch [statement] are terminated
2100 * 'continue', 'return' or 'throw'. 2070 * with 'break', 'continue', 'return' or 'throw'.
2101 * 2071 *
2102 * @param node the switch statement containing the cases to be checked
2103 * @return `true` if and only if an error code is generated on the passed node
2104 * See [StaticWarningCode.CASE_BLOCK_NOT_TERMINATED]. 2072 * See [StaticWarningCode.CASE_BLOCK_NOT_TERMINATED].
2105 */ 2073 */
2106 bool _checkForCaseBlocksNotTerminated(SwitchStatement node) { 2074 bool _checkForCaseBlocksNotTerminated(SwitchStatement node) {
2107 bool foundError = false; 2075 bool foundError = false;
2108 NodeList<SwitchMember> members = node.members; 2076 NodeList<SwitchMember> members = node.members;
2109 int lastMember = members.length - 1; 2077 int lastMember = members.length - 1;
2110 for (int i = 0; i < lastMember; i++) { 2078 for (int i = 0; i < lastMember; i++) {
2111 SwitchMember member = members[i]; 2079 SwitchMember member = members[i];
2112 if (member is SwitchCase && _checkForCaseBlockNotTerminated(member)) { 2080 if (member is SwitchCase && _checkForCaseBlockNotTerminated(member)) {
2113 foundError = true; 2081 foundError = true;
2114 } 2082 }
2115 } 2083 }
2116 return foundError; 2084 return foundError;
2117 } 2085 }
2118 2086
2119 /** 2087 /**
2120 * This verifies that the passed method declaration is abstract only if the en closing class is 2088 * Verify that the given [method] declaration is abstract only if the
2121 * also abstract. 2089 * enclosing class is also abstract.
2122 * 2090 *
2123 * @param node the method declaration to evaluate
2124 * @return `true` if and only if an error code is generated on the passed node
2125 * See [StaticWarningCode.CONCRETE_CLASS_WITH_ABSTRACT_MEMBER]. 2091 * See [StaticWarningCode.CONCRETE_CLASS_WITH_ABSTRACT_MEMBER].
2126 */ 2092 */
2127 bool _checkForConcreteClassWithAbstractMember(MethodDeclaration node) { 2093 bool _checkForConcreteClassWithAbstractMember(MethodDeclaration node) {
2128 if (node.isAbstract && 2094 if (node.isAbstract &&
2129 _enclosingClass != null && 2095 _enclosingClass != null &&
2130 !_enclosingClass.isAbstract) { 2096 !_enclosingClass.isAbstract) {
2131 SimpleIdentifier nameNode = node.name; 2097 SimpleIdentifier nameNode = node.name;
2132 String memberName = nameNode.name; 2098 String memberName = nameNode.name;
2133 ExecutableElement overriddenMember; 2099 ExecutableElement overriddenMember;
2134 if (node.isGetter) { 2100 if (node.isGetter) {
(...skipping 12 matching lines...) Expand all
2147 memberName, 2113 memberName,
2148 _enclosingClass.displayName 2114 _enclosingClass.displayName
2149 ]); 2115 ]);
2150 return true; 2116 return true;
2151 } 2117 }
2152 } 2118 }
2153 return false; 2119 return false;
2154 } 2120 }
2155 2121
2156 /** 2122 /**
2157 * This verifies all possible conflicts of the constructor name with other con structors and 2123 * Verify all possible conflicts of the given [constructor]'s name with other
2158 * members of the same class. 2124 * constructors and members of the same class. The [constructorElement] is the
2125 * constructor's element.
2159 * 2126 *
2160 * @param node the constructor declaration to evaluate
2161 * @param constructorElement the constructor element
2162 * @return `true` if and only if an error code is generated on the passed node
2163 * See [CompileTimeErrorCode.DUPLICATE_CONSTRUCTOR_DEFAULT], 2127 * See [CompileTimeErrorCode.DUPLICATE_CONSTRUCTOR_DEFAULT],
2164 * [CompileTimeErrorCode.DUPLICATE_CONSTRUCTOR_NAME], 2128 * [CompileTimeErrorCode.DUPLICATE_CONSTRUCTOR_NAME],
2165 * [CompileTimeErrorCode.CONFLICTING_CONSTRUCTOR_NAME_AND_FIELD], and 2129 * [CompileTimeErrorCode.CONFLICTING_CONSTRUCTOR_NAME_AND_FIELD], and
2166 * [CompileTimeErrorCode.CONFLICTING_CONSTRUCTOR_NAME_AND_METHOD]. 2130 * [CompileTimeErrorCode.CONFLICTING_CONSTRUCTOR_NAME_AND_METHOD].
2167 */ 2131 */
2168 bool _checkForConflictingConstructorNameAndMember( 2132 bool _checkForConflictingConstructorNameAndMember(
2169 ConstructorDeclaration node, ConstructorElement constructorElement) { 2133 ConstructorDeclaration node, ConstructorElement constructorElement) {
2170 SimpleIdentifier constructorName = node.name; 2134 SimpleIdentifier constructorName = node.name;
2171 String name = constructorElement.name; 2135 String name = constructorElement.name;
2172 ClassElement classElement = constructorElement.enclosingElement; 2136 ClassElement classElement = constructorElement.enclosingElement;
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
2205 _errorReporter.reportErrorForNode( 2169 _errorReporter.reportErrorForNode(
2206 CompileTimeErrorCode.CONFLICTING_CONSTRUCTOR_NAME_AND_METHOD, node, 2170 CompileTimeErrorCode.CONFLICTING_CONSTRUCTOR_NAME_AND_METHOD, node,
2207 [name]); 2171 [name]);
2208 return true; 2172 return true;
2209 } 2173 }
2210 } 2174 }
2211 return false; 2175 return false;
2212 } 2176 }
2213 2177
2214 /** 2178 /**
2215 * This verifies that the [enclosingClass] does not have a method and getter p air with the 2179 * Verify that the [enclosingClass] does not have a method and getter pair
2216 * same name on, via inheritance. 2180 * with the same name on, via inheritance.
2217 * 2181 *
2218 * @return `true` if and only if an error code is generated on the passed node
2219 * See [CompileTimeErrorCode.CONFLICTING_GETTER_AND_METHOD], and 2182 * See [CompileTimeErrorCode.CONFLICTING_GETTER_AND_METHOD], and
2220 * [CompileTimeErrorCode.CONFLICTING_METHOD_AND_GETTER]. 2183 * [CompileTimeErrorCode.CONFLICTING_METHOD_AND_GETTER].
2221 */ 2184 */
2222 bool _checkForConflictingGetterAndMethod() { 2185 bool _checkForConflictingGetterAndMethod() {
2223 if (_enclosingClass == null) { 2186 if (_enclosingClass == null) {
2224 return false; 2187 return false;
2225 } 2188 }
2226 bool hasProblem = false; 2189 bool hasProblem = false;
2227 // method declared in the enclosing class vs. inherited getter 2190 // method declared in the enclosing class vs. inherited getter
2228 for (MethodElement method in _enclosingClass.methods) { 2191 for (MethodElement method in _enclosingClass.methods) {
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
2263 _enclosingClass.displayName, 2226 _enclosingClass.displayName,
2264 inherited.enclosingElement.displayName, 2227 inherited.enclosingElement.displayName,
2265 name 2228 name
2266 ]); 2229 ]);
2267 } 2230 }
2268 // done 2231 // done
2269 return hasProblem; 2232 return hasProblem;
2270 } 2233 }
2271 2234
2272 /** 2235 /**
2273 * This verifies that the superclass of the [enclosingClass] does not declare accessible 2236 * Verify that the superclass of the [enclosingClass] does not declare
2274 * static members with the same name as the instance getters/setters declared in 2237 * accessible static members with the same name as the instance
2275 * [enclosingClass]. 2238 * getters/setters declared in [enclosingClass].
2276 * 2239 *
2277 * @param node the method declaration to evaluate
2278 * @return `true` if and only if an error code is generated on the passed node
2279 * See [StaticWarningCode.CONFLICTING_INSTANCE_GETTER_AND_SUPERCLASS_MEMBER], and 2240 * See [StaticWarningCode.CONFLICTING_INSTANCE_GETTER_AND_SUPERCLASS_MEMBER], and
2280 * [StaticWarningCode.CONFLICTING_INSTANCE_SETTER_AND_SUPERCLASS_MEMBER]. 2241 * [StaticWarningCode.CONFLICTING_INSTANCE_SETTER_AND_SUPERCLASS_MEMBER].
2281 */ 2242 */
2282 bool _checkForConflictingInstanceGetterAndSuperclassMember() { 2243 bool _checkForConflictingInstanceGetterAndSuperclassMember() {
2283 if (_enclosingClass == null) { 2244 if (_enclosingClass == null) {
2284 return false; 2245 return false;
2285 } 2246 }
2286 InterfaceType enclosingType = _enclosingClass.type; 2247 InterfaceType enclosingType = _enclosingClass.type;
2287 // check every accessor 2248 // check every accessor
2288 bool hasProblem = false; 2249 bool hasProblem = false;
(...skipping 43 matching lines...) Expand 10 before | Expand all | Expand 10 after
2332 _errorReporter.reportErrorForElement( 2293 _errorReporter.reportErrorForElement(
2333 StaticWarningCode.CONFLICTING_INSTANCE_SETTER_AND_SUPERCLASS_MEMBER, 2294 StaticWarningCode.CONFLICTING_INSTANCE_SETTER_AND_SUPERCLASS_MEMBER,
2334 accessor, [superElementType.displayName]); 2295 accessor, [superElementType.displayName]);
2335 } 2296 }
2336 } 2297 }
2337 // done 2298 // done
2338 return hasProblem; 2299 return hasProblem;
2339 } 2300 }
2340 2301
2341 /** 2302 /**
2342 * This verifies that the enclosing class does not have a setter with the same name as the passed 2303 * Verify that the enclosing class does not have a setter with the same name
2343 * instance method declaration. 2304 * as the given instance method declaration.
2344 * 2305 *
2345 * TODO(jwren) add other "conflicting" error codes into algorithm/ data struct ure 2306 * TODO(jwren) add other "conflicting" error codes into algorithm/ data
2307 * structure.
2346 * 2308 *
2347 * @param node the method declaration to evaluate
2348 * @return `true` if and only if an error code is generated on the passed node
2349 * See [StaticWarningCode.CONFLICTING_INSTANCE_METHOD_SETTER]. 2309 * See [StaticWarningCode.CONFLICTING_INSTANCE_METHOD_SETTER].
2350 */ 2310 */
2351 bool _checkForConflictingInstanceMethodSetter(ClassDeclaration node) { 2311 bool _checkForConflictingInstanceMethodSetter(ClassDeclaration node) {
2352 // Reference all of the class members in this class. 2312 // Reference all of the class members in this class.
2353 NodeList<ClassMember> classMembers = node.members; 2313 NodeList<ClassMember> classMembers = node.members;
2354 if (classMembers.isEmpty) { 2314 if (classMembers.isEmpty) {
2355 return false; 2315 return false;
2356 } 2316 }
2357 // Create a HashMap to track conflicting members, and then loop through 2317 // Create a HashMap to track conflicting members, and then loop through
2358 // members in the class to construct the HashMap, at the same time, 2318 // members in the class to construct the HashMap, at the same time,
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after
2429 } else { 2389 } else {
2430 memberHashMap[name.name] = method; 2390 memberHashMap[name.name] = method;
2431 } 2391 }
2432 } 2392 }
2433 } 2393 }
2434 } 2394 }
2435 return foundError; 2395 return foundError;
2436 } 2396 }
2437 2397
2438 /** 2398 /**
2439 * This verifies that the enclosing class does not have an instance member wit h the same name as 2399 * Verify that the enclosing class does not have an instance member with the
2440 * the passed static getter method declaration. 2400 * same name as the given static [method] declaration.
2441 * 2401 *
2442 * @param node the method declaration to evaluate
2443 * @return `true` if and only if an error code is generated on the passed node
2444 * See [StaticWarningCode.CONFLICTING_STATIC_GETTER_AND_INSTANCE_SETTER]. 2402 * See [StaticWarningCode.CONFLICTING_STATIC_GETTER_AND_INSTANCE_SETTER].
2445 */ 2403 */
2446 bool _checkForConflictingStaticGetterAndInstanceSetter( 2404 bool _checkForConflictingStaticGetterAndInstanceSetter(
2447 MethodDeclaration node) { 2405 MethodDeclaration node) {
2448 if (!node.isStatic) { 2406 if (!node.isStatic) {
2449 return false; 2407 return false;
2450 } 2408 }
2451 // prepare name 2409 // prepare name
2452 SimpleIdentifier nameNode = node.name; 2410 SimpleIdentifier nameNode = node.name;
2453 if (nameNode == null) { 2411 if (nameNode == null) {
(...skipping 19 matching lines...) Expand all
2473 ClassElement setterClass = setter.enclosingElement as ClassElement; 2431 ClassElement setterClass = setter.enclosingElement as ClassElement;
2474 InterfaceType setterType = setterClass.type; 2432 InterfaceType setterType = setterClass.type;
2475 // report problem 2433 // report problem
2476 _errorReporter.reportErrorForNode( 2434 _errorReporter.reportErrorForNode(
2477 StaticWarningCode.CONFLICTING_STATIC_GETTER_AND_INSTANCE_SETTER, 2435 StaticWarningCode.CONFLICTING_STATIC_GETTER_AND_INSTANCE_SETTER,
2478 nameNode, [setterType.displayName]); 2436 nameNode, [setterType.displayName]);
2479 return true; 2437 return true;
2480 } 2438 }
2481 2439
2482 /** 2440 /**
2483 * This verifies that the enclosing class does not have an instance member wit h the same name as 2441 * Verify that the enclosing class does not have an instance member with the
2484 * the passed static getter method declaration. 2442 * same name as the given static [method] declaration.
2485 * 2443 *
2486 * @param node the method declaration to evaluate
2487 * @return `true` if and only if an error code is generated on the passed node
2488 * See [StaticWarningCode.CONFLICTING_STATIC_SETTER_AND_INSTANCE_MEMBER]. 2444 * See [StaticWarningCode.CONFLICTING_STATIC_SETTER_AND_INSTANCE_MEMBER].
2489 */ 2445 */
2490 bool _checkForConflictingStaticSetterAndInstanceMember( 2446 bool _checkForConflictingStaticSetterAndInstanceMember(
2491 MethodDeclaration node) { 2447 MethodDeclaration node) {
2492 if (!node.isStatic) { 2448 if (!node.isStatic) {
2493 return false; 2449 return false;
2494 } 2450 }
2495 // prepare name 2451 // prepare name
2496 SimpleIdentifier nameNode = node.name; 2452 SimpleIdentifier nameNode = node.name;
2497 if (nameNode == null) { 2453 if (nameNode == null) {
(...skipping 25 matching lines...) Expand all
2523 ClassElement memberClass = member.enclosingElement as ClassElement; 2479 ClassElement memberClass = member.enclosingElement as ClassElement;
2524 InterfaceType memberType = memberClass.type; 2480 InterfaceType memberType = memberClass.type;
2525 // report problem 2481 // report problem
2526 _errorReporter.reportErrorForNode( 2482 _errorReporter.reportErrorForNode(
2527 StaticWarningCode.CONFLICTING_STATIC_SETTER_AND_INSTANCE_MEMBER, 2483 StaticWarningCode.CONFLICTING_STATIC_SETTER_AND_INSTANCE_MEMBER,
2528 nameNode, [memberType.displayName]); 2484 nameNode, [memberType.displayName]);
2529 return true; 2485 return true;
2530 } 2486 }
2531 2487
2532 /** 2488 /**
2533 * This verifies all conflicts between type variable and enclosing class. TODO (scheglov) 2489 * Verify all conflicts between type variable and enclosing class.
2490 * TODO(scheglov)
2534 * 2491 *
2535 * @param node the class declaration to evaluate
2536 * @return `true` if and only if an error code is generated on the passed node
2537 * See [CompileTimeErrorCode.CONFLICTING_TYPE_VARIABLE_AND_CLASS], and 2492 * See [CompileTimeErrorCode.CONFLICTING_TYPE_VARIABLE_AND_CLASS], and
2538 * [CompileTimeErrorCode.CONFLICTING_TYPE_VARIABLE_AND_MEMBER]. 2493 * [CompileTimeErrorCode.CONFLICTING_TYPE_VARIABLE_AND_MEMBER].
2539 */ 2494 */
2540 bool _checkForConflictingTypeVariableErrorCodes(ClassDeclaration node) { 2495 bool _checkForConflictingTypeVariableErrorCodes(ClassDeclaration node) {
2541 bool problemReported = false; 2496 bool problemReported = false;
2542 for (TypeParameterElement typeParameter in _enclosingClass.typeParameters) { 2497 for (TypeParameterElement typeParameter in _enclosingClass.typeParameters) {
2543 String name = typeParameter.name; 2498 String name = typeParameter.name;
2544 // name is same as the name of the enclosing class 2499 // name is same as the name of the enclosing class
2545 if (_enclosingClass.name == name) { 2500 if (_enclosingClass.name == name) {
2546 _errorReporter.reportErrorForOffset( 2501 _errorReporter.reportErrorForOffset(
2547 CompileTimeErrorCode.CONFLICTING_TYPE_VARIABLE_AND_CLASS, 2502 CompileTimeErrorCode.CONFLICTING_TYPE_VARIABLE_AND_CLASS,
2548 typeParameter.nameOffset, name.length, [name]); 2503 typeParameter.nameOffset, name.length, [name]);
2549 problemReported = true; 2504 problemReported = true;
2550 } 2505 }
2551 // check members 2506 // check members
2552 if (_enclosingClass.getMethod(name) != null || 2507 if (_enclosingClass.getMethod(name) != null ||
2553 _enclosingClass.getGetter(name) != null || 2508 _enclosingClass.getGetter(name) != null ||
2554 _enclosingClass.getSetter(name) != null) { 2509 _enclosingClass.getSetter(name) != null) {
2555 _errorReporter.reportErrorForOffset( 2510 _errorReporter.reportErrorForOffset(
2556 CompileTimeErrorCode.CONFLICTING_TYPE_VARIABLE_AND_MEMBER, 2511 CompileTimeErrorCode.CONFLICTING_TYPE_VARIABLE_AND_MEMBER,
2557 typeParameter.nameOffset, name.length, [name]); 2512 typeParameter.nameOffset, name.length, [name]);
2558 problemReported = true; 2513 problemReported = true;
2559 } 2514 }
2560 } 2515 }
2561 return problemReported; 2516 return problemReported;
2562 } 2517 }
2563 2518
2564 /** 2519 /**
2565 * This verifies that if the passed constructor declaration is 'const' then th ere are no 2520 * Verify that if the given [constructor] declaration is 'const' then there
2566 * invocations of non-'const' super constructors. 2521 * are no invocations of non-'const' super constructors.
2567 * 2522 *
2568 * @param node the constructor declaration to evaluate
2569 * @return `true` if and only if an error code is generated on the passed node
2570 * See [CompileTimeErrorCode.CONST_CONSTRUCTOR_WITH_NON_CONST_SUPER]. 2523 * See [CompileTimeErrorCode.CONST_CONSTRUCTOR_WITH_NON_CONST_SUPER].
2571 */ 2524 */
2572 bool _checkForConstConstructorWithNonConstSuper(ConstructorDeclaration node) { 2525 bool _checkForConstConstructorWithNonConstSuper(ConstructorDeclaration node) {
2573 if (!_isEnclosingConstructorConst) { 2526 if (!_isEnclosingConstructorConst) {
2574 return false; 2527 return false;
2575 } 2528 }
2576 // OK, const factory, checked elsewhere 2529 // OK, const factory, checked elsewhere
2577 if (node.factoryKeyword != null) { 2530 if (node.factoryKeyword != null) {
2578 return false; 2531 return false;
2579 } 2532 }
(...skipping 34 matching lines...) Expand 10 before | Expand all | Expand 10 after
2614 return false; 2567 return false;
2615 } 2568 }
2616 // default constructor is not 'const', report problem 2569 // default constructor is not 'const', report problem
2617 _errorReporter.reportErrorForNode( 2570 _errorReporter.reportErrorForNode(
2618 CompileTimeErrorCode.CONST_CONSTRUCTOR_WITH_NON_CONST_SUPER, 2571 CompileTimeErrorCode.CONST_CONSTRUCTOR_WITH_NON_CONST_SUPER,
2619 node.returnType, [supertype.displayName]); 2572 node.returnType, [supertype.displayName]);
2620 return true; 2573 return true;
2621 } 2574 }
2622 2575
2623 /** 2576 /**
2624 * This verifies that if the passed constructor declaration is 'const' then th ere are no non-final 2577 * Verify that if the given constructor [declaration] is 'const' then there
2625 * instance variable. 2578 * are no non-final instance variable. The [constructorElement] is the
2579 * constructor element.
2626 * 2580 *
2627 * @param node the constructor declaration to evaluate
2628 * @param constructorElement the constructor element
2629 * @return `true` if and only if an error code is generated on the passed node
2630 * See [CompileTimeErrorCode.CONST_CONSTRUCTOR_WITH_NON_FINAL_FIELD]. 2581 * See [CompileTimeErrorCode.CONST_CONSTRUCTOR_WITH_NON_FINAL_FIELD].
2631 */ 2582 */
2632 bool _checkForConstConstructorWithNonFinalField( 2583 bool _checkForConstConstructorWithNonFinalField(
2633 ConstructorDeclaration node, ConstructorElement constructorElement) { 2584 ConstructorDeclaration node, ConstructorElement constructorElement) {
2634 if (!_isEnclosingConstructorConst) { 2585 if (!_isEnclosingConstructorConst) {
2635 return false; 2586 return false;
2636 } 2587 }
2637 // check if there is non-final field 2588 // check if there is non-final field
2638 ClassElement classElement = constructorElement.enclosingElement; 2589 ClassElement classElement = constructorElement.enclosingElement;
2639 if (!classElement.hasNonFinalField) { 2590 if (!classElement.hasNonFinalField) {
2640 return false; 2591 return false;
2641 } 2592 }
2642 // report problem 2593 // report problem
2643 _errorReporter.reportErrorForNode( 2594 _errorReporter.reportErrorForNode(
2644 CompileTimeErrorCode.CONST_CONSTRUCTOR_WITH_NON_FINAL_FIELD, node); 2595 CompileTimeErrorCode.CONST_CONSTRUCTOR_WITH_NON_FINAL_FIELD, node);
2645 return true; 2596 return true;
2646 } 2597 }
2647 2598
2648 /** 2599 /**
2649 * This verifies that the passed 'const' instance creation expression is not c reating a deferred 2600 * Verify that the given 'const' instance creation [expression] is not
2650 * type. 2601 * creating a deferred type. The [constructorName] is the constructor name,
2602 * always non-`null`. The [typeName] is the name of the type defining the
2603 * constructor, always non-`null`.
2651 * 2604 *
2652 * @param node the instance creation expression to evaluate
2653 * @param constructorName the constructor name, always non-`null`
2654 * @param typeName the name of the type defining the constructor, always non-` null`
2655 * @return `true` if and only if an error code is generated on the passed node
2656 * See [CompileTimeErrorCode.CONST_DEFERRED_CLASS]. 2605 * See [CompileTimeErrorCode.CONST_DEFERRED_CLASS].
2657 */ 2606 */
2658 bool _checkForConstDeferredClass(InstanceCreationExpression node, 2607 bool _checkForConstDeferredClass(InstanceCreationExpression node,
2659 ConstructorName constructorName, TypeName typeName) { 2608 ConstructorName constructorName, TypeName typeName) {
2660 if (typeName.isDeferred) { 2609 if (typeName.isDeferred) {
2661 _errorReporter.reportErrorForNode( 2610 _errorReporter.reportErrorForNode(
2662 CompileTimeErrorCode.CONST_DEFERRED_CLASS, constructorName, 2611 CompileTimeErrorCode.CONST_DEFERRED_CLASS, constructorName,
2663 [typeName.name.name]); 2612 [typeName.name.name]);
2664 return true; 2613 return true;
2665 } 2614 }
2666 return false; 2615 return false;
2667 } 2616 }
2668 2617
2669 /** 2618 /**
2670 * This verifies that the passed throw expression is not enclosed in a 'const' constructor 2619 * Verify that the given throw [expression] is not enclosed in a 'const'
2671 * declaration. 2620 * constructor declaration.
2672 * 2621 *
2673 * @param node the throw expression expression to evaluate
2674 * @return `true` if and only if an error code is generated on the passed node
2675 * See [CompileTimeErrorCode.CONST_CONSTRUCTOR_THROWS_EXCEPTION]. 2622 * See [CompileTimeErrorCode.CONST_CONSTRUCTOR_THROWS_EXCEPTION].
2676 */ 2623 */
2677 bool _checkForConstEvalThrowsException(ThrowExpression node) { 2624 bool _checkForConstEvalThrowsException(ThrowExpression node) {
2678 if (_isEnclosingConstructorConst) { 2625 if (_isEnclosingConstructorConst) {
2679 _errorReporter.reportErrorForNode( 2626 _errorReporter.reportErrorForNode(
2680 CompileTimeErrorCode.CONST_CONSTRUCTOR_THROWS_EXCEPTION, node); 2627 CompileTimeErrorCode.CONST_CONSTRUCTOR_THROWS_EXCEPTION, node);
2681 return true; 2628 return true;
2682 } 2629 }
2683 return false; 2630 return false;
2684 } 2631 }
2685 2632
2686 /** 2633 /**
2687 * This verifies that the passed normal formal parameter is not 'const'. 2634 * Verify that the given normal formal [parameter] is not 'const'.
2688 * 2635 *
2689 * @param node the normal formal parameter to evaluate
2690 * @return `true` if and only if an error code is generated on the passed node
2691 * See [CompileTimeErrorCode.CONST_FORMAL_PARAMETER]. 2636 * See [CompileTimeErrorCode.CONST_FORMAL_PARAMETER].
2692 */ 2637 */
2693 bool _checkForConstFormalParameter(NormalFormalParameter node) { 2638 bool _checkForConstFormalParameter(NormalFormalParameter node) {
2694 if (node.isConst) { 2639 if (node.isConst) {
2695 _errorReporter.reportErrorForNode( 2640 _errorReporter.reportErrorForNode(
2696 CompileTimeErrorCode.CONST_FORMAL_PARAMETER, node); 2641 CompileTimeErrorCode.CONST_FORMAL_PARAMETER, node);
2697 return true; 2642 return true;
2698 } 2643 }
2699 return false; 2644 return false;
2700 } 2645 }
2701 2646
2702 /** 2647 /**
2703 * This verifies that the passed instance creation expression is not being inv oked on an abstract 2648 * Verify that the given instance creation [expression] is not being invoked
2704 * class. 2649 * on an abstract class. The [typeName] is the [TypeName] of the
2650 * [ConstructorName] from the [InstanceCreationExpression], this is the AST
2651 * node that the error is attached to. The [type] is the type being
2652 * constructed with this [InstanceCreationExpression].
2705 * 2653 *
2706 * @param node the instance creation expression to evaluate
2707 * @param typeName the [TypeName] of the [ConstructorName] from the
2708 * [InstanceCreationExpression], this is the AST node that the error is attached to
2709 * @param type the type being constructed with this [InstanceCreationExpressio n]
2710 * @return `true` if and only if an error code is generated on the passed node
2711 * See [StaticWarningCode.CONST_WITH_ABSTRACT_CLASS], and 2654 * See [StaticWarningCode.CONST_WITH_ABSTRACT_CLASS], and
2712 * [StaticWarningCode.NEW_WITH_ABSTRACT_CLASS]. 2655 * [StaticWarningCode.NEW_WITH_ABSTRACT_CLASS].
2713 */ 2656 */
2714 bool _checkForConstOrNewWithAbstractClass( 2657 bool _checkForConstOrNewWithAbstractClass(
2715 InstanceCreationExpression node, TypeName typeName, InterfaceType type) { 2658 InstanceCreationExpression node, TypeName typeName, InterfaceType type) {
2716 if (type.element.isAbstract) { 2659 if (type.element.isAbstract) {
2717 ConstructorElement element = node.staticElement; 2660 ConstructorElement element = node.staticElement;
2718 if (element != null && !element.isFactory) { 2661 if (element != null && !element.isFactory) {
2719 if ((node.keyword as sc.KeywordToken).keyword == sc.Keyword.CONST) { 2662 if ((node.keyword as sc.KeywordToken).keyword == sc.Keyword.CONST) {
2720 _errorReporter.reportErrorForNode( 2663 _errorReporter.reportErrorForNode(
2721 StaticWarningCode.CONST_WITH_ABSTRACT_CLASS, typeName); 2664 StaticWarningCode.CONST_WITH_ABSTRACT_CLASS, typeName);
2722 } else { 2665 } else {
2723 _errorReporter.reportErrorForNode( 2666 _errorReporter.reportErrorForNode(
2724 StaticWarningCode.NEW_WITH_ABSTRACT_CLASS, typeName); 2667 StaticWarningCode.NEW_WITH_ABSTRACT_CLASS, typeName);
2725 } 2668 }
2726 return true; 2669 return true;
2727 } 2670 }
2728 } 2671 }
2729 return false; 2672 return false;
2730 } 2673 }
2731 2674
2732 /** 2675 /**
2733 * This verifies that the passed instance creation expression is not being inv oked on an enum. 2676 * Verify that the given instance creation [expression] is not being invoked
2677 * on an enum. The [typeName] is the [TypeName] of the [ConstructorName] from
2678 * the [InstanceCreationExpression], this is the AST node that the error is
2679 * attached to. The [type] is the type being constructed with this
2680 * [InstanceCreationExpression].
2734 * 2681 *
2735 * @param node the instance creation expression to verify
2736 * @param typeName the [TypeName] of the [ConstructorName] from the
2737 * [InstanceCreationExpression], this is the AST node that the error is attached to
2738 * @param type the type being constructed with this [InstanceCreationExpressio n]
2739 * @return `true` if and only if an error code is generated on the passed node
2740 * See [CompileTimeErrorCode.INSTANTIATE_ENUM]. 2682 * See [CompileTimeErrorCode.INSTANTIATE_ENUM].
2741 */ 2683 */
2742 bool _checkForConstOrNewWithEnum( 2684 bool _checkForConstOrNewWithEnum(
2743 InstanceCreationExpression node, TypeName typeName, InterfaceType type) { 2685 InstanceCreationExpression node, TypeName typeName, InterfaceType type) {
2744 if (type.element.isEnum) { 2686 if (type.element.isEnum) {
2745 _errorReporter.reportErrorForNode( 2687 _errorReporter.reportErrorForNode(
2746 CompileTimeErrorCode.INSTANTIATE_ENUM, typeName); 2688 CompileTimeErrorCode.INSTANTIATE_ENUM, typeName);
2747 return true; 2689 return true;
2748 } 2690 }
2749 return false; 2691 return false;
2750 } 2692 }
2751 2693
2752 /** 2694 /**
2753 * This verifies that the passed 'const' instance creation expression is not b eing invoked on a 2695 * Verify that the given 'const' instance creation [expression] is not being
2754 * constructor that is not 'const'. 2696 * invoked on a constructor that is not 'const'.
2755 * 2697 *
2756 * This method assumes that the instance creation was tested to be 'const' bef ore being called. 2698 * This method assumes that the instance creation was tested to be 'const'
2699 * before being called.
2757 * 2700 *
2758 * @param node the instance creation expression to verify
2759 * @return `true` if and only if an error code is generated on the passed node
2760 * See [CompileTimeErrorCode.CONST_WITH_NON_CONST]. 2701 * See [CompileTimeErrorCode.CONST_WITH_NON_CONST].
2761 */ 2702 */
2762 bool _checkForConstWithNonConst(InstanceCreationExpression node) { 2703 bool _checkForConstWithNonConst(InstanceCreationExpression node) {
2763 ConstructorElement constructorElement = node.staticElement; 2704 ConstructorElement constructorElement = node.staticElement;
2764 if (constructorElement != null && !constructorElement.isConst) { 2705 if (constructorElement != null && !constructorElement.isConst) {
2765 _errorReporter.reportErrorForNode( 2706 _errorReporter.reportErrorForNode(
2766 CompileTimeErrorCode.CONST_WITH_NON_CONST, node); 2707 CompileTimeErrorCode.CONST_WITH_NON_CONST, node);
2767 return true; 2708 return true;
2768 } 2709 }
2769 return false; 2710 return false;
2770 } 2711 }
2771 2712
2772 /** 2713 /**
2773 * This verifies that the passed type name does not reference any type paramet ers. 2714 * Verify that the given [typeName] does not reference any type parameters.
2774 * 2715 *
2775 * @param typeName the type name to evaluate
2776 * @return `true` if and only if an error code is generated on the passed node
2777 * See [CompileTimeErrorCode.CONST_WITH_TYPE_PARAMETERS]. 2716 * See [CompileTimeErrorCode.CONST_WITH_TYPE_PARAMETERS].
2778 */ 2717 */
2779 bool _checkForConstWithTypeParameters(TypeName typeName) { 2718 bool _checkForConstWithTypeParameters(TypeName typeName) {
2780 // something wrong with AST 2719 // something wrong with AST
2781 if (typeName == null) { 2720 if (typeName == null) {
2782 return false; 2721 return false;
2783 } 2722 }
2784 Identifier name = typeName.name; 2723 Identifier name = typeName.name;
2785 if (name == null) { 2724 if (name == null) {
2786 return false; 2725 return false;
(...skipping 12 matching lines...) Expand all
2799 hasError = true; 2738 hasError = true;
2800 } 2739 }
2801 } 2740 }
2802 return hasError; 2741 return hasError;
2803 } 2742 }
2804 // OK 2743 // OK
2805 return false; 2744 return false;
2806 } 2745 }
2807 2746
2808 /** 2747 /**
2809 * This verifies that if the passed 'const' instance creation expression is be ing invoked on the 2748 * Verify that if the given 'const' instance creation [expression] is being
2810 * resolved constructor. 2749 * invoked on the resolved constructor. The [constructorName] is the
2750 * constructor name, always non-`null`. The [typeName] is the name of the type
2751 * defining the constructor, always non-`null`.
2811 * 2752 *
2812 * This method assumes that the instance creation was tested to be 'const' bef ore being called. 2753 * This method assumes that the instance creation was tested to be 'const'
2754 * before being called.
2813 * 2755 *
2814 * @param node the instance creation expression to evaluate
2815 * @param constructorName the constructor name, always non-`null`
2816 * @param typeName the name of the type defining the constructor, always non-` null`
2817 * @return `true` if and only if an error code is generated on the passed node
2818 * See [CompileTimeErrorCode.CONST_WITH_UNDEFINED_CONSTRUCTOR], and 2756 * See [CompileTimeErrorCode.CONST_WITH_UNDEFINED_CONSTRUCTOR], and
2819 * [CompileTimeErrorCode.CONST_WITH_UNDEFINED_CONSTRUCTOR_DEFAULT]. 2757 * [CompileTimeErrorCode.CONST_WITH_UNDEFINED_CONSTRUCTOR_DEFAULT].
2820 */ 2758 */
2821 bool _checkForConstWithUndefinedConstructor(InstanceCreationExpression node, 2759 bool _checkForConstWithUndefinedConstructor(InstanceCreationExpression node,
2822 ConstructorName constructorName, TypeName typeName) { 2760 ConstructorName constructorName, TypeName typeName) {
2823 // OK if resolved 2761 // OK if resolved
2824 if (node.staticElement != null) { 2762 if (node.staticElement != null) {
2825 return false; 2763 return false;
2826 } 2764 }
2827 DartType type = typeName.type; 2765 DartType type = typeName.type;
(...skipping 15 matching lines...) Expand all
2843 ]); 2781 ]);
2844 } else { 2782 } else {
2845 _errorReporter.reportErrorForNode( 2783 _errorReporter.reportErrorForNode(
2846 CompileTimeErrorCode.CONST_WITH_UNDEFINED_CONSTRUCTOR_DEFAULT, 2784 CompileTimeErrorCode.CONST_WITH_UNDEFINED_CONSTRUCTOR_DEFAULT,
2847 constructorName, [className]); 2785 constructorName, [className]);
2848 } 2786 }
2849 return true; 2787 return true;
2850 } 2788 }
2851 2789
2852 /** 2790 /**
2853 * This verifies that there are no default parameters in the passed function t ype alias. 2791 * Verify that there are no default parameters in the given function type
2792 * [alias].
2854 * 2793 *
2855 * @param node the function type alias to evaluate
2856 * @return `true` if and only if an error code is generated on the passed node
2857 * See [CompileTimeErrorCode.DEFAULT_VALUE_IN_FUNCTION_TYPE_ALIAS]. 2794 * See [CompileTimeErrorCode.DEFAULT_VALUE_IN_FUNCTION_TYPE_ALIAS].
2858 */ 2795 */
2859 bool _checkForDefaultValueInFunctionTypeAlias(FunctionTypeAlias node) { 2796 bool _checkForDefaultValueInFunctionTypeAlias(FunctionTypeAlias node) {
2860 bool result = false; 2797 bool result = false;
2861 FormalParameterList formalParameterList = node.parameters; 2798 FormalParameterList formalParameterList = node.parameters;
2862 NodeList<FormalParameter> parameters = formalParameterList.parameters; 2799 NodeList<FormalParameter> parameters = formalParameterList.parameters;
2863 for (FormalParameter formalParameter in parameters) { 2800 for (FormalParameter formalParameter in parameters) {
2864 if (formalParameter is DefaultFormalParameter) { 2801 if (formalParameter is DefaultFormalParameter) {
2865 DefaultFormalParameter defaultFormalParameter = formalParameter; 2802 DefaultFormalParameter defaultFormalParameter = formalParameter;
2866 if (defaultFormalParameter.defaultValue != null) { 2803 if (defaultFormalParameter.defaultValue != null) {
2867 _errorReporter.reportErrorForNode( 2804 _errorReporter.reportErrorForNode(
2868 CompileTimeErrorCode.DEFAULT_VALUE_IN_FUNCTION_TYPE_ALIAS, node); 2805 CompileTimeErrorCode.DEFAULT_VALUE_IN_FUNCTION_TYPE_ALIAS, node);
2869 result = true; 2806 result = true;
2870 } 2807 }
2871 } 2808 }
2872 } 2809 }
2873 return result; 2810 return result;
2874 } 2811 }
2875 2812
2876 /** 2813 /**
2877 * This verifies that the given default formal parameter is not part of a func tion typed 2814 * Verify that the given default formal [parameter] is not part of a function
2878 * parameter. 2815 * typed parameter.
2879 * 2816 *
2880 * @param node the default formal parameter to evaluate
2881 * @return `true` if and only if an error code is generated on the passed node
2882 * See [CompileTimeErrorCode.DEFAULT_VALUE_IN_FUNCTION_TYPED_PARAMETER]. 2817 * See [CompileTimeErrorCode.DEFAULT_VALUE_IN_FUNCTION_TYPED_PARAMETER].
2883 */ 2818 */
2884 bool _checkForDefaultValueInFunctionTypedParameter( 2819 bool _checkForDefaultValueInFunctionTypedParameter(
2885 DefaultFormalParameter node) { 2820 DefaultFormalParameter node) {
2886 // OK, not in a function typed parameter. 2821 // OK, not in a function typed parameter.
2887 if (!_isInFunctionTypedFormalParameter) { 2822 if (!_isInFunctionTypedFormalParameter) {
2888 return false; 2823 return false;
2889 } 2824 }
2890 // OK, no default value. 2825 // OK, no default value.
2891 if (node.defaultValue == null) { 2826 if (node.defaultValue == null) {
2892 return false; 2827 return false;
2893 } 2828 }
2894 // Report problem. 2829 // Report problem.
2895 _errorReporter.reportErrorForNode( 2830 _errorReporter.reportErrorForNode(
2896 CompileTimeErrorCode.DEFAULT_VALUE_IN_FUNCTION_TYPED_PARAMETER, node); 2831 CompileTimeErrorCode.DEFAULT_VALUE_IN_FUNCTION_TYPED_PARAMETER, node);
2897 return true; 2832 return true;
2898 } 2833 }
2899 2834
2900 /** 2835 /**
2901 * This verifies that any deferred imports in the given compilation unit have a unique prefix. 2836 * Verify that any deferred imports in the given compilation [unit] have a
2837 * unique prefix.
2902 * 2838 *
2903 * @param node the compilation unit containing the imports to be checked
2904 * @return `true` if an error was generated
2905 * See [CompileTimeErrorCode.SHARED_DEFERRED_PREFIX]. 2839 * See [CompileTimeErrorCode.SHARED_DEFERRED_PREFIX].
2906 */ 2840 */
2907 bool _checkForDeferredPrefixCollisions(CompilationUnit node) { 2841 bool _checkForDeferredPrefixCollisions(CompilationUnit node) {
2908 bool foundError = false; 2842 bool foundError = false;
2909 NodeList<Directive> directives = node.directives; 2843 NodeList<Directive> directives = node.directives;
2910 int count = directives.length; 2844 int count = directives.length;
2911 if (count > 0) { 2845 if (count > 0) {
2912 HashMap<PrefixElement, List<ImportDirective>> prefixToDirectivesMap = 2846 HashMap<PrefixElement, List<ImportDirective>> prefixToDirectivesMap =
2913 new HashMap<PrefixElement, List<ImportDirective>>(); 2847 new HashMap<PrefixElement, List<ImportDirective>>();
2914 for (int i = 0; i < count; i++) { 2848 for (int i = 0; i < count; i++) {
(...skipping 19 matching lines...) Expand all
2934 for (List<ImportDirective> imports in prefixToDirectivesMap.values) { 2868 for (List<ImportDirective> imports in prefixToDirectivesMap.values) {
2935 if (_hasDeferredPrefixCollision(imports)) { 2869 if (_hasDeferredPrefixCollision(imports)) {
2936 foundError = true; 2870 foundError = true;
2937 } 2871 }
2938 } 2872 }
2939 } 2873 }
2940 return foundError; 2874 return foundError;
2941 } 2875 }
2942 2876
2943 /** 2877 /**
2944 * This verifies that the enclosing class does not have an instance member wit h the given name of 2878 * Verify that the enclosing class does not have an instance member with the
2945 * the static member. 2879 * given name of the static member.
2946 * 2880 *
2947 * @return `true` if and only if an error code is generated on the passed node
2948 * See [CompileTimeErrorCode.DUPLICATE_DEFINITION_INHERITANCE]. 2881 * See [CompileTimeErrorCode.DUPLICATE_DEFINITION_INHERITANCE].
2949 */ 2882 */
2950 bool _checkForDuplicateDefinitionInheritance() { 2883 bool _checkForDuplicateDefinitionInheritance() {
2951 if (_enclosingClass == null) { 2884 if (_enclosingClass == null) {
2952 return false; 2885 return false;
2953 } 2886 }
2954 bool hasProblem = false; 2887 bool hasProblem = false;
2955 for (ExecutableElement member in _enclosingClass.methods) { 2888 for (ExecutableElement member in _enclosingClass.methods) {
2956 if (member.isStatic && _checkForDuplicateDefinitionOfMember(member)) { 2889 if (member.isStatic && _checkForDuplicateDefinitionOfMember(member)) {
2957 hasProblem = true; 2890 hasProblem = true;
2958 } 2891 }
2959 } 2892 }
2960 for (ExecutableElement member in _enclosingClass.accessors) { 2893 for (ExecutableElement member in _enclosingClass.accessors) {
2961 if (member.isStatic && _checkForDuplicateDefinitionOfMember(member)) { 2894 if (member.isStatic && _checkForDuplicateDefinitionOfMember(member)) {
2962 hasProblem = true; 2895 hasProblem = true;
2963 } 2896 }
2964 } 2897 }
2965 return hasProblem; 2898 return hasProblem;
2966 } 2899 }
2967 2900
2968 /** 2901 /**
2969 * This verifies that the enclosing class does not have an instance member wit h the given name of 2902 * Verify that the enclosing class does not have an instance member with the
2970 * the static member. 2903 * given name of the [staticMember].
2971 * 2904 *
2972 * @param staticMember the static member to check conflict for
2973 * @return `true` if and only if an error code is generated on the passed node
2974 * See [CompileTimeErrorCode.DUPLICATE_DEFINITION_INHERITANCE]. 2905 * See [CompileTimeErrorCode.DUPLICATE_DEFINITION_INHERITANCE].
2975 */ 2906 */
2976 bool _checkForDuplicateDefinitionOfMember(ExecutableElement staticMember) { 2907 bool _checkForDuplicateDefinitionOfMember(ExecutableElement staticMember) {
2977 // prepare name 2908 // prepare name
2978 String name = staticMember.name; 2909 String name = staticMember.name;
2979 if (name == null) { 2910 if (name == null) {
2980 return false; 2911 return false;
2981 } 2912 }
2982 // try to find member 2913 // try to find member
2983 ExecutableElement inheritedMember = 2914 ExecutableElement inheritedMember =
(...skipping 15 matching lines...) Expand all
2999 displayName = enclosingElement.getExtendedDisplayName(null); 2930 displayName = enclosingElement.getExtendedDisplayName(null);
3000 } 2931 }
3001 // report problem 2932 // report problem
3002 _errorReporter.reportErrorForOffset( 2933 _errorReporter.reportErrorForOffset(
3003 CompileTimeErrorCode.DUPLICATE_DEFINITION_INHERITANCE, 2934 CompileTimeErrorCode.DUPLICATE_DEFINITION_INHERITANCE,
3004 staticMember.nameOffset, name.length, [name, displayName]); 2935 staticMember.nameOffset, name.length, [name, displayName]);
3005 return true; 2936 return true;
3006 } 2937 }
3007 2938
3008 /** 2939 /**
3009 * This verifies if the passed list literal has type arguments then there is e xactly one. 2940 * Verify that if the given list [literal] has type arguments then there is
2941 * exactly one. The [typeArguments] are the type arguments.
3010 * 2942 *
3011 * @param node the list literal to evaluate
3012 * @param typeArguments the type arguments, always non-`null`
3013 * @return `true` if and only if an error code is generated on the passed node
3014 * See [StaticTypeWarningCode.EXPECTED_ONE_LIST_TYPE_ARGUMENTS]. 2943 * See [StaticTypeWarningCode.EXPECTED_ONE_LIST_TYPE_ARGUMENTS].
3015 */ 2944 */
3016 bool _checkForExpectedOneListTypeArgument( 2945 bool _checkForExpectedOneListTypeArgument(
3017 ListLiteral node, TypeArgumentList typeArguments) { 2946 ListLiteral node, TypeArgumentList typeArguments) {
3018 // check number of type arguments 2947 // check number of type arguments
3019 int num = typeArguments.arguments.length; 2948 int num = typeArguments.arguments.length;
3020 if (num == 1) { 2949 if (num == 1) {
3021 return false; 2950 return false;
3022 } 2951 }
3023 // report problem 2952 // report problem
3024 _errorReporter.reportErrorForNode( 2953 _errorReporter.reportErrorForNode(
3025 StaticTypeWarningCode.EXPECTED_ONE_LIST_TYPE_ARGUMENTS, typeArguments, 2954 StaticTypeWarningCode.EXPECTED_ONE_LIST_TYPE_ARGUMENTS, typeArguments,
3026 [num]); 2955 [num]);
3027 return true; 2956 return true;
3028 } 2957 }
3029 2958
3030 /** 2959 /**
3031 * This verifies the passed import has unique name among other exported librar ies. 2960 * Verify that the given export ([node]) has a unique name among other
2961 * exported libraries. The [exportElement] is the [ExportElement] retrieved
2962 * from the node, if the element in the node was `null`, then this method is
2963 * not called. The [exportedLibrary] is the library element containing the
2964 * exported element.
3032 * 2965 *
3033 * @param node the export directive to evaluate
3034 * @param exportElement the [ExportElement] retrieved from the node, if the el ement in the
3035 * node was `null`, then this method is not called
3036 * @param exportedLibrary the library element containing the exported element
3037 * @return `true` if and only if an error code is generated on the passed node
3038 * See [CompileTimeErrorCode.EXPORT_DUPLICATED_LIBRARY_NAME]. 2966 * See [CompileTimeErrorCode.EXPORT_DUPLICATED_LIBRARY_NAME].
3039 */ 2967 */
3040 bool _checkForExportDuplicateLibraryName(ExportDirective node, 2968 bool _checkForExportDuplicateLibraryName(ExportDirective node,
3041 ExportElement exportElement, LibraryElement exportedLibrary) { 2969 ExportElement exportElement, LibraryElement exportedLibrary) {
3042 if (exportedLibrary == null) { 2970 if (exportedLibrary == null) {
3043 return false; 2971 return false;
3044 } 2972 }
3045 String name = exportedLibrary.name; 2973 String name = exportedLibrary.name;
3046 // check if there is other exported library with the same name 2974 // check if there is other exported library with the same name
3047 LibraryElement prevLibrary = _nameToExportElement[name]; 2975 LibraryElement prevLibrary = _nameToExportElement[name];
(...skipping 16 matching lines...) Expand all
3064 return true; 2992 return true;
3065 } 2993 }
3066 } else { 2994 } else {
3067 _nameToExportElement[name] = exportedLibrary; 2995 _nameToExportElement[name] = exportedLibrary;
3068 } 2996 }
3069 // OK 2997 // OK
3070 return false; 2998 return false;
3071 } 2999 }
3072 3000
3073 /** 3001 /**
3074 * Check that if the visiting library is not system, then any passed library s hould not be SDK 3002 * Check that if the visiting library is not system, then any given library
3075 * internal library. 3003 * should not be SDK internal library. The [exportElement] is the
3004 * [ExportElement] retrieved from the node, if the element in the node was
3005 * `null`, then this method is not called.
3076 * 3006 *
3077 * @param node the export directive to evaluate
3078 * @param exportElement the [ExportElement] retrieved from the node, if the el ement in the
3079 * node was `null`, then this method is not called
3080 * @return `true` if and only if an error code is generated on the passed node
3081 * See [CompileTimeErrorCode.EXPORT_INTERNAL_LIBRARY]. 3007 * See [CompileTimeErrorCode.EXPORT_INTERNAL_LIBRARY].
3082 */ 3008 */
3083 bool _checkForExportInternalLibrary( 3009 bool _checkForExportInternalLibrary(
3084 ExportDirective node, ExportElement exportElement) { 3010 ExportDirective node, ExportElement exportElement) {
3085 if (_isInSystemLibrary) { 3011 if (_isInSystemLibrary) {
3086 return false; 3012 return false;
3087 } 3013 }
3088 // should be private 3014 // should be private
3089 DartSdk sdk = _currentLibrary.context.sourceFactory.dartSdk; 3015 DartSdk sdk = _currentLibrary.context.sourceFactory.dartSdk;
3090 String uri = exportElement.uri; 3016 String uri = exportElement.uri;
3091 SdkLibrary sdkLibrary = sdk.getSdkLibrary(uri); 3017 SdkLibrary sdkLibrary = sdk.getSdkLibrary(uri);
3092 if (sdkLibrary == null) { 3018 if (sdkLibrary == null) {
3093 return false; 3019 return false;
3094 } 3020 }
3095 if (!sdkLibrary.isInternal) { 3021 if (!sdkLibrary.isInternal) {
3096 return false; 3022 return false;
3097 } 3023 }
3098 // report problem 3024 // report problem
3099 _errorReporter.reportErrorForNode( 3025 _errorReporter.reportErrorForNode(
3100 CompileTimeErrorCode.EXPORT_INTERNAL_LIBRARY, node, [node.uri]); 3026 CompileTimeErrorCode.EXPORT_INTERNAL_LIBRARY, node, [node.uri]);
3101 return true; 3027 return true;
3102 } 3028 }
3103 3029
3104 /** 3030 /**
3105 * This verifies that the passed extends clause does not extend a deferred cla ss. 3031 * Verify that the given extends [clause] does not extend a deferred class.
3106 * 3032 *
3107 * @param node the extends clause to test
3108 * @return `true` if and only if an error code is generated on the passed node
3109 * See [CompileTimeErrorCode.EXTENDS_DEFERRED_CLASS]. 3033 * See [CompileTimeErrorCode.EXTENDS_DEFERRED_CLASS].
3110 */ 3034 */
3111 bool _checkForExtendsDeferredClass(ExtendsClause node) { 3035 bool _checkForExtendsDeferredClass(ExtendsClause node) {
3112 if (node == null) { 3036 if (node == null) {
3113 return false; 3037 return false;
3114 } 3038 }
3115 return _checkForExtendsOrImplementsDeferredClass( 3039 return _checkForExtendsOrImplementsDeferredClass(
3116 node.superclass, CompileTimeErrorCode.EXTENDS_DEFERRED_CLASS); 3040 node.superclass, CompileTimeErrorCode.EXTENDS_DEFERRED_CLASS);
3117 } 3041 }
3118 3042
3119 /** 3043 /**
3120 * This verifies that the passed type alias does not extend a deferred class. 3044 * Verify that the given type [alias] does not extend a deferred class.
3121 * 3045 *
3122 * @param node the extends clause to test
3123 * @return `true` if and only if an error code is generated on the passed node
3124 * See [CompileTimeErrorCode.EXTENDS_DISALLOWED_CLASS]. 3046 * See [CompileTimeErrorCode.EXTENDS_DISALLOWED_CLASS].
3125 */ 3047 */
3126 bool _checkForExtendsDeferredClassInTypeAlias(ClassTypeAlias node) { 3048 bool _checkForExtendsDeferredClassInTypeAlias(ClassTypeAlias node) {
3127 if (node == null) { 3049 if (node == null) {
3128 return false; 3050 return false;
3129 } 3051 }
3130 return _checkForExtendsOrImplementsDeferredClass( 3052 return _checkForExtendsOrImplementsDeferredClass(
3131 node.superclass, CompileTimeErrorCode.EXTENDS_DEFERRED_CLASS); 3053 node.superclass, CompileTimeErrorCode.EXTENDS_DEFERRED_CLASS);
3132 } 3054 }
3133 3055
3134 /** 3056 /**
3135 * This verifies that the passed extends clause does not extend classes such a s num or String. 3057 * Verify that the given extends [clause] does not extend classes such as
3058 * 'num' or 'String'.
3136 * 3059 *
3137 * @param node the extends clause to test
3138 * @return `true` if and only if an error code is generated on the passed node
3139 * See [CompileTimeErrorCode.EXTENDS_DISALLOWED_CLASS]. 3060 * See [CompileTimeErrorCode.EXTENDS_DISALLOWED_CLASS].
3140 */ 3061 */
3141 bool _checkForExtendsDisallowedClass(ExtendsClause node) { 3062 bool _checkForExtendsDisallowedClass(ExtendsClause node) {
3142 if (node == null) { 3063 if (node == null) {
3143 return false; 3064 return false;
3144 } 3065 }
3145 return _checkForExtendsOrImplementsDisallowedClass( 3066 return _checkForExtendsOrImplementsDisallowedClass(
3146 node.superclass, CompileTimeErrorCode.EXTENDS_DISALLOWED_CLASS); 3067 node.superclass, CompileTimeErrorCode.EXTENDS_DISALLOWED_CLASS);
3147 } 3068 }
3148 3069
3149 /** 3070 /**
3150 * This verifies that the passed type alias does not extend classes such as nu m or String. 3071 * Verify that the given type [alias] does not extend classes such as 'num' or
3072 * 'String'.
3151 * 3073 *
3152 * @param node the extends clause to test
3153 * @return `true` if and only if an error code is generated on the passed node
3154 * See [CompileTimeErrorCode.EXTENDS_DISALLOWED_CLASS]. 3074 * See [CompileTimeErrorCode.EXTENDS_DISALLOWED_CLASS].
3155 */ 3075 */
3156 bool _checkForExtendsDisallowedClassInTypeAlias(ClassTypeAlias node) { 3076 bool _checkForExtendsDisallowedClassInTypeAlias(ClassTypeAlias node) {
3157 if (node == null) { 3077 if (node == null) {
3158 return false; 3078 return false;
3159 } 3079 }
3160 return _checkForExtendsOrImplementsDisallowedClass( 3080 return _checkForExtendsOrImplementsDisallowedClass(
3161 node.superclass, CompileTimeErrorCode.EXTENDS_DISALLOWED_CLASS); 3081 node.superclass, CompileTimeErrorCode.EXTENDS_DISALLOWED_CLASS);
3162 } 3082 }
3163 3083
3164 /** 3084 /**
3165 * This verifies that the passed type name does not extend, implement or mixin classes that are 3085 * Verify that the given [typeName] does not extend, implement or mixin
3166 * deferred. 3086 * classes that are deferred.
3167 * 3087 *
3168 * @param node the type name to test
3169 * @return `true` if and only if an error code is generated on the passed node
3170 * See [_checkForExtendsDeferredClass], 3088 * See [_checkForExtendsDeferredClass],
3171 * [_checkForExtendsDeferredClassInTypeAlias], 3089 * [_checkForExtendsDeferredClassInTypeAlias],
3172 * [_checkForImplementsDeferredClass], 3090 * [_checkForImplementsDeferredClass],
3173 * [_checkForAllMixinErrorCodes], 3091 * [_checkForAllMixinErrorCodes],
3174 * [CompileTimeErrorCode.EXTENDS_DEFERRED_CLASS], 3092 * [CompileTimeErrorCode.EXTENDS_DEFERRED_CLASS],
3175 * [CompileTimeErrorCode.IMPLEMENTS_DEFERRED_CLASS], and 3093 * [CompileTimeErrorCode.IMPLEMENTS_DEFERRED_CLASS], and
3176 * [CompileTimeErrorCode.MIXIN_DEFERRED_CLASS]. 3094 * [CompileTimeErrorCode.MIXIN_DEFERRED_CLASS].
3177 */ 3095 */
3178 bool _checkForExtendsOrImplementsDeferredClass( 3096 bool _checkForExtendsOrImplementsDeferredClass(
3179 TypeName typeName, ErrorCode errorCode) { 3097 TypeName typeName, ErrorCode errorCode) {
3180 if (typeName.isSynthetic) { 3098 if (typeName.isSynthetic) {
3181 return false; 3099 return false;
3182 } 3100 }
3183 if (typeName.isDeferred) { 3101 if (typeName.isDeferred) {
3184 _errorReporter.reportErrorForNode( 3102 _errorReporter.reportErrorForNode(
3185 errorCode, typeName, [typeName.name.name]); 3103 errorCode, typeName, [typeName.name.name]);
3186 return true; 3104 return true;
3187 } 3105 }
3188 return false; 3106 return false;
3189 } 3107 }
3190 3108
3191 /** 3109 /**
3192 * This verifies that the passed type name does not extend, implement or mixin classes such as 3110 * Verify that the given [typeName] does not extend, implement or mixin
3193 * 'num' or 'String'. 3111 * classes such as 'num' or 'String'.
3194 * 3112 *
3195 * @param node the type name to test
3196 * @return `true` if and only if an error code is generated on the passed node
3197 * See [_checkForExtendsDisallowedClass], 3113 * See [_checkForExtendsDisallowedClass],
3198 * [_checkForExtendsDisallowedClassInTypeAlias], 3114 * [_checkForExtendsDisallowedClassInTypeAlias],
3199 * [_checkForImplementsDisallowedClass], 3115 * [_checkForImplementsDisallowedClass],
3200 * [_checkForAllMixinErrorCodes], 3116 * [_checkForAllMixinErrorCodes],
3201 * [CompileTimeErrorCode.EXTENDS_DISALLOWED_CLASS], 3117 * [CompileTimeErrorCode.EXTENDS_DISALLOWED_CLASS],
3202 * [CompileTimeErrorCode.IMPLEMENTS_DISALLOWED_CLASS], and 3118 * [CompileTimeErrorCode.IMPLEMENTS_DISALLOWED_CLASS], and
3203 * [CompileTimeErrorCode.MIXIN_OF_DISALLOWED_CLASS]. 3119 * [CompileTimeErrorCode.MIXIN_OF_DISALLOWED_CLASS].
3204 */ 3120 */
3205 bool _checkForExtendsOrImplementsDisallowedClass( 3121 bool _checkForExtendsOrImplementsDisallowedClass(
3206 TypeName typeName, ErrorCode errorCode) { 3122 TypeName typeName, ErrorCode errorCode) {
(...skipping 26 matching lines...) Expand all
3233 // otherwise, report the error 3149 // otherwise, report the error
3234 _errorReporter.reportErrorForNode( 3150 _errorReporter.reportErrorForNode(
3235 errorCode, typeName, [disallowedType.displayName]); 3151 errorCode, typeName, [disallowedType.displayName]);
3236 return true; 3152 return true;
3237 } 3153 }
3238 } 3154 }
3239 return false; 3155 return false;
3240 } 3156 }
3241 3157
3242 /** 3158 /**
3243 * This verifies that the passed constructor field initializer has compatible field and 3159 * Verify that the given constructor field [initializer] has compatible field
3244 * initializer expression types. 3160 * and initializer expression types. The [staticElement] is the static element
3161 * from the name in the [ConstructorFieldInitializer].
3245 * 3162 *
3246 * @param node the constructor field initializer to test
3247 * @param staticElement the static element from the name in the
3248 * [ConstructorFieldInitializer]
3249 * @return `true` if and only if an error code is generated on the passed node
3250 * See [CompileTimeErrorCode.CONST_FIELD_INITIALIZER_NOT_ASSIGNABLE], and 3163 * See [CompileTimeErrorCode.CONST_FIELD_INITIALIZER_NOT_ASSIGNABLE], and
3251 * [StaticWarningCode.FIELD_INITIALIZER_NOT_ASSIGNABLE]. 3164 * [StaticWarningCode.FIELD_INITIALIZER_NOT_ASSIGNABLE].
3252 */ 3165 */
3253 bool _checkForFieldInitializerNotAssignable( 3166 bool _checkForFieldInitializerNotAssignable(
3254 ConstructorFieldInitializer node, Element staticElement) { 3167 ConstructorFieldInitializer node, Element staticElement) {
3255 // prepare field element 3168 // prepare field element
3256 if (staticElement is! FieldElement) { 3169 if (staticElement is! FieldElement) {
3257 return false; 3170 return false;
3258 } 3171 }
3259 FieldElement fieldElement = staticElement as FieldElement; 3172 FieldElement fieldElement = staticElement as FieldElement;
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after
3304 // errorReporter.reportTypeErrorForNode( 3217 // errorReporter.reportTypeErrorForNode(
3305 // StaticWarningCode.FIELD_INITIALIZER_NOT_ASSIGNABLE, 3218 // StaticWarningCode.FIELD_INITIALIZER_NOT_ASSIGNABLE,
3306 // expression, 3219 // expression,
3307 // propagatedType == null ? staticType : propagatedType, 3220 // propagatedType == null ? staticType : propagatedType,
3308 // fieldType); 3221 // fieldType);
3309 // } 3222 // }
3310 // return true; 3223 // return true;
3311 } 3224 }
3312 3225
3313 /** 3226 /**
3314 * This verifies that the passed field formal parameter is in a constructor de claration. 3227 * Verify that the given field formal [parameter] is in a constructor
3228 * declaration.
3315 * 3229 *
3316 * @param node the field formal parameter to test
3317 * @return `true` if and only if an error code is generated on the passed node
3318 * See [CompileTimeErrorCode.FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR]. 3230 * See [CompileTimeErrorCode.FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR].
3319 */ 3231 */
3320 bool _checkForFieldInitializingFormalRedirectingConstructor( 3232 bool _checkForFieldInitializingFormalRedirectingConstructor(
3321 FieldFormalParameter node) { 3233 FieldFormalParameter node) {
3322 ConstructorDeclaration constructor = 3234 ConstructorDeclaration constructor =
3323 node.getAncestor((node) => node is ConstructorDeclaration); 3235 node.getAncestor((node) => node is ConstructorDeclaration);
3324 if (constructor == null) { 3236 if (constructor == null) {
3325 _errorReporter.reportErrorForNode( 3237 _errorReporter.reportErrorForNode(
3326 CompileTimeErrorCode.FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR, node); 3238 CompileTimeErrorCode.FIELD_INITIALIZER_OUTSIDE_CONSTRUCTOR, node);
3327 return true; 3239 return true;
(...skipping 11 matching lines...) Expand all
3339 CompileTimeErrorCode.FIELD_INITIALIZER_REDIRECTING_CONSTRUCTOR, 3251 CompileTimeErrorCode.FIELD_INITIALIZER_REDIRECTING_CONSTRUCTOR,
3340 node); 3252 node);
3341 return true; 3253 return true;
3342 } 3254 }
3343 } 3255 }
3344 // OK 3256 // OK
3345 return false; 3257 return false;
3346 } 3258 }
3347 3259
3348 /** 3260 /**
3349 * This verifies that the passed variable declaration list has only initialize d variables if the 3261 * Verify that the given variable declaration [list] has only initialized
3350 * list is final or const. This method is called by 3262 * variables if the list is final or const.
3351 * [checkForFinalNotInitializedInClass],
3352 * [visitTopLevelVariableDeclaration] and
3353 * [visitVariableDeclarationStatement].
3354 * 3263 *
3355 * @param node the class declaration to test
3356 * @return `true` if and only if an error code is generated on the passed node
3357 * See [CompileTimeErrorCode.CONST_NOT_INITIALIZED], and 3264 * See [CompileTimeErrorCode.CONST_NOT_INITIALIZED], and
3358 * [StaticWarningCode.FINAL_NOT_INITIALIZED]. 3265 * [StaticWarningCode.FINAL_NOT_INITIALIZED].
3359 */ 3266 */
3360 bool _checkForFinalNotInitialized(VariableDeclarationList node) { 3267 bool _checkForFinalNotInitialized(VariableDeclarationList node) {
3361 if (_isInNativeClass) { 3268 if (_isInNativeClass) {
3362 return false; 3269 return false;
3363 } 3270 }
3364 bool foundError = false; 3271 bool foundError = false;
3365 if (!node.isSynthetic) { 3272 if (!node.isSynthetic) {
3366 NodeList<VariableDeclaration> variables = node.variables; 3273 NodeList<VariableDeclaration> variables = node.variables;
3367 for (VariableDeclaration variable in variables) { 3274 for (VariableDeclaration variable in variables) {
3368 if (variable.initializer == null) { 3275 if (variable.initializer == null) {
3369 if (node.isConst) { 3276 if (node.isConst) {
3370 _errorReporter.reportErrorForNode( 3277 _errorReporter.reportErrorForNode(
3371 CompileTimeErrorCode.CONST_NOT_INITIALIZED, variable.name, 3278 CompileTimeErrorCode.CONST_NOT_INITIALIZED, variable.name,
3372 [variable.name.name]); 3279 [variable.name.name]);
3373 } else if (node.isFinal) { 3280 } else if (node.isFinal) {
3374 _errorReporter.reportErrorForNode( 3281 _errorReporter.reportErrorForNode(
3375 StaticWarningCode.FINAL_NOT_INITIALIZED, variable.name, 3282 StaticWarningCode.FINAL_NOT_INITIALIZED, variable.name,
3376 [variable.name.name]); 3283 [variable.name.name]);
3377 } 3284 }
3378 foundError = true; 3285 foundError = true;
3379 } 3286 }
3380 } 3287 }
3381 } 3288 }
3382 return foundError; 3289 return foundError;
3383 } 3290 }
3384 3291
3385 /** 3292 /**
3386 * This verifies that final fields that are declared, without any constructors in the enclosing 3293 * Verify that final fields in the given clas [declaration] that are declared,
3387 * class, are initialized. Cases in which there is at least one constructor ar e handled at the end 3294 * without any constructors in the enclosing class, are initialized. Cases in
3388 * of [checkForAllFinalInitializedErrorCodes]. 3295 * which there is at least one constructor are handled at the end of
3296 * [_checkForAllFinalInitializedErrorCodes].
3389 * 3297 *
3390 * @param node the class declaration to test
3391 * @return `true` if and only if an error code is generated on the passed node
3392 * See [CompileTimeErrorCode.CONST_NOT_INITIALIZED], and 3298 * See [CompileTimeErrorCode.CONST_NOT_INITIALIZED], and
3393 * [StaticWarningCode.FINAL_NOT_INITIALIZED]. 3299 * [StaticWarningCode.FINAL_NOT_INITIALIZED].
3394 */ 3300 */
3395 bool _checkForFinalNotInitializedInClass(ClassDeclaration node) { 3301 bool _checkForFinalNotInitializedInClass(ClassDeclaration node) {
3396 NodeList<ClassMember> classMembers = node.members; 3302 NodeList<ClassMember> classMembers = node.members;
3397 for (ClassMember classMember in classMembers) { 3303 for (ClassMember classMember in classMembers) {
3398 if (classMember is ConstructorDeclaration) { 3304 if (classMember is ConstructorDeclaration) {
3399 return false; 3305 return false;
3400 } 3306 }
3401 } 3307 }
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
3437 } else if (_enclosingFunction.isGenerator) { 3343 } else if (_enclosingFunction.isGenerator) {
3438 if (!_enclosingFunction.returnType 3344 if (!_enclosingFunction.returnType
3439 .isAssignableTo(_typeProvider.iterableDynamicType)) { 3345 .isAssignableTo(_typeProvider.iterableDynamicType)) {
3440 _errorReporter.reportErrorForNode( 3346 _errorReporter.reportErrorForNode(
3441 StaticTypeWarningCode.ILLEGAL_SYNC_GENERATOR_RETURN_TYPE, node); 3347 StaticTypeWarningCode.ILLEGAL_SYNC_GENERATOR_RETURN_TYPE, node);
3442 } 3348 }
3443 } 3349 }
3444 } 3350 }
3445 3351
3446 /** 3352 /**
3447 * This verifies that the passed implements clause does not implement classes that are deferred. 3353 * Verify that the given implements [clause] does not implement classes that
3354 * are deferred.
3448 * 3355 *
3449 * @param node the implements clause to test
3450 * @return `true` if and only if an error code is generated on the passed node
3451 * See [CompileTimeErrorCode.IMPLEMENTS_DEFERRED_CLASS]. 3356 * See [CompileTimeErrorCode.IMPLEMENTS_DEFERRED_CLASS].
3452 */ 3357 */
3453 bool _checkForImplementsDeferredClass(ImplementsClause node) { 3358 bool _checkForImplementsDeferredClass(ImplementsClause node) {
3454 if (node == null) { 3359 if (node == null) {
3455 return false; 3360 return false;
3456 } 3361 }
3457 bool foundError = false; 3362 bool foundError = false;
3458 for (TypeName type in node.interfaces) { 3363 for (TypeName type in node.interfaces) {
3459 if (_checkForExtendsOrImplementsDeferredClass( 3364 if (_checkForExtendsOrImplementsDeferredClass(
3460 type, CompileTimeErrorCode.IMPLEMENTS_DEFERRED_CLASS)) { 3365 type, CompileTimeErrorCode.IMPLEMENTS_DEFERRED_CLASS)) {
3461 foundError = true; 3366 foundError = true;
3462 } 3367 }
3463 } 3368 }
3464 return foundError; 3369 return foundError;
3465 } 3370 }
3466 3371
3467 /** 3372 /**
3468 * This verifies that the passed implements clause does not implement classes such as 'num' or 3373 * Verify that the given implements [clause] does not implement classes such
3469 * 'String'. 3374 * as 'num' or 'String'.
3470 * 3375 *
3471 * @param node the implements clause to test
3472 * @return `true` if and only if an error code is generated on the passed node
3473 * See [CompileTimeErrorCode.IMPLEMENTS_DISALLOWED_CLASS]. 3376 * See [CompileTimeErrorCode.IMPLEMENTS_DISALLOWED_CLASS].
3474 */ 3377 */
3475 bool _checkForImplementsDisallowedClass(ImplementsClause node) { 3378 bool _checkForImplementsDisallowedClass(ImplementsClause node) {
3476 if (node == null) { 3379 if (node == null) {
3477 return false; 3380 return false;
3478 } 3381 }
3479 bool foundError = false; 3382 bool foundError = false;
3480 for (TypeName type in node.interfaces) { 3383 for (TypeName type in node.interfaces) {
3481 if (_checkForExtendsOrImplementsDisallowedClass( 3384 if (_checkForExtendsOrImplementsDisallowedClass(
3482 type, CompileTimeErrorCode.IMPLEMENTS_DISALLOWED_CLASS)) { 3385 type, CompileTimeErrorCode.IMPLEMENTS_DISALLOWED_CLASS)) {
3483 foundError = true; 3386 foundError = true;
3484 } 3387 }
3485 } 3388 }
3486 return foundError; 3389 return foundError;
3487 } 3390 }
3488 3391
3489 /** 3392 /**
3490 * This verifies that if the passed identifier is part of constructor initiali zer, then it does 3393 * Verify that if the given [identifier] is part of a constructor initializer,
3491 * not reference implicitly 'this' expression. 3394 * then it does not implicitly reference 'this' expression.
3492 * 3395 *
3493 * @param node the simple identifier to test
3494 * @return `true` if and only if an error code is generated on the passed node
3495 * See [CompileTimeErrorCode.IMPLICIT_THIS_REFERENCE_IN_INITIALIZER], and 3396 * See [CompileTimeErrorCode.IMPLICIT_THIS_REFERENCE_IN_INITIALIZER], and
3496 * [CompileTimeErrorCode.INSTANCE_MEMBER_ACCESS_FROM_STATIC]. 3397 * [CompileTimeErrorCode.INSTANCE_MEMBER_ACCESS_FROM_STATIC].
3497 * TODO(scheglov) rename thid method 3398 * TODO(scheglov) rename thid method
3498 */ 3399 */
3499 bool _checkForImplicitThisReferenceInInitializer(SimpleIdentifier node) { 3400 bool _checkForImplicitThisReferenceInInitializer(SimpleIdentifier node) {
3500 if (!_isInConstructorInitializer && 3401 if (!_isInConstructorInitializer &&
3501 !_isInStaticMethod && 3402 !_isInStaticMethod &&
3502 !_isInFactory && 3403 !_isInFactory &&
3503 !_isInInstanceVariableInitializer && 3404 !_isInInstanceVariableInitializer &&
3504 !_isInStaticVariableDeclaration) { 3405 !_isInStaticVariableDeclaration) {
(...skipping 48 matching lines...) Expand 10 before | Expand all | Expand 10 after
3553 _errorReporter.reportErrorForNode( 3454 _errorReporter.reportErrorForNode(
3554 CompileTimeErrorCode.INSTANCE_MEMBER_ACCESS_FROM_FACTORY, node); 3455 CompileTimeErrorCode.INSTANCE_MEMBER_ACCESS_FROM_FACTORY, node);
3555 } else { 3456 } else {
3556 _errorReporter.reportErrorForNode( 3457 _errorReporter.reportErrorForNode(
3557 CompileTimeErrorCode.IMPLICIT_THIS_REFERENCE_IN_INITIALIZER, node); 3458 CompileTimeErrorCode.IMPLICIT_THIS_REFERENCE_IN_INITIALIZER, node);
3558 } 3459 }
3559 return true; 3460 return true;
3560 } 3461 }
3561 3462
3562 /** 3463 /**
3563 * This verifies the passed import has unique name among other imported librar ies. 3464 * Verify that the given import [directive] has a unique name among other
3465 * imported libraries. The [importElement] is the [ImportElement] retrieved
3466 * from the node, if the element in the node was `null`, then this method is
3467 * not called.
3564 * 3468 *
3565 * @param node the import directive to evaluate
3566 * @param importElement the [ImportElement] retrieved from the node, if the el ement in the
3567 * node was `null`, then this method is not called
3568 * @return `true` if and only if an error code is generated on the passed node
3569 * See [CompileTimeErrorCode.IMPORT_DUPLICATED_LIBRARY_NAME]. 3469 * See [CompileTimeErrorCode.IMPORT_DUPLICATED_LIBRARY_NAME].
3570 */ 3470 */
3571 bool _checkForImportDuplicateLibraryName( 3471 bool _checkForImportDuplicateLibraryName(
3572 ImportDirective node, ImportElement importElement) { 3472 ImportDirective node, ImportElement importElement) {
3573 // prepare imported library 3473 // prepare imported library
3574 LibraryElement nodeLibrary = importElement.importedLibrary; 3474 LibraryElement nodeLibrary = importElement.importedLibrary;
3575 if (nodeLibrary == null) { 3475 if (nodeLibrary == null) {
3576 return false; 3476 return false;
3577 } 3477 }
3578 String name = nodeLibrary.name; 3478 String name = nodeLibrary.name;
(...skipping 18 matching lines...) Expand all
3597 return true; 3497 return true;
3598 } 3498 }
3599 } else { 3499 } else {
3600 _nameToImportElement[name] = nodeLibrary; 3500 _nameToImportElement[name] = nodeLibrary;
3601 } 3501 }
3602 // OK 3502 // OK
3603 return false; 3503 return false;
3604 } 3504 }
3605 3505
3606 /** 3506 /**
3607 * Check that if the visiting library is not system, then any passed library s hould not be SDK 3507 * Check that if the visiting library is not system, then any given library
3608 * internal library. 3508 * should not be SDK internal library. The [importElement] is the
3509 * [ImportElement] retrieved from the node, if the element in the node was
3510 * `null`, then this method is not called
3609 * 3511 *
3610 * @param node the import directive to evaluate
3611 * @param importElement the [ImportElement] retrieved from the node, if the el ement in the
3612 * node was `null`, then this method is not called
3613 * @return `true` if and only if an error code is generated on the passed node
3614 * See [CompileTimeErrorCode.IMPORT_INTERNAL_LIBRARY]. 3512 * See [CompileTimeErrorCode.IMPORT_INTERNAL_LIBRARY].
3615 */ 3513 */
3616 bool _checkForImportInternalLibrary( 3514 bool _checkForImportInternalLibrary(
3617 ImportDirective node, ImportElement importElement) { 3515 ImportDirective node, ImportElement importElement) {
3618 if (_isInSystemLibrary) { 3516 if (_isInSystemLibrary) {
3619 return false; 3517 return false;
3620 } 3518 }
3621 // should be private 3519 // should be private
3622 DartSdk sdk = _currentLibrary.context.sourceFactory.dartSdk; 3520 DartSdk sdk = _currentLibrary.context.sourceFactory.dartSdk;
3623 String uri = importElement.uri; 3521 String uri = importElement.uri;
3624 SdkLibrary sdkLibrary = sdk.getSdkLibrary(uri); 3522 SdkLibrary sdkLibrary = sdk.getSdkLibrary(uri);
3625 if (sdkLibrary == null) { 3523 if (sdkLibrary == null) {
3626 return false; 3524 return false;
3627 } 3525 }
3628 if (!sdkLibrary.isInternal) { 3526 if (!sdkLibrary.isInternal) {
3629 return false; 3527 return false;
3630 } 3528 }
3631 // report problem 3529 // report problem
3632 _errorReporter.reportErrorForNode( 3530 _errorReporter.reportErrorForNode(
3633 CompileTimeErrorCode.IMPORT_INTERNAL_LIBRARY, node, [node.uri]); 3531 CompileTimeErrorCode.IMPORT_INTERNAL_LIBRARY, node, [node.uri]);
3634 return true; 3532 return true;
3635 } 3533 }
3636 3534
3637 /** 3535 /**
3638 * For each class declaration, this method is called which verifies that all i nherited members are 3536 * For each class declaration, this method is called which verifies that all
3639 * inherited consistently. 3537 * inherited members are inherited consistently.
3640 * 3538 *
3641 * @return `true` if and only if an error code is generated on the passed node
3642 * See [StaticTypeWarningCode.INCONSISTENT_METHOD_INHERITANCE]. 3539 * See [StaticTypeWarningCode.INCONSISTENT_METHOD_INHERITANCE].
3643 */ 3540 */
3644 bool _checkForInconsistentMethodInheritance() { 3541 bool _checkForInconsistentMethodInheritance() {
3645 // Ensure that the inheritance manager has a chance to generate all errors 3542 // Ensure that the inheritance manager has a chance to generate all errors
3646 // we may care about, note that we ensure that the interfaces data since 3543 // we may care about, note that we ensure that the interfaces data since
3647 // there are no errors. 3544 // there are no errors.
3648 _inheritanceManager.getMapOfMembersInheritedFromInterfaces(_enclosingClass); 3545 _inheritanceManager.getMapOfMembersInheritedFromInterfaces(_enclosingClass);
3649 HashSet<AnalysisError> errors = 3546 HashSet<AnalysisError> errors =
3650 _inheritanceManager.getErrors(_enclosingClass); 3547 _inheritanceManager.getErrors(_enclosingClass);
3651 if (errors == null || errors.isEmpty) { 3548 if (errors == null || errors.isEmpty) {
3652 return false; 3549 return false;
3653 } 3550 }
3654 for (AnalysisError error in errors) { 3551 for (AnalysisError error in errors) {
3655 _errorReporter.reportError(error); 3552 _errorReporter.reportError(error);
3656 } 3553 }
3657 return true; 3554 return true;
3658 } 3555 }
3659 3556
3660 /** 3557 /**
3661 * This checks the given "typeReference" is not a type reference and that then the "name" is 3558 * Check that the given [typeReference] is not a type reference and that then
3662 * reference to an instance member. 3559 * the [name] is reference to an instance member.
3663 * 3560 *
3664 * @param typeReference the resolved [ClassElement] of the left hand side of t he expression,
3665 * or `null`, aka, the class element of 'C' in 'C.x', see
3666 * [getTypeReference]
3667 * @param name the accessed name to evaluate
3668 * @return `true` if and only if an error code is generated on the passed node
3669 * See [StaticTypeWarningCode.INSTANCE_ACCESS_TO_STATIC_MEMBER]. 3561 * See [StaticTypeWarningCode.INSTANCE_ACCESS_TO_STATIC_MEMBER].
3670 */ 3562 */
3671 bool _checkForInstanceAccessToStaticMember( 3563 bool _checkForInstanceAccessToStaticMember(
3672 ClassElement typeReference, SimpleIdentifier name) { 3564 ClassElement typeReference, SimpleIdentifier name) {
3673 // OK, in comment 3565 // OK, in comment
3674 if (_isInComment) { 3566 if (_isInComment) {
3675 return false; 3567 return false;
3676 } 3568 }
3677 // OK, target is a type 3569 // OK, target is a type
3678 if (typeReference != null) { 3570 if (typeReference != null) {
(...skipping 14 matching lines...) Expand all
3693 return false; 3585 return false;
3694 } 3586 }
3695 // report problem 3587 // report problem
3696 _errorReporter.reportErrorForNode( 3588 _errorReporter.reportErrorForNode(
3697 StaticTypeWarningCode.INSTANCE_ACCESS_TO_STATIC_MEMBER, name, 3589 StaticTypeWarningCode.INSTANCE_ACCESS_TO_STATIC_MEMBER, name,
3698 [name.name]); 3590 [name.name]);
3699 return true; 3591 return true;
3700 } 3592 }
3701 3593
3702 /** 3594 /**
3703 * This checks whether the given [executableElement] collides with the name of a static 3595 * Check whether the given [executableElement] collides with the name of a
3704 * method in one of its superclasses, and reports the appropriate warning if i t does. 3596 * static method in one of its superclasses, and reports the appropriate
3597 * warning if it does. The [errorNameTarget] is the node to report problems
3598 * on.
3705 * 3599 *
3706 * @param executableElement the method to check.
3707 * @param errorNameTarget the node to report problems on.
3708 * @return `true` if and only if a warning was generated.
3709 * See [StaticTypeWarningCode.INSTANCE_METHOD_NAME_COLLIDES_WITH_SUPERCLASS_ST ATIC]. 3600 * See [StaticTypeWarningCode.INSTANCE_METHOD_NAME_COLLIDES_WITH_SUPERCLASS_ST ATIC].
3710 */ 3601 */
3711 bool _checkForInstanceMethodNameCollidesWithSuperclassStatic( 3602 bool _checkForInstanceMethodNameCollidesWithSuperclassStatic(
3712 ExecutableElement executableElement, SimpleIdentifier errorNameTarget) { 3603 ExecutableElement executableElement, SimpleIdentifier errorNameTarget) {
3713 String executableElementName = executableElement.name; 3604 String executableElementName = executableElement.name;
3714 if (executableElement is! PropertyAccessorElement && 3605 if (executableElement is! PropertyAccessorElement &&
3715 !executableElement.isOperator) { 3606 !executableElement.isOperator) {
3716 HashSet<ClassElement> visitedClasses = new HashSet<ClassElement>(); 3607 HashSet<ClassElement> visitedClasses = new HashSet<ClassElement>();
3717 InterfaceType superclassType = _enclosingClass.supertype; 3608 InterfaceType superclassType = _enclosingClass.supertype;
3718 ClassElement superclassElement = 3609 ClassElement superclassElement =
(...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after
3768 } 3659 }
3769 superclassType = superclassElement.supertype; 3660 superclassType = superclassElement.supertype;
3770 superclassElement = 3661 superclassElement =
3771 superclassType == null ? null : superclassType.element; 3662 superclassType == null ? null : superclassType.element;
3772 } 3663 }
3773 } 3664 }
3774 return false; 3665 return false;
3775 } 3666 }
3776 3667
3777 /** 3668 /**
3778 * This verifies that an 'int' can be assigned to the parameter corresponding to the given 3669 * Verify that an 'int' can be assigned to the parameter corresponding to the
3779 * expression. This is used for prefix and postfix expressions where the argum ent value is 3670 * given [expression]. This is used for prefix and postfix expressions where
3780 * implicit. 3671 * the argument value is implicit.
3781 * 3672 *
3782 * @param argument the expression to which the operator is being applied
3783 * @return `true` if and only if an error code is generated on the passed node
3784 * See [StaticWarningCode.ARGUMENT_TYPE_NOT_ASSIGNABLE]. 3673 * See [StaticWarningCode.ARGUMENT_TYPE_NOT_ASSIGNABLE].
3785 */ 3674 */
3786 bool _checkForIntNotAssignable(Expression argument) { 3675 bool _checkForIntNotAssignable(Expression argument) {
3787 if (argument == null) { 3676 if (argument == null) {
3788 return false; 3677 return false;
3789 } 3678 }
3790 ParameterElement staticParameterElement = argument.staticParameterElement; 3679 ParameterElement staticParameterElement = argument.staticParameterElement;
3791 DartType staticParameterType = 3680 DartType staticParameterType =
3792 staticParameterElement == null ? null : staticParameterElement.type; 3681 staticParameterElement == null ? null : staticParameterElement.type;
3793 return _checkForArgumentTypeNotAssignable(argument, staticParameterType, 3682 return _checkForArgumentTypeNotAssignable(argument, staticParameterType,
3794 _intType, StaticWarningCode.ARGUMENT_TYPE_NOT_ASSIGNABLE); 3683 _intType, StaticWarningCode.ARGUMENT_TYPE_NOT_ASSIGNABLE);
3795 } 3684 }
3796 3685
3797 /** 3686 /**
3798 * This verifies that the passed [Annotation] isn't defined in a deferred libr ary. 3687 * Verify that the given [annotation] isn't defined in a deferred library.
3799 * 3688 *
3800 * @param node the [Annotation]
3801 * @return `true` if and only if an error code is generated on the passed node
3802 * See [CompileTimeErrorCode.INVALID_ANNOTATION_FROM_DEFERRED_LIBRARY]. 3689 * See [CompileTimeErrorCode.INVALID_ANNOTATION_FROM_DEFERRED_LIBRARY].
3803 */ 3690 */
3804 bool _checkForInvalidAnnotationFromDeferredLibrary(Annotation node) { 3691 bool _checkForInvalidAnnotationFromDeferredLibrary(Annotation node) {
3805 Identifier nameIdentifier = node.name; 3692 Identifier nameIdentifier = node.name;
3806 if (nameIdentifier is PrefixedIdentifier) { 3693 if (nameIdentifier is PrefixedIdentifier) {
3807 if (nameIdentifier.isDeferred) { 3694 if (nameIdentifier.isDeferred) {
3808 _errorReporter.reportErrorForNode( 3695 _errorReporter.reportErrorForNode(
3809 CompileTimeErrorCode.INVALID_ANNOTATION_FROM_DEFERRED_LIBRARY, 3696 CompileTimeErrorCode.INVALID_ANNOTATION_FROM_DEFERRED_LIBRARY,
3810 node.name); 3697 node.name);
3811 return true; 3698 return true;
3812 } 3699 }
3813 } 3700 }
3814 return false; 3701 return false;
3815 } 3702 }
3816 3703
3817 /** 3704 /**
3818 * This verifies that the passed left hand side and right hand side represent a valid assignment. 3705 * Verify that the given left hand side ([lhs]) and right hand side ([rhs])
3706 * represent a valid assignment.
3819 * 3707 *
3820 * @param lhs the left hand side expression
3821 * @param rhs the right hand side expression
3822 * @return `true` if and only if an error code is generated on the passed node
3823 * See [StaticTypeWarningCode.INVALID_ASSIGNMENT]. 3708 * See [StaticTypeWarningCode.INVALID_ASSIGNMENT].
3824 */ 3709 */
3825 bool _checkForInvalidAssignment(Expression lhs, Expression rhs) { 3710 bool _checkForInvalidAssignment(Expression lhs, Expression rhs) {
3826 if (lhs == null || rhs == null) { 3711 if (lhs == null || rhs == null) {
3827 return false; 3712 return false;
3828 } 3713 }
3829 VariableElement leftVariableElement = getVariableElement(lhs); 3714 VariableElement leftVariableElement = getVariableElement(lhs);
3830 DartType leftType = (leftVariableElement == null) 3715 DartType leftType = (leftVariableElement == null)
3831 ? getStaticType(lhs) 3716 ? getStaticType(lhs)
3832 : leftVariableElement.type; 3717 : leftVariableElement.type;
3833 DartType staticRightType = getStaticType(rhs); 3718 DartType staticRightType = getStaticType(rhs);
3834 if (!staticRightType.isAssignableTo(leftType)) { 3719 if (!staticRightType.isAssignableTo(leftType)) {
3835 _errorReporter.reportTypeErrorForNode( 3720 _errorReporter.reportTypeErrorForNode(
3836 StaticTypeWarningCode.INVALID_ASSIGNMENT, rhs, [ 3721 StaticTypeWarningCode.INVALID_ASSIGNMENT, rhs, [
3837 staticRightType, 3722 staticRightType,
3838 leftType 3723 leftType
3839 ]); 3724 ]);
3840 return true; 3725 return true;
3841 } 3726 }
3842 return false; 3727 return false;
3843 } 3728 }
3844 3729
3845 /** 3730 /**
3846 * Given an assignment using a compound assignment operator, this verifies tha t the given 3731 * Given an [assignment] using a compound assignment operator, this verifies
3847 * assignment is valid. 3732 * that the given assignment is valid. The [lhs] is the left hand side
3733 * expression. The [rhs] is the right hand side expression.
3848 * 3734 *
3849 * @param node the assignment expression being tested
3850 * @param lhs the left hand side expression
3851 * @param rhs the right hand side expression
3852 * @return `true` if and only if an error code is generated on the passed node
3853 * See [StaticTypeWarningCode.INVALID_ASSIGNMENT]. 3735 * See [StaticTypeWarningCode.INVALID_ASSIGNMENT].
3854 */ 3736 */
3855 bool _checkForInvalidCompoundAssignment( 3737 bool _checkForInvalidCompoundAssignment(
3856 AssignmentExpression node, Expression lhs, Expression rhs) { 3738 AssignmentExpression node, Expression lhs, Expression rhs) {
3857 if (lhs == null) { 3739 if (lhs == null) {
3858 return false; 3740 return false;
3859 } 3741 }
3860 VariableElement leftVariableElement = getVariableElement(lhs); 3742 VariableElement leftVariableElement = getVariableElement(lhs);
3861 DartType leftType = (leftVariableElement == null) 3743 DartType leftType = (leftVariableElement == null)
3862 ? getStaticType(lhs) 3744 ? getStaticType(lhs)
3863 : leftVariableElement.type; 3745 : leftVariableElement.type;
3864 MethodElement invokedMethod = node.staticElement; 3746 MethodElement invokedMethod = node.staticElement;
3865 if (invokedMethod == null) { 3747 if (invokedMethod == null) {
3866 return false; 3748 return false;
3867 } 3749 }
3868 DartType rightType = invokedMethod.type.returnType; 3750 DartType rightType = invokedMethod.type.returnType;
3869 if (leftType == null || rightType == null) { 3751 if (leftType == null || rightType == null) {
3870 return false; 3752 return false;
3871 } 3753 }
3872 if (!rightType.isAssignableTo(leftType)) { 3754 if (!rightType.isAssignableTo(leftType)) {
3873 _errorReporter.reportTypeErrorForNode( 3755 _errorReporter.reportTypeErrorForNode(
3874 StaticTypeWarningCode.INVALID_ASSIGNMENT, rhs, [rightType, leftType]); 3756 StaticTypeWarningCode.INVALID_ASSIGNMENT, rhs, [rightType, leftType]);
3875 return true; 3757 return true;
3876 } 3758 }
3877 return false; 3759 return false;
3878 } 3760 }
3879 3761
3880 /** 3762 /**
3881 * Check the given initializer to ensure that the field being initialized is a valid field. 3763 * Check the given [initializer] to ensure that the field being initialized is
3882 * 3764 * a valid field. The [fieldName] is the field name from the
3883 * @param node the field initializer being checked 3765 * [ConstructorFieldInitializer]. The [staticElement] is the static element
3884 * @param fieldName the field name from the [ConstructorFieldInitializer] 3766 * from the name in the [ConstructorFieldInitializer].
3885 * @param staticElement the static element from the name in the
3886 * [ConstructorFieldInitializer]
3887 */ 3767 */
3888 void _checkForInvalidField(ConstructorFieldInitializer node, 3768 void _checkForInvalidField(ConstructorFieldInitializer node,
3889 SimpleIdentifier fieldName, Element staticElement) { 3769 SimpleIdentifier fieldName, Element staticElement) {
3890 if (staticElement is FieldElement) { 3770 if (staticElement is FieldElement) {
3891 FieldElement fieldElement = staticElement; 3771 FieldElement fieldElement = staticElement;
3892 if (fieldElement.isSynthetic) { 3772 if (fieldElement.isSynthetic) {
3893 _errorReporter.reportErrorForNode( 3773 _errorReporter.reportErrorForNode(
3894 CompileTimeErrorCode.INITIALIZER_FOR_NON_EXISTENT_FIELD, node, 3774 CompileTimeErrorCode.INITIALIZER_FOR_NON_EXISTENT_FIELD, node,
3895 [fieldName]); 3775 [fieldName]);
3896 } else if (fieldElement.isStatic) { 3776 } else if (fieldElement.isStatic) {
3897 _errorReporter.reportErrorForNode( 3777 _errorReporter.reportErrorForNode(
3898 CompileTimeErrorCode.INITIALIZER_FOR_STATIC_FIELD, node, 3778 CompileTimeErrorCode.INITIALIZER_FOR_STATIC_FIELD, node,
3899 [fieldName]); 3779 [fieldName]);
3900 } 3780 }
3901 } else { 3781 } else {
3902 _errorReporter.reportErrorForNode( 3782 _errorReporter.reportErrorForNode(
3903 CompileTimeErrorCode.INITIALIZER_FOR_NON_EXISTENT_FIELD, node, 3783 CompileTimeErrorCode.INITIALIZER_FOR_NON_EXISTENT_FIELD, node,
3904 [fieldName]); 3784 [fieldName]);
3905 return; 3785 return;
3906 } 3786 }
3907 } 3787 }
3908 3788
3909 /** 3789 /**
3910 * Check to see whether the given function body has a modifier associated with it, and report it 3790 * Check to see whether the given function [body] has a modifier associated
3911 * as an error if it does. 3791 * with it, and report it as an error if it does.
3912 *
3913 * @param body the function body being checked
3914 * @param errorCode the error code to be reported if a modifier is found
3915 * @return `true` if an error was reported
3916 */ 3792 */
3917 bool _checkForInvalidModifierOnBody( 3793 bool _checkForInvalidModifierOnBody(
3918 FunctionBody body, CompileTimeErrorCode errorCode) { 3794 FunctionBody body, CompileTimeErrorCode errorCode) {
3919 sc.Token keyword = body.keyword; 3795 sc.Token keyword = body.keyword;
3920 if (keyword != null) { 3796 if (keyword != null) {
3921 _errorReporter.reportErrorForToken(errorCode, keyword, [keyword.lexeme]); 3797 _errorReporter.reportErrorForToken(errorCode, keyword, [keyword.lexeme]);
3922 return true; 3798 return true;
3923 } 3799 }
3924 return false; 3800 return false;
3925 } 3801 }
3926 3802
3927 /** 3803 /**
3928 * This verifies that the usage of the passed 'this' is valid. 3804 * Verify that the usage of the given 'this' is valid.
3929 * 3805 *
3930 * @param node the 'this' expression to evaluate
3931 * @return `true` if and only if an error code is generated on the passed node
3932 * See [CompileTimeErrorCode.INVALID_REFERENCE_TO_THIS]. 3806 * See [CompileTimeErrorCode.INVALID_REFERENCE_TO_THIS].
3933 */ 3807 */
3934 bool _checkForInvalidReferenceToThis(ThisExpression node) { 3808 bool _checkForInvalidReferenceToThis(ThisExpression node) {
3935 if (!_isThisInValidContext(node)) { 3809 if (!_isThisInValidContext(node)) {
3936 _errorReporter.reportErrorForNode( 3810 _errorReporter.reportErrorForNode(
3937 CompileTimeErrorCode.INVALID_REFERENCE_TO_THIS, node); 3811 CompileTimeErrorCode.INVALID_REFERENCE_TO_THIS, node);
3938 return true; 3812 return true;
3939 } 3813 }
3940 return false; 3814 return false;
3941 } 3815 }
3942 3816
3943 /** 3817 /**
3944 * Checks to ensure that the passed [ListLiteral] or [MapLiteral] does not hav e a type 3818 * Checks to ensure that the given list of type [arguments] does not have a
3945 * parameter as a type argument. 3819 * type parameter as a type argument. The [errorCode] is either
3946 * 3820 * [CompileTimeErrorCode.INVALID_TYPE_ARGUMENT_IN_CONST_LIST] or
3947 * @param arguments a non-`null`, non-empty [TypeName] node list from the resp ective 3821 * [CompileTimeErrorCode.INVALID_TYPE_ARGUMENT_IN_CONST_MAP].
3948 * [ListLiteral] or [MapLiteral]
3949 * @param errorCode either [CompileTimeErrorCode.INVALID_TYPE_ARGUMENT_IN_CONS T_LIST] or
3950 * [CompileTimeErrorCode.INVALID_TYPE_ARGUMENT_IN_CONST_MAP]
3951 * @return `true` if and only if an error code is generated on the passed node
3952 */ 3822 */
3953 bool _checkForInvalidTypeArgumentInConstTypedLiteral( 3823 bool _checkForInvalidTypeArgumentInConstTypedLiteral(
3954 NodeList<TypeName> arguments, ErrorCode errorCode) { 3824 NodeList<TypeName> arguments, ErrorCode errorCode) {
3955 bool foundError = false; 3825 bool foundError = false;
3956 for (TypeName typeName in arguments) { 3826 for (TypeName typeName in arguments) {
3957 if (typeName.type is TypeParameterType) { 3827 if (typeName.type is TypeParameterType) {
3958 _errorReporter.reportErrorForNode(errorCode, typeName, [typeName.name]); 3828 _errorReporter.reportErrorForNode(errorCode, typeName, [typeName.name]);
3959 foundError = true; 3829 foundError = true;
3960 } 3830 }
3961 } 3831 }
3962 return foundError; 3832 return foundError;
3963 } 3833 }
3964 3834
3965 /** 3835 /**
3966 * This verifies that the elements given [ListLiteral] are subtypes of the spe cified element 3836 * Verify that the elements given [ListLiteral] are subtypes of the specified
3967 * type. 3837 * element type. The [typeArguments] are the type arguments.
3968 * 3838 *
3969 * @param node the list literal to evaluate
3970 * @param typeArguments the type arguments, always non-`null`
3971 * @return `true` if and only if an error code is generated on the passed node
3972 * See [CompileTimeErrorCode.LIST_ELEMENT_TYPE_NOT_ASSIGNABLE], and 3839 * See [CompileTimeErrorCode.LIST_ELEMENT_TYPE_NOT_ASSIGNABLE], and
3973 * [StaticWarningCode.LIST_ELEMENT_TYPE_NOT_ASSIGNABLE]. 3840 * [StaticWarningCode.LIST_ELEMENT_TYPE_NOT_ASSIGNABLE].
3974 */ 3841 */
3975 bool _checkForListElementTypeNotAssignable( 3842 bool _checkForListElementTypeNotAssignable(
3976 ListLiteral node, TypeArgumentList typeArguments) { 3843 ListLiteral node, TypeArgumentList typeArguments) {
3977 NodeList<TypeName> typeNames = typeArguments.arguments; 3844 NodeList<TypeName> typeNames = typeArguments.arguments;
3978 if (typeNames.length < 1) { 3845 if (typeNames.length < 1) {
3979 return false; 3846 return false;
3980 } 3847 }
3981 DartType listElementType = typeNames[0].type; 3848 DartType listElementType = typeNames[0].type;
(...skipping 12 matching lines...) Expand all
3994 if (_checkForArgumentTypeNotAssignableWithExpectedTypes(element, 3861 if (_checkForArgumentTypeNotAssignableWithExpectedTypes(element,
3995 listElementType, 3862 listElementType,
3996 StaticWarningCode.LIST_ELEMENT_TYPE_NOT_ASSIGNABLE)) { 3863 StaticWarningCode.LIST_ELEMENT_TYPE_NOT_ASSIGNABLE)) {
3997 hasProblems = true; 3864 hasProblems = true;
3998 } 3865 }
3999 } 3866 }
4000 return hasProblems; 3867 return hasProblems;
4001 } 3868 }
4002 3869
4003 /** 3870 /**
4004 * This verifies that the key/value of entries of the given [MapLiteral] are s ubtypes of the 3871 * Verify that the key/value of entries of the given map [literal] are
4005 * key/value types specified in the type arguments. 3872 * subtypes of the key/value types specified in the type arguments. The
3873 * [typeArguments] are the type arguments.
4006 * 3874 *
4007 * @param node the map literal to evaluate
4008 * @param typeArguments the type arguments, always non-`null`
4009 * @return `true` if and only if an error code is generated on the passed node
4010 * See [CompileTimeErrorCode.MAP_KEY_TYPE_NOT_ASSIGNABLE], 3875 * See [CompileTimeErrorCode.MAP_KEY_TYPE_NOT_ASSIGNABLE],
4011 * [CompileTimeErrorCode.MAP_VALUE_TYPE_NOT_ASSIGNABLE], 3876 * [CompileTimeErrorCode.MAP_VALUE_TYPE_NOT_ASSIGNABLE],
4012 * [StaticWarningCode.MAP_KEY_TYPE_NOT_ASSIGNABLE], and 3877 * [StaticWarningCode.MAP_KEY_TYPE_NOT_ASSIGNABLE], and
4013 * [StaticWarningCode.MAP_VALUE_TYPE_NOT_ASSIGNABLE]. 3878 * [StaticWarningCode.MAP_VALUE_TYPE_NOT_ASSIGNABLE].
4014 */ 3879 */
4015 bool _checkForMapTypeNotAssignable( 3880 bool _checkForMapTypeNotAssignable(
4016 MapLiteral node, TypeArgumentList typeArguments) { 3881 MapLiteral node, TypeArgumentList typeArguments) {
4017 // Prepare maps key/value types. 3882 // Prepare maps key/value types.
4018 NodeList<TypeName> typeNames = typeArguments.arguments; 3883 NodeList<TypeName> typeNames = typeArguments.arguments;
4019 if (typeNames.length < 2) { 3884 if (typeNames.length < 2) {
(...skipping 26 matching lines...) Expand all
4046 } 3911 }
4047 if (_checkForArgumentTypeNotAssignableWithExpectedTypes( 3912 if (_checkForArgumentTypeNotAssignableWithExpectedTypes(
4048 value, valueType, StaticWarningCode.MAP_VALUE_TYPE_NOT_ASSIGNABLE)) { 3913 value, valueType, StaticWarningCode.MAP_VALUE_TYPE_NOT_ASSIGNABLE)) {
4049 hasProblems = true; 3914 hasProblems = true;
4050 } 3915 }
4051 } 3916 }
4052 return hasProblems; 3917 return hasProblems;
4053 } 3918 }
4054 3919
4055 /** 3920 /**
4056 * This verifies that the [enclosingClass] does not define members with the sa me name as 3921 * Verify that the [enclosingClass] does not define members with the same name
4057 * the enclosing class. 3922 * as the enclosing class.
4058 * 3923 *
4059 * @return `true` if and only if an error code is generated on the passed node
4060 * See [CompileTimeErrorCode.MEMBER_WITH_CLASS_NAME]. 3924 * See [CompileTimeErrorCode.MEMBER_WITH_CLASS_NAME].
4061 */ 3925 */
4062 bool _checkForMemberWithClassName() { 3926 bool _checkForMemberWithClassName() {
4063 if (_enclosingClass == null) { 3927 if (_enclosingClass == null) {
4064 return false; 3928 return false;
4065 } 3929 }
4066 String className = _enclosingClass.name; 3930 String className = _enclosingClass.name;
4067 if (className == null) { 3931 if (className == null) {
4068 return false; 3932 return false;
4069 } 3933 }
4070 bool problemReported = false; 3934 bool problemReported = false;
4071 // check accessors 3935 // check accessors
4072 for (PropertyAccessorElement accessor in _enclosingClass.accessors) { 3936 for (PropertyAccessorElement accessor in _enclosingClass.accessors) {
4073 if (className == accessor.name) { 3937 if (className == accessor.name) {
4074 _errorReporter.reportErrorForOffset( 3938 _errorReporter.reportErrorForOffset(
4075 CompileTimeErrorCode.MEMBER_WITH_CLASS_NAME, accessor.nameOffset, 3939 CompileTimeErrorCode.MEMBER_WITH_CLASS_NAME, accessor.nameOffset,
4076 className.length); 3940 className.length);
4077 problemReported = true; 3941 problemReported = true;
4078 } 3942 }
4079 } 3943 }
4080 // don't check methods, they would be constructors 3944 // don't check methods, they would be constructors
4081 // done 3945 // done
4082 return problemReported; 3946 return problemReported;
4083 } 3947 }
4084 3948
4085 /** 3949 /**
4086 * Check to make sure that all similarly typed accessors are of the same type (including inherited 3950 * Check to make sure that all similarly typed accessors are of the same type
4087 * accessors). 3951 * (including inherited accessors).
4088 * 3952 *
4089 * @param node the accessor currently being visited
4090 * @return `true` if and only if an error code is generated on the passed node
4091 * See [StaticWarningCode.MISMATCHED_GETTER_AND_SETTER_TYPES], and 3953 * See [StaticWarningCode.MISMATCHED_GETTER_AND_SETTER_TYPES], and
4092 * [StaticWarningCode.MISMATCHED_GETTER_AND_SETTER_TYPES_FROM_SUPERTYPE]. 3954 * [StaticWarningCode.MISMATCHED_GETTER_AND_SETTER_TYPES_FROM_SUPERTYPE].
4093 */ 3955 */
4094 bool _checkForMismatchedAccessorTypes( 3956 bool _checkForMismatchedAccessorTypes(
4095 Declaration accessorDeclaration, String accessorTextName) { 3957 Declaration accessorDeclaration, String accessorTextName) {
4096 ExecutableElement accessorElement = 3958 ExecutableElement accessorElement =
4097 accessorDeclaration.element as ExecutableElement; 3959 accessorDeclaration.element as ExecutableElement;
4098 if (accessorElement is! PropertyAccessorElement) { 3960 if (accessorElement is! PropertyAccessorElement) {
4099 return false; 3961 return false;
4100 } 3962 }
(...skipping 69 matching lines...) Expand 10 before | Expand all | Expand 10 after
4170 setterType, 4032 setterType,
4171 getterType, 4033 getterType,
4172 enclosingClassForCounterpart.displayName 4034 enclosingClassForCounterpart.displayName
4173 ]); 4035 ]);
4174 } 4036 }
4175 } 4037 }
4176 return false; 4038 return false;
4177 } 4039 }
4178 4040
4179 /** 4041 /**
4180 * Check to make sure that switch statements whose static type is an enum type either have a 4042 * Check to make sure that the given switch [statement] whose static type is
4181 * default case or include all of the enum constants. 4043 * an enum type either have a default case or include all of the enum
4182 * 4044 * constants.
4183 * @param statement the switch statement to check
4184 * @return `true` if and only if an error code is generated on the passed node
4185 */ 4045 */
4186 bool _checkForMissingEnumConstantInSwitch(SwitchStatement statement) { 4046 bool _checkForMissingEnumConstantInSwitch(SwitchStatement statement) {
4187 // TODO(brianwilkerson) This needs to be checked after constant values have 4047 // TODO(brianwilkerson) This needs to be checked after constant values have
4188 // been computed. 4048 // been computed.
4189 Expression expression = statement.expression; 4049 Expression expression = statement.expression;
4190 DartType expressionType = getStaticType(expression); 4050 DartType expressionType = getStaticType(expression);
4191 if (expressionType == null) { 4051 if (expressionType == null) {
4192 return false; 4052 return false;
4193 } 4053 }
4194 Element expressionElement = expressionType.element; 4054 Element expressionElement = expressionType.element;
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
4226 } 4086 }
4227 for (int i = 0; i < nameCount; i++) { 4087 for (int i = 0; i < nameCount; i++) {
4228 _errorReporter.reportErrorForNode( 4088 _errorReporter.reportErrorForNode(
4229 CompileTimeErrorCode.MISSING_ENUM_CONSTANT_IN_SWITCH, statement, 4089 CompileTimeErrorCode.MISSING_ENUM_CONSTANT_IN_SWITCH, statement,
4230 [constantNames[i]]); 4090 [constantNames[i]]);
4231 } 4091 }
4232 return true; 4092 return true;
4233 } 4093 }
4234 4094
4235 /** 4095 /**
4236 * This verifies that the given function body does not contain return statemen ts that both have 4096 * Verify that the given function [body] does not contain return statements
4237 * and do not have return values. 4097 * that both have and do not have return values.
4238 * 4098 *
4239 * @param node the function body being tested
4240 * @return `true` if and only if an error code is generated on the passed node
4241 * See [StaticWarningCode.MIXED_RETURN_TYPES]. 4099 * See [StaticWarningCode.MIXED_RETURN_TYPES].
4242 */ 4100 */
4243 bool _checkForMixedReturns(BlockFunctionBody node) { 4101 bool _checkForMixedReturns(BlockFunctionBody node) {
4244 if (_hasReturnWithoutValue) { 4102 if (_hasReturnWithoutValue) {
4245 return false; 4103 return false;
4246 } 4104 }
4247 int withCount = _returnsWith.length; 4105 int withCount = _returnsWith.length;
4248 int withoutCount = _returnsWithout.length; 4106 int withoutCount = _returnsWithout.length;
4249 if (withCount > 0 && withoutCount > 0) { 4107 if (withCount > 0 && withoutCount > 0) {
4250 for (int i = 0; i < withCount; i++) { 4108 for (int i = 0; i < withCount; i++) {
4251 _errorReporter.reportErrorForToken(StaticWarningCode.MIXED_RETURN_TYPES, 4109 _errorReporter.reportErrorForToken(StaticWarningCode.MIXED_RETURN_TYPES,
4252 _returnsWith[i].returnKeyword); 4110 _returnsWith[i].returnKeyword);
4253 } 4111 }
4254 for (int i = 0; i < withoutCount; i++) { 4112 for (int i = 0; i < withoutCount; i++) {
4255 _errorReporter.reportErrorForToken(StaticWarningCode.MIXED_RETURN_TYPES, 4113 _errorReporter.reportErrorForToken(StaticWarningCode.MIXED_RETURN_TYPES,
4256 _returnsWithout[i].returnKeyword); 4114 _returnsWithout[i].returnKeyword);
4257 } 4115 }
4258 return true; 4116 return true;
4259 } 4117 }
4260 return false; 4118 return false;
4261 } 4119 }
4262 4120
4263 /** 4121 /**
4264 * This verifies that the passed mixin does not have an explicitly declared co nstructor. 4122 * Verify that the given mixin does not have an explicitly declared
4123 * constructor. The [mixinName] is the node to report problem on. The
4124 * [mixinElement] is the mixing to evaluate.
4265 * 4125 *
4266 * @param mixinName the node to report problem on
4267 * @param mixinElement the mixing to evaluate
4268 * @return `true` if and only if an error code is generated on the passed node
4269 * See [CompileTimeErrorCode.MIXIN_DECLARES_CONSTRUCTOR]. 4126 * See [CompileTimeErrorCode.MIXIN_DECLARES_CONSTRUCTOR].
4270 */ 4127 */
4271 bool _checkForMixinDeclaresConstructor( 4128 bool _checkForMixinDeclaresConstructor(
4272 TypeName mixinName, ClassElement mixinElement) { 4129 TypeName mixinName, ClassElement mixinElement) {
4273 for (ConstructorElement constructor in mixinElement.constructors) { 4130 for (ConstructorElement constructor in mixinElement.constructors) {
4274 if (!constructor.isSynthetic && !constructor.isFactory) { 4131 if (!constructor.isSynthetic && !constructor.isFactory) {
4275 _errorReporter.reportErrorForNode( 4132 _errorReporter.reportErrorForNode(
4276 CompileTimeErrorCode.MIXIN_DECLARES_CONSTRUCTOR, mixinName, 4133 CompileTimeErrorCode.MIXIN_DECLARES_CONSTRUCTOR, mixinName,
4277 [mixinElement.name]); 4134 [mixinElement.name]);
4278 return true; 4135 return true;
4279 } 4136 }
4280 } 4137 }
4281 return false; 4138 return false;
4282 } 4139 }
4283 4140
4284 /** 4141 /**
4285 * This verifies that the passed mixin has the 'Object' superclass. 4142 * Verify that the given mixin has the 'Object' superclass. The [mixinName] is
4143 * the node to report problem on. The [mixinElement] is the mixing to
4144 * evaluate.
4286 * 4145 *
4287 * @param mixinName the node to report problem on
4288 * @param mixinElement the mixing to evaluate
4289 * @return `true` if and only if an error code is generated on the passed node
4290 * See [CompileTimeErrorCode.MIXIN_INHERITS_FROM_NOT_OBJECT]. 4146 * See [CompileTimeErrorCode.MIXIN_INHERITS_FROM_NOT_OBJECT].
4291 */ 4147 */
4292 bool _checkForMixinInheritsNotFromObject( 4148 bool _checkForMixinInheritsNotFromObject(
4293 TypeName mixinName, ClassElement mixinElement) { 4149 TypeName mixinName, ClassElement mixinElement) {
4294 InterfaceType mixinSupertype = mixinElement.supertype; 4150 InterfaceType mixinSupertype = mixinElement.supertype;
4295 if (mixinSupertype != null) { 4151 if (mixinSupertype != null) {
4296 if (!mixinSupertype.isObject || 4152 if (!mixinSupertype.isObject ||
4297 !mixinElement.isTypedef && mixinElement.mixins.length != 0) { 4153 !mixinElement.isTypedef && mixinElement.mixins.length != 0) {
4298 _errorReporter.reportErrorForNode( 4154 _errorReporter.reportErrorForNode(
4299 CompileTimeErrorCode.MIXIN_INHERITS_FROM_NOT_OBJECT, mixinName, 4155 CompileTimeErrorCode.MIXIN_INHERITS_FROM_NOT_OBJECT, mixinName,
4300 [mixinElement.name]); 4156 [mixinElement.name]);
4301 return true; 4157 return true;
4302 } 4158 }
4303 } 4159 }
4304 return false; 4160 return false;
4305 } 4161 }
4306 4162
4307 /** 4163 /**
4308 * This verifies that the passed mixin does not reference 'super'. 4164 * Verify that the given mixin does not reference 'super'. The [mixinName] is
4165 * the node to report problem on. The [mixinElement] is the mixing to
4166 * evaluate.
4309 * 4167 *
4310 * @param mixinName the node to report problem on
4311 * @param mixinElement the mixing to evaluate
4312 * @return `true` if and only if an error code is generated on the passed node
4313 * See [CompileTimeErrorCode.MIXIN_REFERENCES_SUPER]. 4168 * See [CompileTimeErrorCode.MIXIN_REFERENCES_SUPER].
4314 */ 4169 */
4315 bool _checkForMixinReferencesSuper( 4170 bool _checkForMixinReferencesSuper(
4316 TypeName mixinName, ClassElement mixinElement) { 4171 TypeName mixinName, ClassElement mixinElement) {
4317 if (mixinElement.hasReferenceToSuper) { 4172 if (mixinElement.hasReferenceToSuper) {
4318 _errorReporter.reportErrorForNode( 4173 _errorReporter.reportErrorForNode(
4319 CompileTimeErrorCode.MIXIN_REFERENCES_SUPER, mixinName, 4174 CompileTimeErrorCode.MIXIN_REFERENCES_SUPER, mixinName,
4320 [mixinElement.name]); 4175 [mixinElement.name]);
4321 } 4176 }
4322 return false; 4177 return false;
4323 } 4178 }
4324 4179
4325 /** 4180 /**
4326 * This verifies that the passed constructor has at most one 'super' initializ er. 4181 * Verify that the given [constructor] has at most one 'super' initializer.
4327 * 4182 *
4328 * @param node the constructor declaration to evaluate
4329 * @return `true` if and only if an error code is generated on the passed node
4330 * See [CompileTimeErrorCode.MULTIPLE_SUPER_INITIALIZERS]. 4183 * See [CompileTimeErrorCode.MULTIPLE_SUPER_INITIALIZERS].
4331 */ 4184 */
4332 bool _checkForMultipleSuperInitializers(ConstructorDeclaration node) { 4185 bool _checkForMultipleSuperInitializers(ConstructorDeclaration node) {
4333 int numSuperInitializers = 0; 4186 int numSuperInitializers = 0;
4334 for (ConstructorInitializer initializer in node.initializers) { 4187 for (ConstructorInitializer initializer in node.initializers) {
4335 if (initializer is SuperConstructorInvocation) { 4188 if (initializer is SuperConstructorInvocation) {
4336 numSuperInitializers++; 4189 numSuperInitializers++;
4337 if (numSuperInitializers > 1) { 4190 if (numSuperInitializers > 1) {
4338 _errorReporter.reportErrorForNode( 4191 _errorReporter.reportErrorForNode(
4339 CompileTimeErrorCode.MULTIPLE_SUPER_INITIALIZERS, initializer); 4192 CompileTimeErrorCode.MULTIPLE_SUPER_INITIALIZERS, initializer);
4340 } 4193 }
4341 } 4194 }
4342 } 4195 }
4343 return numSuperInitializers > 0; 4196 return numSuperInitializers > 0;
4344 } 4197 }
4345 4198
4346 /** 4199 /**
4347 * Checks to ensure that native function bodies can only in SDK code. 4200 * Checks to ensure that the given native function [body] is in SDK code.
4348 * 4201 *
4349 * @param node the native function body to test
4350 * @return `true` if and only if an error code is generated on the passed node
4351 * See [ParserErrorCode.NATIVE_FUNCTION_BODY_IN_NON_SDK_CODE]. 4202 * See [ParserErrorCode.NATIVE_FUNCTION_BODY_IN_NON_SDK_CODE].
4352 */ 4203 */
4353 bool _checkForNativeFunctionBodyInNonSDKCode(NativeFunctionBody node) { 4204 bool _checkForNativeFunctionBodyInNonSDKCode(NativeFunctionBody node) {
4354 if (!_isInSystemLibrary && !_hasExtUri) { 4205 if (!_isInSystemLibrary && !_hasExtUri) {
4355 _errorReporter.reportErrorForNode( 4206 _errorReporter.reportErrorForNode(
4356 ParserErrorCode.NATIVE_FUNCTION_BODY_IN_NON_SDK_CODE, node); 4207 ParserErrorCode.NATIVE_FUNCTION_BODY_IN_NON_SDK_CODE, node);
4357 return true; 4208 return true;
4358 } 4209 }
4359 return false; 4210 return false;
4360 } 4211 }
4361 4212
4362 /** 4213 /**
4363 * This verifies that the passed 'new' instance creation expression invokes ex isting constructor. 4214 * Verify that the given instance creation [expression] invokes an existing
4215 * constructor. The [constructorName] is the constructor name. The [typeName]
4216 * is the name of the type defining the constructor.
4364 * 4217 *
4365 * This method assumes that the instance creation was tested to be 'new' befor e being called. 4218 * This method assumes that the instance creation was tested to be 'new'
4219 * before being called.
4366 * 4220 *
4367 * @param node the instance creation expression to evaluate
4368 * @param constructorName the constructor name, always non-`null`
4369 * @param typeName the name of the type defining the constructor, always non-` null`
4370 * @return `true` if and only if an error code is generated on the passed node
4371 * See [StaticWarningCode.NEW_WITH_UNDEFINED_CONSTRUCTOR]. 4221 * See [StaticWarningCode.NEW_WITH_UNDEFINED_CONSTRUCTOR].
4372 */ 4222 */
4373 bool _checkForNewWithUndefinedConstructor(InstanceCreationExpression node, 4223 bool _checkForNewWithUndefinedConstructor(InstanceCreationExpression node,
4374 ConstructorName constructorName, TypeName typeName) { 4224 ConstructorName constructorName, TypeName typeName) {
4375 // OK if resolved 4225 // OK if resolved
4376 if (node.staticElement != null) { 4226 if (node.staticElement != null) {
4377 return false; 4227 return false;
4378 } 4228 }
4379 DartType type = typeName.type; 4229 DartType type = typeName.type;
4380 if (type is InterfaceType) { 4230 if (type is InterfaceType) {
(...skipping 15 matching lines...) Expand all
4396 ]); 4246 ]);
4397 } else { 4247 } else {
4398 _errorReporter.reportErrorForNode( 4248 _errorReporter.reportErrorForNode(
4399 StaticWarningCode.NEW_WITH_UNDEFINED_CONSTRUCTOR_DEFAULT, 4249 StaticWarningCode.NEW_WITH_UNDEFINED_CONSTRUCTOR_DEFAULT,
4400 constructorName, [className]); 4250 constructorName, [className]);
4401 } 4251 }
4402 return true; 4252 return true;
4403 } 4253 }
4404 4254
4405 /** 4255 /**
4406 * This checks that if the passed class declaration implicitly calls default c onstructor of its 4256 * Check that if the given class [declaration] implicitly calls default
4407 * superclass, there should be such default constructor - implicit or explicit . 4257 * constructor of its superclass, there should be such default constructor -
4258 * implicit or explicit.
4408 * 4259 *
4409 * @param node the [ClassDeclaration] to evaluate
4410 * @return `true` if and only if an error code is generated on the passed node
4411 * See [CompileTimeErrorCode.NO_DEFAULT_SUPER_CONSTRUCTOR_IMPLICIT]. 4260 * See [CompileTimeErrorCode.NO_DEFAULT_SUPER_CONSTRUCTOR_IMPLICIT].
4412 */ 4261 */
4413 bool _checkForNoDefaultSuperConstructorImplicit(ClassDeclaration node) { 4262 bool _checkForNoDefaultSuperConstructorImplicit(ClassDeclaration node) {
4414 // do nothing if mixin errors have already been reported for this class. 4263 // do nothing if mixin errors have already been reported for this class.
4415 ClassElementImpl enclosingClass = _enclosingClass; 4264 ClassElementImpl enclosingClass = _enclosingClass;
4416 if (enclosingClass.mixinErrorsReported) { 4265 if (enclosingClass.mixinErrorsReported) {
4417 return false; 4266 return false;
4418 } 4267 }
4419 // do nothing if there is explicit constructor 4268 // do nothing if there is explicit constructor
4420 List<ConstructorElement> constructors = _enclosingClass.constructors; 4269 List<ConstructorElement> constructors = _enclosingClass.constructors;
(...skipping 23 matching lines...) Expand all
4444 } 4293 }
4445 } 4294 }
4446 // report problem 4295 // report problem
4447 _errorReporter.reportErrorForNode( 4296 _errorReporter.reportErrorForNode(
4448 CompileTimeErrorCode.NO_DEFAULT_SUPER_CONSTRUCTOR_IMPLICIT, node.name, 4297 CompileTimeErrorCode.NO_DEFAULT_SUPER_CONSTRUCTOR_IMPLICIT, node.name,
4449 [superType.displayName]); 4298 [superType.displayName]);
4450 return true; 4299 return true;
4451 } 4300 }
4452 4301
4453 /** 4302 /**
4454 * This checks that passed class declaration overrides all members required by its superclasses 4303 * Check that the given class declaration overrides all members required by
4455 * and interfaces. 4304 * its superclasses and interfaces. The [classNameNode] is the
4305 * [SimpleIdentifier] to be used if there is a violation, this is either the
4306 * named from the [ClassDeclaration] or from the [ClassTypeAlias].
4456 * 4307 *
4457 * @param classNameNode the [SimpleIdentifier] to be used if there is a violat ion, this is
4458 * either the named from the [ClassDeclaration] or from the [ClassTyp eAlias].
4459 * @return `true` if and only if an error code is generated on the passed node
4460 * See [StaticWarningCode.NON_ABSTRACT_CLASS_INHERITS_ABSTRACT_MEMBER_ONE], 4308 * See [StaticWarningCode.NON_ABSTRACT_CLASS_INHERITS_ABSTRACT_MEMBER_ONE],
4461 * [StaticWarningCode.NON_ABSTRACT_CLASS_INHERITS_ABSTRACT_MEMBER_TWO], 4309 * [StaticWarningCode.NON_ABSTRACT_CLASS_INHERITS_ABSTRACT_MEMBER_TWO],
4462 * [StaticWarningCode.NON_ABSTRACT_CLASS_INHERITS_ABSTRACT_MEMBER_THREE], 4310 * [StaticWarningCode.NON_ABSTRACT_CLASS_INHERITS_ABSTRACT_MEMBER_THREE],
4463 * [StaticWarningCode.NON_ABSTRACT_CLASS_INHERITS_ABSTRACT_MEMBER_FOUR], and 4311 * [StaticWarningCode.NON_ABSTRACT_CLASS_INHERITS_ABSTRACT_MEMBER_FOUR], and
4464 * [StaticWarningCode.NON_ABSTRACT_CLASS_INHERITS_ABSTRACT_MEMBER_FIVE_PLUS]. 4312 * [StaticWarningCode.NON_ABSTRACT_CLASS_INHERITS_ABSTRACT_MEMBER_FIVE_PLUS].
4465 */ 4313 */
4466 bool _checkForNonAbstractClassInheritsAbstractMember( 4314 bool _checkForNonAbstractClassInheritsAbstractMember(
4467 SimpleIdentifier classNameNode) { 4315 SimpleIdentifier classNameNode) {
4468 if (_enclosingClass.isAbstract) { 4316 if (_enclosingClass.isAbstract) {
4469 return false; 4317 return false;
(...skipping 152 matching lines...) Expand 10 before | Expand all | Expand 10 after
4622 stringMembersArray.length - 4 4470 stringMembersArray.length - 4
4623 ]); 4471 ]);
4624 } 4472 }
4625 analysisError.setProperty( 4473 analysisError.setProperty(
4626 ErrorProperty.UNIMPLEMENTED_METHODS, missingOverridesArray); 4474 ErrorProperty.UNIMPLEMENTED_METHODS, missingOverridesArray);
4627 _errorReporter.reportError(analysisError); 4475 _errorReporter.reportError(analysisError);
4628 return true; 4476 return true;
4629 } 4477 }
4630 4478
4631 /** 4479 /**
4632 * Checks to ensure that the expressions that need to be of type bool, are. Ot herwise an error is 4480 * Check to ensure that the [condition] is of type bool, are. Otherwise an
4633 * reported on the expression. 4481 * error is reported on the expression.
4634 * 4482 *
4635 * @param condition the conditional expression to test
4636 * @return `true` if and only if an error code is generated on the passed node
4637 * See [StaticTypeWarningCode.NON_BOOL_CONDITION]. 4483 * See [StaticTypeWarningCode.NON_BOOL_CONDITION].
4638 */ 4484 */
4639 bool _checkForNonBoolCondition(Expression condition) { 4485 bool _checkForNonBoolCondition(Expression condition) {
4640 DartType conditionType = getStaticType(condition); 4486 DartType conditionType = getStaticType(condition);
4641 if (conditionType != null && !conditionType.isAssignableTo(_boolType)) { 4487 if (conditionType != null && !conditionType.isAssignableTo(_boolType)) {
4642 _errorReporter.reportErrorForNode( 4488 _errorReporter.reportErrorForNode(
4643 StaticTypeWarningCode.NON_BOOL_CONDITION, condition); 4489 StaticTypeWarningCode.NON_BOOL_CONDITION, condition);
4644 return true; 4490 return true;
4645 } 4491 }
4646 return false; 4492 return false;
4647 } 4493 }
4648 4494
4649 /** 4495 /**
4650 * This verifies that the passed assert statement has either a 'bool' or '() - > bool' input. 4496 * Verify that the given assert [statement] has either a 'bool' or
4497 * '() -> bool' input.
4651 * 4498 *
4652 * @param node the assert statement to evaluate
4653 * @return `true` if and only if an error code is generated on the passed node
4654 * See [StaticTypeWarningCode.NON_BOOL_EXPRESSION]. 4499 * See [StaticTypeWarningCode.NON_BOOL_EXPRESSION].
4655 */ 4500 */
4656 bool _checkForNonBoolExpression(AssertStatement node) { 4501 bool _checkForNonBoolExpression(AssertStatement node) {
4657 Expression expression = node.condition; 4502 Expression expression = node.condition;
4658 DartType type = getStaticType(expression); 4503 DartType type = getStaticType(expression);
4659 if (type is InterfaceType) { 4504 if (type is InterfaceType) {
4660 if (!type.isAssignableTo(_boolType)) { 4505 if (!type.isAssignableTo(_boolType)) {
4661 _errorReporter.reportErrorForNode( 4506 _errorReporter.reportErrorForNode(
4662 StaticTypeWarningCode.NON_BOOL_EXPRESSION, expression); 4507 StaticTypeWarningCode.NON_BOOL_EXPRESSION, expression);
4663 return true; 4508 return true;
4664 } 4509 }
4665 } else if (type is FunctionType) { 4510 } else if (type is FunctionType) {
4666 FunctionType functionType = type; 4511 FunctionType functionType = type;
4667 if (functionType.typeArguments.length == 0 && 4512 if (functionType.typeArguments.length == 0 &&
4668 !functionType.returnType.isAssignableTo(_boolType)) { 4513 !functionType.returnType.isAssignableTo(_boolType)) {
4669 _errorReporter.reportErrorForNode( 4514 _errorReporter.reportErrorForNode(
4670 StaticTypeWarningCode.NON_BOOL_EXPRESSION, expression); 4515 StaticTypeWarningCode.NON_BOOL_EXPRESSION, expression);
4671 return true; 4516 return true;
4672 } 4517 }
4673 } 4518 }
4674 return false; 4519 return false;
4675 } 4520 }
4676 4521
4677 /** 4522 /**
4678 * Checks to ensure that the given expression is assignable to bool. 4523 * Checks to ensure that the given [expression] is assignable to bool.
4679 * 4524 *
4680 * @param expression the expression expression to test
4681 * @return `true` if and only if an error code is generated on the passed node
4682 * See [StaticTypeWarningCode.NON_BOOL_NEGATION_EXPRESSION]. 4525 * See [StaticTypeWarningCode.NON_BOOL_NEGATION_EXPRESSION].
4683 */ 4526 */
4684 bool _checkForNonBoolNegationExpression(Expression expression) { 4527 bool _checkForNonBoolNegationExpression(Expression expression) {
4685 DartType conditionType = getStaticType(expression); 4528 DartType conditionType = getStaticType(expression);
4686 if (conditionType != null && !conditionType.isAssignableTo(_boolType)) { 4529 if (conditionType != null && !conditionType.isAssignableTo(_boolType)) {
4687 _errorReporter.reportErrorForNode( 4530 _errorReporter.reportErrorForNode(
4688 StaticTypeWarningCode.NON_BOOL_NEGATION_EXPRESSION, expression); 4531 StaticTypeWarningCode.NON_BOOL_NEGATION_EXPRESSION, expression);
4689 return true; 4532 return true;
4690 } 4533 }
4691 return false; 4534 return false;
4692 } 4535 }
4693 4536
4694 /** 4537 /**
4695 * This verifies the passed map literal either: 4538 * Verify the given map [literal] either:
4696 * * has `const modifier` 4539 * * has `const modifier`
4697 * * has explicit type arguments 4540 * * has explicit type arguments
4698 * * is not start of the statement 4541 * * is not start of the statement
4699 * 4542 *
4700 * @param node the map literal to evaluate
4701 * @return `true` if and only if an error code is generated on the passed node
4702 * See [CompileTimeErrorCode.NON_CONST_MAP_AS_EXPRESSION_STATEMENT]. 4543 * See [CompileTimeErrorCode.NON_CONST_MAP_AS_EXPRESSION_STATEMENT].
4703 */ 4544 */
4704 bool _checkForNonConstMapAsExpressionStatement(MapLiteral node) { 4545 bool _checkForNonConstMapAsExpressionStatement(MapLiteral node) {
4705 // "const" 4546 // "const"
4706 if (node.constKeyword != null) { 4547 if (node.constKeyword != null) {
4707 return false; 4548 return false;
4708 } 4549 }
4709 // has type arguments 4550 // has type arguments
4710 if (node.typeArguments != null) { 4551 if (node.typeArguments != null) {
4711 return false; 4552 return false;
4712 } 4553 }
4713 // prepare statement 4554 // prepare statement
4714 Statement statement = 4555 Statement statement =
4715 node.getAncestor((node) => node is ExpressionStatement); 4556 node.getAncestor((node) => node is ExpressionStatement);
4716 if (statement == null) { 4557 if (statement == null) {
4717 return false; 4558 return false;
4718 } 4559 }
4719 // OK, statement does not start with map 4560 // OK, statement does not start with map
4720 if (!identical(statement.beginToken, node.beginToken)) { 4561 if (!identical(statement.beginToken, node.beginToken)) {
4721 return false; 4562 return false;
4722 } 4563 }
4723 // report problem 4564 // report problem
4724 _errorReporter.reportErrorForNode( 4565 _errorReporter.reportErrorForNode(
4725 CompileTimeErrorCode.NON_CONST_MAP_AS_EXPRESSION_STATEMENT, node); 4566 CompileTimeErrorCode.NON_CONST_MAP_AS_EXPRESSION_STATEMENT, node);
4726 return true; 4567 return true;
4727 } 4568 }
4728 4569
4729 /** 4570 /**
4730 * This verifies the passed method declaration of operator `[]=`, has `void` r eturn 4571 * Verify that the given method [declaration] of operator `[]=`, has `void`
4731 * type. 4572 * return type.
4732 * 4573 *
4733 * @param node the method declaration to evaluate
4734 * @return `true` if and only if an error code is generated on the passed node
4735 * See [StaticWarningCode.NON_VOID_RETURN_FOR_OPERATOR]. 4574 * See [StaticWarningCode.NON_VOID_RETURN_FOR_OPERATOR].
4736 */ 4575 */
4737 bool _checkForNonVoidReturnTypeForOperator(MethodDeclaration node) { 4576 bool _checkForNonVoidReturnTypeForOperator(MethodDeclaration node) {
4738 // check that []= operator 4577 // check that []= operator
4739 SimpleIdentifier name = node.name; 4578 SimpleIdentifier name = node.name;
4740 if (name.name != "[]=") { 4579 if (name.name != "[]=") {
4741 return false; 4580 return false;
4742 } 4581 }
4743 // check return type 4582 // check return type
4744 TypeName typeName = node.returnType; 4583 TypeName typeName = node.returnType;
4745 if (typeName != null) { 4584 if (typeName != null) {
4746 DartType type = typeName.type; 4585 DartType type = typeName.type;
4747 if (type != null && !type.isVoid) { 4586 if (type != null && !type.isVoid) {
4748 _errorReporter.reportErrorForNode( 4587 _errorReporter.reportErrorForNode(
4749 StaticWarningCode.NON_VOID_RETURN_FOR_OPERATOR, typeName); 4588 StaticWarningCode.NON_VOID_RETURN_FOR_OPERATOR, typeName);
4750 } 4589 }
4751 } 4590 }
4752 // no warning 4591 // no warning
4753 return false; 4592 return false;
4754 } 4593 }
4755 4594
4756 /** 4595 /**
4757 * This verifies the passed setter has no return type or the `void` return typ e. 4596 * Verify the given setter has no return type or the `void` return type.
4758 * 4597 *
4759 * @param typeName the type name to evaluate
4760 * @return `true` if and only if an error code is generated on the passed node
4761 * See [StaticWarningCode.NON_VOID_RETURN_FOR_SETTER]. 4598 * See [StaticWarningCode.NON_VOID_RETURN_FOR_SETTER].
4762 */ 4599 */
4763 bool _checkForNonVoidReturnTypeForSetter(TypeName typeName) { 4600 bool _checkForNonVoidReturnTypeForSetter(TypeName typeName) {
4764 if (typeName != null) { 4601 if (typeName != null) {
4765 DartType type = typeName.type; 4602 DartType type = typeName.type;
4766 if (type != null && !type.isVoid) { 4603 if (type != null && !type.isVoid) {
4767 _errorReporter.reportErrorForNode( 4604 _errorReporter.reportErrorForNode(
4768 StaticWarningCode.NON_VOID_RETURN_FOR_SETTER, typeName); 4605 StaticWarningCode.NON_VOID_RETURN_FOR_SETTER, typeName);
4769 } 4606 }
4770 } 4607 }
4771 return false; 4608 return false;
4772 } 4609 }
4773 4610
4774 /** 4611 /**
4775 * This verifies the passed operator-method declaration, does not have an opti onal parameter. 4612 * Verify the given operator-method [declaration], does not have an optional
4613 * parameter. This method assumes that the method declaration was tested to be
4614 * an operator declaration before being called.
4776 * 4615 *
4777 * This method assumes that the method declaration was tested to be an operato r declaration before
4778 * being called.
4779 *
4780 * @param node the method declaration to evaluate
4781 * @return `true` if and only if an error code is generated on the passed node
4782 * See [CompileTimeErrorCode.OPTIONAL_PARAMETER_IN_OPERATOR]. 4616 * See [CompileTimeErrorCode.OPTIONAL_PARAMETER_IN_OPERATOR].
4783 */ 4617 */
4784 bool _checkForOptionalParameterInOperator(MethodDeclaration node) { 4618 bool _checkForOptionalParameterInOperator(MethodDeclaration node) {
4785 FormalParameterList parameterList = node.parameters; 4619 FormalParameterList parameterList = node.parameters;
4786 if (parameterList == null) { 4620 if (parameterList == null) {
4787 return false; 4621 return false;
4788 } 4622 }
4789 bool foundError = false; 4623 bool foundError = false;
4790 NodeList<FormalParameter> formalParameters = parameterList.parameters; 4624 NodeList<FormalParameter> formalParameters = parameterList.parameters;
4791 for (FormalParameter formalParameter in formalParameters) { 4625 for (FormalParameter formalParameter in formalParameters) {
4792 if (formalParameter.kind.isOptional) { 4626 if (formalParameter.kind.isOptional) {
4793 _errorReporter.reportErrorForNode( 4627 _errorReporter.reportErrorForNode(
4794 CompileTimeErrorCode.OPTIONAL_PARAMETER_IN_OPERATOR, 4628 CompileTimeErrorCode.OPTIONAL_PARAMETER_IN_OPERATOR,
4795 formalParameter); 4629 formalParameter);
4796 foundError = true; 4630 foundError = true;
4797 } 4631 }
4798 } 4632 }
4799 return foundError; 4633 return foundError;
4800 } 4634 }
4801 4635
4802 /** 4636 /**
4803 * This checks for named optional parameters that begin with '_'. 4637 * Check that the given named optional [parameter] does not begin with '_'.
4804 * 4638 *
4805 * @param node the default formal parameter to evaluate
4806 * @return `true` if and only if an error code is generated on the passed node
4807 * See [CompileTimeErrorCode.PRIVATE_OPTIONAL_PARAMETER]. 4639 * See [CompileTimeErrorCode.PRIVATE_OPTIONAL_PARAMETER].
4808 */ 4640 */
4809 bool _checkForPrivateOptionalParameter(FormalParameter node) { 4641 bool _checkForPrivateOptionalParameter(FormalParameter node) {
4810 // should be named parameter 4642 // should be named parameter
4811 if (node.kind != ParameterKind.NAMED) { 4643 if (node.kind != ParameterKind.NAMED) {
4812 return false; 4644 return false;
4813 } 4645 }
4814 // name should start with '_' 4646 // name should start with '_'
4815 SimpleIdentifier name = node.identifier; 4647 SimpleIdentifier name = node.identifier;
4816 if (name.isSynthetic || !StringUtilities.startsWithChar(name.name, 0x5F)) { 4648 if (name.isSynthetic || !StringUtilities.startsWithChar(name.name, 0x5F)) {
4817 return false; 4649 return false;
4818 } 4650 }
4819 // report problem 4651 // report problem
4820 _errorReporter.reportErrorForNode( 4652 _errorReporter.reportErrorForNode(
4821 CompileTimeErrorCode.PRIVATE_OPTIONAL_PARAMETER, node); 4653 CompileTimeErrorCode.PRIVATE_OPTIONAL_PARAMETER, node);
4822 return true; 4654 return true;
4823 } 4655 }
4824 4656
4825 /** 4657 /**
4826 * This checks if the passed constructor declaration is the redirecting genera tive constructor and 4658 * Check whether the given constructor [declaration] is the redirecting
4827 * references itself directly or indirectly. 4659 * generative constructor and references itself directly or indirectly. The
4660 * [constructorElement] is the constructor element.
4828 * 4661 *
4829 * @param node the constructor declaration to evaluate
4830 * @param constructorElement the constructor element
4831 * @return `true` if and only if an error code is generated on the passed node
4832 * See [CompileTimeErrorCode.RECURSIVE_CONSTRUCTOR_REDIRECT]. 4662 * See [CompileTimeErrorCode.RECURSIVE_CONSTRUCTOR_REDIRECT].
4833 */ 4663 */
4834 bool _checkForRecursiveConstructorRedirect( 4664 bool _checkForRecursiveConstructorRedirect(
4835 ConstructorDeclaration node, ConstructorElement constructorElement) { 4665 ConstructorDeclaration node, ConstructorElement constructorElement) {
4836 // we check generative constructor here 4666 // we check generative constructor here
4837 if (node.factoryKeyword != null) { 4667 if (node.factoryKeyword != null) {
4838 return false; 4668 return false;
4839 } 4669 }
4840 // try to find redirecting constructor invocation and analyzer it for 4670 // try to find redirecting constructor invocation and analyzer it for
4841 // recursion 4671 // recursion
4842 for (ConstructorInitializer initializer in node.initializers) { 4672 for (ConstructorInitializer initializer in node.initializers) {
4843 if (initializer is RedirectingConstructorInvocation) { 4673 if (initializer is RedirectingConstructorInvocation) {
4844 // OK if no cycle 4674 // OK if no cycle
4845 if (!_hasRedirectingFactoryConstructorCycle(constructorElement)) { 4675 if (!_hasRedirectingFactoryConstructorCycle(constructorElement)) {
4846 return false; 4676 return false;
4847 } 4677 }
4848 // report error 4678 // report error
4849 _errorReporter.reportErrorForNode( 4679 _errorReporter.reportErrorForNode(
4850 CompileTimeErrorCode.RECURSIVE_CONSTRUCTOR_REDIRECT, initializer); 4680 CompileTimeErrorCode.RECURSIVE_CONSTRUCTOR_REDIRECT, initializer);
4851 return true; 4681 return true;
4852 } 4682 }
4853 } 4683 }
4854 // OK, no redirecting constructor invocation 4684 // OK, no redirecting constructor invocation
4855 return false; 4685 return false;
4856 } 4686 }
4857 4687
4858 /** 4688 /**
4859 * This checks if the passed constructor declaration has redirected constructo r and references 4689 * Check whether the given constructor [declaration] has redirected
4860 * itself directly or indirectly. 4690 * constructor and references itself directly or indirectly. The
4691 * [constructorElement] is the constructor element.
4861 * 4692 *
4862 * @param node the constructor declaration to evaluate
4863 * @param constructorElement the constructor element
4864 * @return `true` if and only if an error code is generated on the passed node
4865 * See [CompileTimeErrorCode.RECURSIVE_FACTORY_REDIRECT]. 4693 * See [CompileTimeErrorCode.RECURSIVE_FACTORY_REDIRECT].
4866 */ 4694 */
4867 bool _checkForRecursiveFactoryRedirect( 4695 bool _checkForRecursiveFactoryRedirect(
4868 ConstructorDeclaration node, ConstructorElement constructorElement) { 4696 ConstructorDeclaration node, ConstructorElement constructorElement) {
4869 // prepare redirected constructor 4697 // prepare redirected constructor
4870 ConstructorName redirectedConstructorNode = node.redirectedConstructor; 4698 ConstructorName redirectedConstructorNode = node.redirectedConstructor;
4871 if (redirectedConstructorNode == null) { 4699 if (redirectedConstructorNode == null) {
4872 return false; 4700 return false;
4873 } 4701 }
4874 // OK if no cycle 4702 // OK if no cycle
4875 if (!_hasRedirectingFactoryConstructorCycle(constructorElement)) { 4703 if (!_hasRedirectingFactoryConstructorCycle(constructorElement)) {
4876 return false; 4704 return false;
4877 } 4705 }
4878 // report error 4706 // report error
4879 _errorReporter.reportErrorForNode( 4707 _errorReporter.reportErrorForNode(
4880 CompileTimeErrorCode.RECURSIVE_FACTORY_REDIRECT, 4708 CompileTimeErrorCode.RECURSIVE_FACTORY_REDIRECT,
4881 redirectedConstructorNode); 4709 redirectedConstructorNode);
4882 return true; 4710 return true;
4883 } 4711 }
4884 4712
4885 /** 4713 /**
4886 * This checks the class declaration is not a superinterface to itself. 4714 * Check that the class [element] is not a superinterface to itself.
4887 * 4715 *
4888 * @param classElt the class element to test
4889 * @return `true` if and only if an error code is generated on the passed elem ent
4890 * See [CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE], 4716 * See [CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE],
4891 * [CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_EXTENDS], a nd 4717 * [CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_EXTENDS], a nd
4892 * [CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_IMPLEMENTS] . 4718 * [CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_IMPLEMENTS] .
4893 */ 4719 */
4894 bool _checkForRecursiveInterfaceInheritance(ClassElement classElt) { 4720 bool _checkForRecursiveInterfaceInheritance(ClassElement classElt) {
4895 if (classElt == null) { 4721 if (classElt == null) {
4896 return false; 4722 return false;
4897 } 4723 }
4898 return _safeCheckForRecursiveInterfaceInheritance( 4724 return _safeCheckForRecursiveInterfaceInheritance(
4899 classElt, new List<ClassElement>()); 4725 classElt, new List<ClassElement>());
4900 } 4726 }
4901 4727
4902 /** 4728 /**
4903 * This checks the passed constructor declaration has a valid combination of r edirected 4729 * Check that the given constructor [declaration] has a valid combination of
4904 * constructor invocation(s), super constructor invocations and field initiali zers. 4730 * redirected constructor invocation(s), super constructor invocations and
4731 * field initializers.
4905 * 4732 *
4906 * @param node the constructor declaration to evaluate
4907 * @return `true` if and only if an error code is generated on the passed node
4908 * See [CompileTimeErrorCode.DEFAULT_VALUE_IN_REDIRECTING_FACTORY_CONSTRUCTOR] , 4733 * See [CompileTimeErrorCode.DEFAULT_VALUE_IN_REDIRECTING_FACTORY_CONSTRUCTOR] ,
4909 * [CompileTimeErrorCode.FIELD_INITIALIZER_REDIRECTING_CONSTRUCTOR], 4734 * [CompileTimeErrorCode.FIELD_INITIALIZER_REDIRECTING_CONSTRUCTOR],
4910 * [CompileTimeErrorCode.MULTIPLE_REDIRECTING_CONSTRUCTOR_INVOCATIONS], 4735 * [CompileTimeErrorCode.MULTIPLE_REDIRECTING_CONSTRUCTOR_INVOCATIONS],
4911 * [CompileTimeErrorCode.SUPER_IN_REDIRECTING_CONSTRUCTOR], and 4736 * [CompileTimeErrorCode.SUPER_IN_REDIRECTING_CONSTRUCTOR], and
4912 * [CompileTimeErrorCode.REDIRECT_GENERATIVE_TO_NON_GENERATIVE_CONSTRUCTOR]. 4737 * [CompileTimeErrorCode.REDIRECT_GENERATIVE_TO_NON_GENERATIVE_CONSTRUCTOR].
4913 */ 4738 */
4914 bool _checkForRedirectingConstructorErrorCodes(ConstructorDeclaration node) { 4739 bool _checkForRedirectingConstructorErrorCodes(ConstructorDeclaration node) {
4915 bool errorReported = false; 4740 bool errorReported = false;
4916 // 4741 //
4917 // Check for default values in the parameters 4742 // Check for default values in the parameters
(...skipping 58 matching lines...) Expand 10 before | Expand all | Expand 10 after
4976 initializer); 4801 initializer);
4977 errorReported = true; 4802 errorReported = true;
4978 } 4803 }
4979 } 4804 }
4980 } 4805 }
4981 // done 4806 // done
4982 return errorReported; 4807 return errorReported;
4983 } 4808 }
4984 4809
4985 /** 4810 /**
4986 * This checks if the passed constructor declaration has redirected constructo r and references 4811 * Check whether the given constructor [declaration] has redirected
4987 * itself directly or indirectly. 4812 * constructor and references itself directly or indirectly. The
4813 * [constructorElement] is the constructor element.
4988 * 4814 *
4989 * @param node the constructor declaration to evaluate
4990 * @param constructorElement the constructor element
4991 * @return `true` if and only if an error code is generated on the passed node
4992 * See [CompileTimeErrorCode.REDIRECT_TO_NON_CONST_CONSTRUCTOR]. 4815 * See [CompileTimeErrorCode.REDIRECT_TO_NON_CONST_CONSTRUCTOR].
4993 */ 4816 */
4994 bool _checkForRedirectToNonConstConstructor( 4817 bool _checkForRedirectToNonConstConstructor(
4995 ConstructorDeclaration node, ConstructorElement constructorElement) { 4818 ConstructorDeclaration node, ConstructorElement constructorElement) {
4996 // prepare redirected constructor 4819 // prepare redirected constructor
4997 ConstructorName redirectedConstructorNode = node.redirectedConstructor; 4820 ConstructorName redirectedConstructorNode = node.redirectedConstructor;
4998 if (redirectedConstructorNode == null) { 4821 if (redirectedConstructorNode == null) {
4999 return false; 4822 return false;
5000 } 4823 }
5001 // prepare element 4824 // prepare element
(...skipping 15 matching lines...) Expand all
5017 return false; 4840 return false;
5018 } 4841 }
5019 // report error 4842 // report error
5020 _errorReporter.reportErrorForNode( 4843 _errorReporter.reportErrorForNode(
5021 CompileTimeErrorCode.REDIRECT_TO_NON_CONST_CONSTRUCTOR, 4844 CompileTimeErrorCode.REDIRECT_TO_NON_CONST_CONSTRUCTOR,
5022 redirectedConstructorNode); 4845 redirectedConstructorNode);
5023 return true; 4846 return true;
5024 } 4847 }
5025 4848
5026 /** 4849 /**
5027 * This checks that the rethrow is inside of a catch clause. 4850 * Check that the given rethrow [expression] is inside of a catch clause.
5028 * 4851 *
5029 * @param node the rethrow expression to evaluate
5030 * @return `true` if and only if an error code is generated on the passed node
5031 * See [CompileTimeErrorCode.RETHROW_OUTSIDE_CATCH]. 4852 * See [CompileTimeErrorCode.RETHROW_OUTSIDE_CATCH].
5032 */ 4853 */
5033 bool _checkForRethrowOutsideCatch(RethrowExpression node) { 4854 bool _checkForRethrowOutsideCatch(RethrowExpression node) {
5034 if (!_isInCatchClause) { 4855 if (!_isInCatchClause) {
5035 _errorReporter.reportErrorForNode( 4856 _errorReporter.reportErrorForNode(
5036 CompileTimeErrorCode.RETHROW_OUTSIDE_CATCH, node); 4857 CompileTimeErrorCode.RETHROW_OUTSIDE_CATCH, node);
5037 return true; 4858 return true;
5038 } 4859 }
5039 return false; 4860 return false;
5040 } 4861 }
5041 4862
5042 /** 4863 /**
5043 * This checks that if the the given constructor declaration is generative, th en it does not have 4864 * Check that if the the given constructor [declaration] is generative, then
5044 * an expression function body. 4865 * it does not have an expression function body.
5045 * 4866 *
5046 * @param node the constructor to evaluate
5047 * @return `true` if and only if an error code is generated on the passed node
5048 * See [CompileTimeErrorCode.RETURN_IN_GENERATIVE_CONSTRUCTOR]. 4867 * See [CompileTimeErrorCode.RETURN_IN_GENERATIVE_CONSTRUCTOR].
5049 */ 4868 */
5050 bool _checkForReturnInGenerativeConstructor(ConstructorDeclaration node) { 4869 bool _checkForReturnInGenerativeConstructor(ConstructorDeclaration node) {
5051 // ignore factory 4870 // ignore factory
5052 if (node.factoryKeyword != null) { 4871 if (node.factoryKeyword != null) {
5053 return false; 4872 return false;
5054 } 4873 }
5055 // block body (with possible return statement) is checked elsewhere 4874 // block body (with possible return statement) is checked elsewhere
5056 FunctionBody body = node.body; 4875 FunctionBody body = node.body;
5057 if (body is! ExpressionFunctionBody) { 4876 if (body is! ExpressionFunctionBody) {
5058 return false; 4877 return false;
5059 } 4878 }
5060 // report error 4879 // report error
5061 _errorReporter.reportErrorForNode( 4880 _errorReporter.reportErrorForNode(
5062 CompileTimeErrorCode.RETURN_IN_GENERATIVE_CONSTRUCTOR, body); 4881 CompileTimeErrorCode.RETURN_IN_GENERATIVE_CONSTRUCTOR, body);
5063 return true; 4882 return true;
5064 } 4883 }
5065 4884
5066 /** 4885 /**
5067 * This checks that a type mis-match between the return type and the expressed return type by the 4886 * Check that a type mis-match between the type of the [returnExpression] and
5068 * enclosing method or function. 4887 * the [expectedReturnType] by the enclosing method or function.
5069 * 4888 *
5070 * This method is called both by [checkForAllReturnStatementErrorCodes] 4889 * This method is called both by [_checkForAllReturnStatementErrorCodes]
5071 * and [visitExpressionFunctionBody]. 4890 * and [visitExpressionFunctionBody].
5072 * 4891 *
5073 * @param returnExpression the returned expression to evaluate
5074 * @param expectedReturnType the expressed return type by the enclosing method or function
5075 * @return `true` if and only if an error code is generated on the passed node
5076 * See [StaticTypeWarningCode.RETURN_OF_INVALID_TYPE]. 4892 * See [StaticTypeWarningCode.RETURN_OF_INVALID_TYPE].
5077 */ 4893 */
5078 bool _checkForReturnOfInvalidType( 4894 bool _checkForReturnOfInvalidType(
5079 Expression returnExpression, DartType expectedReturnType) { 4895 Expression returnExpression, DartType expectedReturnType) {
5080 if (_enclosingFunction == null) { 4896 if (_enclosingFunction == null) {
5081 return false; 4897 return false;
5082 } 4898 }
5083 if (_inGenerator) { 4899 if (_inGenerator) {
5084 // "return expression;" is disallowed in generators, but this is checked 4900 // "return expression;" is disallowed in generators, but this is checked
5085 // elsewhere. Bare "return" is always allowed in generators regardless 4901 // elsewhere. Bare "return" is always allowed in generators regardless
(...skipping 35 matching lines...) Expand 10 before | Expand all | Expand 10 after
5121 // errorReporter.reportTypeErrorForNode( 4937 // errorReporter.reportTypeErrorForNode(
5122 // StaticTypeWarningCode.RETURN_OF_INVALID_TYPE, 4938 // StaticTypeWarningCode.RETURN_OF_INVALID_TYPE,
5123 // returnExpression, 4939 // returnExpression,
5124 // staticReturnType, 4940 // staticReturnType,
5125 // expectedReturnType, 4941 // expectedReturnType,
5126 // enclosingFunction.getDisplayName()); 4942 // enclosingFunction.getDisplayName());
5127 // return true; 4943 // return true;
5128 } 4944 }
5129 4945
5130 /** 4946 /**
5131 * This checks the given "typeReference" and that the "name" is not the refere nce to an instance 4947 * Check the given [typeReference] and that the [name] is not the reference to
5132 * member. 4948 * an instance member.
5133 * 4949 *
5134 * @param typeReference the resolved [ClassElement] of the left hand side of t he expression,
5135 * or `null`, aka, the class element of 'C' in 'C.x', see
5136 * [getTypeReference]
5137 * @param name the accessed name to evaluate
5138 * @return `true` if and only if an error code is generated on the passed node
5139 * See [StaticWarningCode.STATIC_ACCESS_TO_INSTANCE_MEMBER]. 4950 * See [StaticWarningCode.STATIC_ACCESS_TO_INSTANCE_MEMBER].
5140 */ 4951 */
5141 bool _checkForStaticAccessToInstanceMember( 4952 bool _checkForStaticAccessToInstanceMember(
5142 ClassElement typeReference, SimpleIdentifier name) { 4953 ClassElement typeReference, SimpleIdentifier name) {
5143 // OK, target is not a type 4954 // OK, target is not a type
5144 if (typeReference == null) { 4955 if (typeReference == null) {
5145 return false; 4956 return false;
5146 } 4957 }
5147 // prepare member Element 4958 // prepare member Element
5148 Element element = name.staticElement; 4959 Element element = name.staticElement;
5149 if (element is! ExecutableElement) { 4960 if (element is! ExecutableElement) {
5150 return false; 4961 return false;
5151 } 4962 }
5152 ExecutableElement memberElement = element as ExecutableElement; 4963 ExecutableElement memberElement = element as ExecutableElement;
5153 // OK, static 4964 // OK, static
5154 if (memberElement.isStatic) { 4965 if (memberElement.isStatic) {
5155 return false; 4966 return false;
5156 } 4967 }
5157 // report problem 4968 // report problem
5158 _errorReporter.reportErrorForNode( 4969 _errorReporter.reportErrorForNode(
5159 StaticWarningCode.STATIC_ACCESS_TO_INSTANCE_MEMBER, name, [name.name]); 4970 StaticWarningCode.STATIC_ACCESS_TO_INSTANCE_MEMBER, name, [name.name]);
5160 return true; 4971 return true;
5161 } 4972 }
5162 4973
5163 /** 4974 /**
5164 * This checks that the type of the passed 'switch' expression is assignable t o the type of the 4975 * Check that the type of the expression in the given 'switch' [statement] is
5165 * 'case' members. 4976 * assignable to the type of the 'case' members.
5166 * 4977 *
5167 * @param node the 'switch' statement to evaluate
5168 * @return `true` if and only if an error code is generated on the passed node
5169 * See [StaticWarningCode.SWITCH_EXPRESSION_NOT_ASSIGNABLE]. 4978 * See [StaticWarningCode.SWITCH_EXPRESSION_NOT_ASSIGNABLE].
5170 */ 4979 */
5171 bool _checkForSwitchExpressionNotAssignable(SwitchStatement node) { 4980 bool _checkForSwitchExpressionNotAssignable(SwitchStatement node) {
5172 // prepare 'switch' expression type 4981 // prepare 'switch' expression type
5173 Expression expression = node.expression; 4982 Expression expression = node.expression;
5174 DartType expressionType = getStaticType(expression); 4983 DartType expressionType = getStaticType(expression);
5175 if (expressionType == null) { 4984 if (expressionType == null) {
5176 return false; 4985 return false;
5177 } 4986 }
5178 // compare with type of the first 'case' 4987 // compare with type of the first 'case'
(...skipping 15 matching lines...) Expand all
5194 StaticWarningCode.SWITCH_EXPRESSION_NOT_ASSIGNABLE, expression, [ 5003 StaticWarningCode.SWITCH_EXPRESSION_NOT_ASSIGNABLE, expression, [
5195 expressionType, 5004 expressionType,
5196 caseType 5005 caseType
5197 ]); 5006 ]);
5198 return true; 5007 return true;
5199 } 5008 }
5200 return false; 5009 return false;
5201 } 5010 }
5202 5011
5203 /** 5012 /**
5204 * This verifies that the passed function type alias does not reference itself directly. 5013 * Verify that the given function type [alias] does not reference itself
5014 * directly.
5205 * 5015 *
5206 * @param node the function type alias to evaluate
5207 * @return `true` if and only if an error code is generated on the passed node
5208 * See [CompileTimeErrorCode.TYPE_ALIAS_CANNOT_REFERENCE_ITSELF]. 5016 * See [CompileTimeErrorCode.TYPE_ALIAS_CANNOT_REFERENCE_ITSELF].
5209 */ 5017 */
5210 bool _checkForTypeAliasCannotReferenceItself_function( 5018 bool _checkForTypeAliasCannotReferenceItself_function(
5211 FunctionTypeAlias node) { 5019 FunctionTypeAlias node) {
5212 FunctionTypeAliasElement element = node.element; 5020 FunctionTypeAliasElement element = node.element;
5213 if (!_hasTypedefSelfReference(element)) { 5021 if (!_hasTypedefSelfReference(element)) {
5214 return false; 5022 return false;
5215 } 5023 }
5216 _errorReporter.reportErrorForNode( 5024 _errorReporter.reportErrorForNode(
5217 CompileTimeErrorCode.TYPE_ALIAS_CANNOT_REFERENCE_ITSELF, node); 5025 CompileTimeErrorCode.TYPE_ALIAS_CANNOT_REFERENCE_ITSELF, node);
5218 return true; 5026 return true;
5219 } 5027 }
5220 5028
5221 /** 5029 /**
5222 * This verifies that the passed type name is not a deferred type. 5030 * Verify that the given type [name] is not a deferred type.
5223 * 5031 *
5224 * @param expression the expression to evaluate
5225 * @return `true` if and only if an error code is generated on the passed node
5226 * See [StaticWarningCode.TYPE_ANNOTATION_DEFERRED_CLASS]. 5032 * See [StaticWarningCode.TYPE_ANNOTATION_DEFERRED_CLASS].
5227 */ 5033 */
5228 bool _checkForTypeAnnotationDeferredClass(TypeName node) { 5034 bool _checkForTypeAnnotationDeferredClass(TypeName node) {
5229 if (node != null && node.isDeferred) { 5035 if (node != null && node.isDeferred) {
5230 _errorReporter.reportErrorForNode( 5036 _errorReporter.reportErrorForNode(
5231 StaticWarningCode.TYPE_ANNOTATION_DEFERRED_CLASS, node, [node.name]); 5037 StaticWarningCode.TYPE_ANNOTATION_DEFERRED_CLASS, node, [node.name]);
5232 } 5038 }
5233 return false; 5039 return false;
5234 } 5040 }
5235 5041
5236 /** 5042 /**
5237 * This verifies that the type arguments in the passed type name are all withi n their bounds. 5043 * Verify that the type arguments in the given type [name] are all within
5044 * their bounds.
5238 * 5045 *
5239 * @param node the [TypeName] to evaluate
5240 * @return `true` if and only if an error code is generated on the passed node
5241 * See [StaticTypeWarningCode.TYPE_ARGUMENT_NOT_MATCHING_BOUNDS]. 5046 * See [StaticTypeWarningCode.TYPE_ARGUMENT_NOT_MATCHING_BOUNDS].
5242 */ 5047 */
5243 bool _checkForTypeArgumentNotMatchingBounds(TypeName node) { 5048 bool _checkForTypeArgumentNotMatchingBounds(TypeName node) {
5244 if (node.typeArguments == null) { 5049 if (node.typeArguments == null) {
5245 return false; 5050 return false;
5246 } 5051 }
5247 // prepare Type 5052 // prepare Type
5248 DartType type = node.type; 5053 DartType type = node.type;
5249 if (type == null) { 5054 if (type == null) {
5250 return false; 5055 return false;
(...skipping 32 matching lines...) Expand 10 before | Expand all | Expand 10 after
5283 _errorReporter.reportTypeErrorForNode( 5088 _errorReporter.reportTypeErrorForNode(
5284 errorCode, argTypeName, [argType, boundType]); 5089 errorCode, argTypeName, [argType, boundType]);
5285 foundError = true; 5090 foundError = true;
5286 } 5091 }
5287 } 5092 }
5288 } 5093 }
5289 return foundError; 5094 return foundError;
5290 } 5095 }
5291 5096
5292 /** 5097 /**
5293 * This checks that if the passed type name is a type parameter being used to define a static 5098 * Check whether the given type [name] is a type parameter being used to
5294 * member. 5099 * define a static member.
5295 * 5100 *
5296 * @param node the type name to evaluate
5297 * @return `true` if and only if an error code is generated on the passed node
5298 * See [StaticWarningCode.TYPE_PARAMETER_REFERENCED_BY_STATIC]. 5101 * See [StaticWarningCode.TYPE_PARAMETER_REFERENCED_BY_STATIC].
5299 */ 5102 */
5300 bool _checkForTypeParameterReferencedByStatic(TypeName node) { 5103 bool _checkForTypeParameterReferencedByStatic(TypeName node) {
5301 if (_isInStaticMethod || _isInStaticVariableDeclaration) { 5104 if (_isInStaticMethod || _isInStaticVariableDeclaration) {
5302 DartType type = node.type; 5105 DartType type = node.type;
5303 if (type is TypeParameterType) { 5106 if (type is TypeParameterType) {
5304 _errorReporter.reportErrorForNode( 5107 _errorReporter.reportErrorForNode(
5305 StaticWarningCode.TYPE_PARAMETER_REFERENCED_BY_STATIC, node); 5108 StaticWarningCode.TYPE_PARAMETER_REFERENCED_BY_STATIC, node);
5306 return true; 5109 return true;
5307 } 5110 }
5308 } 5111 }
5309 return false; 5112 return false;
5310 } 5113 }
5311 5114
5312 /** 5115 /**
5313 * This checks that if the passed type parameter is a supertype of its bound. 5116 * Check whether the given type [parameter] is a supertype of its bound.
5314 * 5117 *
5315 * @param node the type parameter to evaluate
5316 * @return `true` if and only if an error code is generated on the passed node
5317 * See [StaticTypeWarningCode.TYPE_PARAMETER_SUPERTYPE_OF_ITS_BOUND]. 5118 * See [StaticTypeWarningCode.TYPE_PARAMETER_SUPERTYPE_OF_ITS_BOUND].
5318 */ 5119 */
5319 bool _checkForTypeParameterSupertypeOfItsBound(TypeParameter node) { 5120 bool _checkForTypeParameterSupertypeOfItsBound(TypeParameter node) {
5320 TypeParameterElement element = node.element; 5121 TypeParameterElement element = node.element;
5321 // prepare bound 5122 // prepare bound
5322 DartType bound = element.bound; 5123 DartType bound = element.bound;
5323 if (bound == null) { 5124 if (bound == null) {
5324 return false; 5125 return false;
5325 } 5126 }
5326 // OK, type parameter is not supertype of its bound 5127 // OK, type parameter is not supertype of its bound
5327 if (!bound.isMoreSpecificThan(element.type)) { 5128 if (!bound.isMoreSpecificThan(element.type)) {
5328 return false; 5129 return false;
5329 } 5130 }
5330 // report problem 5131 // report problem
5331 _errorReporter.reportErrorForNode( 5132 _errorReporter.reportErrorForNode(
5332 StaticTypeWarningCode.TYPE_PARAMETER_SUPERTYPE_OF_ITS_BOUND, node, 5133 StaticTypeWarningCode.TYPE_PARAMETER_SUPERTYPE_OF_ITS_BOUND, node,
5333 [element.displayName]); 5134 [element.displayName]);
5334 return true; 5135 return true;
5335 } 5136 }
5336 5137
5337 /** 5138 /**
5338 * This checks that if the passed generative constructor has neither an explic it super constructor 5139 * Check that if the given generative [constructor] has neither an explicit
5339 * invocation nor a redirecting constructor invocation, that the superclass ha s a default 5140 * super constructor invocation nor a redirecting constructor invocation, that
5340 * generative constructor. 5141 * the superclass has a default generative constructor.
5341 * 5142 *
5342 * @param node the constructor declaration to evaluate
5343 * @return `true` if and only if an error code is generated on the passed node
5344 * See [CompileTimeErrorCode.UNDEFINED_CONSTRUCTOR_IN_INITIALIZER_DEFAULT], 5143 * See [CompileTimeErrorCode.UNDEFINED_CONSTRUCTOR_IN_INITIALIZER_DEFAULT],
5345 * [CompileTimeErrorCode.NON_GENERATIVE_CONSTRUCTOR], and 5144 * [CompileTimeErrorCode.NON_GENERATIVE_CONSTRUCTOR], and
5346 * [StaticWarningCode.NO_DEFAULT_SUPER_CONSTRUCTOR_EXPLICIT]. 5145 * [StaticWarningCode.NO_DEFAULT_SUPER_CONSTRUCTOR_EXPLICIT].
5347 */ 5146 */
5348 bool _checkForUndefinedConstructorInInitializerImplicit( 5147 bool _checkForUndefinedConstructorInInitializerImplicit(
5349 ConstructorDeclaration node) { 5148 ConstructorDeclaration node) {
5350 if (_enclosingClass == null) { 5149 if (_enclosingClass == null) {
5351 return false; 5150 return false;
5352 } 5151 }
5353 // do nothing if mixin errors have already been reported for this class. 5152 // do nothing if mixin errors have already been reported for this class.
(...skipping 52 matching lines...) Expand 10 before | Expand all | Expand 10 after
5406 } 5205 }
5407 return false; 5206 return false;
5408 } 5207 }
5409 _errorReporter.reportErrorForNode( 5208 _errorReporter.reportErrorForNode(
5410 CompileTimeErrorCode.UNDEFINED_CONSTRUCTOR_IN_INITIALIZER_DEFAULT, 5209 CompileTimeErrorCode.UNDEFINED_CONSTRUCTOR_IN_INITIALIZER_DEFAULT,
5411 node.returnType, [superElement.name]); 5210 node.returnType, [superElement.name]);
5412 return true; 5211 return true;
5413 } 5212 }
5414 5213
5415 /** 5214 /**
5416 * This checks that if the given name is a reference to a static member it is defined in the 5215 * Check that if the given [name] is a reference to a static member it is
5417 * enclosing class rather than in a superclass. 5216 * defined in the enclosing class rather than in a superclass.
5418 * 5217 *
5419 * @param name the name to be evaluated
5420 * @return `true` if and only if an error code is generated on the passed node
5421 * See [StaticTypeWarningCode.UNQUALIFIED_REFERENCE_TO_NON_LOCAL_STATIC_MEMBER ]. 5218 * See [StaticTypeWarningCode.UNQUALIFIED_REFERENCE_TO_NON_LOCAL_STATIC_MEMBER ].
5422 */ 5219 */
5423 bool _checkForUnqualifiedReferenceToNonLocalStaticMember( 5220 bool _checkForUnqualifiedReferenceToNonLocalStaticMember(
5424 SimpleIdentifier name) { 5221 SimpleIdentifier name) {
5425 Element element = name.staticElement; 5222 Element element = name.staticElement;
5426 if (element == null || element is TypeParameterElement) { 5223 if (element == null || element is TypeParameterElement) {
5427 return false; 5224 return false;
5428 } 5225 }
5429 Element enclosingElement = element.enclosingElement; 5226 Element enclosingElement = element.enclosingElement;
5430 if (enclosingElement is! ClassElement) { 5227 if (enclosingElement is! ClassElement) {
(...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after
5485 } 5282 }
5486 } 5283 }
5487 } 5284 }
5488 // else { 5285 // else {
5489 // // TODO(jwren) Report error, constructor initializer variable is a top level element 5286 // // TODO(jwren) Report error, constructor initializer variable is a top level element
5490 // // (Either here or in ErrorVerifier.checkForAllFinalInitializedErrorCo des) 5287 // // (Either here or in ErrorVerifier.checkForAllFinalInitializedErrorCo des)
5491 // } 5288 // }
5492 } 5289 }
5493 5290
5494 /** 5291 /**
5495 * This verifies that the given getter does not have a return type of 'void'. 5292 * Verify that the given [getter] does not have a return type of 'void'.
5496 * 5293 *
5497 * @param node the method declaration to evaluate
5498 * @return `true` if and only if an error code is generated on the passed node
5499 * See [StaticWarningCode.VOID_RETURN_FOR_GETTER]. 5294 * See [StaticWarningCode.VOID_RETURN_FOR_GETTER].
5500 */ 5295 */
5501 bool _checkForVoidReturnType(MethodDeclaration node) { 5296 bool _checkForVoidReturnType(MethodDeclaration node) {
5502 TypeName returnType = node.returnType; 5297 TypeName returnType = node.returnType;
5503 if (returnType == null || returnType.name.name != "void") { 5298 if (returnType == null || returnType.name.name != "void") {
5504 return false; 5299 return false;
5505 } 5300 }
5506 _errorReporter.reportErrorForNode( 5301 _errorReporter.reportErrorForNode(
5507 StaticWarningCode.VOID_RETURN_FOR_GETTER, returnType); 5302 StaticWarningCode.VOID_RETURN_FOR_GETTER, returnType);
5508 return true; 5303 return true;
5509 } 5304 }
5510 5305
5511 /** 5306 /**
5512 * This verifies the passed operator-method declaration, has correct number of parameters. 5307 * Verify the given operator-method [declaration], has correct number of
5308 * parameters.
5513 * 5309 *
5514 * This method assumes that the method declaration was tested to be an operato r declaration before 5310 * This method assumes that the method declaration was tested to be an
5515 * being called. 5311 * operator declaration before being called.
5516 * 5312 *
5517 * @param node the method declaration to evaluate
5518 * @return `true` if and only if an error code is generated on the passed node
5519 * See [CompileTimeErrorCode.WRONG_NUMBER_OF_PARAMETERS_FOR_OPERATOR]. 5313 * See [CompileTimeErrorCode.WRONG_NUMBER_OF_PARAMETERS_FOR_OPERATOR].
5520 */ 5314 */
5521 bool _checkForWrongNumberOfParametersForOperator(MethodDeclaration node) { 5315 bool _checkForWrongNumberOfParametersForOperator(MethodDeclaration node) {
5522 // prepare number of parameters 5316 // prepare number of parameters
5523 FormalParameterList parameterList = node.parameters; 5317 FormalParameterList parameterList = node.parameters;
5524 if (parameterList == null) { 5318 if (parameterList == null) {
5525 return false; 5319 return false;
5526 } 5320 }
5527 int numParameters = parameterList.parameters.length; 5321 int numParameters = parameterList.parameters.length;
5528 // prepare operator name 5322 // prepare operator name
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
5566 _errorReporter.reportErrorForNode( 5360 _errorReporter.reportErrorForNode(
5567 CompileTimeErrorCode.WRONG_NUMBER_OF_PARAMETERS_FOR_OPERATOR_MINUS, 5361 CompileTimeErrorCode.WRONG_NUMBER_OF_PARAMETERS_FOR_OPERATOR_MINUS,
5568 nameNode, [numParameters]); 5362 nameNode, [numParameters]);
5569 return true; 5363 return true;
5570 } 5364 }
5571 // OK 5365 // OK
5572 return false; 5366 return false;
5573 } 5367 }
5574 5368
5575 /** 5369 /**
5576 * This verifies if the passed setter parameter list have only one required pa rameter. 5370 * Verify that the given setter [parameterList] has only one required
5371 * parameter. The [setterName] is the name of the setter to report problems
5372 * on.
5577 * 5373 *
5578 * This method assumes that the method declaration was tested to be a setter b efore being called. 5374 * This method assumes that the method declaration was tested to be a setter
5375 * before being called.
5579 * 5376 *
5580 * @param setterName the name of the setter to report problems on
5581 * @param parameterList the parameter list to evaluate
5582 * @return `true` if and only if an error code is generated on the passed node
5583 * See [CompileTimeErrorCode.WRONG_NUMBER_OF_PARAMETERS_FOR_SETTER]. 5377 * See [CompileTimeErrorCode.WRONG_NUMBER_OF_PARAMETERS_FOR_SETTER].
5584 */ 5378 */
5585 bool _checkForWrongNumberOfParametersForSetter( 5379 bool _checkForWrongNumberOfParametersForSetter(
5586 SimpleIdentifier setterName, FormalParameterList parameterList) { 5380 SimpleIdentifier setterName, FormalParameterList parameterList) {
5587 if (setterName == null) { 5381 if (setterName == null) {
5588 return false; 5382 return false;
5589 } 5383 }
5590 if (parameterList == null) { 5384 if (parameterList == null) {
5591 return false; 5385 return false;
5592 } 5386 }
(...skipping 56 matching lines...) Expand 10 before | Expand all | Expand 10 after
5649 impliedReturnType, 5443 impliedReturnType,
5650 requiredReturnType 5444 requiredReturnType
5651 ]); 5445 ]);
5652 return true; 5446 return true;
5653 } 5447 }
5654 } 5448 }
5655 return false; 5449 return false;
5656 } 5450 }
5657 5451
5658 /** 5452 /**
5659 * This verifies that if the given class declaration implements the class Func tion that it has a 5453 * Verify that if the given class [declaration] implements the class Function
5660 * concrete implementation of the call method. 5454 * that it has a concrete implementation of the call method.
5661 * 5455 *
5662 * @return `true` if and only if an error code is generated on the passed node
5663 * See [StaticWarningCode.FUNCTION_WITHOUT_CALL]. 5456 * See [StaticWarningCode.FUNCTION_WITHOUT_CALL].
5664 */ 5457 */
5665 bool _checkImplementsFunctionWithoutCall(ClassDeclaration node) { 5458 bool _checkImplementsFunctionWithoutCall(ClassDeclaration node) {
5666 if (node.isAbstract) { 5459 if (node.isAbstract) {
5667 return false; 5460 return false;
5668 } 5461 }
5669 ClassElement classElement = node.element; 5462 ClassElement classElement = node.element;
5670 if (classElement == null) { 5463 if (classElement == null) {
5671 return false; 5464 return false;
5672 } 5465 }
(...skipping 12 matching lines...) Expand all
5685 callMethod is! MethodElement || 5478 callMethod is! MethodElement ||
5686 (callMethod as MethodElement).isAbstract) { 5479 (callMethod as MethodElement).isAbstract) {
5687 _errorReporter.reportErrorForNode( 5480 _errorReporter.reportErrorForNode(
5688 StaticWarningCode.FUNCTION_WITHOUT_CALL, node.name); 5481 StaticWarningCode.FUNCTION_WITHOUT_CALL, node.name);
5689 return true; 5482 return true;
5690 } 5483 }
5691 return false; 5484 return false;
5692 } 5485 }
5693 5486
5694 /** 5487 /**
5695 * This verifies that the given class declaration does not have the same class in the 'extends' 5488 * Verify that the given class [declaration] does not have the same class in
5696 * and 'implements' clauses. 5489 * the 'extends' and 'implements' clauses.
5697 * 5490 *
5698 * @return `true` if and only if an error code is generated on the passed node
5699 * See [CompileTimeErrorCode.IMPLEMENTS_SUPER_CLASS]. 5491 * See [CompileTimeErrorCode.IMPLEMENTS_SUPER_CLASS].
5700 */ 5492 */
5701 bool _checkImplementsSuperClass(ClassDeclaration node) { 5493 bool _checkImplementsSuperClass(ClassDeclaration node) {
5702 // prepare super type 5494 // prepare super type
5703 InterfaceType superType = _enclosingClass.supertype; 5495 InterfaceType superType = _enclosingClass.supertype;
5704 if (superType == null) { 5496 if (superType == null) {
5705 return false; 5497 return false;
5706 } 5498 }
5707 // prepare interfaces 5499 // prepare interfaces
5708 ImplementsClause implementsClause = node.implementsClause; 5500 ImplementsClause implementsClause = node.implementsClause;
(...skipping 28 matching lines...) Expand all
5737 DartType staticReturnType = getStaticType(returnExpression); 5529 DartType staticReturnType = getStaticType(returnExpression);
5738 if (staticReturnType != null && _enclosingFunction.isAsynchronous) { 5530 if (staticReturnType != null && _enclosingFunction.isAsynchronous) {
5739 return _typeProvider.futureType.substitute4(<DartType>[ 5531 return _typeProvider.futureType.substitute4(<DartType>[
5740 StaticTypeAnalyzer.flattenFutures(_typeProvider, staticReturnType) 5532 StaticTypeAnalyzer.flattenFutures(_typeProvider, staticReturnType)
5741 ]); 5533 ]);
5742 } 5534 }
5743 return staticReturnType; 5535 return staticReturnType;
5744 } 5536 }
5745 5537
5746 /** 5538 /**
5747 * Return the error code that should be used when the given class references i tself directly. 5539 * Return the error code that should be used when the given class [element]
5748 * 5540 * references itself directly.
5749 * @param classElt the class that references itself
5750 * @return the error code that should be used
5751 */ 5541 */
5752 ErrorCode _getBaseCaseErrorCode(ClassElement classElt) { 5542 ErrorCode _getBaseCaseErrorCode(ClassElement classElt) {
5753 InterfaceType supertype = classElt.supertype; 5543 InterfaceType supertype = classElt.supertype;
5754 if (supertype != null && _enclosingClass == supertype.element) { 5544 if (supertype != null && _enclosingClass == supertype.element) {
5755 return CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_EXTE NDS; 5545 return CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_EXTE NDS;
5756 } 5546 }
5757 List<InterfaceType> mixins = classElt.mixins; 5547 List<InterfaceType> mixins = classElt.mixins;
5758 for (int i = 0; i < mixins.length; i++) { 5548 for (int i = 0; i < mixins.length; i++) {
5759 if (_enclosingClass == mixins[i].element) { 5549 if (_enclosingClass == mixins[i].element) {
5760 return CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_WI TH; 5550 return CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_WI TH;
5761 } 5551 }
5762 } 5552 }
5763 return CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_IMPLEM ENTS; 5553 return CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_IMPLEM ENTS;
5764 } 5554 }
5765 5555
5766 /** 5556 /**
5767 * Given an expression in a switch case whose value is expected to be an enum constant, return the 5557 * Given an [expression] in a switch case whose value is expected to be an
5768 * name of the constant. 5558 * enum constant, return the name of the constant.
5769 *
5770 * @param expression the expression from the switch case
5771 * @return the name of the constant referenced by the expression
5772 */ 5559 */
5773 String _getConstantName(Expression expression) { 5560 String _getConstantName(Expression expression) {
5774 // TODO(brianwilkerson) Convert this to return the element representing the 5561 // TODO(brianwilkerson) Convert this to return the element representing the
5775 // constant. 5562 // constant.
5776 if (expression is SimpleIdentifier) { 5563 if (expression is SimpleIdentifier) {
5777 return expression.name; 5564 return expression.name;
5778 } else if (expression is PrefixedIdentifier) { 5565 } else if (expression is PrefixedIdentifier) {
5779 return expression.identifier.name; 5566 return expression.identifier.name;
5780 } else if (expression is PropertyAccess) { 5567 } else if (expression is PropertyAccess) {
5781 return expression.propertyName.name; 5568 return expression.propertyName.name;
5782 } 5569 }
5783 return null; 5570 return null;
5784 } 5571 }
5785 5572
5786 /** 5573 /**
5787 * Returns the Type (return type) for a given getter. 5574 * Return the return type of the given [getter].
5788 *
5789 * @param propertyAccessorElement
5790 * @return The type of the given getter.
5791 */ 5575 */
5792 DartType _getGetterType(PropertyAccessorElement propertyAccessorElement) { 5576 DartType _getGetterType(PropertyAccessorElement propertyAccessorElement) {
5793 FunctionType functionType = propertyAccessorElement.type; 5577 FunctionType functionType = propertyAccessorElement.type;
5794 if (functionType != null) { 5578 if (functionType != null) {
5795 return functionType.returnType; 5579 return functionType.returnType;
5796 } else { 5580 } else {
5797 return null; 5581 return null;
5798 } 5582 }
5799 } 5583 }
5800 5584
5801 /** 5585 /**
5802 * Returns the Type (first and only parameter) for a given setter. 5586 * Return the type of the first and only parameter of the given [setter].
5803 *
5804 * @param propertyAccessorElement
5805 * @return The type of the given setter.
5806 */ 5587 */
5807 DartType _getSetterType(PropertyAccessorElement propertyAccessorElement) { 5588 DartType _getSetterType(PropertyAccessorElement propertyAccessorElement) {
5808 // Get the parameters for MethodDeclaration or FunctionDeclaration 5589 // Get the parameters for MethodDeclaration or FunctionDeclaration
5809 List<ParameterElement> setterParameters = 5590 List<ParameterElement> setterParameters =
5810 propertyAccessorElement.parameters; 5591 propertyAccessorElement.parameters;
5811 // If there are no setter parameters, return no type. 5592 // If there are no setter parameters, return no type.
5812 if (setterParameters.length == 0) { 5593 if (setterParameters.length == 0) {
5813 return null; 5594 return null;
5814 } 5595 }
5815 return setterParameters[0].type; 5596 return setterParameters[0].type;
5816 } 5597 }
5817 5598
5818 /** 5599 /**
5819 * Given a list of directives that have the same prefix, generate an error if there is more than 5600 * Given a list of [directives] that have the same prefix, generate an error
5820 * one import and any of those imports is deferred. 5601 * if there is more than one import and any of those imports is deferred.
5821 * 5602 *
5822 * @param directives the list of directives that have the same prefix
5823 * @return `true` if an error was generated
5824 * See [CompileTimeErrorCode.SHARED_DEFERRED_PREFIX]. 5603 * See [CompileTimeErrorCode.SHARED_DEFERRED_PREFIX].
5825 */ 5604 */
5826 bool _hasDeferredPrefixCollision(List<ImportDirective> directives) { 5605 bool _hasDeferredPrefixCollision(List<ImportDirective> directives) {
5827 bool foundError = false; 5606 bool foundError = false;
5828 int count = directives.length; 5607 int count = directives.length;
5829 if (count > 1) { 5608 if (count > 1) {
5830 for (int i = 0; i < count; i++) { 5609 for (int i = 0; i < count; i++) {
5831 sc.Token deferredToken = directives[i].deferredKeyword; 5610 sc.Token deferredToken = directives[i].deferredKeyword;
5832 if (deferredToken != null) { 5611 if (deferredToken != null) {
5833 _errorReporter.reportErrorForToken( 5612 _errorReporter.reportErrorForToken(
5834 CompileTimeErrorCode.SHARED_DEFERRED_PREFIX, deferredToken); 5613 CompileTimeErrorCode.SHARED_DEFERRED_PREFIX, deferredToken);
5835 foundError = true; 5614 foundError = true;
5836 } 5615 }
5837 } 5616 }
5838 } 5617 }
5839 return foundError; 5618 return foundError;
5840 } 5619 }
5841 5620
5842 /** 5621 /**
5843 * @return `true` if the given constructor redirects to itself, directly or in directly 5622 * Return `true` if the given [constructor] redirects to itself, directly or
5623 * indirectly.
5844 */ 5624 */
5845 bool _hasRedirectingFactoryConstructorCycle(ConstructorElement element) { 5625 bool _hasRedirectingFactoryConstructorCycle(ConstructorElement element) {
5846 Set<ConstructorElement> constructors = new HashSet<ConstructorElement>(); 5626 Set<ConstructorElement> constructors = new HashSet<ConstructorElement>();
5847 ConstructorElement current = element; 5627 ConstructorElement current = element;
5848 while (current != null) { 5628 while (current != null) {
5849 if (constructors.contains(current)) { 5629 if (constructors.contains(current)) {
5850 return identical(current, element); 5630 return identical(current, element);
5851 } 5631 }
5852 constructors.add(current); 5632 constructors.add(current);
5853 current = current.redirectedConstructor; 5633 current = current.redirectedConstructor;
5854 if (current is ConstructorMember) { 5634 if (current is ConstructorMember) {
5855 current = (current as ConstructorMember).baseElement; 5635 current = (current as ConstructorMember).baseElement;
5856 } 5636 }
5857 } 5637 }
5858 return false; 5638 return false;
5859 } 5639 }
5860 5640
5861 /** 5641 /**
5862 * @return <code>true</code> if given [Element] has direct or indirect referen ce to itself 5642 * Return `true` if the given [element] has direct or indirect reference to
5863 * from anywhere except [ClassElement] or type parameter bounds. 5643 * itself from anywhere except a class element or type parameter bounds.
5864 */ 5644 */
5865 bool _hasTypedefSelfReference(Element target) { 5645 bool _hasTypedefSelfReference(Element target) {
5866 Set<Element> checked = new HashSet<Element>(); 5646 Set<Element> checked = new HashSet<Element>();
5867 List<Element> toCheck = new List<Element>(); 5647 List<Element> toCheck = new List<Element>();
5868 GeneralizingElementVisitor_ErrorVerifier_hasTypedefSelfReference elementVisi tor = 5648 GeneralizingElementVisitor_ErrorVerifier_hasTypedefSelfReference elementVisi tor =
5869 new GeneralizingElementVisitor_ErrorVerifier_hasTypedefSelfReference( 5649 new GeneralizingElementVisitor_ErrorVerifier_hasTypedefSelfReference(
5870 toCheck); 5650 toCheck);
5871 toCheck.add(target); 5651 toCheck.add(target);
5872 bool firstIteration = true; 5652 bool firstIteration = true;
5873 while (true) { 5653 while (true) {
(...skipping 31 matching lines...) Expand 10 before | Expand all | Expand 10 after
5905 return true; 5685 return true;
5906 } else if (type is InterfaceType) { 5686 } else if (type is InterfaceType) {
5907 MethodElement callMethod = 5687 MethodElement callMethod =
5908 type.lookUpMethod(FunctionElement.CALL_METHOD_NAME, _currentLibrary); 5688 type.lookUpMethod(FunctionElement.CALL_METHOD_NAME, _currentLibrary);
5909 return callMethod != null; 5689 return callMethod != null;
5910 } 5690 }
5911 return false; 5691 return false;
5912 } 5692 }
5913 5693
5914 /** 5694 /**
5915 * Return `true` iff the passed [ClassElement] has a method, getter or setter that 5695 * Return `true` iff the given class [element] has a method, getter or setter
5916 * matches the name of the passed [ExecutableElement] in either the class itse lf, or one of 5696 * that matches the name of the given executable [element] in either the class
5917 * its' mixins that is concrete. 5697 * itself, or one of its' mixins that is concrete.
5918 * 5698 *
5919 * By "match", only the name of the member is tested to match, it does not hav e to equal or be a 5699 * By "match", only the name of the member is tested to match, it does not
5920 * subtype of the passed executable element, this is due to the specific use w here this method is 5700 * have to equal or be a subtype of the given executable element, this is due
5921 * used in [checkForNonAbstractClassInheritsAbstractMember]. 5701 * to the specific use where this method is used in
5922 * 5702 * [_checkForNonAbstractClassInheritsAbstractMember].
5923 * @param executableElt the executable to search for in the passed class eleme nt
5924 * @param classElt the class method to search through the members of
5925 * @return `true` iff the passed member is found in the passed class element
5926 */ 5703 */
5927 bool _isMemberInClassOrMixin( 5704 bool _isMemberInClassOrMixin(
5928 ExecutableElement executableElt, ClassElement classElt) { 5705 ExecutableElement executableElt, ClassElement classElt) {
5929 ExecutableElement foundElt = null; 5706 ExecutableElement foundElt = null;
5930 String executableName = executableElt.name; 5707 String executableName = executableElt.name;
5931 if (executableElt is MethodElement) { 5708 if (executableElt is MethodElement) {
5932 foundElt = classElt.getMethod(executableName); 5709 foundElt = classElt.getMethod(executableName);
5933 if (foundElt != null && !(foundElt as MethodElement).isAbstract) { 5710 if (foundElt != null && !(foundElt as MethodElement).isAbstract) {
5934 return true; 5711 return true;
5935 } 5712 }
(...skipping 25 matching lines...) Expand all
5961 } 5738 }
5962 if (foundElt != null && 5739 if (foundElt != null &&
5963 !(foundElt as PropertyAccessorElement).isAbstract) { 5740 !(foundElt as PropertyAccessorElement).isAbstract) {
5964 return true; 5741 return true;
5965 } 5742 }
5966 } 5743 }
5967 return false; 5744 return false;
5968 } 5745 }
5969 5746
5970 /** 5747 /**
5971 * @param node the 'this' expression to analyze 5748 * Return `true` if the given 'this' [expression] is in a valid context.
5972 * @return `true` if the given 'this' expression is in the valid context
5973 */ 5749 */
5974 bool _isThisInValidContext(ThisExpression node) { 5750 bool _isThisInValidContext(ThisExpression node) {
5975 for (AstNode n = node; n != null; n = n.parent) { 5751 for (AstNode n = node; n != null; n = n.parent) {
5976 if (n is CompilationUnit) { 5752 if (n is CompilationUnit) {
5977 return false; 5753 return false;
5978 } 5754 }
5979 if (n is ConstructorDeclaration) { 5755 if (n is ConstructorDeclaration) {
5980 return n.factoryKeyword == null; 5756 return n.factoryKeyword == null;
5981 } 5757 }
5982 if (n is ConstructorInitializer) { 5758 if (n is ConstructorInitializer) {
5983 return false; 5759 return false;
5984 } 5760 }
5985 if (n is MethodDeclaration) { 5761 if (n is MethodDeclaration) {
5986 return !n.isStatic; 5762 return !n.isStatic;
5987 } 5763 }
5988 } 5764 }
5989 return false; 5765 return false;
5990 } 5766 }
5991 5767
5992 /** 5768 /**
5993 * Return `true` if the given identifier is in a location where it is allowed to resolve to 5769 * Return `true` if the given [identifier] is in a location where it is
5994 * a static member of a supertype. 5770 * allowed to resolve to a static member of a supertype.
5995 *
5996 * @param node the node being tested
5997 * @return `true` if the given identifier is in a location where it is allowed to resolve to
5998 * a static member of a supertype
5999 */ 5771 */
6000 bool _isUnqualifiedReferenceToNonLocalStaticMemberAllowed( 5772 bool _isUnqualifiedReferenceToNonLocalStaticMemberAllowed(
6001 SimpleIdentifier node) { 5773 SimpleIdentifier node) {
6002 if (node.inDeclarationContext()) { 5774 if (node.inDeclarationContext()) {
6003 return true; 5775 return true;
6004 } 5776 }
6005 AstNode parent = node.parent; 5777 AstNode parent = node.parent;
6006 if (parent is ConstructorName || 5778 if (parent is ConstructorName ||
6007 parent is MethodInvocation || 5779 parent is MethodInvocation ||
6008 parent is PropertyAccess || 5780 parent is PropertyAccess ||
(...skipping 12 matching lines...) Expand all
6021 return true; 5793 return true;
6022 } 5794 }
6023 } 5795 }
6024 return false; 5796 return false;
6025 } 5797 }
6026 5798
6027 bool _isUserDefinedObject(EvaluationResultImpl result) => result == null || 5799 bool _isUserDefinedObject(EvaluationResultImpl result) => result == null ||
6028 (result.value != null && result.value.isUserDefinedObject); 5800 (result.value != null && result.value.isUserDefinedObject);
6029 5801
6030 /** 5802 /**
6031 * This checks the class declaration is not a superinterface to itself. 5803 * Check that the given class [element] is not a superinterface to itself. The
5804 * [path] is a list containing the potentially cyclic implements path.
6032 * 5805 *
6033 * @param classElt the class element to test
6034 * @param path a list containing the potentially cyclic implements path
6035 * @return `true` if and only if an error code is generated on the passed elem ent
6036 * See [CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE], 5806 * See [CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE],
6037 * [CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_EXTENDS], 5807 * [CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_EXTENDS],
6038 * [CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_IMPLEMENTS] , and 5808 * [CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_IMPLEMENTS] ,
6039 * [CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_WITH]. 5809 * and [CompileTimeErrorCode.RECURSIVE_INTERFACE_INHERITANCE_BASE_CASE_WITH].
6040 */ 5810 */
6041 bool _safeCheckForRecursiveInterfaceInheritance( 5811 bool _safeCheckForRecursiveInterfaceInheritance(
6042 ClassElement classElt, List<ClassElement> path) { 5812 ClassElement classElt, List<ClassElement> path) {
6043 // Detect error condition. 5813 // Detect error condition.
6044 int size = path.length; 5814 int size = path.length;
6045 // If this is not the base case (size > 0), and the enclosing class is the 5815 // If this is not the base case (size > 0), and the enclosing class is the
6046 // passed class element then an error an error. 5816 // given class element then an error an error.
6047 if (size > 0 && _enclosingClass == classElt) { 5817 if (size > 0 && _enclosingClass == classElt) {
6048 String enclosingClassName = _enclosingClass.displayName; 5818 String enclosingClassName = _enclosingClass.displayName;
6049 if (size > 1) { 5819 if (size > 1) {
6050 // Construct a string showing the cyclic implements path: 5820 // Construct a string showing the cyclic implements path:
6051 // "A, B, C, D, A" 5821 // "A, B, C, D, A"
6052 String separator = ", "; 5822 String separator = ", ";
6053 StringBuffer buffer = new StringBuffer(); 5823 StringBuffer buffer = new StringBuffer();
6054 for (int i = 0; i < size; i++) { 5824 for (int i = 0; i < size; i++) {
6055 buffer.write(path[i].displayName); 5825 buffer.write(path[i].displayName);
6056 buffer.write(separator); 5826 buffer.write(separator);
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
6094 for (InterfaceType mixinType in mixinTypes) { 5864 for (InterfaceType mixinType in mixinTypes) {
6095 if (_safeCheckForRecursiveInterfaceInheritance(mixinType.element, path)) { 5865 if (_safeCheckForRecursiveInterfaceInheritance(mixinType.element, path)) {
6096 return true; 5866 return true;
6097 } 5867 }
6098 } 5868 }
6099 path.removeAt(path.length - 1); 5869 path.removeAt(path.length - 1);
6100 return false; 5870 return false;
6101 } 5871 }
6102 5872
6103 /** 5873 /**
6104 * Return the static type of the given expression that is to be used for type analysis. 5874 * Return the static type of the given [expression] that is to be used for
6105 * 5875 * type analysis.
6106 * @param expression the expression whose type is to be returned
6107 * @return the static type of the given expression
6108 */ 5876 */
6109 static DartType getStaticType(Expression expression) { 5877 static DartType getStaticType(Expression expression) {
6110 DartType type = expression.staticType; 5878 DartType type = expression.staticType;
6111 if (type == null) { 5879 if (type == null) {
6112 // TODO(brianwilkerson) This should never happen. 5880 // TODO(brianwilkerson) This should never happen.
6113 return DynamicTypeImpl.instance; 5881 return DynamicTypeImpl.instance;
6114 } 5882 }
6115 return type; 5883 return type;
6116 } 5884 }
6117 5885
6118 /** 5886 /**
6119 * Return the variable element represented by the given expression, or `null` if there is no 5887 * Return the variable element represented by the given [expression], or
6120 * such element. 5888 * `null` if there is no such element.
6121 *
6122 * @param expression the expression whose element is to be returned
6123 * @return the variable element represented by the expression
6124 */ 5889 */
6125 static VariableElement getVariableElement(Expression expression) { 5890 static VariableElement getVariableElement(Expression expression) {
6126 if (expression is Identifier) { 5891 if (expression is Identifier) {
6127 Element element = expression.staticElement; 5892 Element element = expression.staticElement;
6128 if (element is VariableElement) { 5893 if (element is VariableElement) {
6129 return element; 5894 return element;
6130 } 5895 }
6131 } 5896 }
6132 return null; 5897 return null;
6133 } 5898 }
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after
6172 toCheck.add(type.element); 5937 toCheck.add(type.element);
6173 // type arguments 5938 // type arguments
6174 if (type is InterfaceType) { 5939 if (type is InterfaceType) {
6175 InterfaceType interfaceType = type; 5940 InterfaceType interfaceType = type;
6176 for (DartType typeArgument in interfaceType.typeArguments) { 5941 for (DartType typeArgument in interfaceType.typeArguments) {
6177 _addTypeToCheck(typeArgument); 5942 _addTypeToCheck(typeArgument);
6178 } 5943 }
6179 } 5944 }
6180 } 5945 }
6181 } 5946 }
OLDNEW
« no previous file with comments | « no previous file | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698