Canonicalize array access

Rémi Forax forax at univ-mlv.fr
Tue Apr 3 03:14:17 PDT 2012


On 04/02/2012 12:10 PM, Douglas Simon wrote:
> Hi Remi,
>
> On Mar 30, 2012, at 7:13 PM, Rémi Forax wrote:
>
>> Hi guys,
>> I've played a little with Graal and I've some questions (a lot in fact but I will send several messages :)
> We're ready for your questions - fire away ;-)

A small contribution.
This code canonicalizes array access if the array and the index are a 
constant.

cheers,
Rémi


diff --git 
a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/LoadIndexedNode.java 
b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/LoadIndexedNode.java
--- 
a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/LoadIndexedNode.java
+++ 
b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/java/LoadIndexedNode.java
@@ -32,7 +32,7 @@
  /**
   * The {@code LoadIndexedNode} represents a read from an element of an 
array.
   */
-public final class LoadIndexedNode extends AccessIndexedNode implements 
Lowerable, Node.IterableNodeType {
+public final class LoadIndexedNode extends AccessIndexedNode implements 
Canonicalizable, Lowerable, Node.IterableNodeType {

      /**
       * Creates a new LoadIndexedNode.
@@ -62,4 +62,17 @@
      public void lower(CiLoweringTool tool) {
          tool.getRuntime().lower(this, tool);
      }
+
+    @Override
+    public ValueNode canonical(CanonicalizerTool tool) {
+        if (index().isConstant() && array().isConstant() && 
!array().isNullConstant()) {
+            int arrayIndex = index().asConstant().asInt();
+            CiConstant constArray = array().asConstant();
+            if (arrayIndex >= 0 && arrayIndex < 
tool.runtime().getArrayLength(constArray)) {
+                CiConstant constant = 
elementKind().readUnsafeArrayConstant(constArray.asObject(), arrayIndex);
+                return ConstantNode.forCiConstant(constant, 
tool.runtime(), graph());
+            }
+        }
+        return this;
+    }
  }
diff --git 
a/graal/com.oracle.max.cri/src/com/oracle/max/cri/ci/CiKind.java 
b/graal/com.oracle.max.cri/src/com/oracle/max/cri/ci/CiKind.java
--- a/graal/com.oracle.max.cri/src/com/oracle/max/cri/ci/CiKind.java
+++ b/graal/com.oracle.max.cri/src/com/oracle/max/cri/ci/CiKind.java
@@ -337,5 +337,33 @@
                  return null;
          }
      }
+
+    public CiConstant readUnsafeArrayConstant(Object value, long index) {
+      assert value != null;
+      Unsafe u = Unsafe.getUnsafe();
+      switch(this) {
+          case Boolean:
+              return CiConstant.forBoolean(u.getBoolean(value, 
Unsafe.ARRAY_BOOLEAN_BASE_OFFSET + index * 
Unsafe.ARRAY_BOOLEAN_INDEX_SCALE));
+          case Byte:
+              return CiConstant.forByte(u.getByte(value, 
Unsafe.ARRAY_BYTE_BASE_OFFSET + index * Unsafe.ARRAY_BYTE_INDEX_SCALE));
+          case Char:
+              return CiConstant.forChar(u.getChar(value, 
Unsafe.ARRAY_CHAR_BASE_OFFSET + index * Unsafe.ARRAY_CHAR_INDEX_SCALE));
+          case Short:
+              return CiConstant.forShort(u.getShort(value, 
Unsafe.ARRAY_SHORT_BASE_OFFSET + index * Unsafe.ARRAY_SHORT_INDEX_SCALE));
+          case Int:
+              return CiConstant.forInt(u.getInt(value, 
Unsafe.ARRAY_INT_BASE_OFFSET + index * Unsafe.ARRAY_INT_INDEX_SCALE));
+          case Long:
+              return CiConstant.forLong(u.getLong(value, 
Unsafe.ARRAY_LONG_BASE_OFFSET + index * Unsafe.ARRAY_LONG_INDEX_SCALE));
+          case Float:
+              return CiConstant.forFloat(u.getFloat(value, 
Unsafe.ARRAY_FLOAT_BASE_OFFSET + index * Unsafe.ARRAY_FLOAT_INDEX_SCALE));
+          case Double:
+              return CiConstant.forDouble(u.getDouble(value, 
Unsafe.ARRAY_DOUBLE_BASE_OFFSET + index * Unsafe.ARRAY_DOUBLE_INDEX_SCALE));
+          case Object:
+              return CiConstant.forObject(u.getObject(value, 
Unsafe.ARRAY_OBJECT_BASE_OFFSET + index * Unsafe.ARRAY_OBJECT_INDEX_SCALE));
+          default:
+              assert false : "unexpected kind: " + this;
+              return null;
+      }
+  }

  }



More information about the graal-dev mailing list