| 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 part of ssa; | 5 part of ssa; |
| 6 | 6 |
| 7 abstract class HVisitor<R> { | 7 abstract class HVisitor<R> { |
| 8 R visitAdd(HAdd node); | 8 R visitAdd(HAdd node); |
| 9 R visitAwait(HAwait node); | 9 R visitAwait(HAwait node); |
| 10 R visitBitAnd(HBitAnd node); | 10 R visitBitAnd(HBitAnd node); |
| (...skipping 824 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 835 * A pure instruction is an instruction that does not have any side | 835 * A pure instruction is an instruction that does not have any side |
| 836 * effect, nor any dependency. They can be moved anywhere in the | 836 * effect, nor any dependency. They can be moved anywhere in the |
| 837 * graph. | 837 * graph. |
| 838 */ | 838 */ |
| 839 bool isPure() { | 839 bool isPure() { |
| 840 return !sideEffects.hasSideEffects() | 840 return !sideEffects.hasSideEffects() |
| 841 && !sideEffects.dependsOnSomething() | 841 && !sideEffects.dependsOnSomething() |
| 842 && !canThrow(); | 842 && !canThrow(); |
| 843 } | 843 } |
| 844 | 844 |
| 845 /// An instruction is an 'allocation' is it is the sole alias for an object. |
| 846 /// This applies to to instructions that allocate new objects and can be |
| 847 /// extended to methods that return other allocations without escaping them. |
| 848 bool get isAllocation => false; |
| 849 |
| 845 /// Overridden by [HCheck] to return the actual non-[HCheck] | 850 /// Overridden by [HCheck] to return the actual non-[HCheck] |
| 846 /// instruction it checks against. | 851 /// instruction it checks against. |
| 847 HInstruction nonCheck() => this; | 852 HInstruction nonCheck() => this; |
| 848 | 853 |
| 849 /// Can this node throw an exception? | 854 /// Can this node throw an exception? |
| 850 bool canThrow() => false; | 855 bool canThrow() => false; |
| 851 | 856 |
| 852 /// Does this node potentially affect control flow. | 857 /// Does this node potentially affect control flow. |
| 853 bool isControlFlow() => false; | 858 bool isControlFlow() => false; |
| 854 | 859 |
| (...skipping 893 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1748 effects: effects, nativeBehavior: nativeBehavior); | 1753 effects: effects, nativeBehavior: nativeBehavior); |
| 1749 | 1754 |
| 1750 accept(HVisitor visitor) => visitor.visitForeignCode(this); | 1755 accept(HVisitor visitor) => visitor.visitForeignCode(this); |
| 1751 | 1756 |
| 1752 bool isJsStatement() => isStatement; | 1757 bool isJsStatement() => isStatement; |
| 1753 bool canThrow() => canBeNull() | 1758 bool canThrow() => canBeNull() |
| 1754 ? throwBehavior.canThrow | 1759 ? throwBehavior.canThrow |
| 1755 : throwBehavior.onNonNull.canThrow; | 1760 : throwBehavior.onNonNull.canThrow; |
| 1756 | 1761 |
| 1757 bool onlyThrowsNSM() => throwBehavior.isOnlyNullNSMGuard; | 1762 bool onlyThrowsNSM() => throwBehavior.isOnlyNullNSMGuard; |
| 1763 |
| 1764 bool get isAllocation => nativeBehavior != null && |
| 1765 nativeBehavior.isAllocation && |
| 1766 !canBeNull(); |
| 1758 } | 1767 } |
| 1759 | 1768 |
| 1760 class HForeignNew extends HForeign { | 1769 class HForeignNew extends HForeign { |
| 1761 ClassElement element; | 1770 ClassElement element; |
| 1762 | 1771 |
| 1763 /// If this field is not `null`, this call is from an inlined constructor and | 1772 /// If this field is not `null`, this call is from an inlined constructor and |
| 1764 /// we have to register the instantiated type in the code generator. The | 1773 /// we have to register the instantiated type in the code generator. The |
| 1765 /// [instructionType] of this node is not enough, because we also need the | 1774 /// [instructionType] of this node is not enough, because we also need the |
| 1766 /// type arguments. See also [SsaFromAstMixin.currentInlinedInstantiations]. | 1775 /// type arguments. See also [SsaFromAstMixin.currentInlinedInstantiations]. |
| 1767 List<DartType> instantiatedTypes; | 1776 List<DartType> instantiatedTypes; |
| 1768 | 1777 |
| 1769 HForeignNew(this.element, TypeMask type, List<HInstruction> inputs, | 1778 HForeignNew(this.element, TypeMask type, List<HInstruction> inputs, |
| 1770 [this.instantiatedTypes]) | 1779 [this.instantiatedTypes]) |
| 1771 : super(type, inputs); | 1780 : super(type, inputs); |
| 1772 | 1781 |
| 1773 accept(HVisitor visitor) => visitor.visitForeignNew(this); | 1782 accept(HVisitor visitor) => visitor.visitForeignNew(this); |
| 1783 |
| 1784 bool get isAllocation => true; |
| 1774 } | 1785 } |
| 1775 | 1786 |
| 1776 abstract class HInvokeBinary extends HInstruction { | 1787 abstract class HInvokeBinary extends HInstruction { |
| 1777 final Selector selector; | 1788 final Selector selector; |
| 1778 HInvokeBinary(HInstruction left, HInstruction right, this.selector, type) | 1789 HInvokeBinary(HInstruction left, HInstruction right, this.selector, type) |
| 1779 : super(<HInstruction>[left, right], type) { | 1790 : super(<HInstruction>[left, right], type) { |
| 1780 sideEffects.clearAllSideEffects(); | 1791 sideEffects.clearAllSideEffects(); |
| 1781 sideEffects.clearAllDependencies(); | 1792 sideEffects.clearAllDependencies(); |
| 1782 setUseGvn(); | 1793 setUseGvn(); |
| 1783 } | 1794 } |
| (...skipping 624 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 2408 int typeCode() => HInstruction.STATIC_STORE_TYPECODE; | 2419 int typeCode() => HInstruction.STATIC_STORE_TYPECODE; |
| 2409 bool typeEquals(other) => other is HStaticStore; | 2420 bool typeEquals(other) => other is HStaticStore; |
| 2410 bool dataEquals(HStaticStore other) => element == other.element; | 2421 bool dataEquals(HStaticStore other) => element == other.element; |
| 2411 bool isJsStatement() => true; | 2422 bool isJsStatement() => true; |
| 2412 } | 2423 } |
| 2413 | 2424 |
| 2414 class HLiteralList extends HInstruction { | 2425 class HLiteralList extends HInstruction { |
| 2415 HLiteralList(List<HInstruction> inputs, TypeMask type) : super(inputs, type); | 2426 HLiteralList(List<HInstruction> inputs, TypeMask type) : super(inputs, type); |
| 2416 toString() => 'literal list'; | 2427 toString() => 'literal list'; |
| 2417 accept(HVisitor visitor) => visitor.visitLiteralList(this); | 2428 accept(HVisitor visitor) => visitor.visitLiteralList(this); |
| 2429 |
| 2430 bool get isAllocation => true; |
| 2418 } | 2431 } |
| 2419 | 2432 |
| 2420 /** | 2433 /** |
| 2421 * The primitive array indexing operation. Note that this instruction | 2434 * The primitive array indexing operation. Note that this instruction |
| 2422 * does not throw because we generate the checks explicitly. | 2435 * does not throw because we generate the checks explicitly. |
| 2423 */ | 2436 */ |
| 2424 class HIndex extends HInstruction { | 2437 class HIndex extends HInstruction { |
| 2425 final Selector selector; | 2438 final Selector selector; |
| 2426 HIndex(HInstruction receiver, HInstruction index, this.selector, type) | 2439 HIndex(HInstruction receiver, HInstruction index, this.selector, type) |
| 2427 : super(<HInstruction>[receiver, index], type) { | 2440 : super(<HInstruction>[receiver, index], type) { |
| (...skipping 734 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3162 class HDynamicType extends HRuntimeType { | 3175 class HDynamicType extends HRuntimeType { |
| 3163 HDynamicType(DynamicType dartType, TypeMask instructionType) | 3176 HDynamicType(DynamicType dartType, TypeMask instructionType) |
| 3164 : super(const <HInstruction>[], dartType, instructionType); | 3177 : super(const <HInstruction>[], dartType, instructionType); |
| 3165 | 3178 |
| 3166 accept(HVisitor visitor) => visitor.visitDynamicType(this); | 3179 accept(HVisitor visitor) => visitor.visitDynamicType(this); |
| 3167 | 3180 |
| 3168 int typeCode() => HInstruction.DYNAMIC_TYPE_TYPECODE; | 3181 int typeCode() => HInstruction.DYNAMIC_TYPE_TYPECODE; |
| 3169 | 3182 |
| 3170 bool typeEquals(HInstruction other) => other is HDynamicType; | 3183 bool typeEquals(HInstruction other) => other is HDynamicType; |
| 3171 } | 3184 } |
| OLD | NEW |