OpenJDK / graal / graal-jvmci-8
changeset 2863:4f64bd98f9dc
Canonicalization work
author | Gilles Duboscq <gilles.duboscq@oracle.com> |
---|---|
date | Tue, 07 Jun 2011 17:04:55 +0200 |
parents | e1be0d206934 |
children | 32c3d7b51716 |
files | graal/GraalCompiler/src/com/oracle/max/graal/opt/CanonicalizerPhase.java graal/GraalCompiler/src/com/sun/c1x/C1XMetrics.java graal/GraalCompiler/src/com/sun/c1x/C1XOptions.java graal/GraalCompiler/src/com/sun/c1x/graph/IR.java graal/GraalCompiler/src/com/sun/c1x/ir/Or.java graal/GraalCompiler/src/com/sun/c1x/ir/Xor.java graal/GraalGraph/src/com/oracle/graal/graph/NodeBitMap.java |
diffstat | 7 files changed, 171 insertions(+), 2 deletions(-) [+] |
line wrap: on
line diff
--- a/graal/GraalCompiler/src/com/oracle/max/graal/opt/CanonicalizerPhase.java Tue Jun 07 16:13:22 2011 +0200 +++ b/graal/GraalCompiler/src/com/oracle/max/graal/opt/CanonicalizerPhase.java Tue Jun 07 17:04:55 2011 +0200 @@ -22,15 +22,47 @@ */ package com.oracle.max.graal.opt; +import java.util.*; + import com.oracle.graal.graph.*; +import com.sun.c1x.*; public class CanonicalizerPhase extends Phase { @Override protected void run(Graph graph) { - // TODO Auto-generated method stub + NodeBitMap visited = graph.createNodeBitMap(); + List<Node> nodes = new ArrayList<Node>(graph.getNodes()); + for (Node n : nodes) { + if (n == null) { + continue; + } + if (!visited.isMarked(n)) { + this.canonicalize(n, visited); + } + } + } + private void canonicalize(Node n, NodeBitMap visited) { + visited.mark(n); + for (Node input : n.inputs()) { + if (input == null) { + continue; + } + if (!visited.isNew(input) && !visited.isMarked(input)) { + canonicalize(input, visited); + } + } + + CanonicalizerOp op = n.lookup(CanonicalizerOp.class); + if (op != null) { + Node canonical = op.canonical(n); + if (canonical != n) { + n.replace(canonical); + C1XMetrics.NodesCanonicalized++; + } + } } public interface CanonicalizerOp extends Op {
--- a/graal/GraalCompiler/src/com/sun/c1x/C1XMetrics.java Tue Jun 07 16:13:22 2011 +0200 +++ b/graal/GraalCompiler/src/com/sun/c1x/C1XMetrics.java Tue Jun 07 17:04:55 2011 +0200 @@ -62,6 +62,7 @@ public static int UniqueValueIdsAssigned; public static int FrameStatesCreated; public static int FrameStateValuesCreated; + public static int NodesCanonicalized; public static void print() { printClassFields(C1XMetrics.class);
--- a/graal/GraalCompiler/src/com/sun/c1x/C1XOptions.java Tue Jun 07 16:13:22 2011 +0200 +++ b/graal/GraalCompiler/src/com/sun/c1x/C1XOptions.java Tue Jun 07 17:04:55 2011 +0200 @@ -127,4 +127,6 @@ // Assembler settings public static boolean CommentedAssembly = ____; public static boolean PrintLIRWithAssembly = ____; + + public static boolean OptCanonicalizer = true; }
--- a/graal/GraalCompiler/src/com/sun/c1x/graph/IR.java Tue Jun 07 16:13:22 2011 +0200 +++ b/graal/GraalCompiler/src/com/sun/c1x/graph/IR.java Tue Jun 07 17:04:55 2011 +0200 @@ -26,6 +26,7 @@ import java.util.*; import com.oracle.graal.graph.*; +import com.oracle.max.graal.opt.*; import com.oracle.max.graal.schedule.*; import com.sun.c1x.*; import com.sun.c1x.debug.*; @@ -85,6 +86,7 @@ new PhiSimplifier(this); + // Graph newGraph = new Graph(); // HashMap<Node, Node> replacement = new HashMap<Node, Node>(); // replacement.put(compilation.graph.start(), newGraph.start()); @@ -94,6 +96,11 @@ Graph graph = compilation.graph; + if (C1XOptions.OptCanonicalizer) { + new CanonicalizerPhase().apply(graph); + verifyAndPrint("After canonicalization"); + } + // Split critical edges. List<Node> nodes = graph.getNodes(); for (int i = 0; i < nodes.size(); ++i) {
--- a/graal/GraalCompiler/src/com/sun/c1x/ir/Or.java Tue Jun 07 16:13:22 2011 +0200 +++ b/graal/GraalCompiler/src/com/sun/c1x/ir/Or.java Tue Jun 07 17:04:55 2011 +0200 @@ -23,6 +23,7 @@ package com.sun.c1x.ir; import com.oracle.graal.graph.*; +import com.oracle.max.graal.opt.CanonicalizerPhase.CanonicalizerOp; import com.sun.cri.bytecode.*; import com.sun.cri.ci.*; @@ -31,6 +32,7 @@ * */ public final class Or extends Logic { + private static final OrCanonicalizerOp CANONICALIZER = new OrCanonicalizerOp(); /** * @param opcode @@ -54,4 +56,61 @@ return x; } + @SuppressWarnings("unchecked") + @Override + public <T extends Op> T lookup(Class<T> clazz) { + if (clazz == CanonicalizerOp.class) { + return (T) CANONICALIZER; + } + return super.lookup(clazz); + } + + private static class OrCanonicalizerOp implements CanonicalizerOp { + @Override + public Node canonical(Node node) { + assert node instanceof Or; + Or or = (Or) node; + CiKind kind = or.kind; + Graph graph = or.graph(); + Value x = or.x(); + Value y = or.y(); + if (x == y) { + return x; + } + if (x.isConstant() && !y.isConstant()) { + or.swapOperands(); + Value t = y; + y = x; + x = t; + } + if (x.isConstant()) { + if (kind == CiKind.Int) { + return Constant.forInt(x.asConstant().asInt() | y.asConstant().asInt(), graph); + } else { + assert kind == CiKind.Long; + return Constant.forLong(x.asConstant().asLong() | y.asConstant().asLong(), graph); + } + } else if (y.isConstant()) { + if (kind == CiKind.Int) { + int c = y.asConstant().asInt(); + if (c == -1) { + return Constant.forInt(-1, graph); + } + if (c == 0) { + return x; + } + } else { + assert kind == CiKind.Long; + long c = y.asConstant().asLong(); + if (c == -1) { + return Constant.forLong(-1, graph); + } + if (c == 0) { + return x; + } + } + } + return or; + } + } }
--- a/graal/GraalCompiler/src/com/sun/c1x/ir/Xor.java Tue Jun 07 16:13:22 2011 +0200 +++ b/graal/GraalCompiler/src/com/sun/c1x/ir/Xor.java Tue Jun 07 17:04:55 2011 +0200 @@ -23,10 +23,12 @@ package com.sun.c1x.ir; import com.oracle.graal.graph.*; +import com.oracle.max.graal.opt.CanonicalizerPhase.CanonicalizerOp; import com.sun.cri.bytecode.*; import com.sun.cri.ci.*; public final class Xor extends Logic { + private static final XorCanonicalizerOp CANONICALIZER = new XorCanonicalizerOp(); /** * @param opcode @@ -50,4 +52,66 @@ return x; } + @SuppressWarnings("unchecked") + @Override + public <T extends Op> T lookup(Class<T> clazz) { + if (clazz == CanonicalizerOp.class) { + return (T) CANONICALIZER; + } + return super.lookup(clazz); + } + + private static class XorCanonicalizerOp implements CanonicalizerOp { + @Override + public Node canonical(Node node) { + assert node instanceof Xor; + Xor xor = (Xor) node; + CiKind kind = xor.kind; + Graph graph = xor.graph(); + Value x = xor.x(); + Value y = xor.y(); + if (x == y) { + if (kind == CiKind.Int) { + return Constant.forInt(0, graph); + } else { + assert kind == CiKind.Long; + return Constant.forLong(0L, graph); + } + } + if (x.isConstant() && !y.isConstant()) { + xor.swapOperands(); + Value t = y; + y = x; + x = t; + } + if (x.isConstant()) { + if (kind == CiKind.Int) { + return Constant.forInt(x.asConstant().asInt() ^ y.asConstant().asInt(), graph); + } else { + assert kind == CiKind.Long; + return Constant.forLong(x.asConstant().asLong() ^ y.asConstant().asLong(), graph); + } + } else if (y.isConstant()) { + if (kind == CiKind.Int) { + int c = y.asConstant().asInt(); + if (c == -1) { + return new Negate(x, graph); + } + if (c == 0) { + return x; + } + } else { + assert kind == CiKind.Long; + long c = y.asConstant().asLong(); + if (c == -1) { + return new Negate(x, graph); + } + if (c == 0) { + return x; + } + } + } + return xor; + } + } }
--- a/graal/GraalGraph/src/com/oracle/graal/graph/NodeBitMap.java Tue Jun 07 16:13:22 2011 +0200 +++ b/graal/GraalGraph/src/com/oracle/graal/graph/NodeBitMap.java Tue Jun 07 17:04:55 2011 +0200 @@ -48,6 +48,10 @@ return bitMap.get(node.id()); } + public boolean isNew(Node node) { + return node.id() >= bitMap.size(); + } + public void mark(Node node) { check(node); bitMap.set(node.id()); @@ -60,7 +64,7 @@ private void check(Node node) { assert node.graph == graph : "this node is not part of the graph"; - assert node.id() < bitMap.size() : "this node (" + node.id() + ") was added to the graph after creating the node bitmap (" + bitMap.length() + ")"; + assert !isNew(node) : "this node (" + node.id() + ") was added to the graph after creating the node bitmap (" + bitMap.length() + ")"; } @Override