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

Unified Diff: pkg/compiler/lib/src/cps_ir/type_propagation.dart

Issue 1218223004: dart2js cps: Reanalyze subterms when they get inserted. (Closed) Base URL: git@github.com:dart-lang/sdk.git@master
Patch Set: Created 5 years, 6 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 side-by-side diff with in-line comments
Download patch
« no previous file with comments | « pkg/compiler/lib/src/cps_ir/cps_ir_nodes.dart ('k') | no next file » | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: pkg/compiler/lib/src/cps_ir/type_propagation.dart
diff --git a/pkg/compiler/lib/src/cps_ir/type_propagation.dart b/pkg/compiler/lib/src/cps_ir/type_propagation.dart
index f93f4932bd797d5b91f747ebbd5a3b5634092922..578589bafdbf0a21863a4c0fd782b5a2af830acf 100644
--- a/pkg/compiler/lib/src/cps_ir/type_propagation.dart
+++ b/pkg/compiler/lib/src/cps_ir/type_propagation.dart
@@ -426,8 +426,7 @@ class TypePropagator extends Pass {
TransformingVisitor transformer = new TransformingVisitor(
_compiler,
_lattice,
- analyzer.reachableNodes,
- analyzer.values,
+ analyzer,
replacements,
_internalError);
transformer.transform(root);
@@ -455,8 +454,7 @@ final Map<String, BuiltinOperator> NumBinaryBuiltins =
* actual transformations on the CPS graph.
*/
class TransformingVisitor extends RecursiveVisitor {
- final Set<Node> reachable;
- final Map<Node, AbstractValue> values;
+ final TypePropagationVisitor analyzer;
final Map<Expression, ConstantValue> replacements;
final ConstantPropagationLattice lattice;
final dart2js.Compiler compiler;
@@ -464,13 +462,14 @@ class TransformingVisitor extends RecursiveVisitor {
JavaScriptBackend get backend => compiler.backend;
TypeMaskSystem get typeSystem => lattice.typeSystem;
types.DartTypes get dartTypes => lattice.dartTypes;
+ Set<Node> get reachable => analyzer.reachableNodes;
+ Map<Node, AbstractValue> get values => analyzer.values;
final dart2js.InternalErrorFunction internalError;
TransformingVisitor(this.compiler,
this.lattice,
- this.reachable,
- this.values,
+ this.analyzer,
this.replacements,
this.internalError);
@@ -480,7 +479,7 @@ class TransformingVisitor extends RecursiveVisitor {
/// Removes the entire subtree of [node] and inserts [replacement].
/// All references in the [node] subtree are unlinked, and parent pointers
- /// in [replacement] are initialized.
+ /// in [replacement] are initialized and its types recomputed.
///
/// [replacement] must be "fresh", i.e. it must not contain significant parts
/// of the original IR inside of it since the [ParentVisitor] will
@@ -492,6 +491,7 @@ class TransformingVisitor extends RecursiveVisitor {
node.parent = null;
RemovalVisitor.remove(node);
new ParentVisitor().visit(replacement);
+ analyzer.reanalyzeSubtree(replacement);
}
/// Make a constant primitive for [constant] and set its entry in [values].
@@ -525,7 +525,8 @@ class TransformingVisitor extends RecursiveVisitor {
/// The new expression will be visited.
///
/// Returns true if the node was replaced.
- bool constifyExpression(Expression node, Continuation continuation) {
+ bool constifyExpression(Invoke node) {
+ Continuation continuation = node.continuation.definition;
ConstantValue constant = replacements[node];
if (constant == null) return false;
Constant primitive = makeConstantPrimitive(constant);
@@ -585,7 +586,7 @@ class TransformingVisitor extends RecursiveVisitor {
/// Replaces [node] with a more specialized instruction, if possible.
///
/// Returns `true` if the node was replaced.
- bool specializeInvoke(InvokeMethod node) {
+ bool specializeOperatorCall(InvokeMethod node) {
Continuation cont = node.continuation.definition;
bool replaceWithBinary(BuiltinOperator operator,
Primitive left,
@@ -698,10 +699,9 @@ class TransformingVisitor extends RecursiveVisitor {
/// invocation with a direct access to a field.
///
/// Returns `true` if the node was replaced.
- bool inlineFieldAccess(InvokeMethod node) {
+ bool specializeFieldAccess(InvokeMethod node) {
if (!node.selector.isGetter && !node.selector.isSetter) return false;
AbstractValue receiver = getValue(getDartReceiver(node));
- if (receiver.isNothing) return false;
Element target =
typeSystem.locateSingleElement(receiver.type, node.selector);
if (target is! FieldElement) return false;
@@ -711,7 +711,6 @@ class TransformingVisitor extends RecursiveVisitor {
Continuation cont = node.continuation.definition;
if (node.selector.isGetter) {
GetField get = new GetField(getDartReceiver(node), target);
- get.objectIsNotNull = receiver.isDefinitelyNotNull;
LetPrim let = makeLetPrimInvoke(get, cont);
replaceSubtree(node, let);
visitLetPrim(let);
@@ -731,10 +730,9 @@ class TransformingVisitor extends RecursiveVisitor {
}
void visitInvokeMethod(InvokeMethod node) {
- Continuation cont = node.continuation.definition;
- if (constifyExpression(node, cont)) return;
- if (specializeInvoke(node)) return;
- if (inlineFieldAccess(node)) return;
+ if (constifyExpression(node)) return;
+ if (specializeOperatorCall(node)) return;
+ if (specializeFieldAccess(node)) return;
AbstractValue receiver = getValue(node.receiver.definition);
node.receiverIsNotNull = receiver.isDefinitelyNotNull;
@@ -768,10 +766,10 @@ class TransformingVisitor extends RecursiveVisitor {
super.visitTypeCast(node);
}
- /// Specialize calls to static methods.
+ /// Specialize calls to internal static methods.
///
/// Returns true if the call was replaced.
- bool specializeInvokeStatic(InvokeStatic node) {
+ bool specializeInternalMethodCall(InvokeStatic node) {
// TODO(asgerf): This is written to easily scale to more cases,
// either add more cases or clean up.
Continuation cont = node.continuation.definition;
@@ -794,8 +792,8 @@ class TransformingVisitor extends RecursiveVisitor {
}
void visitInvokeStatic(InvokeStatic node) {
- if (constifyExpression(node, node.continuation.definition)) return;
- if (specializeInvokeStatic(node)) return;
+ if (constifyExpression(node)) return;
+ if (specializeInternalMethodCall(node)) return;
}
AbstractValue getValue(Primitive primitive) {
@@ -986,12 +984,20 @@ class TypePropagationVisitor implements Visitor {
void analyze(FunctionDefinition root) {
reachableNodes.clear();
- defWorkset.clear();
- nodeWorklist.clear();
// Initially, only the root node is reachable.
setReachable(root);
+ iterateWorklist();
+ }
+
+ void reanalyzeSubtree(Node node) {
+ new ResetAnalysisInfo(reachableNodes, values).visit(node);
+ setReachable(node);
+ iterateWorklist();
+ }
+
+ void iterateWorklist() {
while (true) {
if (nodeWorklist.isNotEmpty) {
// Process a new reachable expression.
@@ -1195,8 +1201,6 @@ class TypePropagationVisitor implements Visitor {
}
void visitApplyBuiltinOperator(ApplyBuiltinOperator node) {
- // Note that most built-in operators do not exist before the transformation
- // pass after this analysis has finished.
switch (node.operator) {
case BuiltinOperator.StringConcatenate:
DartString stringValue = const LiteralDartString('');
@@ -1252,8 +1256,31 @@ class TypePropagationVisitor implements Visitor {
}
break;
- default:
- setValue(node, nonConstant());
+ // TODO(asgerf): Implement constant propagation for builtins.
+ case BuiltinOperator.NumAdd:
+ case BuiltinOperator.NumSubtract:
+ case BuiltinOperator.NumMultiply:
+ case BuiltinOperator.NumAnd:
+ case BuiltinOperator.NumOr:
+ case BuiltinOperator.NumXor:
+ setValue(node, nonConstant(typeSystem.numType));
+ break;
+
+ case BuiltinOperator.NumLt:
+ case BuiltinOperator.NumLe:
+ case BuiltinOperator.NumGt:
+ case BuiltinOperator.NumGe:
+ case BuiltinOperator.StrictEq:
+ case BuiltinOperator.StrictNeq:
+ case BuiltinOperator.LooseEq:
+ case BuiltinOperator.LooseNeq:
+ case BuiltinOperator.IsFalsy:
+ case BuiltinOperator.IsNumber:
+ case BuiltinOperator.IsNotNumber:
+ case BuiltinOperator.IsFloor:
+ case BuiltinOperator.IsNumberAndFloor:
+ setValue(node, nonConstant(typeSystem.boolType));
+ break;
}
}
@@ -1541,7 +1568,7 @@ class AbstractValue {
}
AbstractValue.nothing()
- : this._internal(NOTHING, null, null);
+ : this._internal(NOTHING, null, new TypeMask.nonNullEmpty());
AbstractValue.constantValue(ConstantValue constant, TypeMask type)
: this._internal(CONSTANT, constant, type);
@@ -1583,3 +1610,16 @@ class AbstractValue {
abstract class InternalMethod {
static const String Stringify = 'S';
}
+
+class ResetAnalysisInfo extends RecursiveVisitor {
+ Set<Node> reachableNodes;
+ Map<Definition, AbstractValue> values;
+
+ ResetAnalysisInfo(this.reachableNodes, this.values);
+
+ visit(Node node) {
+ reachableNodes.remove(node);
+ if (node is Definition) values.remove(node);
+ node.accept(this);
+ }
+}
« no previous file with comments | « pkg/compiler/lib/src/cps_ir/cps_ir_nodes.dart ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698