changeset 5879:77196bba5575

Change one more GraalCodeCacheProvider to MetaAccessProvider Add static methods to BoxingMethodPool In the default inlining policy for snippets, do not inline boxing Factor arraycopy code
author Gilles Duboscq <duboscq@ssw.jku.at>
date Mon, 30 Jul 2012 08:37:04 -0700
parents 191e08da4de4
children afd2508528f5 a7b2eaf364de
files graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/phases/IterativeCheckCastEliminationPhase.java graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/snippets/ArrayCopySnippets.java graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/extended/BoxingMethodPool.java graal/com.oracle.graal.snippets/src/com/oracle/graal/snippets/Snippet.java graal/com.oracle.graal.snippets/src/com/oracle/graal/snippets/nodes/BitScanForwardNode.java
diffstat 5 files changed, 82 insertions(+), 153 deletions(-) [+]
line wrap: on
line diff
--- a/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/phases/IterativeCheckCastEliminationPhase.java	Thu Jul 26 17:47:09 2012 +0200
+++ b/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/phases/IterativeCheckCastEliminationPhase.java	Mon Jul 30 08:37:04 2012 -0700
@@ -25,18 +25,18 @@
 import java.util.*;
 
 import com.oracle.graal.api.code.*;
+import com.oracle.graal.api.meta.*;
+import com.oracle.graal.graph.Graph.InputChangedListener;
 import com.oracle.graal.graph.*;
-import com.oracle.graal.graph.Graph.*;
 import com.oracle.graal.nodes.*;
