| OLD | NEW |
| 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.incremental_resolver; | 5 library engine.incremental_resolver; |
| 6 | 6 |
| 7 import 'dart:collection'; | 7 import 'dart:collection'; |
| 8 | 8 |
| 9 import 'ast.dart'; | 9 import 'ast.dart'; |
| 10 import 'element.dart'; | 10 import 'element.dart'; |
| 11 import 'error.dart'; | 11 import 'error.dart'; |
| 12 import 'java_engine.dart'; | 12 import 'java_engine.dart'; |
| 13 import 'resolver.dart'; | 13 import 'resolver.dart'; |
| 14 import 'scanner.dart'; | 14 import 'scanner.dart'; |
| 15 import 'source.dart'; | 15 import 'source.dart'; |
| 16 | 16 |
| 17 | 17 |
| 18 /** | 18 /** |
| 19 * Instances of the class [DeclarationMatcher] determine whether the element | 19 * Instances of the class [DeclarationMatcher] determine whether the element |
| 20 * model defined by a given AST structure matches an existing element model. | 20 * model defined by a given AST structure matches an existing element model. |
| 21 */ | 21 */ |
| 22 class DeclarationMatcher extends RecursiveAstVisitor { | 22 class DeclarationMatcher extends RecursiveAstVisitor { |
| 23 /** | 23 /** |
| 24 * The libary containing the AST nodes being visited. |
| 25 */ |
| 26 LibraryElement _enclosingLibrary; |
| 27 |
| 28 /** |
| 24 * The compilation unit containing the AST nodes being visited. | 29 * The compilation unit containing the AST nodes being visited. |
| 25 */ | 30 */ |
| 26 CompilationUnitElement _enclosingUnit; | 31 CompilationUnitElement _enclosingUnit; |
| 27 | 32 |
| 28 /** | 33 /** |
| 29 * The function type alias containing the AST nodes being visited, or `null` i
f we are not | 34 * The function type alias containing the AST nodes being visited, or `null` i
f we are not |
| 30 * in the scope of a function type alias. | 35 * in the scope of a function type alias. |
| 31 */ | 36 */ |
| 32 FunctionTypeAliasElement _enclosingAlias; | 37 FunctionTypeAliasElement _enclosingAlias; |
| 33 | 38 |
| (...skipping 105 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 139 _hasConstructor = true; | 144 _hasConstructor = true; |
| 140 SimpleIdentifier constructorName = node.name; | 145 SimpleIdentifier constructorName = node.name; |
| 141 ConstructorElement element = constructorName == null ? | 146 ConstructorElement element = constructorName == null ? |
| 142 _enclosingClass.unnamedConstructor : | 147 _enclosingClass.unnamedConstructor : |
| 143 _enclosingClass.getNamedConstructor(constructorName.name); | 148 _enclosingClass.getNamedConstructor(constructorName.name); |
| 144 _processElement(element); | 149 _processElement(element); |
| 145 _assertCompatibleParameters(node.parameters, element.parameters); | 150 _assertCompatibleParameters(node.parameters, element.parameters); |
| 146 } | 151 } |
| 147 | 152 |
| 148 @override | 153 @override |
| 154 visitEnumConstantDeclaration(EnumConstantDeclaration node) { |
| 155 String name = node.name.name; |
| 156 FieldElement element = _findElement(_enclosingClass.fields, name); |
| 157 _processElement(element); |
| 158 } |
| 159 |
| 160 @override |
| 149 visitEnumDeclaration(EnumDeclaration node) { | 161 visitEnumDeclaration(EnumDeclaration node) { |
| 150 String name = node.name.name; | 162 String name = node.name.name; |
| 151 ClassElement element = _findElement(_enclosingUnit.enums, name); | 163 ClassElement element = _findElement(_enclosingUnit.enums, name); |
| 152 _enclosingClass = element; | 164 _enclosingClass = element; |
| 153 _processElement(element); | 165 _processElement(element); |
| 154 _assertTrue(element.isEnum); | 166 _assertTrue(element.isEnum); |
| 155 super.visitEnumDeclaration(node); | 167 super.visitEnumDeclaration(node); |
| 156 } | 168 } |
| 157 | 169 |
| 158 @override | 170 @override |
| 159 visitEnumConstantDeclaration(EnumConstantDeclaration node) { | 171 visitExportDirective(ExportDirective node) { |
| 160 String name = node.name.name; | 172 String uri = _getStringValue(node.uri); |
| 161 FieldElement element = _findElement(_enclosingClass.fields, name); | 173 if (uri != null) { |
| 162 _processElement(element); | 174 ExportElement element = |
| 175 _findUriReferencedElement(_enclosingLibrary.exports, uri); |
| 176 _processElement(element); |
| 177 _assertCombinators(node.combinators, element.combinators); |
| 178 } |
| 163 } | 179 } |
| 164 | 180 |
| 165 @override | 181 @override |
| 166 visitExportDirective(ExportDirective node) { | |
| 167 String uri = _getStringValue(node.uri); | |
| 168 if (uri != null) { | |
| 169 LibraryElement library = _enclosingUnit.library; | |
| 170 ExportElement exportElement = _findExport( | |
| 171 library.exports, | |
| 172 _enclosingUnit.context.sourceFactory.resolveUri(_enclosingUnit.source,
uri)); | |
| 173 _processElement(exportElement); | |
| 174 } | |
| 175 super.visitExportDirective(node); | |
| 176 } | |
| 177 | |
| 178 @override | |
| 179 visitExpressionFunctionBody(ExpressionFunctionBody node) { | 182 visitExpressionFunctionBody(ExpressionFunctionBody node) { |
| 180 // ignore bodies | 183 // ignore bodies |
| 181 } | 184 } |
| 182 | 185 |
| 183 @override | 186 @override |
| 184 visitExtendsClause(ExtendsClause node) { | 187 visitExtendsClause(ExtendsClause node) { |
| 185 _assertSameType(node.superclass, _enclosingClass.supertype); | 188 _assertSameType(node.superclass, _enclosingClass.supertype); |
| 186 } | 189 } |
| 187 | 190 |
| 188 @override | 191 @override |
| (...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 238 visitImplementsClause(ImplementsClause node) { | 241 visitImplementsClause(ImplementsClause node) { |
| 239 List<TypeName> nodes = node.interfaces; | 242 List<TypeName> nodes = node.interfaces; |
| 240 List<InterfaceType> types = _enclosingClass.interfaces; | 243 List<InterfaceType> types = _enclosingClass.interfaces; |
| 241 _assertSameTypes(nodes, types); | 244 _assertSameTypes(nodes, types); |
| 242 } | 245 } |
| 243 | 246 |
| 244 @override | 247 @override |
| 245 visitImportDirective(ImportDirective node) { | 248 visitImportDirective(ImportDirective node) { |
| 246 String uri = _getStringValue(node.uri); | 249 String uri = _getStringValue(node.uri); |
| 247 if (uri != null) { | 250 if (uri != null) { |
| 248 LibraryElement library = _enclosingUnit.library; | 251 ImportElement element = |
| 249 ImportElement importElement = _findImport( | 252 _findUriReferencedElement(_enclosingLibrary.imports, uri); |
| 250 library.imports, | 253 _processElement(element); |
| 251 _enclosingUnit.context.sourceFactory.resolveUri(_enclosingUnit.source,
uri), | 254 // match the prefix |
| 252 node.prefix); | 255 SimpleIdentifier prefixNode = node.prefix; |
| 253 _processElement(importElement); | 256 PrefixElement prefixElement = element.prefix; |
| 257 if (prefixNode == null) { |
| 258 _assertNull(prefixElement); |
| 259 } else { |
| 260 _assertNotNull(prefixElement); |
| 261 _assertEquals(prefixNode.name, prefixElement.name); |
| 262 } |
| 263 // match combinators |
| 264 _assertCombinators(node.combinators, element.combinators); |
| 254 } | 265 } |
| 255 super.visitImportDirective(node); | |
| 256 } | 266 } |
| 257 | 267 |
| 258 @override | 268 @override |
| 259 visitMethodDeclaration(MethodDeclaration node) { | 269 visitMethodDeclaration(MethodDeclaration node) { |
| 260 // prepare element name | 270 // prepare element name |
| 261 String name = node.name.name; | 271 String name = node.name.name; |
| 262 if (name == TokenType.MINUS.lexeme && | 272 if (name == TokenType.MINUS.lexeme && |
| 263 node.parameters.parameters.length == 0) { | 273 node.parameters.parameters.length == 0) { |
| 264 name = "unary-"; | 274 name = "unary-"; |
| 265 } | 275 } |
| (...skipping 15 matching lines...) Expand all Loading... |
| 281 _processElement(element); | 291 _processElement(element); |
| 282 // TODO(scheglov) test returnType | 292 // TODO(scheglov) test returnType |
| 283 _assertSameType(node.returnType, element.returnType); | 293 _assertSameType(node.returnType, element.returnType); |
| 284 _assertCompatibleParameters(node.parameters, element.parameters); | 294 _assertCompatibleParameters(node.parameters, element.parameters); |
| 285 } | 295 } |
| 286 | 296 |
| 287 @override | 297 @override |
| 288 visitPartDirective(PartDirective node) { | 298 visitPartDirective(PartDirective node) { |
| 289 String uri = _getStringValue(node.uri); | 299 String uri = _getStringValue(node.uri); |
| 290 if (uri != null) { | 300 if (uri != null) { |
| 291 Source partSource = | |
| 292 _enclosingUnit.context.sourceFactory.resolveUri(_enclosingUnit.source,
uri); | |
| 293 CompilationUnitElement element = | 301 CompilationUnitElement element = |
| 294 _findPart(_enclosingUnit.library.parts, partSource); | 302 _findUriReferencedElement(_enclosingLibrary.parts, uri); |
| 295 _processElement(element); | 303 _processElement(element); |
| 296 } | 304 } |
| 297 super.visitPartDirective(node); | 305 super.visitPartDirective(node); |
| 298 } | 306 } |
| 299 | 307 |
| 300 @override | 308 @override |
| 301 visitTopLevelVariableDeclaration(TopLevelVariableDeclaration node) { | 309 visitTopLevelVariableDeclaration(TopLevelVariableDeclaration node) { |
| 302 _inTopLevelVariableDeclaration = true; | 310 _inTopLevelVariableDeclaration = true; |
| 303 try { | 311 try { |
| 304 super.visitTopLevelVariableDeclaration(node); | 312 super.visitTopLevelVariableDeclaration(node); |
| (...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 343 element.type); | 351 element.type); |
| 344 } | 352 } |
| 345 | 353 |
| 346 @override | 354 @override |
| 347 visitWithClause(WithClause node) { | 355 visitWithClause(WithClause node) { |
| 348 List<TypeName> nodes = node.mixinTypes; | 356 List<TypeName> nodes = node.mixinTypes; |
| 349 List<InterfaceType> types = _enclosingClass.mixins; | 357 List<InterfaceType> types = _enclosingClass.mixins; |
| 350 _assertSameTypes(nodes, types); | 358 _assertSameTypes(nodes, types); |
| 351 } | 359 } |
| 352 | 360 |
| 361 void _assertCombinators(List<Combinator> nodeCombinators, |
| 362 List<NamespaceCombinator> elementCombinators) { |
| 363 // prepare shown/hidden names in the element |
| 364 Set<String> showNames = new Set<String>(); |
| 365 Set<String> hideNames = new Set<String>(); |
| 366 for (NamespaceCombinator combinator in elementCombinators) { |
| 367 if (combinator is ShowElementCombinator) { |
| 368 showNames.addAll(combinator.shownNames); |
| 369 } else if (combinator is HideElementCombinator) { |
| 370 hideNames.addAll(combinator.hiddenNames); |
| 371 } |
| 372 } |
| 373 // match combinators with the node |
| 374 for (Combinator combinator in nodeCombinators) { |
| 375 if (combinator is ShowCombinator) { |
| 376 for (SimpleIdentifier nameNode in combinator.shownNames) { |
| 377 String name = nameNode.name; |
| 378 _assertTrue(showNames.remove(name)); |
| 379 } |
| 380 } else if (combinator is HideCombinator) { |
| 381 for (SimpleIdentifier nameNode in combinator.hiddenNames) { |
| 382 String name = nameNode.name; |
| 383 _assertTrue(hideNames.remove(name)); |
| 384 } |
| 385 } |
| 386 } |
| 387 _assertTrue(showNames.isEmpty); |
| 388 _assertTrue(hideNames.isEmpty); |
| 389 } |
| 390 |
| 353 void _assertCompatibleParameter(FormalParameter node, | 391 void _assertCompatibleParameter(FormalParameter node, |
| 354 ParameterElement element) { | 392 ParameterElement element) { |
| 355 if (node is SimpleFormalParameter) { | 393 if (node is SimpleFormalParameter) { |
| 356 _assertSameType(node.type, element.type); | 394 _assertSameType(node.type, element.type); |
| 357 } else { | 395 } else { |
| 358 // TODO(scheglov) support other parameter types | 396 // TODO(scheglov) support other parameter types |
| 359 _assertTrue(false); | 397 _assertTrue(false); |
| 360 } | 398 } |
| 361 // TODO(scheglov) check names of named parameters | 399 // TODO(scheglov) check names of named parameters |
| 362 } | 400 } |
| (...skipping 19 matching lines...) Expand all Loading... |
| 382 throw new _DeclarationMismatchException(); | 420 throw new _DeclarationMismatchException(); |
| 383 } | 421 } |
| 384 } | 422 } |
| 385 | 423 |
| 386 void _assertNotNull(Element element) { | 424 void _assertNotNull(Element element) { |
| 387 if (element == null) { | 425 if (element == null) { |
| 388 throw new _DeclarationMismatchException(); | 426 throw new _DeclarationMismatchException(); |
| 389 } | 427 } |
| 390 } | 428 } |
| 391 | 429 |
| 430 void _assertNull(Element element) { |
| 431 if (element != null) { |
| 432 throw new _DeclarationMismatchException(); |
| 433 } |
| 434 } |
| 435 |
| 392 void _assertSameType(TypeName node, DartType type) { | 436 void _assertSameType(TypeName node, DartType type) { |
| 393 // no return type == dynamic | 437 // no return type == dynamic |
| 394 if (node == null) { | 438 if (node == null) { |
| 395 return _assertTrue(type == null || type.isDynamic); | 439 return _assertTrue(type == null || type.isDynamic); |
| 396 } | 440 } |
| 397 // check specific type kinds | 441 // check specific type kinds |
| 398 String nodeName = node.name.name; | 442 String nodeName = node.name.name; |
| 399 if (type is InterfaceType) { | 443 if (type is InterfaceType) { |
| 400 _assertEquals(nodeName, type.name); | 444 _assertEquals(nodeName, type.name); |
| 401 // check arguments | 445 // check arguments |
| (...skipping 22 matching lines...) Expand all Loading... |
| 424 } | 468 } |
| 425 } | 469 } |
| 426 | 470 |
| 427 void _assertTrue(bool condition) { | 471 void _assertTrue(bool condition) { |
| 428 if (!condition) { | 472 if (!condition) { |
| 429 throw new _DeclarationMismatchException(); | 473 throw new _DeclarationMismatchException(); |
| 430 } | 474 } |
| 431 } | 475 } |
| 432 | 476 |
| 433 /** | 477 /** |
| 434 * Given that the comparison is to begin with the given element, capture the e
nclosing elements | 478 * Given that the comparison is to begin with the given [element], capture |
| 435 * that might be used while performing the comparison. | 479 * the enclosing elements that might be used while performing the comparison. |
| 436 * | |
| 437 * @param element the element corresponding to the AST structure to be compare
d | |
| 438 */ | 480 */ |
| 439 void _captureEnclosingElements(Element element) { | 481 void _captureEnclosingElements(Element element) { |
| 440 Element parent = | 482 Element parent = |
| 441 element is CompilationUnitElement ? element : element.enclosingElement; | 483 element is CompilationUnitElement ? element : element.enclosingElement; |
| 442 while (parent != null) { | 484 while (parent != null) { |
| 443 if (parent is CompilationUnitElement) { | 485 if (parent is CompilationUnitElement) { |
| 444 _enclosingUnit = parent as CompilationUnitElement; | 486 _enclosingUnit = parent as CompilationUnitElement; |
| 487 _enclosingLibrary = element.library; |
| 445 } else if (parent is ClassElement) { | 488 } else if (parent is ClassElement) { |
| 446 if (_enclosingClass == null) { | 489 if (_enclosingClass == null) { |
| 447 _enclosingClass = parent as ClassElement; | 490 _enclosingClass = parent as ClassElement; |
| 448 } | 491 } |
| 449 } else if (parent is FunctionTypeAliasElement) { | 492 } else if (parent is FunctionTypeAliasElement) { |
| 450 if (_enclosingAlias == null) { | 493 if (_enclosingAlias == null) { |
| 451 _enclosingAlias = parent as FunctionTypeAliasElement; | 494 _enclosingAlias = parent as FunctionTypeAliasElement; |
| 452 } | 495 } |
| 453 } else if (parent is ParameterElement) { | 496 } else if (parent is ParameterElement) { |
| 454 if (_enclosingParameter == null) { | 497 if (_enclosingParameter == null) { |
| (...skipping 10 matching lines...) Expand all Loading... |
| 465 Element _findElement(List<Element> elements, String name) { | 508 Element _findElement(List<Element> elements, String name) { |
| 466 for (Element element in elements) { | 509 for (Element element in elements) { |
| 467 if (element.displayName == name) { | 510 if (element.displayName == name) { |
| 468 return element; | 511 return element; |
| 469 } | 512 } |
| 470 } | 513 } |
| 471 return null; | 514 return null; |
| 472 } | 515 } |
| 473 | 516 |
| 474 /** | 517 /** |
| 475 * Return the export element from the given array whose library has the given
source, or | |
| 476 * `null` if there is no such export. | |
| 477 * | |
| 478 * @param exports the export elements being searched | |
| 479 * @param source the source of the library associated with the export element
to being searched | |
| 480 * for | |
| 481 * @return the export element whose library has the given source | |
| 482 */ | |
| 483 ExportElement _findExport(List<ExportElement> exports, Source source) { | |
| 484 for (ExportElement export in exports) { | |
| 485 if (export.exportedLibrary.source == source) { | |
| 486 return export; | |
| 487 } | |
| 488 } | |
| 489 return null; | |
| 490 } | |
| 491 | |
| 492 /** | |
| 493 * Return the element in the given array of elements that was created for the
declaration with the | 518 * Return the element in the given array of elements that was created for the
declaration with the |
| 494 * given name. | 519 * given name. |
| 495 * | 520 * |
| 496 * @param elements the elements of the appropriate kind that exist in the curr
ent context | 521 * @param elements the elements of the appropriate kind that exist in the curr
ent context |
| 497 * @param identifier the name node in the declaration of the element to be ret
urned | 522 * @param identifier the name node in the declaration of the element to be ret
urned |
| 498 * @return the element created for the declaration with the given name | 523 * @return the element created for the declaration with the given name |
| 499 */ | 524 */ |
| 500 Element _findIdentifier(List<Element> elements, | 525 Element _findIdentifier(List<Element> elements, |
| 501 SimpleIdentifier identifier) => | 526 SimpleIdentifier identifier) => |
| 502 _findWithNameAndOffset(elements, identifier.name, identifier.offset); | 527 _findWithNameAndOffset(elements, identifier.name, identifier.offset); |
| 503 | 528 |
| 504 /** | 529 /** |
| 505 * Return the import element from the given array whose library has the given
source and that has | |
| 506 * the given prefix, or `null` if there is no such import. | |
| 507 * | |
| 508 * @param imports the import elements being searched | |
| 509 * @param source the source of the library associated with the import element
to being searched | |
| 510 * for | |
| 511 * @param prefix the prefix with which the library was imported | |
| 512 * @return the import element whose library has the given source and prefix | |
| 513 */ | |
| 514 ImportElement _findImport(List<ImportElement> imports, Source source, | |
| 515 SimpleIdentifier prefix) { | |
| 516 for (ImportElement element in imports) { | |
| 517 if (element.importedLibrary.source == source) { | |
| 518 PrefixElement prefixElement = element.prefix; | |
| 519 if (prefix == null) { | |
| 520 if (prefixElement == null) { | |
| 521 return element; | |
| 522 } | |
| 523 } else { | |
| 524 if (prefixElement != null && | |
| 525 prefix.name == prefixElement.displayName) { | |
| 526 return element; | |
| 527 } | |
| 528 } | |
| 529 } | |
| 530 } | |
| 531 return null; | |
| 532 } | |
| 533 | |
| 534 /** | |
| 535 * Return the element for the part with the given source, or `null` if there i
s no element | |
| 536 * for the given source. | |
| 537 * | |
| 538 * @param parts the elements for the parts | |
| 539 * @param partSource the source for the part whose element is to be returned | |
| 540 * @return the element for the part with the given source | |
| 541 */ | |
| 542 CompilationUnitElement _findPart(List<CompilationUnitElement> parts, | |
| 543 Source partSource) { | |
| 544 for (CompilationUnitElement part in parts) { | |
| 545 if (part.source == partSource) { | |
| 546 return part; | |
| 547 } | |
| 548 } | |
| 549 return null; | |
| 550 } | |
| 551 | |
| 552 /** | |
| 553 * Return the element in the given array of elements that was created for the
declaration with the | 530 * Return the element in the given array of elements that was created for the
declaration with the |
| 554 * given name at the given offset. | 531 * given name at the given offset. |
| 555 * | 532 * |
| 556 * @param elements the elements of the appropriate kind that exist in the curr
ent context | 533 * @param elements the elements of the appropriate kind that exist in the curr
ent context |
| 557 * @param name the name of the element to be returned | 534 * @param name the name of the element to be returned |
| 558 * @param offset the offset of the name of the element to be returned | 535 * @param offset the offset of the name of the element to be returned |
| 559 * @return the element with the given name and offset | 536 * @return the element with the given name and offset |
| 560 */ | 537 */ |
| 561 Element _findWithNameAndOffset(List<Element> elements, String name, | 538 Element _findWithNameAndOffset(List<Element> elements, String name, |
| 562 int offset) { | 539 int offset) { |
| 563 for (Element element in elements) { | 540 for (Element element in elements) { |
| 564 if (element.displayName == name && element.nameOffset == offset) { | 541 if (element.displayName == name && element.nameOffset == offset) { |
| 565 return element; | 542 return element; |
| 566 } | 543 } |
| 567 } | 544 } |
| 568 return null; | 545 return null; |
| 569 } | 546 } |
| 570 | 547 |
| 571 void _gatherElements(Element element) { | 548 void _gatherElements(Element element) { |
| 572 element.accept(new _ElementsGatherer(this)); | 549 _ElementsGatherer gatherer = new _ElementsGatherer(this); |
| 550 element.accept(gatherer); |
| 551 // TODO(scheglov) push into CompilationUnitElement |
| 552 if (identical(_enclosingUnit, _enclosingLibrary.definingCompilationUnit)) { |
| 553 gatherer.addElements(_enclosingLibrary.imports); |
| 554 gatherer.addElements(_enclosingLibrary.exports); |
| 555 gatherer.addElements(_enclosingLibrary.parts); |
| 556 } |
| 573 } | 557 } |
| 574 | 558 |
| 575 /** | 559 /** |
| 576 * Return the value of the given string literal, or `null` if the string is no
t a constant | 560 * Return the value of the given string literal, or `null` if the string is no
t a constant |
| 577 * string without any string interpolation. | 561 * string without any string interpolation. |
| 578 * | 562 * |
| 579 * @param literal the string literal whose value is to be returned | 563 * @param literal the string literal whose value is to be returned |
| 580 * @return the value of the given string literal | 564 * @return the value of the given string literal |
| 581 */ | 565 */ |
| 582 String _getStringValue(StringLiteral literal) { | 566 String _getStringValue(StringLiteral literal) { |
| 583 if (literal is StringInterpolation) { | 567 if (literal is StringInterpolation) { |
| 584 return null; | 568 return null; |
| 585 } | 569 } |
| 586 return literal.stringValue; | 570 return literal.stringValue; |
| 587 } | 571 } |
| 588 | 572 |
| 589 void _processElement(Element element) { | 573 void _processElement(Element element) { |
| 590 _assertNotNull(element); | 574 _assertNotNull(element); |
| 591 if (!_allElements.contains(element)) { | 575 if (!_allElements.contains(element)) { |
| 592 throw new _DeclarationMismatchException(); | 576 throw new _DeclarationMismatchException(); |
| 593 } | 577 } |
| 594 _unmatchedElements.remove(element); | 578 _unmatchedElements.remove(element); |
| 595 } | 579 } |
| 580 |
| 581 /** |
| 582 * Return the [UriReferencedElement] from [elements] with the given [uri], or |
| 583 * `null` if there is no such element. |
| 584 */ |
| 585 static UriReferencedElement |
| 586 _findUriReferencedElement(List<UriReferencedElement> elements, String uri)
{ |
| 587 for (UriReferencedElement element in elements) { |
| 588 if (element.uri == uri) { |
| 589 return element; |
| 590 } |
| 591 } |
| 592 return null; |
| 593 } |
| 596 } | 594 } |
| 597 | 595 |
| 598 | 596 |
| 599 /** | 597 /** |
| 600 * Instances of the class [IncrementalResolver] resolve the smallest portion of | 598 * Instances of the class [IncrementalResolver] resolve the smallest portion of |
| 601 * an AST structure that we currently know how to resolve. | 599 * an AST structure that we currently know how to resolve. |
| 602 */ | 600 */ |
| 603 class IncrementalResolver { | 601 class IncrementalResolver { |
| 604 /** | 602 /** |
| 605 * The error listener that will be informed of any errors that are found | 603 * The error listener that will be informed of any errors that are found |
| (...skipping 320 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 926 super.visitElement(element); | 924 super.visitElement(element); |
| 927 } | 925 } |
| 928 } | 926 } |
| 929 | 927 |
| 930 | 928 |
| 931 class _ElementsGatherer extends GeneralizingElementVisitor { | 929 class _ElementsGatherer extends GeneralizingElementVisitor { |
| 932 final DeclarationMatcher matcher; | 930 final DeclarationMatcher matcher; |
| 933 | 931 |
| 934 _ElementsGatherer(this.matcher); | 932 _ElementsGatherer(this.matcher); |
| 935 | 933 |
| 934 void addElements(List<Element> elements) { |
| 935 for (Element element in elements) { |
| 936 if (!element.isSynthetic) { |
| 937 _addElement(element); |
| 938 } |
| 939 } |
| 940 } |
| 941 |
| 936 @override | 942 @override |
| 937 visitElement(Element element) { | 943 visitElement(Element element) { |
| 938 _addElement(element); | 944 _addElement(element); |
| 939 super.visitElement(element); | 945 super.visitElement(element); |
| 940 } | 946 } |
| 941 | 947 |
| 942 @override | 948 @override |
| 943 visitExecutableElement(ExecutableElement element) { | 949 visitExecutableElement(ExecutableElement element) { |
| 944 _addElement(element); | 950 _addElement(element); |
| 945 } | 951 } |
| (...skipping 14 matching lines...) Expand all Loading... |
| 960 // Don't visit children (such as property accessors). | 966 // Don't visit children (such as property accessors). |
| 961 } | 967 } |
| 962 | 968 |
| 963 void _addElement(Element element) { | 969 void _addElement(Element element) { |
| 964 if (element != null) { | 970 if (element != null) { |
| 965 matcher._allElements.add(element); | 971 matcher._allElements.add(element); |
| 966 matcher._unmatchedElements.add(element); | 972 matcher._unmatchedElements.add(element); |
| 967 } | 973 } |
| 968 } | 974 } |
| 969 } | 975 } |
| OLD | NEW |