changeset 22389:bdfd42480dc9

Merge
author Tom Rodriguez <tom.rodriguez@oracle.com>
date Tue, 28 Jul 2015 13:19:14 -0700
parents 59a2f85de5c7 (current diff) 88b623010537 (diff)
children aeb7a47e272d
files
diffstat 5 files changed, 153 insertions(+), 4 deletions(-) [+]
line wrap: on
line diff
--- a/graal/com.oracle.graal.lir/src/com/oracle/graal/lir/alloc/trace/TraceLinearScan.java	Tue Jul 28 13:00:32 2015 -0700
+++ b/graal/com.oracle.graal.lir/src/com/oracle/graal/lir/alloc/trace/TraceLinearScan.java	Tue Jul 28 13:19:14 2015 -0700
@@ -46,7 +46,7 @@
 
     public static class Options {
         // @formatter:off
-        @Option(help = "", type = OptionType.Debug)
+        @Option(help = "Use simplified lifetime analysis.", type = OptionType.Debug)
         public static final OptionValue<Boolean> TraceRAsimpleLifetimeAnalysis = new OptionValue<>(true);
         // @formatter:on
     }
--- a/graal/com.oracle.graal.lir/src/com/oracle/graal/lir/alloc/trace/TraceRegisterAllocationPhase.java	Tue Jul 28 13:00:32 2015 -0700
+++ b/graal/com.oracle.graal.lir/src/com/oracle/graal/lir/alloc/trace/TraceRegisterAllocationPhase.java	Tue Jul 28 13:19:14 2015 -0700
@@ -22,6 +22,7 @@
  */
 package com.oracle.graal.lir.alloc.trace;
 
+import static com.oracle.graal.lir.alloc.trace.TraceRegisterAllocationPhase.Options.*;
 import static jdk.internal.jvmci.code.ValueUtil.*;
 
 import java.util.*;
@@ -46,10 +47,14 @@
         // @formatter:off
         @Option(help = "Use inter-trace register hints.", type = OptionType.Debug)
         public static final OptionValue<Boolean> TraceRAuseInterTraceHints = new OptionValue<>(true);
+        @Option(help = "Use special allocator for trivial blocks.", type = OptionType.Debug)
+        public static final OptionValue<Boolean> TraceRAtrivialBlockAllocator = new OptionValue<>(true);
         // @formatter:on
     }
 
     static final int TRACE_DUMP_LEVEL = 3;