-import com.oracle.graal.nodes.spi.*;
 
 
 public class IterativeCheckCastEliminationPhase extends Phase {
     private final TargetDescription target;
-    private final GraalCodeCacheProvider runtime;
+    private final MetaAccessProvider runtime;
     private final Assumptions assumptions;
 
-    public IterativeCheckCastEliminationPhase(TargetDescription target, GraalCodeCacheProvider runtime, Assumptions assumptions) {
+    public IterativeCheckCastEliminationPhase(TargetDescription target, MetaAccessProvider runtime, Assumptions assumptions) {
         this.target = target;
         this.runtime = runtime;
         this.assumptions = assumptions;
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/snippets/ArrayCopySnippets.java	Thu Jul 26 17:47:09 2012 +0200
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/snippets/ArrayCopySnippets.java	Mon Jul 30 08:37:04 2012 -0700
@@ -38,17 +38,17 @@
     private static final Kind VECTOR_KIND = Kind.Long;
     private static final long VECTOR_SIZE = arrayIndexScale(Kind.Long);
 
-    //@Snippet
+    @Snippet
     public static void vectorizedCopy(Object src, int srcPos, Object dest, int destPos, int length, @ConstantParameter("baseKind") Kind baseKind) {
         int header = arrayBaseOffset(baseKind);
-        long byteLength = length * arrayIndexScale(baseKind);
+        int elementSize = arrayIndexScale(baseKind);
+        long byteLength = length * elementSize;
         long nonVectorBytes = byteLength % VECTOR_SIZE;
-        long srcOffset = srcPos * arrayIndexScale(baseKind);
-        long destOffset = destPos * arrayIndexScale(baseKind);
+        long srcOffset = srcPos * elementSize;
+        long destOffset = destPos * elementSize;
         if (src == dest && srcPos < destPos) { // bad aliased case
-            for (long i = byteLength - 1; i > byteLength - 1 - nonVectorBytes; i--) {
-                Byte a = UnsafeLoadNode.load(src, header, i + srcOffset, Kind.Byte);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.byteValue(), Kind.Byte);
+            for (long i = byteLength - elementSize; i >= byteLength - nonVectorBytes; i -= elementSize) {
+                UnsafeStoreNode.store(dest, header, i + destOffset, UnsafeLoadNode.load(src, header, i + srcOffset, baseKind), baseKind);
             }
             long vectorLength = byteLength - nonVectorBytes;
             for (long i = vectorLength - VECTOR_SIZE; i >= 0; i -= VECTOR_SIZE) {
@@ -56,9 +56,8 @@
                 UnsafeStoreNode.store(dest, header, i + destOffset, a.longValue(), VECTOR_KIND);
             }
         } else {
-            for (long i = 0; i < nonVectorBytes; i++) {
-                Byte a = UnsafeLoadNode.load(src, header, i + srcOffset, Kind.Byte);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.byteValue(), Kind.Byte);
+            for (long i = 0; i < nonVectorBytes; i += elementSize) {
+                UnsafeStoreNode.store(dest, header, i + destOffset, UnsafeLoadNode.load(src, header, i + srcOffset, baseKind), baseKind);
             }
             for (long i = nonVectorBytes; i < byteLength; i += VECTOR_SIZE) {
                 Long a = UnsafeLoadNode.load(src, header, i + srcOffset, VECTOR_KIND);
@@ -75,32 +74,7 @@
         if (srcPos < 0 || destPos < 0 || length < 0 || srcPos + length > src.length || destPos + length > dest.length) {
             throw new IndexOutOfBoundsException();
         }
-        Kind baseKind = Kind.Byte;
-        int header = arrayBaseOffset(baseKind);
-        long byteLength = length * arrayIndexScale(baseKind);
-        long nonVectorBytes = byteLength % VECTOR_SIZE;
-        long srcOffset = srcPos * arrayIndexScale(baseKind);
-        long destOffset = destPos * arrayIndexScale(baseKind);
-        if (src == dest && srcPos < destPos) { // bad aliased case
-            for (long i = byteLength - arrayIndexScale(Kind.Byte); i >= byteLength - nonVectorBytes; i -= arrayIndexScale(Kind.Byte)) {
-                Byte a = UnsafeLoadNode.load(src, header, i + srcOffset, Kind.Byte);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.byteValue(), Kind.Byte);
-            }
-            long vectorLength = byteLength - nonVectorBytes;
-            for (long i = vectorLength - VECTOR_SIZE; i >= 0; i -= VECTOR_SIZE) {
-                Long a = UnsafeLoadNode.load(src, header, i + srcOffset, VECTOR_KIND);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.longValue(), VECTOR_KIND);
-            }
-        } else {
-            for (long i = 0; i < nonVectorBytes; i += arrayIndexScale(Kind.Byte)) {
-                Byte a = UnsafeLoadNode.load(src, header, i + srcOffset, Kind.Byte);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.byteValue(), Kind.Byte);
-            }
-            for (long i = nonVectorBytes; i < byteLength; i += VECTOR_SIZE) {
-                Long a = UnsafeLoadNode.load(src, header, i + srcOffset, VECTOR_KIND);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.longValue(), VECTOR_KIND);
-            }
-        }
+        vectorizedCopy(src, srcPos, dest, destPos, length, Kind.Byte);
     }
 
     @Snippet
@@ -111,32 +85,7 @@
         if (srcPos < 0 || destPos < 0 || length < 0 || srcPos + length > src.length || destPos + length > dest.length) {
             throw new IndexOutOfBoundsException();
         }
-        Kind baseKind = Kind.Char;
-        int header = arrayBaseOffset(baseKind);
-        long byteLength = length * arrayIndexScale(baseKind);
-        long nonVectorBytes = byteLength % VECTOR_SIZE;
-        long srcOffset = srcPos * arrayIndexScale(baseKind);
-        long destOffset = destPos * arrayIndexScale(baseKind);
-        if (src == dest && srcPos < destPos) { // bad aliased case
-            for (long i = byteLength - arrayIndexScale(Kind.Char); i >= byteLength - nonVectorBytes; i -= arrayIndexScale(Kind.Char)) {
-                Character a = UnsafeLoadNode.load(src, header, i + srcOffset, Kind.Char);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.charValue(), Kind.Char);
-            }
-            long vectorLength = byteLength - nonVectorBytes;
-            for (long i = vectorLength - VECTOR_SIZE; i >= 0; i -= VECTOR_SIZE) {
-                Long a = UnsafeLoadNode.load(src, header, i + srcOffset, VECTOR_KIND);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.longValue(), VECTOR_KIND);
-            }
-        } else {
-            for (long i = 0; i < nonVectorBytes; i += arrayIndexScale(Kind.Char)) {
-                Character a = UnsafeLoadNode.load(src, header, i + srcOffset, Kind.Char);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.charValue(), Kind.Char);
-            }
-            for (long i = nonVectorBytes; i < byteLength; i += VECTOR_SIZE) {
-                Long a = UnsafeLoadNode.load(src, header, i + srcOffset, VECTOR_KIND);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.longValue(), VECTOR_KIND);
-            }
-        }
+        vectorizedCopy(src, srcPos, dest, destPos, length, Kind.Char);
     }
 
     @Snippet
