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

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

Issue 2319863002: Revert "dart2js: Pass type information to constructor rather than add later." (Closed)
Patch Set: Created 4 years, 3 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
« no previous file with comments | « pkg/compiler/lib/src/ssa/nodes.dart ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
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 import '../common/codegen.dart' show CodegenRegistry, CodegenWorkItem; 5 import '../common/codegen.dart' show CodegenWorkItem;
6 import '../common/tasks.dart' show CompilerTask; 6 import '../common/tasks.dart' show CompilerTask;
7 import '../compiler.dart' show Compiler; 7 import '../compiler.dart' show Compiler;
8 import '../constants/constant_system.dart'; 8 import '../constants/constant_system.dart';
9 import '../constants/values.dart'; 9 import '../constants/values.dart';
10 import '../core_types.dart' show CoreClasses; 10 import '../core_types.dart' show CoreClasses;
11 import '../dart_types.dart'; 11 import '../dart_types.dart';
12 import '../elements/elements.dart'; 12 import '../elements/elements.dart';
13 import '../js/js.dart' as js; 13 import '../js/js.dart' as js;
14 import '../js_backend/backend_helpers.dart' show BackendHelpers; 14 import '../js_backend/backend_helpers.dart' show BackendHelpers;
15 import '../js_backend/js_backend.dart'; 15 import '../js_backend/js_backend.dart';
(...skipping 27 matching lines...) Expand all
43 43
44 void optimize(CodegenWorkItem work, HGraph graph) { 44 void optimize(CodegenWorkItem work, HGraph graph) {
45 void runPhase(OptimizationPhase phase) { 45 void runPhase(OptimizationPhase phase) {
46 measureSubtask(phase.name, () => phase.visitGraph(graph)); 46 measureSubtask(phase.name, () => phase.visitGraph(graph));
47 compiler.tracer.traceGraph(phase.name, graph); 47 compiler.tracer.traceGraph(phase.name, graph);
48 assert(graph.isValid()); 48 assert(graph.isValid());
49 } 49 }
50 50
51 ConstantSystem constantSystem = compiler.backend.constantSystem; 51 ConstantSystem constantSystem = compiler.backend.constantSystem;
52 bool trustPrimitives = compiler.options.trustPrimitives; 52 bool trustPrimitives = compiler.options.trustPrimitives;
53 CodegenRegistry registry = work.registry;
54 Set<HInstruction> boundsChecked = new Set<HInstruction>(); 53 Set<HInstruction> boundsChecked = new Set<HInstruction>();
55 SsaCodeMotion codeMotion; 54 SsaCodeMotion codeMotion;
56 measure(() { 55 measure(() {
57 List<OptimizationPhase> phases = <OptimizationPhase>[ 56 List<OptimizationPhase> phases = <OptimizationPhase>[
58 // Run trivial instruction simplification first to optimize 57 // Run trivial instruction simplification first to optimize
59 // some patterns useful for type conversion. 58 // some patterns useful for type conversion.
60 new SsaInstructionSimplifier(constantSystem, backend, this, registry), 59 new SsaInstructionSimplifier(constantSystem, backend, this),
61 new SsaTypeConversionInserter(compiler), 60 new SsaTypeConversionInserter(compiler),
62 new SsaRedundantPhiEliminator(), 61 new SsaRedundantPhiEliminator(),
63 new SsaDeadPhiEliminator(), 62 new SsaDeadPhiEliminator(),
64 new SsaTypePropagator(compiler), 63 new SsaTypePropagator(compiler),
65 // After type propagation, more instructions can be 64 // After type propagation, more instructions can be
66 // simplified. 65 // simplified.
67 new SsaInstructionSimplifier(constantSystem, backend, this, registry), 66 new SsaInstructionSimplifier(constantSystem, backend, this),
68 new SsaCheckInserter(trustPrimitives, backend, boundsChecked), 67 new SsaCheckInserter(trustPrimitives, backend, boundsChecked),
69 new SsaInstructionSimplifier(constantSystem, backend, this, registry), 68 new SsaInstructionSimplifier(constantSystem, backend, this),
70 new SsaCheckInserter(trustPrimitives, backend, boundsChecked), 69 new SsaCheckInserter(trustPrimitives, backend, boundsChecked),
71 new SsaTypePropagator(compiler), 70 new SsaTypePropagator(compiler),
72 // Run a dead code eliminator before LICM because dead 71 // Run a dead code eliminator before LICM because dead
73 // interceptors are often in the way of LICM'able instructions. 72 // interceptors are often in the way of LICM'able instructions.
74 new SsaDeadCodeEliminator(compiler, this), 73 new SsaDeadCodeEliminator(compiler, this),
75 new SsaGlobalValueNumberer(compiler), 74 new SsaGlobalValueNumberer(compiler),
76 // After GVN, some instructions might need their type to be 75 // After GVN, some instructions might need their type to be
77 // updated because they now have different inputs. 76 // updated because they now have different inputs.
78 new SsaTypePropagator(compiler), 77 new SsaTypePropagator(compiler),
79 codeMotion = new SsaCodeMotion(), 78 codeMotion = new SsaCodeMotion(),
80 new SsaLoadElimination(compiler), 79 new SsaLoadElimination(compiler),
81 new SsaRedundantPhiEliminator(), 80 new SsaRedundantPhiEliminator(),
82 new SsaDeadPhiEliminator(), 81 new SsaDeadPhiEliminator(),
83 new SsaTypePropagator(compiler), 82 new SsaTypePropagator(compiler),
84 new SsaValueRangeAnalyzer(compiler, constantSystem, this), 83 new SsaValueRangeAnalyzer(compiler, constantSystem, this),
85 // Previous optimizations may have generated new 84 // Previous optimizations may have generated new
86 // opportunities for instruction simplification. 85 // opportunities for instruction simplification.
87 new SsaInstructionSimplifier(constantSystem, backend, this, registry), 86 new SsaInstructionSimplifier(constantSystem, backend, this),
88 new SsaCheckInserter(trustPrimitives, backend, boundsChecked), 87 new SsaCheckInserter(trustPrimitives, backend, boundsChecked),
89 ]; 88 ];
90 phases.forEach(runPhase); 89 phases.forEach(runPhase);
91 90
92 // Simplifying interceptors is not strictly just an optimization, it is 91 // Simplifying interceptors is not strictly just an optimization, it is
93 // required for implementation correctness because the code generator 92 // required for implementation correctness because the code generator
94 // assumes it is always performed. 93 // assumes it is always performed.
95 runPhase( 94 runPhase(
96 new SsaSimplifyInterceptors(compiler, constantSystem, work.element)); 95 new SsaSimplifyInterceptors(compiler, constantSystem, work.element));
97 96
98 SsaDeadCodeEliminator dce = new SsaDeadCodeEliminator(compiler, this); 97 SsaDeadCodeEliminator dce = new SsaDeadCodeEliminator(compiler, this);
99 runPhase(dce); 98 runPhase(dce);
100 if (codeMotion.movedCode || dce.eliminatedSideEffects) { 99 if (codeMotion.movedCode || dce.eliminatedSideEffects) {
101 phases = <OptimizationPhase>[ 100 phases = <OptimizationPhase>[
102 new SsaTypePropagator(compiler), 101 new SsaTypePropagator(compiler),
103 new SsaGlobalValueNumberer(compiler), 102 new SsaGlobalValueNumberer(compiler),
104 new SsaCodeMotion(), 103 new SsaCodeMotion(),
105 new SsaValueRangeAnalyzer(compiler, constantSystem, this), 104 new SsaValueRangeAnalyzer(compiler, constantSystem, this),
106 new SsaInstructionSimplifier(constantSystem, backend, this, registry), 105 new SsaInstructionSimplifier(constantSystem, backend, this),
107 new SsaCheckInserter(trustPrimitives, backend, boundsChecked), 106 new SsaCheckInserter(trustPrimitives, backend, boundsChecked),
108 new SsaSimplifyInterceptors(compiler, constantSystem, work.element), 107 new SsaSimplifyInterceptors(compiler, constantSystem, work.element),
109 new SsaDeadCodeEliminator(compiler, this), 108 new SsaDeadCodeEliminator(compiler, this),
110 ]; 109 ];
111 } else { 110 } else {
112 phases = <OptimizationPhase>[ 111 phases = <OptimizationPhase>[
113 new SsaTypePropagator(compiler), 112 new SsaTypePropagator(compiler),
114 // Run the simplifier to remove unneeded type checks inserted by 113 // Run the simplifier to remove unneeded type checks inserted by
115 // type propagation. 114 // type propagation.
116 new SsaInstructionSimplifier(constantSystem, backend, this, registry), 115 new SsaInstructionSimplifier(constantSystem, backend, this),
117 ]; 116 ];
118 } 117 }
119 phases.forEach(runPhase); 118 phases.forEach(runPhase);
120 }); 119 });
121 } 120 }
122 } 121 }
123 122
124 /// Returns `true` if [mask] represents only types that have a length that 123 /// Returns `true` if [mask] represents only types that have a length that
125 /// cannot change. The current implementation is conservative for the purpose 124 /// cannot change. The current implementation is conservative for the purpose
126 /// of identifying gvn-able lengths and mis-identifies some unions of fixed 125 /// of identifying gvn-able lengths and mis-identifies some unions of fixed
(...skipping 22 matching lines...) Expand all
149 class SsaInstructionSimplifier extends HBaseVisitor 148 class SsaInstructionSimplifier extends HBaseVisitor
150 implements OptimizationPhase { 149 implements OptimizationPhase {
151 // We don't produce constant-folded strings longer than this unless they have 150 // We don't produce constant-folded strings longer than this unless they have
152 // a single use. This protects against exponentially large constant folded 151 // a single use. This protects against exponentially large constant folded
153 // strings. 152 // strings.
154 static const MAX_SHARED_CONSTANT_FOLDED_STRING_LENGTH = 512; 153 static const MAX_SHARED_CONSTANT_FOLDED_STRING_LENGTH = 512;
155 154
156 final String name = "SsaInstructionSimplifier"; 155 final String name = "SsaInstructionSimplifier";
157 final JavaScriptBackend backend; 156 final JavaScriptBackend backend;
158 final ConstantSystem constantSystem; 157 final ConstantSystem constantSystem;
159 final CodegenRegistry registry;
160 HGraph graph; 158 HGraph graph;
161 Compiler get compiler => backend.compiler; 159 Compiler get compiler => backend.compiler;
162 final SsaOptimizerTask optimizer; 160 final SsaOptimizerTask optimizer;
163 161
164 SsaInstructionSimplifier( 162 SsaInstructionSimplifier(this.constantSystem, this.backend, this.optimizer);
165 this.constantSystem, this.backend, this.optimizer, this.registry);
166 163
167 CoreClasses get coreClasses => compiler.coreClasses; 164 CoreClasses get coreClasses => compiler.coreClasses;
168 165
169 BackendHelpers get helpers => backend.helpers; 166 BackendHelpers get helpers => backend.helpers;
170 167
171 void visitGraph(HGraph visitee) { 168 void visitGraph(HGraph visitee) {
172 graph = visitee; 169 graph = visitee;
173 visitDominatorTree(visitee); 170 visitDominatorTree(visitee);
174 } 171 }
175 172
(...skipping 979 matching lines...) Expand 10 before | Expand all | Expand 10 after
1155 } 1152 }
1156 return node; 1153 return node;
1157 } 1154 }
1158 1155
1159 // Look for an allocation with type information and re-write type variable 1156 // Look for an allocation with type information and re-write type variable
1160 // as a function of the type parameters of the allocation. This effectively 1157 // as a function of the type parameters of the allocation. This effectively
1161 // store-forwards a type variable read through an allocation. 1158 // store-forwards a type variable read through an allocation.
1162 1159
1163 // Match: 1160 // Match:
1164 // 1161 //
1165 // HCreate(ClassElement, 1162 // setRuntimeTypeInfo(
1166 // [arg_i, 1163 // HCreate(ClassElement),
1167 // ..., 1164 // HTypeInfoExpression(t_0, t_1, t_2, ...));
1168 // HTypeInfoExpression(t_0, t_1, t_2, ...)]);
1169 // 1165 //
1170 // The `t_i` are the values of the type parameters of ClassElement. 1166 // The `t_i` are the values of the type parameters of ClassElement.
1171 1167 if (object is HInvokeStatic) {
1172 if (object is HCreate) { 1168 if (object.element == helpers.setRuntimeTypeInfo) {
1173 void registerInstantiations() { 1169 HInstruction allocation = object.inputs[0];
1174 // Forwarding the type variable references might cause the HCreate to 1170 if (allocation is HCreate) {
1175 // become dead. This breaks the algorithm for generating the per-type 1171 HInstruction typeInfo = object.inputs[1];
1176 // runtime type information, so we instantiate them here in case the 1172 if (typeInfo is HTypeInfoExpression) {
1177 // HCreate becomes dead. 1173 return finishSubstituted(
1178 object.instantiatedTypes?.forEach(registry.registerInstantiation); 1174 allocation.element, (int index) => typeInfo.inputs[index]);
1175 }
1176 }
1177 return node;
1179 } 1178 }
1180 1179 // TODO(sra): Factory constructors pass type arguments after the value
1181 if (object.hasRtiInput) { 1180 // arguments. The [select] argument indexes into these type arguments.
1182 HInstruction typeInfo = object.rtiInput;
1183 if (typeInfo is HTypeInfoExpression) {
1184 registerInstantiations();
1185 return finishSubstituted(
1186 object.element, (int index) => typeInfo.inputs[index]);
1187 }
1188 } else {
1189 // Non-generic type (which extends or mixes in a generic type, for
1190 // example CodeUnits extends UnmodifiableListBase<int>). Also used for
1191 // raw-type when the type parameters are elided.
1192 registerInstantiations();
1193 return finishSubstituted(
1194 object.element,
1195 // If there are type arguments, all type arguments are 'dynamic'.
1196 (int i) => graph.addConstantNull(compiler));
1197 }
1198 } 1181 }
1199 1182
1200 // TODO(sra): Factory constructors pass type arguments after the value 1183 // Non-generic type (which extends or mixes in a generic type, for example
1201 // arguments. The [selectTypeArgumentFromObjectCreation] argument of 1184 // CodeUnits extends UnmodifiableListBase<int>).
1202 // [finishSubstituted] indexes into these type arguments. 1185 // Also used for raw-type when the type parameters are elided.
1186 if (object is HCreate) {
1187 return finishSubstituted(
1188 object.element,
1189 // If there are type arguments, all type arguments are 'dynamic'.
1190 (int i) => graph.addConstantNull(compiler));
1191 }
1203 1192
1204 return node; 1193 return node;
1205 } 1194 }
1206 } 1195 }
1207 1196
1208 class SsaCheckInserter extends HBaseVisitor implements OptimizationPhase { 1197 class SsaCheckInserter extends HBaseVisitor implements OptimizationPhase {
1209 final Set<HInstruction> boundsChecked; 1198 final Set<HInstruction> boundsChecked;
1210 final bool trustPrimitives; 1199 final bool trustPrimitives;
1211 final JavaScriptBackend backend; 1200 final JavaScriptBackend backend;
1212 final String name = "SsaCheckInserter"; 1201 final String name = "SsaCheckInserter";
(...skipping 1382 matching lines...) Expand 10 before | Expand all | Expand 10 after
2595 2584
2596 keyedValues.forEach((receiver, values) { 2585 keyedValues.forEach((receiver, values) {
2597 result.keyedValues[receiver] = 2586 result.keyedValues[receiver] =
2598 new Map<HInstruction, HInstruction>.from(values); 2587 new Map<HInstruction, HInstruction>.from(values);
2599 }); 2588 });
2600 2589
2601 result.nonEscapingReceivers.addAll(nonEscapingReceivers); 2590 result.nonEscapingReceivers.addAll(nonEscapingReceivers);
2602 return result; 2591 return result;
2603 } 2592 }
2604 } 2593 }
OLDNEW
« no previous file with comments | « pkg/compiler/lib/src/ssa/nodes.dart ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698