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

Side by Side Diff: pkg/compiler/lib/src/ssa/interceptor_simplifier.dart

Issue 2366363002: Move remaining functionality from ClassWorld to ClosedWorld (Closed)
Patch Set: Created 4 years, 2 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
OLDNEW
1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file 1 // Copyright (c) 2013, 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 import '../common/codegen.dart' show CodegenWorkItem; 5 import '../common/codegen.dart' show CodegenWorkItem;
6 import '../compiler.dart' show Compiler; 6 import '../compiler.dart' show Compiler;
7 import '../constants/constant_system.dart'; 7 import '../constants/constant_system.dart';
8 import '../constants/values.dart'; 8 import '../constants/values.dart';
9 import '../elements/elements.dart'; 9 import '../elements/elements.dart';
10 import '../js_backend/backend_helpers.dart' show BackendHelpers; 10 import '../js_backend/backend_helpers.dart' show BackendHelpers;
11 import '../js_backend/js_backend.dart'; 11 import '../js_backend/js_backend.dart';
12 import '../types/types.dart'; 12 import '../types/types.dart';
13 import '../universe/selector.dart' show Selector; 13 import '../universe/selector.dart' show Selector;
14 import '../world.dart' show ClassWorld; 14 import '../world.dart' show ClosedWorld;
15 import 'nodes.dart'; 15 import 'nodes.dart';
16 import 'optimize.dart'; 16 import 'optimize.dart';
17 17
18 /** 18 /**
19 * This phase simplifies interceptors in multiple ways: 19 * This phase simplifies interceptors in multiple ways:
20 * 20 *
21 * 1) If the interceptor is for an object whose type is known, it 21 * 1) If the interceptor is for an object whose type is known, it
22 * tries to use a constant interceptor instead. 22 * tries to use a constant interceptor instead.
23 * 23 *
24 * 2) Interceptors are specialized based on the selector it is used with. 24 * 2) Interceptors are specialized based on the selector it is used with.
(...skipping 17 matching lines...) Expand all
42 final Compiler compiler; 42 final Compiler compiler;
43 final Element element; 43 final Element element;
44 HGraph graph; 44 HGraph graph;
45 45
46 SsaSimplifyInterceptors(this.compiler, this.constantSystem, this.element); 46 SsaSimplifyInterceptors(this.compiler, this.constantSystem, this.element);
47 47
48 JavaScriptBackend get backend => compiler.backend; 48 JavaScriptBackend get backend => compiler.backend;
49 49
50 BackendHelpers get helpers => backend.helpers; 50 BackendHelpers get helpers => backend.helpers;
51 51
52 ClassWorld get classWorld => compiler.closedWorld; 52 ClosedWorld get closedWorld => compiler.closedWorld;
53 53
54 void visitGraph(HGraph graph) { 54 void visitGraph(HGraph graph) {
55 this.graph = graph; 55 this.graph = graph;
56 visitDominatorTree(graph); 56 visitDominatorTree(graph);
57 } 57 }
58 58
59 void visitBasicBlock(HBasicBlock node) { 59 void visitBasicBlock(HBasicBlock node) {
60 currentBlock = node; 60 currentBlock = node;
61 61
62 HInstruction instruction = node.first; 62 HInstruction instruction = node.first;
(...skipping 39 matching lines...) Expand 10 before | Expand all | Expand 10 after
102 return false; 102 return false;
103 } 103 }
104 if (receiver.canBeNull() && 104 if (receiver.canBeNull() &&
105 interceptedClasses.contains(helpers.jsNullClass)) { 105 interceptedClasses.contains(helpers.jsNullClass)) {
106 // Need the JSNull interceptor. 106 // Need the JSNull interceptor.
107 return false; 107 return false;
108 } 108 }
109 109
110 // All intercepted classes extend `Interceptor`, so if the receiver can't be 110 // All intercepted classes extend `Interceptor`, so if the receiver can't be
111 // a class extending `Interceptor` then it can be called directly. 111 // a class extending `Interceptor` then it can be called directly.
112 return new TypeMask.nonNullSubclass(helpers.jsInterceptorClass, classWorld) 112 return new TypeMask.nonNullSubclass(helpers.jsInterceptorClass, closedWorld)
113 .isDisjoint(receiver.instructionType, classWorld); 113 .isDisjoint(receiver.instructionType, closedWorld);
114 } 114 }
115 115
116 HInstruction tryComputeConstantInterceptor( 116 HInstruction tryComputeConstantInterceptor(
117 HInstruction input, Set<ClassElement> interceptedClasses) { 117 HInstruction input, Set<ClassElement> interceptedClasses) {
118 if (input == graph.explicitReceiverParameter) { 118 if (input == graph.explicitReceiverParameter) {
119 // If `explicitReceiverParameter` is set it means the current method is an 119 // If `explicitReceiverParameter` is set it means the current method is an
120 // interceptor method, and `this` is the interceptor. The caller just did 120 // interceptor method, and `this` is the interceptor. The caller just did
121 // `getInterceptor(foo).currentMethod(foo)` to enter the current method. 121 // `getInterceptor(foo).currentMethod(foo)` to enter the current method.
122 return graph.thisInstruction; 122 return graph.thisInstruction;
123 } 123 }
(...skipping 14 matching lines...) Expand all
138 new InterceptorConstantValue(constantInterceptor.thisType); 138 new InterceptorConstantValue(constantInterceptor.thisType);
139 return graph.addConstant(constant, compiler); 139 return graph.addConstant(constant, compiler);
140 } 140 }
141 141
142 ClassElement tryComputeConstantInterceptorFromType( 142 ClassElement tryComputeConstantInterceptorFromType(
143 TypeMask type, Set<ClassElement> interceptedClasses) { 143 TypeMask type, Set<ClassElement> interceptedClasses) {
144 if (type.isNullable) { 144 if (type.isNullable) {
145 if (type.isNull) { 145 if (type.isNull) {
146 return helpers.jsNullClass; 146 return helpers.jsNullClass;
147 } 147 }
148 } else if (type.containsOnlyInt(classWorld)) { 148 } else if (type.containsOnlyInt(closedWorld)) {
149 return helpers.jsIntClass; 149 return helpers.jsIntClass;
150 } else if (type.containsOnlyDouble(classWorld)) { 150 } else if (type.containsOnlyDouble(closedWorld)) {
151 return helpers.jsDoubleClass; 151 return helpers.jsDoubleClass;
152 } else if (type.containsOnlyBool(classWorld)) { 152 } else if (type.containsOnlyBool(closedWorld)) {
153 return helpers.jsBoolClass; 153 return helpers.jsBoolClass;
154 } else if (type.containsOnlyString(classWorld)) { 154 } else if (type.containsOnlyString(closedWorld)) {
155 return helpers.jsStringClass; 155 return helpers.jsStringClass;
156 } else if (type.satisfies(helpers.jsArrayClass, classWorld)) { 156 } else if (type.satisfies(helpers.jsArrayClass, closedWorld)) {
157 return helpers.jsArrayClass; 157 return helpers.jsArrayClass;
158 } else if (type.containsOnlyNum(classWorld) && 158 } else if (type.containsOnlyNum(closedWorld) &&
159 !interceptedClasses.contains(helpers.jsIntClass) && 159 !interceptedClasses.contains(helpers.jsIntClass) &&
160 !interceptedClasses.contains(helpers.jsDoubleClass)) { 160 !interceptedClasses.contains(helpers.jsDoubleClass)) {
161 // If the method being intercepted is not defined in [int] or [double] we 161 // If the method being intercepted is not defined in [int] or [double] we
162 // can safely use the number interceptor. This is because none of the 162 // can safely use the number interceptor. This is because none of the
163 // [int] or [double] methods are called from a method defined on [num]. 163 // [int] or [double] methods are called from a method defined on [num].
164 return helpers.jsNumberClass; 164 return helpers.jsNumberClass;
165 } else { 165 } else {
166 // Try to find constant interceptor for a native class. If the receiver 166 // Try to find constant interceptor for a native class. If the receiver
167 // is constrained to a leaf native class, we can use the class's 167 // is constrained to a leaf native class, we can use the class's
168 // interceptor directly. 168 // interceptor directly.
169 169
170 // TODO(sra): Key DOM classes like Node, Element and Event are not leaf 170 // TODO(sra): Key DOM classes like Node, Element and Event are not leaf
171 // classes. When the receiver type is not a leaf class, we might still be 171 // classes. When the receiver type is not a leaf class, we might still be
172 // able to use the receiver class as a constant interceptor. It is 172 // able to use the receiver class as a constant interceptor. It is
173 // usually the case that methods defined on a non-leaf class don't test 173 // usually the case that methods defined on a non-leaf class don't test
174 // for a subclass or call methods defined on a subclass. Provided the 174 // for a subclass or call methods defined on a subclass. Provided the
175 // code is completely insensitive to the specific instance subclasses, we 175 // code is completely insensitive to the specific instance subclasses, we
176 // can use the non-leaf class directly. 176 // can use the non-leaf class directly.
177 ClassElement element = type.singleClass(classWorld); 177 ClassElement element = type.singleClass(closedWorld);
178 if (element != null && backend.isNative(element)) { 178 if (element != null && backend.isNative(element)) {
179 return element; 179 return element;
180 } 180 }
181 } 181 }
182 182
183 return null; 183 return null;
184 } 184 }
185 185
186 HInstruction findDominator(Iterable<HInstruction> instructions) { 186 HInstruction findDominator(Iterable<HInstruction> instructions) {
187 HInstruction result; 187 HInstruction result;
(...skipping 231 matching lines...) Expand 10 before | Expand all | Expand 10 after
419 instruction = new HInvokeDynamicMethod( 419 instruction = new HInvokeDynamicMethod(
420 selector, mask, inputs, node.instructionType, true); 420 selector, mask, inputs, node.instructionType, true);
421 } 421 }
422 422
423 HBasicBlock block = node.block; 423 HBasicBlock block = node.block;
424 block.addAfter(node, instruction); 424 block.addAfter(node, instruction);
425 block.rewrite(node, instruction); 425 block.rewrite(node, instruction);
426 return true; 426 return true;
427 } 427 }
428 } 428 }
OLDNEW

Powered by Google App Engine
This is Rietveld 408576698