@@ -147,32 +96,7 @@
         if (srcPos < 0 || destPos < 0 || length < 0 || srcPos + length > src.length || destPos + length > dest.length) {
             throw new IndexOutOfBoundsException();
         }
-        Kind baseKind = Kind.Short;
-        int header = arrayBaseOffset(baseKind);
-        long byteLength = length * arrayIndexScale(baseKind);
-        long nonVectorBytes = byteLength % VECTOR_SIZE;
-        long srcOffset = srcPos * arrayIndexScale(baseKind);
-        long destOffset = destPos * arrayIndexScale(baseKind);
-        if (src == dest && srcPos < destPos) { // bad aliased case
-            for (long i = byteLength - arrayIndexScale(Kind.Short); i >= byteLength - nonVectorBytes; i -= arrayIndexScale(Kind.Short)) {
-                Short a = UnsafeLoadNode.load(src, header, i + srcOffset, Kind.Short);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.shortValue(), Kind.Short);
-            }
-            long vectorLength = byteLength - nonVectorBytes;
-            for (long i = vectorLength - VECTOR_SIZE; i >= 0; i -= VECTOR_SIZE) {
-                Long a = UnsafeLoadNode.load(src, header, i + srcOffset, VECTOR_KIND);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.longValue(), VECTOR_KIND);
-            }
-        } else {
-            for (long i = 0; i < nonVectorBytes; i += arrayIndexScale(Kind.Short)) {
-                Short a = UnsafeLoadNode.load(src, header, i + srcOffset, Kind.Short);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.shortValue(), Kind.Short);
-            }
-            for (long i = nonVectorBytes; i < byteLength; i += VECTOR_SIZE) {
-                Long a = UnsafeLoadNode.load(src, header, i + srcOffset, VECTOR_KIND);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.longValue(), VECTOR_KIND);
-            }
-        }
+        vectorizedCopy(src, srcPos, dest, destPos, length, Kind.Short);
     }
 
     @Snippet
@@ -183,32 +107,7 @@
         if (srcPos < 0 || destPos < 0 || length < 0 || srcPos + length > src.length || destPos + length > dest.length) {
             throw new IndexOutOfBoundsException();
         }
-        Kind baseKind = Kind.Int;
-        int header = arrayBaseOffset(baseKind);
-        long byteLength = length * arrayIndexScale(baseKind);
-        long nonVectorBytes = byteLength % VECTOR_SIZE;
-        long srcOffset = srcPos * arrayIndexScale(baseKind);
-        long destOffset = destPos * arrayIndexScale(baseKind);
-        if (src == dest && srcPos < destPos) { // bad aliased case
-            for (long i = byteLength - arrayIndexScale(Kind.Int); i >= byteLength - nonVectorBytes; i -= arrayIndexScale(Kind.Int)) {
-                Integer a = UnsafeLoadNode.load(src, header, i + srcOffset, Kind.Int);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.intValue(), Kind.Int);
-            }
-            long vectorLength = byteLength - nonVectorBytes;
-            for (long i = vectorLength - VECTOR_SIZE; i >= 0; i -= VECTOR_SIZE) {
-                Long a = UnsafeLoadNode.load(src, header, i + srcOffset, VECTOR_KIND);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.longValue(), VECTOR_KIND);
-            }
-        } else {
-            for (long i = 0; i < nonVectorBytes; i += arrayIndexScale(Kind.Int)) {
-                Integer a = UnsafeLoadNode.load(src, header, i + srcOffset, Kind.Int);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.intValue(), Kind.Int);
-            }
-            for (long i = nonVectorBytes; i < byteLength; i += VECTOR_SIZE) {
-                Long a = UnsafeLoadNode.load(src, header, i + srcOffset, VECTOR_KIND);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.longValue(), VECTOR_KIND);
-            }
-        }
+        vectorizedCopy(src, srcPos, dest, destPos, length, Kind.Int);
     }
 
     @Snippet