+    private static final DebugMetric trivialTracesMetric = Debug.metric("TraceRA[trivialTraces]");
+    private static final DebugMetric tracesMetric = Debug.metric("TraceRA[traces]");
 
     @Override
     protected <B extends AbstractBlockBase<B>> void run(TargetDescription target, LIRGenerationResult lirGenRes, List<B> codeEmittingOrder, List<B> linearScanOrder, SpillMoveFactory spillMoveFactory,
@@ -64,9 +69,17 @@
         int traceNumber = 0;
         for (List<B> trace : resultTraces.getTraces()) {
             try (Indent i = Debug.logAndIndent("Allocating Trace%d: %s", traceNumber, trace); Scope s = Debug.scope("AllocateTrace", trace)) {
+                tracesMetric.increment();
+                if (trivialTracesMetric.isEnabled() && isTrivialTrace(lir, trace)) {
+                    trivialTracesMetric.increment();
+                }
                 Debug.dump(TRACE_DUMP_LEVEL, trace, "Trace" + traceNumber + ": " + trace);
-                TraceLinearScan allocator = new TraceLinearScan(target, lirGenRes, spillMoveFactory, registerAllocationConfig, trace, resultTraces);
-                allocator.allocate(target, lirGenRes, codeEmittingOrder, linearScanOrder, spillMoveFactory, registerAllocationConfig);
+                if (TraceRAtrivialBlockAllocator.getValue() && isTrivialTrace(lir, trace)) {
+                    new TraceTrivialAllocator(resultTraces).apply(target, lirGenRes, codeEmittingOrder, trace, new AllocationContext(spillMoveFactory, registerAllocationConfig), false);
+                } else {
+                    TraceLinearScan allocator = new TraceLinearScan(target, lirGenRes, spillMoveFactory, registerAllocationConfig, trace, resultTraces);
+                    allocator.allocate(target, lirGenRes, codeEmittingOrder, linearScanOrder, spillMoveFactory, registerAllocationConfig);
+                }
                 Debug.dump(TRACE_DUMP_LEVEL, trace, "After Trace" + traceNumber + ": " + trace);
                 traceNumber++;
             } catch (Throwable e) {
@@ -95,6 +108,10 @@
         }
     }
 
+    static boolean isTrivialTrace(LIR lir, List<? extends AbstractBlockBase<?>> trace) {
+        return trace.size() == 1 && lir.getLIRforBlock(trace.iterator().next()).size() == 2;
+    }
+
     /**
      * Fixup stack to stack moves introduced by stack arguments.
      *
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.lir/src/com/oracle/graal/lir/alloc/trace/TraceTrivialAllocator.java	Tue Jul 28 13:19:14 2015 -0700
@@ -0,0 +1,90 @@
+/*
+ * Copyright (c) 2015, 2015, 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.lir.alloc.trace;
+
+import static com.oracle.graal.lir.LIRValueUtil.*;
+import static com.oracle.graal.lir.alloc.trace.TraceRegisterAllocationPhase.*;
+
+import java.util.*;
+
+import jdk.internal.jvmci.code.*;
+import jdk.internal.jvmci.meta.*;
+
+import com.oracle.graal.compiler.common.alloc.*;
+import com.oracle.graal.compiler.common.alloc.TraceBuilder.TraceBuilderResult;
+import com.oracle.graal.compiler.common.cfg.*;
+import com.oracle.graal.lir.*;
+import com.oracle.graal.lir.StandardOp.BlockEndOp;
+import com.oracle.graal.lir.StandardOp.LabelOp;
+import com.oracle.graal.lir.gen.*;
+import com.oracle.graal.lir.gen.LIRGeneratorTool.SpillMoveFactory;
+import com.oracle.graal.lir.phases.*;
+import com.oracle.graal.lir.ssi.*;
+import com.oracle.graal.lir.util.*;
+
+/**
+ * Allocates a trivial trace i.e. a trace consisting of a single block with no instructions other
+ * than the {@link LabelOp} and the {@link BlockEndOp}.
+ */
+public class TraceTrivialAllocator extends AllocationPhase {
+
+    private final TraceBuilderResult<?> resultTraces;
+
+    public TraceTrivialAllocator(TraceBuilderResult<?> resultTraces) {
+        this.resultTraces = resultTraces;
+    }
+
+    @Override
+    protected <B extends AbstractBlockBase<B>> void run(TargetDescription target, LIRGenerationResult lirGenRes, List<B> codeEmittingOrder, List<B> trace, SpillMoveFactory spillMoveFactory,
+                    RegisterAllocationConfig registerAllocationConfig) {
+        LIR lir = lirGenRes.getLIR();
+        assert isTrivialTrace(lir, trace) : "Not a trivial trace! " + trace;
+        B block = trace.iterator().next();
+
+        AbstractBlockBase<?> pred = TraceUtil.getBestTraceInterPredecessor(resultTraces, block);
+
+        VariableVirtualStackValueMap<Variable, Value> variableMap = new VariableVirtualStackValueMap<>(lir.nextVariable(), 0);
+        SSIUtil.forEachValuePair(lir, block, pred, (to, from) -> {
+            if (isVariable(to)) {
+                variableMap.put(asVariable(to), from);
+            }
+        });
+
+        ValueProcedure outputConsumer = (value, mode, flags) -> {
+            if (isVariable(value)) {
+                return variableMap.get(asVariable(value));
+            }
+            return value;
+        };
+
+        List<LIRInstruction> instructions = lir.getLIRforBlock(block);
+        for (LIRInstruction op : instructions) {
+
+            op.forEachOutput(outputConsumer);
+            op.forEachTemp(outputConsumer);
+            op.forEachAlive(outputConsumer);
+            op.forEachInput(outputConsumer);
+            op.forEachState(outputConsumer);
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.lir/src/com/oracle/graal/lir/alloc/trace/TraceUtil.java	Tue Jul 28 13:19:14 2015 -0700
@@ -0,0 +1,42 @@
+/*
+ * Copyright (c) 2015, 2015, 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.lir.alloc.trace;
+
+import com.oracle.graal.compiler.common.alloc.TraceBuilder.TraceBuilderResult;
+import com.oracle.graal.compiler.common.cfg.*;
+
+class TraceUtil {
+
+    static AbstractBlockBase<?> getBestTraceInterPredecessor(TraceBuilderResult<?> traceResult, AbstractBlockBase<?> block) {
+        AbstractBlockBase<?> bestPred = null;
+        int bestTraceId = traceResult.getTraceForBlock(block);
+        for (AbstractBlockBase<?> pred : block.getPredecessors()) {
+            int predTraceId = traceResult.getTraceForBlock(pred);
+            if (predTraceId < bestTraceId) {
+                bestPred = pred;
+                bestTraceId = predTraceId;
+            }
+        }
+        return bestPred;
+    }
+}
--- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/TypeCheckNode.java	Tue Jul 28 13:00:32 2015 -0700
+++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/TypeCheckNode.java	Tue Jul 28 13:19:14 2015 -0700
@@ -47,6 +47,7 @@
         this.type = type;
         assert type != null;
         assert type.isConcrete() || type.isArray();
+        assert ((ObjectStamp) object.stamp()).nonNull();
     }
 
     public static LogicNode create(ResolvedJavaType type, ValueNode object) {
@@ -71,7 +72,6 @@
             return this;
         }
         ObjectStamp objectStamp = (ObjectStamp) forValue.stamp();
-        assert objectStamp.nonNull();
 
         ResolvedJavaType stampType = objectStamp.type();
         if (stampType != null) {