| OLD | NEW |
| 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, 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 interface TreeElements { | 5 interface TreeElements { |
| 6 Element operator[](Node node); | 6 Element operator[](Node node); |
| 7 Selector getSelector(Send send); | 7 Selector getSelector(Send send); |
| 8 Type getType(TypeAnnotation annotation); | 8 Type getType(TypeAnnotation annotation); |
| 9 } | 9 } |
| 10 | 10 |
| (...skipping 411 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 422 visitor.warning(node, kind, arguments); | 422 visitor.warning(node, kind, arguments); |
| 423 } | 423 } |
| 424 | 424 |
| 425 bool isFieldInitializer(SendSet node) { | 425 bool isFieldInitializer(SendSet node) { |
| 426 if (node.selector.asIdentifier() == null) return false; | 426 if (node.selector.asIdentifier() == null) return false; |
| 427 if (node.receiver == null) return true; | 427 if (node.receiver == null) return true; |
| 428 if (node.receiver.asIdentifier() == null) return false; | 428 if (node.receiver.asIdentifier() == null) return false; |
| 429 return node.receiver.asIdentifier().isThis(); | 429 return node.receiver.asIdentifier().isThis(); |
| 430 } | 430 } |
| 431 | 431 |
| 432 void checkForDuplicateInitializers(SourceString name, Node init) { |
| 433 if (initialized.containsKey(name)) { |
| 434 error(init, MessageKind.DUPLICATE_INITIALIZER, [name]); |
| 435 warning(initialized[name], MessageKind.ALREADY_INITIALIZED, [name]); |
| 436 } |
| 437 initialized[name] = init; |
| 438 } |
| 439 |
| 432 void resolveFieldInitializer(FunctionElement constructor, SendSet init) { | 440 void resolveFieldInitializer(FunctionElement constructor, SendSet init) { |
| 433 // init is of the form [this.]field = value. | 441 // init is of the form [this.]field = value. |
| 434 final Node selector = init.selector; | 442 final Node selector = init.selector; |
| 435 final SourceString name = selector.asIdentifier().source; | 443 final SourceString name = selector.asIdentifier().source; |
| 436 // Lookup target field. | 444 // Lookup target field. |
| 437 Element target; | 445 Element target; |
| 438 if (isFieldInitializer(init)) { | 446 if (isFieldInitializer(init)) { |
| 439 final ClassElement classElement = constructor.getEnclosingClass(); | 447 final ClassElement classElement = constructor.getEnclosingClass(); |
| 440 target = classElement.lookupLocalMember(name); | 448 target = classElement.lookupLocalMember(name); |
| 441 if (target === null) { | 449 if (target === null) { |
| 442 error(selector, MessageKind.CANNOT_RESOLVE, [name]); | 450 error(selector, MessageKind.CANNOT_RESOLVE, [name]); |
| 443 } else if (target.kind != ElementKind.FIELD) { | 451 } else if (target.kind != ElementKind.FIELD) { |
| 444 error(selector, MessageKind.NOT_A_FIELD, [name]); | 452 error(selector, MessageKind.NOT_A_FIELD, [name]); |
| 445 } else if (!target.isInstanceMember()) { | 453 } else if (!target.isInstanceMember()) { |
| 446 error(selector, MessageKind.INIT_STATIC_FIELD, [name]); | 454 error(selector, MessageKind.INIT_STATIC_FIELD, [name]); |
| 447 } | 455 } |
| 448 } else { | 456 } else { |
| 449 error(init, MessageKind.INVALID_RECEIVER_IN_INITIALIZER); | 457 error(init, MessageKind.INVALID_RECEIVER_IN_INITIALIZER); |
| 450 } | 458 } |
| 451 visitor.useElement(init, target); | 459 visitor.useElement(init, target); |
| 452 visitor.world.registerStaticUse(target); | 460 visitor.world.registerStaticUse(target); |
| 453 // Check for duplicate initializers. | 461 checkForDuplicateInitializers(name, init); |
| 454 if (initialized.containsKey(name)) { | |
| 455 error(init, MessageKind.DUPLICATE_INITIALIZER, [name]); | |
| 456 warning(initialized[name], MessageKind.ALREADY_INITIALIZED, [name]); | |
| 457 } | |
| 458 initialized[name] = init; | |
| 459 // Resolve initializing value. | 462 // Resolve initializing value. |
| 460 visitor.visitInStaticContext(init.arguments.head); | 463 visitor.visitInStaticContext(init.arguments.head); |
| 461 } | 464 } |
| 462 | 465 |
| 463 Element resolveSuperOrThisForSend(FunctionElement constructor, | 466 Element resolveSuperOrThisForSend(FunctionElement constructor, |
| 464 FunctionExpression functionNode, | 467 FunctionExpression functionNode, |
| 465 Send call) { | 468 Send call) { |
| 466 // Resolve the selector and the arguments. | 469 // Resolve the selector and the arguments. |
| 467 ResolverTask resolver = visitor.compiler.resolver; | 470 ResolverTask resolver = visitor.compiler.resolver; |
| 468 visitor.inStaticContext(() { | 471 visitor.inStaticContext(() { |
| (...skipping 78 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 547 } | 550 } |
| 548 return null; | 551 return null; |
| 549 } | 552 } |
| 550 | 553 |
| 551 /** | 554 /** |
| 552 * Resolve all initializers of this constructor. In the case of a redirecting | 555 * Resolve all initializers of this constructor. In the case of a redirecting |
| 553 * constructor, the resolved constructor's function element is returned. | 556 * constructor, the resolved constructor's function element is returned. |
| 554 */ | 557 */ |
| 555 FunctionElement resolveInitializers(FunctionElement constructor, | 558 FunctionElement resolveInitializers(FunctionElement constructor, |
| 556 FunctionExpression functionNode) { | 559 FunctionExpression functionNode) { |
| 560 // Keep track of all "this.param" parameters specified for constructor so |
| 561 // that we can ensure that fields are initialized only once. |
| 562 FunctionSignature functionParameters = |
| 563 constructor.computeSignature(visitor.compiler); |
| 564 functionParameters.forEachParameter((Element element) { |
| 565 if (element.kind === ElementKind.FIELD_PARAMETER) { |
| 566 checkForDuplicateInitializers(element.name, |
| 567 element.parseNode(visitor.compiler)); |
| 568 } |
| 569 }); |
| 570 |
| 557 if (functionNode.initializers === null) { | 571 if (functionNode.initializers === null) { |
| 558 initializers = const EmptyLink<Node>(); | 572 initializers = const EmptyLink<Node>(); |
| 559 } else { | 573 } else { |
| 560 initializers = functionNode.initializers.nodes; | 574 initializers = functionNode.initializers.nodes; |
| 561 } | 575 } |
| 562 FunctionElement result; | 576 FunctionElement result; |
| 563 bool resolvedSuper = false; | 577 bool resolvedSuper = false; |
| 564 for (Link<Node> link = initializers; | 578 for (Link<Node> link = initializers; |
| 565 !link.isEmpty(); | 579 !link.isEmpty(); |
| 566 link = link.tail) { | 580 link = link.tail) { |
| (...skipping 1905 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2472 TopScope(LibraryElement library) : super(null, library); | 2486 TopScope(LibraryElement library) : super(null, library); |
| 2473 Element lookup(SourceString name) { | 2487 Element lookup(SourceString name) { |
| 2474 return library.find(name); | 2488 return library.find(name); |
| 2475 } | 2489 } |
| 2476 | 2490 |
| 2477 Element add(Element newElement) { | 2491 Element add(Element newElement) { |
| 2478 throw "Cannot add an element in the top scope"; | 2492 throw "Cannot add an element in the top scope"; |
| 2479 } | 2493 } |
| 2480 String toString() => '$element'; | 2494 String toString() => '$element'; |
| 2481 } | 2495 } |
| OLD | NEW |