@@ -219,32 +118,7 @@
         if (srcPos < 0 || destPos < 0 || length < 0 || srcPos + length > src.length || destPos + length > dest.length) {
             throw new IndexOutOfBoundsException();
         }
-        Kind baseKind = Kind.Float;
-        int header = arrayBaseOffset(baseKind);
-        long byteLength = length * arrayIndexScale(baseKind);
-        long nonVectorBytes = byteLength % VECTOR_SIZE;
-        long srcOffset = srcPos * arrayIndexScale(baseKind);
-        long destOffset = destPos * arrayIndexScale(baseKind);
-        if (src == dest && srcPos < destPos) { // bad aliased case
-            for (long i = byteLength - arrayIndexScale(Kind.Float); i >= byteLength - nonVectorBytes; i -= arrayIndexScale(Kind.Float)) {
-                Float a = UnsafeLoadNode.load(src, header, i + srcOffset, Kind.Float);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.floatValue(), Kind.Float);
-            }
-            long vectorLength = byteLength - nonVectorBytes;
-            for (long i = vectorLength - VECTOR_SIZE; i >= 0; i -= VECTOR_SIZE) {
-                Long a = UnsafeLoadNode.load(src, header, i + srcOffset, VECTOR_KIND);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.longValue(), VECTOR_KIND);
-            }
-        } else {
-            for (long i = 0; i < nonVectorBytes; i += arrayIndexScale(Kind.Float)) {
-                Float a = UnsafeLoadNode.load(src, header, i + srcOffset, Kind.Float);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.floatValue(), Kind.Float);
-            }
-            for (long i = nonVectorBytes; i < byteLength; i += VECTOR_SIZE) {
-                Long a = UnsafeLoadNode.load(src, header, i + srcOffset, VECTOR_KIND);
-                UnsafeStoreNode.store(dest, header, i + destOffset, a.longValue(), VECTOR_KIND);
-            }
-        }
+        vectorizedCopy(src, srcPos, dest, destPos, length, Kind.Float);
     }
 
     @Snippet
--- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/extended/BoxingMethodPool.java	Thu Jul 26 17:47:09 2012 +0200
+++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/extended/BoxingMethodPool.java	Mon Jul 30 08:37:04 2012 -0700
@@ -22,11 +22,32 @@
  */
 package com.oracle.graal.nodes.extended;
 
+import java.lang.reflect.*;
 import java.util.*;
