# HG changeset patch # User Lukas Stadler # Date 1377591246 -7200 # Node ID 58b72cc1710906c644b3b67ea624493541c8d269 # Parent 3ceffcb771e510c75e1f20f2d09a2315f18c7b64 incremental canonicalization for PartialEscapePhase / EffectsPhase diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/BoxingEliminationTest.java --- a/graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/BoxingEliminationTest.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/BoxingEliminationTest.java Tue Aug 27 10:14:06 2013 +0200 @@ -309,7 +309,7 @@ Assumptions assumptions = new Assumptions(false); HighTierContext context = new HighTierContext(runtime(), assumptions, replacements, null, getDefaultPhasePlan(), OptimisticOptimizations.ALL); new InliningPhase().apply(graph, context); - new PartialEscapePhase(false, new CanonicalizerPhase(true)).apply(graph, context); + new PartialEscapePhase(false).apply(graph, context); } private void compareGraphs(final String snippet, final String referenceSnippet) { @@ -332,7 +332,7 @@ } new DeadCodeEliminationPhase().apply(graph); canonicalizer.apply(graph, context); - new PartialEscapePhase(false, canonicalizer).apply(graph, context); + new PartialEscapePhase(false).apply(graph, context); new DeadCodeEliminationPhase().apply(graph); canonicalizer.apply(graph, context); diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/ea/EarlyReadEliminationTest.java --- a/graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/ea/EarlyReadEliminationTest.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/ea/EarlyReadEliminationTest.java Tue Aug 27 10:14:06 2013 +0200 @@ -43,7 +43,6 @@ Assumptions assumptions = new Assumptions(false); HighTierContext context = new HighTierContext(runtime(), assumptions, replacements, null, getDefaultPhasePlan(), OptimisticOptimizations.ALL); new InliningPhase().apply(graph, context); - CanonicalizerPhase canonicalizer = new CanonicalizerPhase(true); - new EarlyReadEliminationPhase(canonicalizer).apply(graph, context); + new EarlyReadEliminationPhase().apply(graph, context); } } diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/ea/EscapeAnalysisTest.java --- a/graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/ea/EscapeAnalysisTest.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/ea/EscapeAnalysisTest.java Tue Aug 27 10:14:06 2013 +0200 @@ -236,7 +236,7 @@ HighTierContext context = new HighTierContext(runtime(), assumptions, replacements, null, getDefaultPhasePlan(), OptimisticOptimizations.ALL); new InliningPhase().apply(graph, context); new DeadCodeEliminationPhase().apply(graph); - new PartialEscapePhase(iterativeEscapeAnalysis, new CanonicalizerPhase(true)).apply(graph, context); + new PartialEscapePhase(iterativeEscapeAnalysis).apply(graph, context); Assert.assertEquals(1, graph.getNodes(ReturnNode.class).count()); ReturnNode returnNode = graph.getNodes(ReturnNode.class).first(); if (expectedConstantResult != null) { diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/ea/PEAReadEliminationTest.java --- a/graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/ea/PEAReadEliminationTest.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/ea/PEAReadEliminationTest.java Tue Aug 27 10:14:06 2013 +0200 @@ -245,7 +245,6 @@ Assumptions assumptions = new Assumptions(false); HighTierContext context = new HighTierContext(runtime(), assumptions, replacements, null, getDefaultPhasePlan(), OptimisticOptimizations.ALL); new InliningPhase().apply(graph, context); - CanonicalizerPhase canonicalizer = new CanonicalizerPhase(true); - new PartialEscapePhase(false, true, canonicalizer).apply(graph, context); + new PartialEscapePhase(false, true).apply(graph, context); } } diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/ea/PartialEscapeAnalysisTest.java --- a/graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/ea/PartialEscapeAnalysisTest.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/ea/PartialEscapeAnalysisTest.java Tue Aug 27 10:14:06 2013 +0200 @@ -164,7 +164,7 @@ new DeadCodeEliminationPhase().apply(graph); CanonicalizerPhase canonicalizer = new CanonicalizerPhase(true); canonicalizer.apply(graph, context); - new PartialEscapePhase(false, canonicalizer).apply(graph, context); + new PartialEscapePhase(false).apply(graph, context); for (MergeNode merge : graph.getNodes(MergeNode.class)) { merge.setStateAfter(null); diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/phases/HighTier.java --- a/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/phases/HighTier.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/phases/HighTier.java Tue Aug 27 10:14:06 2013 +0200 @@ -81,7 +81,7 @@ } if (PartialEscapeAnalysis.getValue()) { - appendPhase(new PartialEscapePhase(true, canonicalizer)); + appendPhase(new PartialEscapePhase(true)); } if (OptConvertDeoptsToGuards.getValue()) { diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/phases/MidTier.java --- a/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/phases/MidTier.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/phases/MidTier.java Tue Aug 27 10:14:06 2013 +0200 @@ -47,7 +47,7 @@ appendPhase(new LockEliminationPhase()); if (OptReadElimination.getValue()) { - appendPhase(new EarlyReadEliminationPhase(canonicalizer)); + appendPhase(new EarlyReadEliminationPhase()); } if (OptFloatingReads.getValue()) { diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.graph/src/com/oracle/graal/graph/Graph.java --- a/graal/com.oracle.graal.graph/src/com/oracle/graal/graph/Graph.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.graph/src/com/oracle/graal/graph/Graph.java Tue Aug 27 10:14:06 2013 +0200 @@ -159,18 +159,22 @@ } public void trackInputChange(NodeChangedListener inputChangedListener) { + assert this.inputChanged == null; this.inputChanged = inputChangedListener; } public void stopTrackingInputChange() { + assert inputChanged != null; inputChanged = null; } public void trackUsagesDroppedZero(NodeChangedListener usagesDroppedZeroListener) { + assert this.usagesDroppedZero == null; this.usagesDroppedZero = usagesDroppedZeroListener; } public void stopTrackingUsagesDroppedZero() { + assert usagesDroppedZero != null; usagesDroppedZero = null; } diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/IterativeConditionalEliminationPhase.java --- a/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/IterativeConditionalEliminationPhase.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/IterativeConditionalEliminationPhase.java Tue Aug 27 10:14:06 2013 +0200 @@ -24,13 +24,12 @@ import static com.oracle.graal.phases.GraalOptions.*; -import java.util.*; - import com.oracle.graal.api.code.*; -import com.oracle.graal.graph.Graph.NodeChangedListener; import com.oracle.graal.graph.*; import com.oracle.graal.nodes.*; +import com.oracle.graal.nodes.spi.*; import com.oracle.graal.phases.*; +import com.oracle.graal.phases.common.util.*; import com.oracle.graal.phases.tiers.*; public class IterativeConditionalEliminationPhase extends BasePhase { @@ -39,36 +38,28 @@ @Override protected void run(StructuredGraph graph, PhaseContext context) { - Set canonicalizationRoots = new HashSet<>(); ConditionalEliminationPhase eliminate = new ConditionalEliminationPhase(context.getRuntime()); - Listener listener = new Listener(canonicalizationRoots); + HashSetNodeChangeListener listener = new HashSetNodeChangeListener(); int count = 0; while (true) { graph.trackInputChange(listener); + graph.trackUsagesDroppedZero(listener); eliminate.apply(graph); graph.stopTrackingInputChange(); - if (canonicalizationRoots.isEmpty()) { + graph.stopTrackingUsagesDroppedZero(); + if (listener.getChangedNodes().isEmpty()) { break; } - new CanonicalizerPhase.Instance(context.getRuntime(), context.getAssumptions(), !AOTCompilation.getValue(), canonicalizationRoots, null).apply(graph); - canonicalizationRoots.clear(); + for (Node node : graph.getNodes()) { + if (node instanceof Simplifiable) { + listener.getChangedNodes().add(node); + } + } + new CanonicalizerPhase.Instance(context.getRuntime(), context.getAssumptions(), !AOTCompilation.getValue(), listener.getChangedNodes(), null).apply(graph); + listener.getChangedNodes().clear(); if (++count > MAX_ITERATIONS) { throw new BailoutException("Number of iterations in conditional elimination phase exceeds " + MAX_ITERATIONS); } } } - - private static class Listener implements NodeChangedListener { - - private final Set canonicalizationRoots; - - public Listener(Set canonicalizationRoots) { - this.canonicalizationRoots = canonicalizationRoots; - } - - @Override - public void nodeChanged(Node node) { - canonicalizationRoots.add(node); - } - } } diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/util/HashSetNodeChangeListener.java --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/util/HashSetNodeChangeListener.java Tue Aug 27 10:14:06 2013 +0200 @@ -0,0 +1,50 @@ +/* + * Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved. + * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. + * + * This code is free software; you can redistribute it and/or modify it + * under the terms of the GNU General Public License version 2 only, as + * published by the Free Software Foundation. + * + * This code is distributed in the hope that it will be useful, but WITHOUT + * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or + * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License + * version 2 for more details (a copy is included in the LICENSE file that + * accompanied this code). + * + * You should have received a copy of the GNU General Public License version + * 2 along with this work; if not, write to the Free Software Foundation, + * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA. + * + * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA + * or visit www.oracle.com if you need additional information or have any + * questions. + */ +package com.oracle.graal.phases.common.util; + +import java.util.*; + +import com.oracle.graal.graph.*; +import com.oracle.graal.graph.Graph.*; + +/** + * A simple {@link NodeChangedListener} implementation that accumulates the changed nodes in a + * {@link HashSet}. + */ +public class HashSetNodeChangeListener implements NodeChangedListener { + + private final Set changedNodes; + + public HashSetNodeChangeListener() { + this.changedNodes = new HashSet<>(); + } + + @Override + public void nodeChanged(Node node) { + changedNodes.add(node); + } + + public Set getChangedNodes() { + return changedNodes; + } +} diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.truffle.test/src/com/oracle/graal/truffle/test/PartialEvaluationTest.java --- a/graal/com.oracle.graal.truffle.test/src/com/oracle/graal/truffle/test/PartialEvaluationTest.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.truffle.test/src/com/oracle/graal/truffle/test/PartialEvaluationTest.java Tue Aug 27 10:14:06 2013 +0200 @@ -131,7 +131,7 @@ } new DeadCodeEliminationPhase().apply(resultGraph); - new PartialEscapePhase(true, canonicalizer).apply(resultGraph, context); + new PartialEscapePhase(true).apply(resultGraph, context); if (TruffleInlinePrinter.getValue()) { InlinePrinterProcessor.printTree(); diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/PartialEvaluator.java --- a/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/PartialEvaluator.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/PartialEvaluator.java Tue Aug 27 10:14:06 2013 +0200 @@ -178,7 +178,7 @@ // EA frame and clean up. new VerifyFrameDoesNotEscapePhase().apply(graph, false); - new PartialEscapePhase(false, new CanonicalizerPhase(!AOTCompilation.getValue())).apply(graph, context); + new PartialEscapePhase(false).apply(graph, context); new VerifyNoIntrinsicsLeftPhase().apply(graph, false); for (MaterializeFrameNode materializeNode : graph.getNodes(MaterializeFrameNode.class).snapshot()) { materializeNode.replaceAtUsages(materializeNode.getFrame()); diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/TruffleCache.java --- a/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/TruffleCache.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/TruffleCache.java Tue Aug 27 10:14:06 2013 +0200 @@ -112,7 +112,7 @@ optimizeGraph(newGraph, tmpAssumptions); PhaseContext context = new PhaseContext(metaAccessProvider, tmpAssumptions, replacements); - PartialEscapePhase partialEscapePhase = new PartialEscapePhase(false, new CanonicalizerPhase(true)); + PartialEscapePhase partialEscapePhase = new PartialEscapePhase(false); partialEscapePhase.apply(newGraph, context); cache.put(method, newGraph); @@ -153,7 +153,7 @@ ConditionalEliminationPhase conditionalEliminationPhase = new ConditionalEliminationPhase(metaAccessProvider); ConvertDeoptimizeToGuardPhase convertDeoptimizeToGuardPhase = new ConvertDeoptimizeToGuardPhase(); CanonicalizerPhase canonicalizerPhase = new CanonicalizerPhase(!AOTCompilation.getValue()); - EarlyReadEliminationPhase readEliminationPhase = new EarlyReadEliminationPhase(canonicalizerPhase); + EarlyReadEliminationPhase readEliminationPhase = new EarlyReadEliminationPhase(); int maxNodes = TruffleCompilerOptions.TruffleOperationCacheMaxNodes.getValue(); diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/EarlyReadEliminationPhase.java --- a/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/EarlyReadEliminationPhase.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/EarlyReadEliminationPhase.java Tue Aug 27 10:14:06 2013 +0200 @@ -25,14 +25,13 @@ import static com.oracle.graal.phases.GraalOptions.*; import com.oracle.graal.nodes.*; -import com.oracle.graal.phases.common.*; import com.oracle.graal.phases.schedule.*; import com.oracle.graal.phases.tiers.*; public class EarlyReadEliminationPhase extends EffectsPhase { - public EarlyReadEliminationPhase(CanonicalizerPhase canonicalizer) { - super(1, canonicalizer); + public EarlyReadEliminationPhase() { + super(1); } @Override diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/EffectsPhase.java --- a/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/EffectsPhase.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/EffectsPhase.java Tue Aug 27 10:14:06 2013 +0200 @@ -27,9 +27,12 @@ import java.util.concurrent.*; import com.oracle.graal.debug.*; +import com.oracle.graal.graph.*; import com.oracle.graal.nodes.*; +import com.oracle.graal.nodes.spi.*; import com.oracle.graal.phases.*; import com.oracle.graal.phases.common.*; +import com.oracle.graal.phases.common.util.*; import com.oracle.graal.phases.graph.*; import com.oracle.graal.phases.schedule.*; import com.oracle.graal.phases.tiers.*; @@ -44,11 +47,9 @@ } private final int maxIterations; - private CanonicalizerPhase canonicalizer; - public EffectsPhase(int maxIterations, CanonicalizerPhase canonicalizer) { + public EffectsPhase(int maxIterations) { this.maxIterations = maxIterations; - this.canonicalizer = canonicalizer; } @Override @@ -73,15 +74,23 @@ } // apply the effects collected during this iteration + HashSetNodeChangeListener listener = new HashSetNodeChangeListener(); + graph.trackInputChange(listener); + graph.trackUsagesDroppedZero(listener); closure.applyEffects(); + graph.stopTrackingInputChange(); + graph.stopTrackingUsagesDroppedZero(); Debug.dump(graph, "after " + getName() + " iteration"); new DeadCodeEliminationPhase().apply(graph); - if (OptCanonicalizer.getValue()) { - canonicalizer.apply(graph, context); + for (Node node : graph.getNodes()) { + if (node instanceof Simplifiable) { + listener.getChangedNodes().add(node); + } } + new CanonicalizerPhase.Instance(context.getRuntime(), context.getAssumptions(), !AOTCompilation.getValue(), listener.getChangedNodes(), null).apply(graph); return true; } diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/IterativeInliningPhase.java --- a/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/IterativeInliningPhase.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/IterativeInliningPhase.java Tue Aug 27 10:14:06 2013 +0200 @@ -60,7 +60,7 @@ @Override public Boolean call() { boolean progress = false; - PartialEscapePhase ea = new PartialEscapePhase(false, canonicalizer); + PartialEscapePhase ea = new PartialEscapePhase(false); boolean eaResult = ea.runAnalysis(graph, context); progress |= eaResult; diff -r 3ceffcb771e5 -r 58b72cc17109 graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/PartialEscapePhase.java --- a/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/PartialEscapePhase.java Tue Aug 27 12:08:12 2013 +0200 +++ b/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/PartialEscapePhase.java Tue Aug 27 10:14:06 2013 +0200 @@ -33,7 +33,6 @@ import com.oracle.graal.nodes.util.*; import com.oracle.graal.nodes.virtual.*; import com.oracle.graal.options.*; -import com.oracle.graal.phases.common.*; import com.oracle.graal.phases.graph.*; import com.oracle.graal.phases.schedule.*; import com.oracle.graal.phases.tiers.*; @@ -47,12 +46,12 @@ private final boolean readElimination; - public PartialEscapePhase(boolean iterative, CanonicalizerPhase canonicalizer) { - this(iterative, OptEarlyReadElimination.getValue(), canonicalizer); + public PartialEscapePhase(boolean iterative) { + this(iterative, OptEarlyReadElimination.getValue()); } - public PartialEscapePhase(boolean iterative, boolean readElimination, CanonicalizerPhase canonicalizer) { - super(iterative ? EscapeAnalysisIterations.getValue() : 1, canonicalizer); + public PartialEscapePhase(boolean iterative, boolean readElimination) { + super(iterative ? EscapeAnalysisIterations.getValue() : 1); this.readElimination = readElimination; }