Chromium Code Reviews| 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 #library('elements'); | 5 #library('elements'); |
| 6 | 6 |
| 7 #import('../tree/tree.dart'); | 7 #import('../tree/tree.dart'); |
| 8 #import('../scanner/scannerlib.dart'); | 8 #import('../scanner/scannerlib.dart'); |
| 9 #import('../leg.dart'); // TODO(karlklose): we only need type. | 9 #import('../leg.dart'); // TODO(karlklose): we only need type. |
| 10 #import('../util/util.dart'); | 10 #import('../util/util.dart'); |
| (...skipping 186 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 197 | 197 |
| 198 Element getOutermostEnclosingMemberOrTopLevel() { | 198 Element getOutermostEnclosingMemberOrTopLevel() { |
| 199 for (Element e = this; e !== null; e = e.enclosingElement) { | 199 for (Element e = this; e !== null; e = e.enclosingElement) { |
| 200 if (e.isMember() || e.isTopLevel()) { | 200 if (e.isMember() || e.isTopLevel()) { |
| 201 return e; | 201 return e; |
| 202 } | 202 } |
| 203 } | 203 } |
| 204 return null; | 204 return null; |
| 205 } | 205 } |
| 206 | 206 |
| 207 toString() { | 207 String toString() { |
|
Johnni Winther
2012/06/29 09:34:43
Thank you!
| |
| 208 if (!isTopLevel()) { | 208 if (!isTopLevel()) { |
| 209 String holderName = enclosingElement.name.slowToString(); | 209 String holderName = enclosingElement.name.slowToString(); |
| 210 return '$kind($holderName#${name.slowToString()})'; | 210 return '$kind($holderName#${name.slowToString()})'; |
| 211 } else { | 211 } else { |
| 212 return '$kind(${name.slowToString()})'; | 212 return '$kind(${name.slowToString()})'; |
| 213 } | 213 } |
| 214 } | 214 } |
| 215 | 215 |
| 216 bool _isNative = false; | 216 bool _isNative = false; |
| 217 void setNative() { _isNative = true; } | 217 void setNative() { _isNative = true; } |
| (...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 297 class LibraryElement extends CompilationUnitElement { | 297 class LibraryElement extends CompilationUnitElement { |
| 298 // TODO(ahe): Library element should not be a subclass of | 298 // TODO(ahe): Library element should not be a subclass of |
| 299 // CompilationUnitElement. | 299 // CompilationUnitElement. |
| 300 | 300 |
| 301 Link<CompilationUnitElement> compilationUnits = | 301 Link<CompilationUnitElement> compilationUnits = |
| 302 const EmptyLink<CompilationUnitElement>(); | 302 const EmptyLink<CompilationUnitElement>(); |
| 303 Link<ScriptTag> tags = const EmptyLink<ScriptTag>(); | 303 Link<ScriptTag> tags = const EmptyLink<ScriptTag>(); |
| 304 ScriptTag libraryTag; | 304 ScriptTag libraryTag; |
| 305 Map<SourceString, Element> elements; | 305 Map<SourceString, Element> elements; |
| 306 bool canUseNative = false; | 306 bool canUseNative = false; |
| 307 LibraryElement patch = null; | |
| 307 | 308 |
| 308 LibraryElement(Script script) | 309 LibraryElement(Script script) |
| 309 : elements = new Map<SourceString, Element>(), | 310 : elements = new Map<SourceString, Element>(), |
| 310 super.library(script); | 311 super.library(script); |
| 311 | 312 |
| 313 bool get isPatched() => patch !== null; | |
| 314 | |
| 312 void addCompilationUnit(CompilationUnitElement element) { | 315 void addCompilationUnit(CompilationUnitElement element) { |
| 313 compilationUnits = compilationUnits.prepend(element); | 316 compilationUnits = compilationUnits.prepend(element); |
| 314 } | 317 } |
| 315 | 318 |
| 316 void addTag(ScriptTag tag, DiagnosticListener listener) { | 319 void addTag(ScriptTag tag, DiagnosticListener listener) { |
| 317 tags = tags.prepend(tag); | 320 tags = tags.prepend(tag); |
| 318 } | 321 } |
| 319 | 322 |
| 320 void addMember(Element element, DiagnosticListener listener) { | 323 void addMember(Element element, DiagnosticListener listener) { |
| 321 topLevelElements = topLevelElements.prepend(element); | 324 topLevelElements = topLevelElements.prepend(element); |
| (...skipping 252 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 574 } | 577 } |
| 575 | 578 |
| 576 class FunctionElement extends Element { | 579 class FunctionElement extends Element { |
| 577 FunctionExpression cachedNode; | 580 FunctionExpression cachedNode; |
| 578 Type type; | 581 Type type; |
| 579 final Modifiers modifiers; | 582 final Modifiers modifiers; |
| 580 | 583 |
| 581 FunctionSignature functionSignature; | 584 FunctionSignature functionSignature; |
| 582 | 585 |
| 583 /** | 586 /** |
| 587 * A function declaration that should be parsed instead of the current one. | |
| 588 * The patch should be parsed as if it was in the current scope. Its | |
| 589 * signature must match this function's signature. | |
| 590 */ | |
| 591 // TODO(lrn): Consider using [defaultImplementation] to store the patch. | |
| 592 FunctionElement patch = null; | |
| 593 | |
| 594 /** | |
| 584 * If this is an interface constructor, [defaultImplementation] will | 595 * If this is an interface constructor, [defaultImplementation] will |
| 585 * changed by the resolver to point to the default | 596 * changed by the resolver to point to the default |
| 586 * implementation. Otherwise, [:defaultImplementation === this:]. | 597 * implementation. Otherwise, [:defaultImplementation === this:]. |
| 587 */ | 598 */ |
| 588 FunctionElement defaultImplementation; | 599 FunctionElement defaultImplementation; |
| 589 | 600 |
| 590 FunctionElement(SourceString name, | 601 FunctionElement(SourceString name, |
| 591 ElementKind kind, | 602 ElementKind kind, |
| 592 Modifiers modifiers, | 603 Modifiers modifiers, |
| 593 Element enclosing) | 604 Element enclosing) |
| 594 : this.tooMuchOverloading(name, null, kind, modifiers, enclosing, null); | 605 : this.tooMuchOverloading(name, null, kind, modifiers, enclosing, null); |
| 595 | 606 |
| 596 FunctionElement.node(SourceString name, | 607 FunctionElement.node(SourceString name, |
| 597 FunctionExpression node, | 608 FunctionExpression node, |
| 598 ElementKind kind, | 609 ElementKind kind, |
| 599 Modifiers modifiers, | 610 Modifiers modifiers, |
| 600 Element enclosing) | 611 Element enclosing) |
| 601 : this.tooMuchOverloading(name, node, kind, modifiers, enclosing, null); | 612 : this.tooMuchOverloading(name, node, kind, modifiers, enclosing, null); |
| 602 | 613 |
| 603 FunctionElement.from(SourceString name, | 614 FunctionElement.from(SourceString name, |
| 604 FunctionElement other, | 615 FunctionElement other, |
| 605 Element enclosing) | 616 Element enclosing) |
| 606 : this.tooMuchOverloading(name, other.cachedNode, other.kind, | 617 : this.tooMuchOverloading(name, other.cachedNode, other.kind, |
| 607 other.modifiers, enclosing, | 618 other.modifiers, enclosing, |
| 608 other.functionSignature); | 619 other.functionSignature); |
| 609 | 620 |
| 610 FunctionElement.tooMuchOverloading(SourceString name, | 621 FunctionElement.tooMuchOverloading(SourceString name, |
| 611 FunctionExpression this.cachedNode, | 622 FunctionExpression this.cachedNode, |
| 612 ElementKind kind, | 623 ElementKind kind, |
| 613 Modifiers this.modifiers, | 624 Modifiers this.modifiers, |
| 614 Element enclosing, | 625 Element enclosing, |
| 615 FunctionSignature this.functionSignature) | 626 FunctionSignature this.functionSignature) |
| 616 : super(name, kind, enclosing) | 627 : super(name, kind, enclosing) { |
| 617 { | |
| 618 defaultImplementation = this; | 628 defaultImplementation = this; |
| 619 } | 629 } |
| 620 | 630 |
| 631 CompilationUnitElement getCompilationUnit() { | |
| 632 if (patch !== null) return patch.getCompilationUnit(); | |
| 633 return super.getCompilationUnit(); | |
| 634 } | |
| 635 | |
| 636 void setPatch(FunctionElement patchElement) { | |
| 637 if (cachedNode !== null) throw "Patch After Parsing"; | |
|
Johnni Winther
2012/06/29 09:34:43
Is that the appropriate way to signal internal err
Lasse Reichstein Nielsen
2012/06/29 12:01:35
It isn't really. The problem is that the element d
| |
| 638 this.patch = patchElement; | |
| 639 cachedNode = patchElement.cachedNode; | |
| 640 } | |
| 641 | |
| 621 bool isInstanceMember() { | 642 bool isInstanceMember() { |
| 622 return isMember() | 643 return isMember() |
| 623 && kind != ElementKind.GENERATIVE_CONSTRUCTOR | 644 && kind != ElementKind.GENERATIVE_CONSTRUCTOR |
| 624 && !modifiers.isFactory() | 645 && !modifiers.isFactory() |
| 625 && !modifiers.isStatic(); | 646 && !modifiers.isStatic(); |
| 626 } | 647 } |
| 627 | 648 |
| 628 FunctionSignature computeSignature(Compiler compiler) { | 649 FunctionSignature computeSignature(Compiler compiler) { |
| 629 if (functionSignature !== null) return functionSignature; | 650 if (functionSignature !== null) return functionSignature; |
| 630 compiler.withCurrentElement(this, () { | 651 compiler.withCurrentElement(this, () { |
| (...skipping 13 matching lines...) Expand all Loading... | |
| 644 int parameterCount(Compiler compiler) { | 665 int parameterCount(Compiler compiler) { |
| 645 return computeSignature(compiler).parameterCount; | 666 return computeSignature(compiler).parameterCount; |
| 646 } | 667 } |
| 647 | 668 |
| 648 FunctionType computeType(Compiler compiler) { | 669 FunctionType computeType(Compiler compiler) { |
| 649 if (type != null) return type; | 670 if (type != null) return type; |
| 650 type = compiler.computeFunctionType(this, computeSignature(compiler)); | 671 type = compiler.computeFunctionType(this, computeSignature(compiler)); |
| 651 return type; | 672 return type; |
| 652 } | 673 } |
| 653 | 674 |
| 654 Node parseNode(DiagnosticListener listener) => cachedNode; | 675 Node parseNode(DiagnosticListener listener) { |
|
Johnni Winther
2012/06/29 09:34:43
This is also overridden in ConstructorBodyElement
Lasse Reichstein Nielsen
2012/06/29 12:01:35
True. I don't try to handle constructors yet (or a
| |
| 676 if (cachedNode !== null) return cachedNode; | |
| 677 if (patch !== null) { | |
| 678 cachedNode = patch.parseNode(listener); | |
| 679 } | |
| 680 return cachedNode; | |
| 681 } | |
| 655 | 682 |
| 656 Token position() => cachedNode.getBeginToken(); | 683 Token position() => cachedNode.getBeginToken(); |
| 657 | 684 |
| 658 FunctionElement asFunctionElement() => this; | 685 FunctionElement asFunctionElement() => this; |
| 659 } | 686 } |
| 660 | 687 |
| 661 class ConstructorBodyElement extends FunctionElement { | 688 class ConstructorBodyElement extends FunctionElement { |
| 662 FunctionElement constructor; | 689 FunctionElement constructor; |
| 663 | 690 |
| 664 ConstructorBodyElement(FunctionElement constructor) | 691 ConstructorBodyElement(FunctionElement constructor) |
| (...skipping 49 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 714 Map<SourceString, Element> constructors; | 741 Map<SourceString, Element> constructors; |
| 715 Link<Type> interfaces = const EmptyLink<Type>(); | 742 Link<Type> interfaces = const EmptyLink<Type>(); |
| 716 LinkedHashMap<SourceString, TypeVariableElement> typeParameters; | 743 LinkedHashMap<SourceString, TypeVariableElement> typeParameters; |
| 717 bool isResolved = false; | 744 bool isResolved = false; |
| 718 bool isBeingResolved = false; | 745 bool isBeingResolved = false; |
| 719 // backendMembers are members that have been added by the backend to simplify | 746 // backendMembers are members that have been added by the backend to simplify |
| 720 // compilation. They don't have any user-side counter-part. | 747 // compilation. They don't have any user-side counter-part. |
| 721 Link<Element> backendMembers = const EmptyLink<Element>(); | 748 Link<Element> backendMembers = const EmptyLink<Element>(); |
| 722 | 749 |
| 723 Link<Type> allSupertypes; | 750 Link<Type> allSupertypes; |
| 751 ClassElement patch = null; | |
|
Johnni Winther
2012/06/29 09:34:43
This is currently unused, right?
Lasse Reichstein Nielsen
2012/06/29 12:01:35
Yes. At some point there will be a patch class ele
| |
| 724 | 752 |
| 725 ClassElement(SourceString name, CompilationUnitElement enclosing, this.id) | 753 ClassElement(SourceString name, CompilationUnitElement enclosing, this.id) |
| 726 : localMembers = new Map<SourceString, Element>(), | 754 : localMembers = new Map<SourceString, Element>(), |
| 727 constructors = new Map<SourceString, Element>(), | 755 constructors = new Map<SourceString, Element>(), |
| 728 typeParameters = new LinkedHashMap<SourceString, TypeVariableElement>(), | 756 typeParameters = new LinkedHashMap<SourceString, TypeVariableElement>(), |
| 729 super(name, ElementKind.CLASS, enclosing); | 757 super(name, ElementKind.CLASS, enclosing); |
| 730 | 758 |
| 731 void addMember(Element element, DiagnosticListener listener) { | 759 void addMember(Element element, DiagnosticListener listener) { |
| 732 members = members.prepend(element); | 760 members = members.prepend(element); |
| 733 if (element.kind == ElementKind.GENERATIVE_CONSTRUCTOR || | 761 if (element.kind == ElementKind.GENERATIVE_CONSTRUCTOR || |
| (...skipping 340 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1074 final Node node; | 1102 final Node node; |
| 1075 Type bound; | 1103 Type bound; |
| 1076 Type type; | 1104 Type type; |
| 1077 TypeVariableElement(name, Element enclosing, this.node, this.type, | 1105 TypeVariableElement(name, Element enclosing, this.node, this.type, |
| 1078 [this.bound]) | 1106 [this.bound]) |
| 1079 : super(name, ElementKind.TYPE_VARIABLE, enclosing); | 1107 : super(name, ElementKind.TYPE_VARIABLE, enclosing); |
| 1080 Type computeType(compiler) => type; | 1108 Type computeType(compiler) => type; |
| 1081 Node parseNode(compiler) => node; | 1109 Node parseNode(compiler) => node; |
| 1082 toString() => "${enclosingElement.toString()}.${name.slowToString()}"; | 1110 toString() => "${enclosingElement.toString()}.${name.slowToString()}"; |
| 1083 } | 1111 } |
| OLD | NEW |