+import java.util.Map.Entry;
 
 import com.oracle.graal.api.meta.*;
 
 public class BoxingMethodPool {
+    private static final Map<Kind, BoxingMethod> boxings = new HashMap<>();
+    private static class BoxingMethod {
+        final Class<?> type;
+        final String unboxMethod;
+        public BoxingMethod(Class< ? > type, String unboxMethod) {
+            this.type = type;
+            this.unboxMethod = unboxMethod;
+        }
+    }
+    static {
+        boxings.put(Kind.Boolean, new BoxingMethod(Boolean.class, "booleanValue"));
+        boxings.put(Kind.Byte, new BoxingMethod(Byte.class, "byteValue"));
+        boxings.put(Kind.Char, new BoxingMethod(Character.class, "charValue"));
+        boxings.put(Kind.Short, new BoxingMethod(Short.class, "shortValue"));
+        boxings.put(Kind.Int, new BoxingMethod(Integer.class, "intValue"));
+        boxings.put(Kind.Long, new BoxingMethod(Long.class, "longValue"));
+        boxings.put(Kind.Float, new BoxingMethod(Float.class, "floatValue"));
+        boxings.put(Kind.Double, new BoxingMethod(Double.class, "doubleValue"));
+    }
 
     private final Set<JavaMethod> specialMethods = new HashSet<>();
     private final MetaAccessProvider runtime;
@@ -41,14 +62,11 @@
 
     private void initialize() {
         try {
-            initialize(Kind.Boolean, Boolean.class, "booleanValue");
-            initialize(Kind.Byte, Byte.class, "byteValue");
-            initialize(Kind.Char, Character.class, "charValue");
-            initialize(Kind.Short, Short.class, "shortValue");
-            initialize(Kind.Int, Integer.class, "intValue");
-            initialize(Kind.Long, Long.class, "longValue");
-            initialize(Kind.Float, Float.class, "floatValue");
-            initialize(Kind.Double, Double.class, "doubleValue");
+            for (Entry<Kind, BoxingMethod> entry : boxings.entrySet()) {
+                Kind kind = entry.getKey();
+                BoxingMethod boxing = entry.getValue();
+                initialize(kind, boxing.type, boxing.unboxMethod);
+            }
         } catch (SecurityException e) {
             throw new RuntimeException(e);
         } catch (NoSuchMethodException e) {
@@ -98,4 +116,38 @@
     public ResolvedJavaField getBoxField(Kind kind) {
         return boxFields[kind.ordinal()];
     }
+
+    public static boolean isSpecialMethodStatic(ResolvedJavaMethod method) {
+        return isUnboxingMethodStatic(method) || isBoxingMethodStatic(method);
+    }
+
+    public static boolean isBoxingMethodStatic(ResolvedJavaMethod method) {
+        Signature signature = method.signature();
+        if (!Modifier.isStatic(method.accessFlags())
+                        || signature.returnKind() == Kind.Object
+                        || signature.argumentCount(false) != 1) {
+            return false;
+        }
+        Kind kind = signature.argumentKindAt(0);
+        BoxingMethod boxing = boxings.get(kind);
+        if (boxing == null) {
+            return false;
+        }
+        return method.holder().toJava() == boxing.type && method.name().equals("valueOf");
+    }
+
+    public static boolean isUnboxingMethodStatic(ResolvedJavaMethod method) {
+        Signature signature = method.signature();
+        if (signature.returnKind() == Kind.Object
+                        || signature.argumentCount(false) != 0
+                        || Modifier.isStatic(method.accessFlags())) {
+            return false;
+        }
+        Kind kind = signature.returnKind();
+        BoxingMethod boxing = boxings.get(kind);
+        if (boxing == null) {
+            return false;
+        }
+        return method.holder().toJava() == boxing.type && method.name().equals(boxing.unboxMethod);
+    }
 }
--- a/graal/com.oracle.graal.snippets/src/com/oracle/graal/snippets/Snippet.java	Thu Jul 26 17:47:09 2012 +0200
+++ b/graal/com.oracle.graal.snippets/src/com/oracle/graal/snippets/Snippet.java	Mon Jul 30 08:37:04 2012 -0700
@@ -27,6 +27,7 @@
 
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.graph.Node.NodeIntrinsic;
+import com.oracle.graal.nodes.extended.*;
 import com.oracle.graal.snippets.Word.Operation;
 import com.oracle.graal.snippets.nodes.*;
 
@@ -86,6 +87,9 @@
                 if (method.getAnnotation(Operation.class) != null) {
                     return false;
                 }
+                if (BoxingMethodPool.isSpecialMethodStatic(method)) {
+                    return false;
+                }
                 return true;
             }
         };
--- a/graal/com.oracle.graal.snippets/src/com/oracle/graal/snippets/nodes/BitScanForwardNode.java	Thu Jul 26 17:47:09 2012 +0200
+++ b/graal/com.oracle.graal.snippets/src/com/oracle/graal/snippets/nodes/BitScanForwardNode.java	Mon Jul 30 08:37:04 2012 -0700
@@ -66,5 +66,4 @@
         gen.append(new AMD64BitScanOp(IntrinsicOpcode.BSF, result, gen.operand(value)));
         gen.setResult(this, result);
     }
-
 }