changeset 14595:ff2095ec7bdb

Merge
author Tom Rodriguez <tom.rodriguez@oracle.com>
date Tue, 18 Mar 2014 11:51:37 -0700
parents 3eda945af90a (current diff) 90b43a808eb0 (diff)
children e845cd0b033f
files graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/GraalCompiler.java graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/bridge/Marks.java graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotLoweringProvider.java graal/com.oracle.graal.java.decompiler.test/src/com/oracle/graal/java/decompiler/test/Test.java mx/mx_graal.py
diffstat 168 files changed, 2987 insertions(+), 1729 deletions(-) [+]
line wrap: on
line diff
--- a/CHANGELOG.md	Tue Mar 18 11:07:47 2014 -0700
+++ b/CHANGELOG.md	Tue Mar 18 11:51:37 2014 -0700
@@ -7,7 +7,16 @@
 * Made graph caching compilation-local.
 
 ### Truffle
-* ...
+* New API TruffleRuntime#createCallNode to create call nodes and to give the runtime system control over its implementation.
+* New API RootNode#getCachedCallNodes to get a weak set of CallNodes that have registered to call the RootNode.
+* New API to split the AST of a call-site context sensitively. CallNode#split, CallNode#isSplittable, CallNode#getSplitCallTarget, CallNode#getCurrentCallTarget, RootNode#isSplittable, RootNode#split.
+* New API to inline a call-site into the call-graph. CallNode#isInlinable, CallNode#inline, CallNode#isInlined.
+* New API for the runtime environment to register CallTargets as caller to the RootNode. CallNode#registerCallTarget.
+* Improved API for counting nodes in Truffle ASTS. NodeUtil#countNodes can be used with a NodeFilter filter Nodes.
+* New API to declare the cost of a Node for use in runtime environment specific heuristics. See NodeCost, Node#getCost() and NodeInfo#cost().
+* Removed old API for NodeInfo#Kind and NodeInfo#kind(). As a replacement the new Node cost API can be used.
+
+
 
 ## Version 0.1
 5-Feb-2014, [Repository Revision](http://hg.openjdk.java.net/graal/graal/rev/b124e22eb772)
--- a/graal/com.oracle.graal.amd64/src/com/oracle/graal/amd64/AMD64.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.amd64/src/com/oracle/graal/amd64/AMD64.java	Tue Mar 18 11:51:37 2014 -0700
@@ -146,7 +146,6 @@
                 case Short:
                 case Int:
                 case Long:
-                case NarrowOop:
                 case Object:
                     return true;
             }
--- a/graal/com.oracle.graal.api.code/src/com/oracle/graal/api/code/Architecture.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.api.code/src/com/oracle/graal/api/code/Architecture.java	Tue Mar 18 11:51:37 2014 -0700
@@ -198,8 +198,6 @@
                 return 8;
             case Object:
                 return wordSize;
-            case NarrowOop:
-                return wordSize / 2;
             default:
                 return 0;
         }
--- a/graal/com.oracle.graal.api.code/src/com/oracle/graal/api/code/CalleeSaveLayout.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.api.code/src/com/oracle/graal/api/code/CalleeSaveLayout.java	Tue Mar 18 11:51:37 2014 -0700
@@ -71,7 +71,7 @@
      *            CSA
      * @param registers the registers that can be saved in the CSA
      */
-    public CalleeSaveLayout(Architecture architecture, int frameOffsetToCSA, int size, int slotSize, Register... registers) {
+    public CalleeSaveLayout(TargetDescription target, int frameOffsetToCSA, int size, int slotSize, Register... registers) {
         this.frameOffsetToCSA = frameOffsetToCSA;
         assert slotSize == 0 || CodeUtil.isPowerOf2(slotSize);
         this.slotSize = slotSize;
@@ -88,8 +88,8 @@
             if (offset > maxOffset) {
                 maxOffset = offset;
             }
-            PlatformKind kind = architecture.getLargestStorableKind(reg.getRegisterCategory());
-            offset += architecture.getSizeInBytes(kind);
+            PlatformKind kind = target.arch.getLargestStorableKind(reg.getRegisterCategory());
+            offset += target.getSizeInBytes(kind);
         }
         if (size == -1) {
             this.size = offset;
@@ -106,8 +106,8 @@
             int index = offset / slotSize;
             regNumToIndex[reg.number] = index;
             indexToReg[index] = reg;
-            PlatformKind kind = architecture.getLargestStorableKind(reg.getRegisterCategory());
-            offset += architecture.getSizeInBytes(kind);
+            PlatformKind kind = target.arch.getLargestStorableKind(reg.getRegisterCategory());
+            offset += target.getSizeInBytes(kind);
         }
     }
 
--- a/graal/com.oracle.graal.api.code/src/com/oracle/graal/api/code/CodeCacheProvider.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.api.code/src/com/oracle/graal/api/code/CodeCacheProvider.java	Tue Mar 18 11:51:37 2014 -0700
@@ -22,6 +22,7 @@
  */
 package com.oracle.graal.api.code;
 
+import com.oracle.graal.api.code.CompilationResult.Data;
 import com.oracle.graal.api.code.CompilationResult.DataPatch;
 import com.oracle.graal.api.meta.*;
 
@@ -85,6 +86,11 @@
     boolean needsDataPatch(Constant constant);
 
     /**
+     * Create a {@link Data} item for a {@link Constant}, that can be used in a {@link DataPatch}.
+     */
+    Data createDataItem(Constant constant, int alignment);
+
+    /**
      * Gets a description of the target architecture.
      */
     TargetDescription getTarget();
--- a/graal/com.oracle.graal.api.code/src/com/oracle/graal/api/code/CodeUtil.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.api.code/src/com/oracle/graal/api/code/CodeUtil.java	Tue Mar 18 11:51:37 2014 -0700
@@ -281,6 +281,17 @@
         }
     }
 
+    public static class NumberedRefMapFormatter implements RefMapFormatter {
+
+        public String formatStackSlot(int frameRefMapIndex) {
+            return "s" + frameRefMapIndex;
+        }
+
+        public String formatRegister(int regRefMapIndex) {
+            return "r" + regRefMapIndex;
+        }
+    }
+
     /**
      * Appends a formatted debug info to a {@link StringBuilder}.
      * 
@@ -288,7 +299,11 @@
      * @param info the debug info to format and append to {@code sb}
      * @return the value of {@code sb}
      */
-    public static StringBuilder append(StringBuilder sb, DebugInfo info, RefMapFormatter formatter) {
+    public static StringBuilder append(StringBuilder sb, DebugInfo info, RefMapFormatter formatterArg) {
+        RefMapFormatter formatter = formatterArg;
+        if (formatter == null) {
+            formatter = new NumberedRefMapFormatter();
+        }
         String nl = NEW_LINE;
         ReferenceMap refMap = info.getReferenceMap();
         if (refMap != null && refMap.hasRegisterRefMap()) {
--- a/graal/com.oracle.graal.api.code/src/com/oracle/graal/api/code/CompilationResult.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.api.code/src/com/oracle/graal/api/code/CompilationResult.java	Tue Mar 18 11:51:37 2014 -0700
@@ -28,6 +28,7 @@
 import java.nio.*;
 import java.util.*;
 
+import com.oracle.graal.api.code.CodeUtil.*;
 import com.oracle.graal.api.meta.*;
 
 /**
@@ -152,66 +153,64 @@
             return alignment;
         }
 
-        public abstract int getSize(Architecture arch);
+        public abstract int getSize(TargetDescription target);
 
-        public abstract void emit(Architecture arch, ByteBuffer buffer);
+        public abstract Kind getKind();
+
+        public abstract void emit(TargetDescription target, ByteBuffer buffer);
     }
 
-    public static final class ConstantData extends Data {
+    /**
+     * Represents a Java primitive value used in a {@link DataPatch}. This implementation uses
+     * {@link Kind#getByteCount()} bytes to encode each value.
+     */
+    public static final class PrimitiveData extends Data {
 
         public final Constant constant;
 
-        public ConstantData(Constant constant, int alignment) {
+        public PrimitiveData(Constant constant, int alignment) {
             super(alignment);
+            assert constant.getKind().isPrimitive();
             this.constant = constant;
         }
 
         @Override
-        public int getSize(Architecture arch) {
-            return arch.getSizeInBytes(constant.getPlatformKind());
+        public int getSize(TargetDescription target) {
+            return constant.getKind().getByteCount();
+        }
+
+        @Override
+        public Kind getKind() {
+            return constant.getKind();
         }
 
         @Override
-        public void emit(Architecture arch, ByteBuffer buffer) {
+        public void emit(TargetDescription target, ByteBuffer buffer) {
             switch (constant.getKind()) {
                 case Boolean:
-                    assert getSize(arch) == 1;
                     buffer.put(constant.asBoolean() ? (byte) 1 : (byte) 0);
                     break;
                 case Byte:
-                    assert getSize(arch) == 1;
                     buffer.put((byte) constant.asInt());
                     break;
                 case Char:
-                    assert getSize(arch) == 2;
                     buffer.putChar((char) constant.asInt());
                     break;
                 case Short:
-                    assert getSize(arch) == 2;
                     buffer.putShort((short) constant.asInt());
                     break;
                 case Int:
-                    assert getSize(arch) == 4;
                     buffer.putInt(constant.asInt());
                     break;
                 case Long:
-                    assert getSize(arch) == 8;
                     buffer.putLong(constant.asLong());
                     break;
                 case Float:
-                    assert getSize(arch) == 4;
                     buffer.putFloat(constant.asFloat());
                     break;
                 case Double:
-                    assert getSize(arch) == 8;
                     buffer.putDouble(constant.asDouble());
                     break;
-                case Object:
-                    // placeholder for oop value
-                    for (int i = 0; i < getSize(arch); i++) {
-                        buffer.put((byte) 0);
-                    }
-                    break;
             }
         }
 
@@ -219,6 +218,24 @@
         public String toString() {
             return constant.toString();
         }
+
+        @Override
+        public int hashCode() {
+            return constant.hashCode();
+        }
+
+        @Override
+        public boolean equals(Object obj) {
+            if (this == obj) {
+                return true;
+            }
+            if (obj instanceof PrimitiveData) {
+                PrimitiveData other = (PrimitiveData) obj;
+                return constant.equals(other.constant);
+            } else {
+                return false;
+            }
+        }
     }
 
     public static final class RawData extends Data {
@@ -231,12 +248,17 @@
         }
 
         @Override
-        public int getSize(Architecture arch) {
+        public int getSize(TargetDescription target) {
             return data.length;
         }
 
         @Override
-        public void emit(Architecture arch, ByteBuffer buffer) {
+        public Kind getKind() {
+            return Kind.Illegal;
+        }
+
+        @Override
+        public void emit(TargetDescription target, ByteBuffer buffer) {
             buffer.put(data);
         }
 
@@ -250,6 +272,24 @@
             }
             return ret.toString();
         }
+
+        @Override
+        public int hashCode() {
+            return Arrays.hashCode(data);
+        }
+
+        @Override
+        public boolean equals(Object obj) {
+            if (this == obj) {
+                return true;
+            }
+            if (obj instanceof RawData) {
+                RawData other = (RawData) obj;
+                return Arrays.equals(data, other.data);
+            } else {
+                return false;
+            }
+        }
     }
 
     /**
@@ -260,53 +300,18 @@
     public static final class DataPatch extends Site {
 
         private static final long serialVersionUID = 5771730331604867476L;
-        public Data externalData;
-        public Constant inlineData;
-
-        DataPatch(int pcOffset, Data externalData) {
-            this(pcOffset, externalData, null);
-        }
-
-        DataPatch(int pcOffset, Constant inlineData) {
-            this(pcOffset, null, inlineData);
-        }
-
-        private DataPatch(int pcOffset, Data externalData, Constant inlineData) {
-            super(pcOffset);
-            assert (externalData == null) != (inlineData == null) : "data patch can not be both external and inlined";
-            this.externalData = externalData;
-            this.inlineData = inlineData;
-        }
+        public Data data;
+        public boolean inline;
 
-        public Constant getConstant() {
-            if (inlineData != null) {
-                return inlineData;
-            } else if (externalData instanceof ConstantData) {
-                return ((ConstantData) externalData).constant;
-            } else {
-                return null;
-            }
-        }
-
-        public int getAlignment() {
-            if (externalData instanceof ConstantData) {
-                return ((ConstantData) externalData).getAlignment();
-            } else {
-                return 0;
-            }
-        }
-
-        public String getDataString() {
-            if (inlineData != null) {
-                return inlineData.toString();
-            } else {
-                return externalData.toString();
-            }
+        public DataPatch(int pcOffset, Data data, boolean inline) {
+            super(pcOffset);
+            this.data = data;
+            this.inline = inline;
         }
 
         @Override
         public String toString() {
-            return String.format("%d[<data patch referring to data %s>]", pcOffset, getDataString());
+            return String.format("%d[<data patch referring to %s data %s>]", pcOffset, inline ? "inline" : "external", data.toString());
         }
     }
 
@@ -538,18 +543,18 @@
      */
     public void recordDataReference(int codePos, Data data) {
         assert codePos >= 0 && data != null;
-        dataReferences.add(new DataPatch(codePos, data));
+        dataReferences.add(new DataPatch(codePos, data, false));
     }
 
     /**
      * Records a reference to an inlined constant in the code section (e.g. to load a constant oop).
      * 
      * @param codePos the position in the code where the inlined constant occurs
-     * @param constant the constant that is referenced
+     * @param data the data that is referenced
      */
-    public void recordInlineData(int codePos, Constant constant) {
-        assert codePos >= 0 && constant != null;
-        dataReferences.add(new DataPatch(codePos, constant));
+    public void recordInlineData(int codePos, Data data) {
+        assert codePos >= 0 && data != null;
+        dataReferences.add(new DataPatch(codePos, data, true));
     }
 
     /**
@@ -691,14 +696,15 @@
         if (info != null) {
             ReferenceMap refMap = info.getReferenceMap();
             if (refMap != null) {
+                RefMapFormatter formatter = new CodeUtil.NumberedRefMapFormatter();
                 if (refMap.hasFrameRefMap()) {
                     sb.append(" stackMap[");
-                    refMap.appendFrameMap(sb, null);
+                    refMap.appendFrameMap(sb, formatter);
                     sb.append(']');
                 }
                 if (refMap.hasRegisterRefMap()) {
                     sb.append(" registerMap[");
-                    refMap.appendRegisterMap(sb, null);
+                    refMap.appendRegisterMap(sb, formatter);
                     sb.append(']');
                 }
             }
--- a/graal/com.oracle.graal.api.code/src/com/oracle/graal/api/code/ReferenceMap.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.api.code/src/com/oracle/graal/api/code/ReferenceMap.java	Tue Mar 18 11:51:37 2014 -0700
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2009, 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2009, 2014, 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
@@ -22,123 +22,20 @@
  */
 package com.oracle.graal.api.code;
 
-import java.io.*;
-import java.util.*;
-
 import com.oracle.graal.api.code.CodeUtil.RefMapFormatter;
-
-public class ReferenceMap implements Serializable {
-
-    private static final long serialVersionUID = -1052183095979496819L;
-
-    /**
-     * Contains 2 bits per register.
-     * <ul>
-     * <li>bit0 = 0: contains no references</li>
-     * <li>bit0 = 1, bit1 = 0: contains a wide oop</li>
-     * <li>bit0 = 1, bit1 = 1: contains a narrow oop</li>
-     * </ul>
-     */
-    private final BitSet registerRefMap;
-
-    /**
-     * Contains 3 bits per stack slot.
-     * <ul>
-     * <li>bit0 = 0: contains no references</li>
-     * <li>bit0 = 1, bit1+2 = 0: contains a wide oop</li>
-     * <li>bit0 = 1, bit1 = 1: contains a narrow oop in the lower half</li>
-     * <li>bit0 = 1, bit2 = 1: contains a narrow oop in the upper half</li>
-     * </ul>
-     */
-    private final BitSet frameRefMap;
+import com.oracle.graal.api.meta.*;
 
-    public ReferenceMap(int registerCount, int frameSlotCount) {
-        if (registerCount > 0) {
-            this.registerRefMap = new BitSet(registerCount * 2);
-        } else {
-            this.registerRefMap = null;
-        }
-        this.frameRefMap = new BitSet(frameSlotCount * 3);
-    }
+public interface ReferenceMap {
 
-    public void setRegister(int idx, boolean narrow) {
-        registerRefMap.set(2 * idx);
-        if (narrow) {
-            registerRefMap.set(2 * idx + 1);
-        }
-    }
+    void setRegister(int idx, PlatformKind kind);
 
-    public void setStackSlot(int idx, boolean narrow1, boolean narrow2) {
-        frameRefMap.set(3 * idx);
-        if (narrow1) {
-            frameRefMap.set(3 * idx + 1);
-        }
-        if (narrow2) {
-            frameRefMap.set(3 * idx + 2);
-        }
-    }
-
-    public boolean hasRegisterRefMap() {
-        return registerRefMap != null && registerRefMap.size() > 0;
-    }
+    void setStackSlot(int offset, PlatformKind kind);
 
-    public boolean hasFrameRefMap() {
-        return frameRefMap != null && frameRefMap.size() > 0;
-    }
-
-    public interface Iterator {
-        void register(int idx, boolean narrow);
-
-        void stackSlot(int idx, boolean narrow1, boolean narrow2);
-    }
+    boolean hasRegisterRefMap();
 
-    public void iterate(Iterator iterator) {
-        if (hasRegisterRefMap()) {
-            for (int i = 0; i < registerRefMap.size() / 2; i++) {
-                if (registerRefMap.get(2 * i)) {
-                    iterator.register(i, registerRefMap.get(2 * i + 1));
-                }
-            }
-        }
-        if (hasFrameRefMap()) {
-            for (int i = 0; i < frameRefMap.size() / 3; i++) {
-                if (frameRefMap.get(3 * i)) {
-                    iterator.stackSlot(i, frameRefMap.get(3 * i + 1), frameRefMap.get(3 * i + 2));
-                }
-            }
-        }
-    }
-
-    private static class NumberedRefMapFormatter implements RefMapFormatter {
+    boolean hasFrameRefMap();
 
-        public String formatStackSlot(int frameRefMapIndex) {
-            return "s" + frameRefMapIndex;
-        }
-
-        public String formatRegister(int regRefMapIndex) {
-            return "r" + regRefMapIndex;
-        }
-    }
-
-    public void appendRegisterMap(StringBuilder sb, RefMapFormatter formatterArg) {
-        RefMapFormatter formatter = formatterArg;
-        if (formatter == null) {
-            formatter = new NumberedRefMapFormatter();
-        }
+    void appendRegisterMap(StringBuilder sb, RefMapFormatter formatterArg);
 
-        for (int reg = registerRefMap.nextSetBit(0); reg >= 0; reg = registerRefMap.nextSetBit(reg + 2)) {
-            sb.append(' ').append(formatter.formatRegister(reg / 2));
-        }
-    }
-
-    public void appendFrameMap(StringBuilder sb, RefMapFormatter formatterArg) {
-        RefMapFormatter formatter = formatterArg;
-        if (formatter == null) {
-            formatter = new NumberedRefMapFormatter();
-        }
-
-        for (int slot = frameRefMap.nextSetBit(0); slot >= 0; slot = frameRefMap.nextSetBit(slot + 3)) {
-            sb.append(' ').append(formatter.formatStackSlot(slot / 3));
-        }
-    }
+    void appendFrameMap(StringBuilder sb, RefMapFormatter formatterArg);
 }
--- a/graal/com.oracle.graal.api.code/src/com/oracle/graal/api/code/TargetDescription.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.api.code/src/com/oracle/graal/api/code/TargetDescription.java	Tue Mar 18 11:51:37 2014 -0700
@@ -28,7 +28,7 @@
  * Represents the target machine for a compiler, including the CPU architecture, the size of
  * pointers and references, alignment of stacks, caches, etc.
  */
-public class TargetDescription {
+public abstract class TargetDescription {
 
     public final Architecture arch;
 
@@ -81,4 +81,10 @@
         this.implicitNullCheckLimit = implicitNullCheckLimit;
         this.inlineObjects = inlineObjects;
     }
+
+    public int getSizeInBytes(PlatformKind kind) {
+        return arch.getSizeInBytes(kind);
+    }
+
+    public abstract ReferenceMap createReferenceMap(boolean hasRegisters, int stackSlotCount);
 }
--- a/graal/com.oracle.graal.api.meta.test/src/com/oracle/graal/api/meta/test/TestResolvedJavaMethod.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.api.meta.test/src/com/oracle/graal/api/meta/test/TestResolvedJavaMethod.java	Tue Mar 18 11:51:37 2014 -0700
@@ -77,22 +77,6 @@
         }
     }
 
-    /**
-     * @see ResolvedJavaMethod#getCompiledCodeSize()
-     */
-    @Test
-    public void getCompiledCodeSizeTest() {
-        for (Map.Entry<Method, ResolvedJavaMethod> e : methods.entrySet()) {
-            ResolvedJavaMethod m = e.getValue();
-            int size = m.getCompiledCodeSize();
-            if (isAbstract(m.getModifiers())) {
-                assertTrue(size == 0);
-            } else {
-                assertTrue(size >= 0);
-            }
-        }
-    }
-
     @Test
     public void getModifiersTest() {
         for (Map.Entry<Method, ResolvedJavaMethod> e : methods.entrySet()) {
--- a/graal/com.oracle.graal.api.meta/src/com/oracle/graal/api/meta/Constant.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.api.meta/src/com/oracle/graal/api/meta/Constant.java	Tue Mar 18 11:51:37 2014 -0700
@@ -159,7 +159,6 @@
             case Double:
                 return asDouble();
             case Object:
-            case NarrowOop:
                 return object;
             case Illegal:
                 return this;
@@ -172,7 +171,7 @@
         if (!ignoreKind && getKind() != other.getKind()) {
             return false;
         }
-        if (getKind() == Kind.Object || getKind() == Kind.NarrowOop) {
+        if (getKind() == Kind.Object) {
             return object == other.object;
         }
         return primitive == other.primitive && getPrimitiveAnnotation() == other.getPrimitiveAnnotation();
@@ -235,12 +234,12 @@
 
     /**
      * Returns the object reference this constant represents. The constant must have kind
-     * {@link Kind#Object} or {@link Kind#NarrowOop}.
+     * {@link Kind#Object}.
      * 
      * @return the constant value
      */
     public Object asObject() {
-        assert getKind() == Kind.Object || getKind() == Kind.NarrowOop;
+        assert getKind() == Kind.Object;
         return object;
     }
 
@@ -250,7 +249,7 @@
      * @return null if this constant is not primitive or has no annotation
      */
     public Object getPrimitiveAnnotation() {
-        return getKind() == Kind.Object || getKind() == Kind.NarrowOop ? null : object;
+        return getKind() == Kind.Object ? null : object;
     }
 
     /**
@@ -260,7 +259,7 @@
      */
     @Override
     public int hashCode() {
-        if (getKind() == Kind.Object || getKind() == Kind.NarrowOop) {
+        if (getKind() == Kind.Object) {
             return System.identityHashCode(object);
         }
         return (int) primitive * getKind().ordinal();
@@ -394,16 +393,6 @@
     }
 
     /**
-     * Creates a boxed narrow oop constant.
-     * 
-     * @param o the object value to box
-     * @return a boxed copy of {@code value}
-     */
-    public static Constant forNarrowOop(Object o) {
-        return new Constant(Kind.NarrowOop, o, 0L);
-    }
-
-    /**
      * Creates an annotated int or long constant. An annotation enables a client to associate some
      * extra semantic or debugging information with a primitive. An annotated primitive constant is
      * never {@linkplain #equals(Object) equal} to a non-annotated constant.
@@ -463,8 +452,6 @@
                 return forDouble((Double) value);
             case Object:
                 return forObject(value);
-            case NarrowOop:
-                return forNarrowOop(value);
             default:
                 throw new RuntimeException("cannot create Constant for boxed " + kind + " value");
         }
@@ -497,8 +484,6 @@
                 return LONG_0;
             case Object:
                 return NULL_OBJECT;
-            case NarrowOop:
-                return forNarrowOop(null);
             default:
                 throw new IllegalArgumentException(kind.toString());
         }
--- a/graal/com.oracle.graal.api.meta/src/com/oracle/graal/api/meta/DefaultProfilingInfo.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.api.meta/src/com/oracle/graal/api/meta/DefaultProfilingInfo.java	Tue Mar 18 11:51:37 2014 -0700
@@ -99,4 +99,12 @@
     public void setMature() {
         // Do nothing
     }
+
+    public boolean setCompilerIRSize(Class<?> irType, int nodeCount) {
+        return false;
+    }
+
+    public int getCompilerIRSize(Class<?> irType) {
+        return -1;
+    }
 }
--- a/graal/com.oracle.graal.api.meta/src/com/oracle/graal/api/meta/Kind.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.api.meta/src/com/oracle/graal/api/meta/Kind.java	Tue Mar 18 11:51:37 2014 -0700
@@ -57,9 +57,6 @@
     /** The Object kind, also used for arrays. */
     Object('a', "Object", false, null, null),
 
-    /** The narrow oop kind. */
-    NarrowOop('n', "NarrowOop", false, null, null),
-
     /** The void float kind. */
     Void('v', "void", false, java.lang.Void.TYPE, java.lang.Void.class),
 
@@ -149,10 +146,10 @@
     /**
      * Checks whether this represent an Object of some sort.
      * 
-     * @return {@code true} if this is {@link #Object} or {@link #NarrowOop}.
+     * @return {@code true} if this is {@link #Object}.
      */
     public boolean isObject() {
-        return this == Kind.Object || this == Kind.NarrowOop;
+        return this == Kind.Object;
     }
 
     /**
--- a/graal/com.oracle.graal.api.meta/src/com/oracle/graal/api/meta/ObjectLocationIdentity.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.api.meta/src/com/oracle/graal/api/meta/ObjectLocationIdentity.java	Tue Mar 18 11:51:37 2014 -0700
@@ -25,7 +25,7 @@
 import java.util.*;
 
 /**
- * A {@link LocationIdentity} warpping an object.
+ * A {@link LocationIdentity} wrapping an object.
  */
 public final class ObjectLocationIdentity implements LocationIdentity {
 
--- a/graal/com.oracle.graal.api.meta/src/com/oracle/graal/api/meta/ProfilingInfo.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.api.meta/src/com/oracle/graal/api/meta/ProfilingInfo.java	Tue Mar 18 11:51:37 2014 -0700
@@ -114,6 +114,25 @@
     int getDeoptimizationCount(DeoptimizationReason reason);
 
     /**
+     * Records the size of the compiler intermediate representation (IR) associated with this
+     * method.
+     * 
+     * @param irType the IR type for which the size is being recorded
+     * @param irSize the IR size to be recorded. The unit depends on the IR.
+     * @return whether recording this information for {@code irType} is supported
+     */
+    boolean setCompilerIRSize(Class<?> irType, int irSize);
+
+    /**
+     * Gets the size of the compiler intermediate representation (IR) associated with this method
+     * last recorded by {@link #setCompilerIRSize(Class, int)}.
+     * 
+     * @param irType the IR type for which the size is being requested
+     * @return the requested IR size or -1 if it is unavailable for {@code irType}
+     */
+    int getCompilerIRSize(Class<?> irType);
+
+    /**
      * Returns true if the profiling information can be assumed as sufficiently accurate.
      * 
      * @return true if the profiling information was recorded often enough mature enough, false
@@ -124,6 +143,5 @@
     /**
      * Force data to be treated as mature if possible.
      */
-
     void setMature();
 }
--- a/graal/com.oracle.graal.api.meta/src/com/oracle/graal/api/meta/ResolvedJavaMethod.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.api.meta/src/com/oracle/graal/api/meta/ResolvedJavaMethod.java	Tue Mar 18 11:51:37 2014 -0700
@@ -24,7 +24,6 @@
 
 import java.lang.annotation.*;
 import java.lang.reflect.*;
-import java.util.*;
 
 /**
  * Represents a resolved Java method. Methods, like fields and types, are resolved through
@@ -54,13 +53,6 @@
     int getCodeSize();
 
     /**
-     * Returns the size of the compiled machine code of this method.
-     * 
-     * @return the size of the compiled machine code in bytes, or 0 if no compiled code exists.
-     */
-    int getCompiledCodeSize();
-
-    /**
      * Returns the {@link ResolvedJavaType} object representing the class or interface that declares
      * this method.
      */
@@ -144,12 +136,6 @@
     void reprofile();
 
     /**
-     * Returns a map that the compiler can use to store objects that should survive the current
-     * compilation.
-     */
-    Map<Object, Object> getCompilerStorage();
-
-    /**
      * Returns the constant pool of this method.
      */
     ConstantPool getConstantPool();
--- a/graal/com.oracle.graal.asm.amd64.test/src/com/oracle/graal/asm/amd64/test/SimpleAssemblerTest.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.asm.amd64.test/src/com/oracle/graal/asm/amd64/test/SimpleAssemblerTest.java	Tue Mar 18 11:51:37 2014 -0700
@@ -27,7 +27,7 @@
 import org.junit.*;
 
 import com.oracle.graal.api.code.*;
-import com.oracle.graal.api.code.CompilationResult.ConstantData;
+import com.oracle.graal.api.code.CompilationResult.PrimitiveData;
 import com.oracle.graal.api.code.CompilationResult.RawData;
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.asm.amd64.*;
@@ -59,7 +59,7 @@
             public byte[] generateCode(CompilationResult compResult, TargetDescription target, RegisterConfig registerConfig, CallingConvention cc) {
                 AMD64MacroAssembler asm = new AMD64MacroAssembler(target, registerConfig);
                 Register ret = registerConfig.getReturnRegister(Kind.Double);
-                compResult.recordDataReference(asm.position(), new ConstantData(Constant.forDouble(84.72), 8));
+                compResult.recordDataReference(asm.position(), new PrimitiveData(Constant.forDouble(84.72), 8));
                 asm.movdbl(ret, asm.getPlaceholder());
                 asm.ret(0);
                 return asm.close(true);
--- a/graal/com.oracle.graal.asm.amd64/src/com/oracle/graal/asm/amd64/AMD64MacroAssembler.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.asm.amd64/src/com/oracle/graal/asm/amd64/AMD64MacroAssembler.java	Tue Mar 18 11:51:37 2014 -0700
@@ -261,7 +261,7 @@
     private AMD64Address trigPrologue(Register value) {
         assert value.getRegisterCategory() == AMD64.XMM;
         AMD64Address tmp = new AMD64Address(AMD64.rsp);
-        subq(AMD64.rsp, target.arch.getSizeInBytes(Kind.Double));
+        subq(AMD64.rsp, target.getSizeInBytes(Kind.Double));
         movdbl(tmp, value);
         fldd(tmp);
         return tmp;
@@ -271,7 +271,7 @@
         assert dest.getRegisterCategory() == AMD64.XMM;
         fstpd(tmp);
         movdbl(dest, tmp);
-        addq(AMD64.rsp, target.arch.getSizeInBytes(Kind.Double));
+        addq(AMD64.rsp, target.getSizeInBytes(Kind.Double));
     }
 
     /**
--- a/graal/com.oracle.graal.asm.hsail/src/com/oracle/graal/asm/hsail/HSAILAssembler.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.asm.hsail/src/com/oracle/graal/asm/hsail/HSAILAssembler.java	Tue Mar 18 11:51:37 2014 -0700
@@ -264,9 +264,6 @@
             case Byte:
                 prefix = "s8";
                 break;
-            case NarrowOop:
-                prefix = "u32";
-                break;
             default:
                 throw GraalInternalError.shouldNotReachHere();
         }
--- a/graal/com.oracle.graal.compiler.amd64/src/com/oracle/graal/compiler/amd64/AMD64LIRGenerator.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.compiler.amd64/src/com/oracle/graal/compiler/amd64/AMD64LIRGenerator.java	Tue Mar 18 11:51:37 2014 -0700
@@ -360,9 +360,9 @@
     }
 
     @Override
-    public void emitNullCheck(ValueNode v, DeoptimizingNode deoping) {
-        assert v.stamp() instanceof ObjectStamp;
-        append(new AMD64Move.NullCheckOp(load(operand(v)), state(deoping)));
+    public void emitNullCheck(ValueNode v, DeoptimizingNode deopt) {
+        assert v.kind() == Kind.Object : v + " - " + v.stamp() + " @ " + deopt;
+        append(new AMD64Move.NullCheckOp(load(operand(v)), state(deopt)));
     }
 
     @Override
--- a/graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/CheckGraalInvariants.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.compiler.test/src/com/oracle/graal/compiler/test/CheckGraalInvariants.java	Tue Mar 18 11:51:37 2014 -0700
@@ -120,6 +120,9 @@
                                 errors.add(e.getMessage());
                             } catch (LinkageError e) {
                                 // suppress linkages errors resulting from eager resolution
+                            } catch (BailoutException e) {
+                                // Graal bail outs on certain patterns in Java bytecode (e.g.,
+                                // unbalanced monitors introduced by jacoco).
                             } catch (Throwable e) {
                                 StringWriter sw = new StringWriter();
                                 e.printStackTrace(new PrintWriter(sw));
--- a/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/GraalCompiler.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/GraalCompiler.java	Tue Mar 18 11:51:37 2014 -0700
@@ -198,11 +198,6 @@
         suites.getLowTier().apply(graph, lowTierContext);
         graph.maybeCompress();
 
-        // we do not want to store statistics about OSR compilations because it may prevent inlining
-        if (!graph.isOSR()) {
-            InliningPhase.storeStatisticsAfterLowTier(graph);
-        }
-
         SchedulePhase schedule = new SchedulePhase();
         schedule.apply(graph);
         Debug.dump(schedule, "Final HIR schedule");
@@ -298,14 +293,9 @@
             for (int i = 0; i < dms.length; i++) {
                 dms[i] = Debug.metric("DataPatches-" + Kind.values()[i].toString());
             }
-            DebugMetric dmRaw = Debug.metric("DataPatches-raw");
 
             for (DataPatch dp : ldp) {
-                if (dp.getConstant() != null) {
-                    dms[dp.getConstant().getKind().ordinal()].add(1);
-                } else {
-                    dmRaw.add(1);
-                }
+                dms[dp.data.getKind().ordinal()].add(1);
             }
 
             Debug.metric("CompilationResults").increment();
--- a/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/gen/DebugInfoBuilder.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/gen/DebugInfoBuilder.java	Tue Mar 18 11:51:37 2014 -0700
@@ -45,8 +45,8 @@
         this.nodeOperands = nodeOperands;
     }
 
-    protected HashMap<VirtualObjectNode, VirtualObject> virtualObjects = new HashMap<>();
-    protected IdentityHashMap<VirtualObjectNode, EscapeObjectState> objectStates = new IdentityHashMap<>();
+    protected final HashMap<VirtualObjectNode, VirtualObject> virtualObjects = new HashMap<>();
+    protected final IdentityHashMap<VirtualObjectNode, EscapeObjectState> objectStates = new IdentityHashMap<>();
 
     public LIRFrameState build(FrameState topState, LabelRef exceptionEdge) {
         assert virtualObjects.size() == 0;
--- a/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/phases/HighTier.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.compiler/src/com/oracle/graal/compiler/phases/HighTier.java	Tue Mar 18 11:51:37 2014 -0700
@@ -25,15 +25,12 @@
 import static com.oracle.graal.compiler.phases.HighTier.Options.*;
 import static com.oracle.graal.phases.GraalOptions.*;
 
-import com.oracle.graal.api.code.*;
-import com.oracle.graal.api.meta.*;
 import com.oracle.graal.loop.phases.*;
 import com.oracle.graal.nodes.spi.*;
 import com.oracle.graal.options.*;
 import com.oracle.graal.phases.*;
 import com.oracle.graal.phases.common.*;
 import com.oracle.graal.phases.tiers.*;
-import com.oracle.graal.phases.verify.*;
 import com.oracle.graal.virtual.phases.ea.*;
 
 public class HighTier extends PhaseSuite<HighTierContext> {
@@ -41,8 +38,6 @@
     public static class Options {
 
         // @formatter:off
-        @Option(help = "")
-        public static final OptionValue<Boolean> VerifyUsageWithEquals = new OptionValue<>(true);
         @Option(help = "Enable inlining")
         public static final OptionValue<Boolean> Inline = new OptionValue<>(true);
         // @formatter:on
@@ -51,11 +46,6 @@
     public HighTier() {
         CanonicalizerPhase canonicalizer = new CanonicalizerPhase(!ImmutableCode.getValue());
 
-        if (VerifyUsageWithEquals.getValue()) {
-            appendPhase(new VerifyUsageWithEquals(Value.class));
-            appendPhase(new VerifyUsageWithEquals(Register.class));
-        }
-
         if (OptCanonicalizer.getValue()) {
             appendPhase(canonicalizer);
         }
--- a/graal/com.oracle.graal.debug/src/com/oracle/graal/debug/Debug.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.debug/src/com/oracle/graal/debug/Debug.java	Tue Mar 18 11:51:37 2014 -0700
@@ -167,7 +167,7 @@
      * @return the scope entered by this method which will be exited when its {@link Scope#close()}
      *         method is called
      */
-    public static Scope scope(String name, Object... context) {
+    public static Scope scope(CharSequence name, Object... context) {
         if (ENABLED) {
             return DebugScope.getInstance().scope(name, null, context);
         } else {
@@ -195,7 +195,7 @@
      * @return the scope entered by this method which will be exited when its {@link Scope#close()}
      *         method is called
      */
-    public static Scope sandbox(String name, DebugConfig config, Object... context) {
+    public static Scope sandbox(CharSequence name, DebugConfig config, Object... context) {
         if (ENABLED) {
             DebugConfig sandboxConfig = config == null ? silentConfig() : config;
             return DebugScope.getInstance().scope(name, sandboxConfig, context);
@@ -379,11 +379,11 @@
      * <p>
      * A disabled metric has virtually no overhead.
      */
-    public static DebugMetric metric(String name) {
-        if (Boolean.getBoolean(ENABLE_METRIC_PROPERTY_NAME_PREFIX + name)) {
-            return new MetricImpl(name, false);
+    public static DebugMetric metric(CharSequence name) {
+        if (enabledMetrics != null && enabledMetrics.contains(name.toString())) {
+            return new MetricImpl(name.toString(), false);
         } else if (ENABLED) {
-            return new MetricImpl(name, true);
+            return new MetricImpl(name.toString(), true);
         } else {
             return VOID_METRIC;
         }
@@ -495,15 +495,33 @@
     };
 
     /**
-     * @see #timer(String)
+     * @see #timer(CharSequence)
      */
     public static final String ENABLE_TIMER_PROPERTY_NAME_PREFIX = "graal.debug.timer.";
 
     /**
-     * @see #metric(String)
+     * @see #metric(CharSequence)
      */
     public static final String ENABLE_METRIC_PROPERTY_NAME_PREFIX = "graal.debug.metric.";
 
+    private static final Set<String> enabledMetrics;
+    private static final Set<String> enabledTimers;
+    static {
+        Set<String> metrics = new HashSet<>();
+        Set<String> timers = new HashSet<>();
+        for (Map.Entry<Object, Object> e : System.getProperties().entrySet()) {
+            String name = e.getKey().toString();
+            if (name.startsWith(ENABLE_METRIC_PROPERTY_NAME_PREFIX) && Boolean.parseBoolean(e.getValue().toString())) {
+                metrics.add(name.substring(ENABLE_METRIC_PROPERTY_NAME_PREFIX.length()));
+            }
+            if (name.startsWith(ENABLE_TIMER_PROPERTY_NAME_PREFIX) && Boolean.parseBoolean(e.getValue().toString())) {
+                timers.add(name.substring(ENABLE_TIMER_PROPERTY_NAME_PREFIX.length()));
+            }
+        }
+        enabledMetrics = metrics.isEmpty() ? null : metrics;
+        enabledTimers = timers.isEmpty() ? null : timers;
+    }
+
     /**
      * Creates a {@linkplain DebugTimer timer} that is enabled iff debugging is
      * {@linkplain #isEnabled() enabled} or the system property whose name is formed by adding to
@@ -514,11 +532,11 @@
      * <p>
      * A disabled timer has virtually no overhead.
      */
-    public static DebugTimer timer(String name) {
-        if (Boolean.getBoolean(ENABLE_TIMER_PROPERTY_NAME_PREFIX + name)) {
-            return new TimerImpl(name, false);
+    public static DebugTimer timer(CharSequence name) {
+        if (enabledTimers != null && enabledTimers.contains(name.toString())) {
+            return new TimerImpl(name.toString(), false);
         } else if (ENABLED) {
-            return new TimerImpl(name, true);
+            return new TimerImpl(name.toString(), true);
         } else {
             return VOID_TIMER;
         }
--- a/graal/com.oracle.graal.debug/src/com/oracle/graal/debug/DebugConfig.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.debug/src/com/oracle/graal/debug/DebugConfig.java	Tue Mar 18 11:51:37 2014 -0700
@@ -45,7 +45,7 @@
      * Determines if metering is enabled in the {@linkplain Debug#currentScope() current debug
      * scope}.
      * 
-     * @see Debug#metric(String)
+     * @see Debug#metric(CharSequence)
      */
     boolean isMeterEnabled();
 
@@ -76,7 +76,7 @@
     void removeFromContext(Object o);
 
     /**
-     * @see Debug#timer(String)
+     * @see Debug#timer(CharSequence)
      */
     boolean isTimeEnabled();
 
--- a/graal/com.oracle.graal.debug/src/com/oracle/graal/debug/DebugHistogram.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.debug/src/com/oracle/graal/debug/DebugHistogram.java	Tue Mar 18 11:51:37 2014 -0700
@@ -72,6 +72,10 @@
             count++;
         }
 
+        public void add(int n) {
+            count += n;
+        }
+
         public int getCount() {
             return count;
         }
--- a/graal/com.oracle.graal.debug/src/com/oracle/graal/debug/internal/DebugScope.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.debug/src/com/oracle/graal/debug/internal/DebugScope.java	Tue Mar 18 11:51:37 2014 -0700
@@ -231,13 +231,13 @@
      * @param newContextObjects objects to be appended to the debug context
      * @return the new scope which will be exited when its {@link #close()} method is called
      */
-    public DebugScope scope(String name, DebugConfig sandboxConfig, Object... newContextObjects) {
+    public DebugScope scope(CharSequence name, DebugConfig sandboxConfig, Object... newContextObjects) {
         DebugScope newScope = null;
         if (sandboxConfig != null) {
-            newScope = new DebugScope(name, name, this, true, newContextObjects);
+            newScope = new DebugScope(name.toString(), name.toString(), this, true, newContextObjects);
             configTL.set(sandboxConfig);
         } else {
-            newScope = this.createChild(name, newContextObjects);
+            newScope = this.createChild(name.toString(), newContextObjects);
         }
         instanceTL.set(newScope);
         newScope.updateFlags();
--- a/graal/com.oracle.graal.graph/src/com/oracle/graal/graph/Node.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.graph/src/com/oracle/graal/graph/Node.java	Tue Mar 18 11:51:37 2014 -0700
@@ -458,6 +458,7 @@
      * newInput: removes this node from oldInput's usages and adds this node to newInput's usages.
      */
     protected void updateUsages(Node oldInput, Node newInput) {
+        assert isAlive() && (newInput == null || newInput.isAlive()) : "adding " + newInput + " to " + this + " instead of " + oldInput;
         if (oldInput != newInput) {
             if (oldInput != null) {
                 if (oldInput.recordsUsages()) {
@@ -482,6 +483,7 @@
      * this node to newSuccessor's predecessors.
      */
     protected void updatePredecessor(Node oldSuccessor, Node newSuccessor) {
+        assert isAlive() && (newSuccessor == null || newSuccessor.isAlive()) : "adding " + newSuccessor + " to " + this + " instead of " + oldSuccessor;
         assert graph == null || !graph.isFrozen();
         if (oldSuccessor != newSuccessor) {
             if (oldSuccessor != null) {
--- a/graal/com.oracle.graal.graph/src/com/oracle/graal/graph/NodeList.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.graph/src/com/oracle/graal/graph/NodeList.java	Tue Mar 18 11:51:37 2014 -0700
@@ -257,7 +257,7 @@
     }
 
     @Override
-    public void snapshotTo(List<T> to) {
+    public void snapshotTo(Collection<T> to) {
         for (int i = 0; i < size; i++) {
             to.add(get(i));
         }
--- a/graal/com.oracle.graal.graph/src/com/oracle/graal/graph/iterators/AbstractNodeIterable.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.graph/src/com/oracle/graal/graph/iterators/AbstractNodeIterable.java	Tue Mar 18 11:51:37 2014 -0700
@@ -74,7 +74,7 @@
     }
 
     @Override
-    public void snapshotTo(List<T> to) {
+    public void snapshotTo(Collection<T> to) {
         for (T n : this) {
             to.add(n);
         }
--- a/graal/com.oracle.graal.graph/src/com/oracle/graal/graph/iterators/NodeIterable.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.graph/src/com/oracle/graal/graph/iterators/NodeIterable.java	Tue Mar 18 11:51:37 2014 -0700
@@ -44,7 +44,7 @@
 
     List<T> snapshot();
 
-    void snapshotTo(List<T> to);
+    void snapshotTo(Collection<T> to);
 
     T first();
 
--- a/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotBackend.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotBackend.java	Tue Mar 18 11:51:37 2014 -0700
@@ -41,8 +41,8 @@
 import com.oracle.graal.compiler.gen.*;
 import com.oracle.graal.compiler.target.*;
 import com.oracle.graal.hotspot.*;
-import com.oracle.graal.hotspot.bridge.*;
 import com.oracle.graal.hotspot.meta.*;
+import com.oracle.graal.hotspot.meta.HotSpotCodeCacheProvider.MarkId;
 import com.oracle.graal.hotspot.nfi.*;
 import com.oracle.graal.hotspot.stubs.*;
 import com.oracle.graal.lir.*;
@@ -249,7 +249,7 @@
     public void emitCodePrefix(ResolvedJavaMethod installedCodeOwner, CompilationResultBuilder crb, AMD64MacroAssembler asm, RegisterConfig regConfig, HotSpotVMConfig config, Label verifiedEntry) {
         HotSpotProviders providers = getProviders();
         if (installedCodeOwner != null && !isStatic(installedCodeOwner.getModifiers())) {
-            crb.recordMark(Marks.MARK_UNVERIFIED_ENTRY);
+            MarkId.recordMark(crb, MarkId.UNVERIFIED_ENTRY);
             CallingConvention cc = regConfig.getCallingConvention(JavaCallee, null, new JavaType[]{providers.getMetaAccess().lookupJavaType(Object.class)}, getTarget(), false);
             Register inlineCacheKlass = rax; // see definition of IC_Klass in
                                              // c1_LIRAssembler_x86.cpp
@@ -271,9 +271,9 @@
         }
 
         asm.align(config.codeEntryAlignment);
-        crb.recordMark(Marks.MARK_OSR_ENTRY);
+        MarkId.recordMark(crb, MarkId.OSR_ENTRY);
         asm.bind(verifiedEntry);
-        crb.recordMark(Marks.MARK_VERIFIED_ENTRY);
+        MarkId.recordMark(crb, MarkId.VERIFIED_ENTRY);
     }
 
     /**
@@ -293,9 +293,9 @@
         HotSpotFrameContext frameContext = (HotSpotFrameContext) crb.frameContext;
         if (!frameContext.isStub) {
             HotSpotForeignCallsProvider foreignCalls = providers.getForeignCalls();
-            crb.recordMark(Marks.MARK_EXCEPTION_HANDLER_ENTRY);
+            MarkId.recordMark(crb, MarkId.EXCEPTION_HANDLER_ENTRY);
             AMD64Call.directCall(crb, asm, foreignCalls.lookupForeignCall(EXCEPTION_HANDLER), null, false, null);
-            crb.recordMark(Marks.MARK_DEOPT_HANDLER_ENTRY);
+            MarkId.recordMark(crb, MarkId.DEOPT_HANDLER_ENTRY);
             AMD64Call.directCall(crb, asm, foreignCalls.lookupForeignCall(DEOPT_HANDLER), null, false, null);
         } else {
             // No need to emit the stubs for entries back into the method since
--- a/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotBackendFactory.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotBackendFactory.java	Tue Mar 18 11:51:37 2014 -0700
@@ -89,7 +89,7 @@
         final int stackFrameAlignment = 16;
         final int implicitNullCheckLimit = 4096;
         final boolean inlineObjects = true;
-        return new TargetDescription(createArchitecture(config), true, stackFrameAlignment, implicitNullCheckLimit, inlineObjects);
+        return new HotSpotTargetDescription(createArchitecture(config), true, stackFrameAlignment, implicitNullCheckLimit, inlineObjects, Kind.Int);
     }
 
     @Override
--- a/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotLIRGenerator.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotLIRGenerator.java	Tue Mar 18 11:51:37 2014 -0700
@@ -473,8 +473,6 @@
     protected static Constant compress(Constant c, CompressEncoding encoding) {
         if (c.getKind() == Kind.Long) {
             return Constant.forIntegerKind(Kind.Int, (int) (((c.asLong() - encoding.base) >> encoding.shift) & 0xffffffffL), c.getPrimitiveAnnotation());
-        } else if (c.getKind() == Kind.Object) {
-            return Constant.forNarrowOop(c.asObject());
         } else {
             throw GraalInternalError.shouldNotReachHere();
         }
@@ -523,8 +521,7 @@
             if (canStoreConstant(c, isCompressed)) {
                 if (isCompressed) {
                     if (c.getKind() == Kind.Object) {
-                        Constant value = c.isNull() ? c : compress(c, config.getOopEncoding());
-                        append(new StoreCompressedConstantOp(kind, storeAddress, value, state));
+                        append(new StoreCompressedConstantOp(kind, storeAddress, c, state));
                     } else if (c.getKind() == Kind.Long) {
                         // It's always a good idea to directly store compressed constants since they
                         // have to be materialized as 64 bits encoded otherwise.
--- a/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotMove.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotMove.java	Tue Mar 18 11:51:37 2014 -0700
@@ -33,6 +33,7 @@
 import com.oracle.graal.asm.amd64.AMD64Assembler.ConditionFlag;
 import com.oracle.graal.graph.*;
 import com.oracle.graal.hotspot.HotSpotVMConfig.CompressEncoding;
+import com.oracle.graal.hotspot.data.*;
 import com.oracle.graal.lir.*;
 import com.oracle.graal.lir.amd64.*;
 import com.oracle.graal.lir.amd64.AMD64Move.LoadOp;
@@ -51,6 +52,9 @@
         public void emitMemAccess(CompilationResultBuilder crb, AMD64MacroAssembler masm) {
             if (kind == Kind.Long) {
                 if (NumUtil.isInt(input.asLong())) {
+                    if (input.getPrimitiveAnnotation() != null) {
+                        crb.recordInlineDataInCode(new MetaspaceData(0, input.asLong(), input.getPrimitiveAnnotation(), true));
+                    }
                     masm.movl(address.toAddress(), (int) input.asLong());
                 } else {
                     throw GraalInternalError.shouldNotReachHere("Cannot store 64-bit constants to memory");
@@ -59,7 +63,7 @@
                 if (input.isNull()) {
                     masm.movl(address.toAddress(), 0);
                 } else if (crb.target.inlineObjects) {
-                    crb.recordInlineDataInCode(input);
+                    crb.recordInlineDataInCode(new OopData(0, input.asObject(), true));
                     masm.movl(address.toAddress(), 0xDEADDEAD);
                 } else {
                     throw GraalInternalError.shouldNotReachHere("Cannot store 64-bit constants to memory");
--- a/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotRegisterConfig.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotRegisterConfig.java	Tue Mar 18 11:51:37 2014 -0700
@@ -33,6 +33,7 @@
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.graph.*;
 import com.oracle.graal.hotspot.*;
+import com.oracle.graal.hotspot.nodes.type.*;
 
 public class AMD64HotSpotRegisterConfig implements RegisterConfig {
 
@@ -61,9 +62,16 @@
             return categorized.get(kind);
         }
 
+        PlatformKind primitiveKind;
+        if (kind == NarrowOopStamp.NarrowOop) {
+            primitiveKind = Kind.Int;
+        } else {
+            primitiveKind = kind;
+        }
+
         ArrayList<Register> list = new ArrayList<>();
         for (Register reg : getAllocatableRegisters()) {
-            if (architecture.canStoreValue(reg.getRegisterCategory(), kind)) {
+            if (architecture.canStoreValue(reg.getRegisterCategory(), primitiveKind)) {
                 list.add(reg);
             }
         }
@@ -211,7 +219,7 @@
 
             if (locations[i] == null) {
                 locations[i] = StackSlot.get(kind.getStackKind(), currentStackOffset, !type.out);
-                currentStackOffset += Math.max(target.arch.getSizeInBytes(kind), target.wordSize);
+                currentStackOffset += Math.max(target.getSizeInBytes(kind), target.wordSize);
             }
         }
 
--- a/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotSafepointOp.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotSpotSafepointOp.java	Tue Mar 18 11:51:37 2014 -0700
@@ -24,13 +24,13 @@
 
 import static com.oracle.graal.amd64.AMD64.*;
 import static com.oracle.graal.asm.NumUtil.*;
-import static com.oracle.graal.hotspot.bridge.Marks.*;
 import static com.oracle.graal.phases.GraalOptions.*;
 
 import com.oracle.graal.api.code.*;
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.asm.amd64.*;
 import com.oracle.graal.hotspot.*;
+import com.oracle.graal.hotspot.meta.HotSpotCodeCacheProvider.*;
 import com.oracle.graal.lir.*;
 import com.oracle.graal.lir.amd64.*;
 import com.oracle.graal.lir.asm.*;
@@ -82,21 +82,21 @@
             // co-located with the immutable code.
             asm.movq(scratch, (AMD64Address) crb.recordDataReferenceInCode(pollingPageAddress, alignment));
             final int pos = asm.position();
-            crb.recordMark(atReturn ? MARK_POLL_RETURN_FAR : MARK_POLL_FAR);
+            MarkId.recordMark(crb, atReturn ? MarkId.POLL_RETURN_FAR : MarkId.POLL_FAR);
             if (state != null) {
                 crb.recordInfopoint(pos, state, InfopointReason.SAFEPOINT);
             }
             asm.testl(rax, new AMD64Address(scratch));
         } else if (isPollingPageFar(config)) {
             asm.movq(scratch, config.safepointPollingAddress);
-            crb.recordMark(atReturn ? MARK_POLL_RETURN_FAR : MARK_POLL_FAR);
+            MarkId.recordMark(crb, atReturn ? MarkId.POLL_RETURN_FAR : MarkId.POLL_FAR);
             final int pos = asm.position();
             if (state != null) {
                 crb.recordInfopoint(pos, state, InfopointReason.SAFEPOINT);
             }
             asm.testl(rax, new AMD64Address(scratch));
         } else {
-            crb.recordMark(atReturn ? MARK_POLL_RETURN_NEAR : MARK_POLL_NEAR);
+            MarkId.recordMark(crb, atReturn ? MarkId.POLL_RETURN_NEAR : MarkId.POLL_NEAR);
             final int pos = asm.position();
             if (state != null) {
                 crb.recordInfopoint(pos, state, InfopointReason.SAFEPOINT);
--- a/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotspotDirectStaticCallOp.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotspotDirectStaticCallOp.java	Tue Mar 18 11:51:37 2014 -0700
@@ -26,7 +26,7 @@
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.asm.amd64.*;
 import com.oracle.graal.hotspot.*;
-import com.oracle.graal.hotspot.bridge.*;
+import com.oracle.graal.hotspot.meta.HotSpotCodeCacheProvider.MarkId;
 import com.oracle.graal.lir.*;
 import com.oracle.graal.lir.amd64.*;
 import com.oracle.graal.lir.amd64.AMD64Call.DirectCallOp;
@@ -55,7 +55,7 @@
         // The mark for an invocation that uses an inline cache must be placed at the
         // instruction that loads the Klass from the inline cache.
         AMD64Move.move(crb, masm, AMD64.rbx.asValue(Kind.Long), metaspaceMethod);
-        crb.recordMark(invokeKind == InvokeKind.Static ? Marks.MARK_INVOKESTATIC : Marks.MARK_INVOKESPECIAL);
+        MarkId.recordMark(crb, invokeKind == InvokeKind.Static ? MarkId.INVOKESTATIC : MarkId.INVOKESPECIAL);
         // This must be emitted exactly like this to ensure it's patchable
         masm.movq(AMD64.rax, HotSpotGraalRuntime.runtime().getConfig().nonOopBits);
         super.emitCode(crb, masm);
--- a/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotspotDirectVirtualCallOp.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64HotspotDirectVirtualCallOp.java	Tue Mar 18 11:51:37 2014 -0700
@@ -28,7 +28,7 @@
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.asm.amd64.*;
 import com.oracle.graal.hotspot.*;
-import com.oracle.graal.hotspot.bridge.*;
+import com.oracle.graal.hotspot.meta.HotSpotCodeCacheProvider.MarkId;
 import com.oracle.graal.lir.*;
 import com.oracle.graal.lir.amd64.AMD64Call.DirectCallOp;
 import com.oracle.graal.lir.asm.*;
@@ -53,7 +53,7 @@
     public void emitCode(CompilationResultBuilder crb, AMD64MacroAssembler masm) {
         // The mark for an invocation that uses an inline cache must be placed at the
         // instruction that loads the Klass from the inline cache.
-        crb.recordMark(invokeKind == Virtual ? Marks.MARK_INVOKEVIRTUAL : Marks.MARK_INVOKEINTERFACE);
+        MarkId.recordMark(crb, invokeKind == Virtual ? MarkId.INVOKEVIRTUAL : MarkId.INVOKEINTERFACE);
         // This must be emitted exactly like this to ensure it's patchable
         masm.movq(AMD64.rax, HotSpotGraalRuntime.runtime().getConfig().nonOopBits);
         super.emitCode(crb, masm);
--- a/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64IndirectCallOp.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.amd64/src/com/oracle/graal/hotspot/amd64/AMD64IndirectCallOp.java	Tue Mar 18 11:51:37 2014 -0700
@@ -29,7 +29,7 @@
 import com.oracle.graal.api.code.*;
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.asm.amd64.*;
-import com.oracle.graal.hotspot.bridge.*;
+import com.oracle.graal.hotspot.meta.HotSpotCodeCacheProvider.MarkId;
 import com.oracle.graal.lir.*;
 import com.oracle.graal.lir.amd64.*;
 import com.oracle.graal.lir.amd64.AMD64Call.IndirectCallOp;
@@ -58,7 +58,7 @@
 
     @Override
     public void emitCode(CompilationResultBuilder crb, AMD64MacroAssembler masm) {
-        crb.recordMark(Marks.MARK_INLINE_INVOKE);
+        MarkId.recordMark(crb, MarkId.INLINE_INVOKE);
         Register callReg = asRegister(targetAddress);
         assert !callReg.equals(METHOD);
         AMD64Call.indirectCall(crb, masm, callReg, callTarget, state);
--- a/graal/com.oracle.graal.hotspot.hsail/src/com/oracle/graal/hotspot/hsail/HSAILHotSpotBackendFactory.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.hsail/src/com/oracle/graal/hotspot/hsail/HSAILHotSpotBackendFactory.java	Tue Mar 18 11:51:37 2014 -0700
@@ -62,7 +62,7 @@
         final int stackFrameAlignment = 8;
         final int implicitNullCheckLimit = 0;
         final boolean inlineObjects = true;
-        return new TargetDescription(new HSAIL(), true, stackFrameAlignment, implicitNullCheckLimit, inlineObjects);
+        return new HotSpotTargetDescription(new HSAIL(), true, stackFrameAlignment, implicitNullCheckLimit, inlineObjects, Kind.Int);
     }
 
     public String getArchitecture() {
--- a/graal/com.oracle.graal.hotspot.hsail/src/com/oracle/graal/hotspot/hsail/HSAILHotSpotLIRGenerator.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.hsail/src/com/oracle/graal/hotspot/hsail/HSAILHotSpotLIRGenerator.java	Tue Mar 18 11:51:37 2014 -0700
@@ -162,7 +162,7 @@
             if (canStoreConstant(c, isCompressed)) {
                 if (isCompressed) {
                     if ((c.getKind() == Kind.Object) && c.isNull()) {
-                        append(new StoreConstantOp(Kind.NarrowOop, storeAddress, c, state));
+                        append(new StoreConstantOp(Kind.Int, storeAddress, Constant.forInt(0), state));
                     } else {
                         throw GraalInternalError.shouldNotReachHere("can't handle: " + access);
                     }
--- a/graal/com.oracle.graal.hotspot.ptx/src/com/oracle/graal/hotspot/ptx/PTXHotSpotBackendFactory.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.ptx/src/com/oracle/graal/hotspot/ptx/PTXHotSpotBackendFactory.java	Tue Mar 18 11:51:37 2014 -0700
@@ -59,7 +59,7 @@
         final int stackFrameAlignment = 1;
         final int implicitNullCheckLimit = 0;
         final boolean inlineObjects = true;
-        return new TargetDescription(createArchitecture(), true, stackFrameAlignment, implicitNullCheckLimit, inlineObjects);
+        return new HotSpotTargetDescription(createArchitecture(), true, stackFrameAlignment, implicitNullCheckLimit, inlineObjects, Kind.Int);
     }
 
     public String getArchitecture() {
--- a/graal/com.oracle.graal.hotspot.ptx/src/com/oracle/graal/hotspot/ptx/PTXHotSpotRegisterConfig.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.ptx/src/com/oracle/graal/hotspot/ptx/PTXHotSpotRegisterConfig.java	Tue Mar 18 11:51:37 2014 -0700
@@ -133,7 +133,7 @@
 
             if (locations[i] == null) {
                 locations[i] = StackSlot.get(kind.getStackKind(), currentStackOffset, !type.out);
-                currentStackOffset += Math.max(target.arch.getSizeInBytes(kind), target.wordSize);
+                currentStackOffset += Math.max(target.getSizeInBytes(kind), target.wordSize);
             }
         }
 
--- a/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotBackend.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotBackend.java	Tue Mar 18 11:51:37 2014 -0700
@@ -34,8 +34,8 @@
 import com.oracle.graal.compiler.gen.LIRGenerator;
 import com.oracle.graal.graph.*;
 import com.oracle.graal.hotspot.*;
-import com.oracle.graal.hotspot.bridge.*;
 import com.oracle.graal.hotspot.meta.*;
+import com.oracle.graal.hotspot.meta.HotSpotCodeCacheProvider.MarkId;
 import com.oracle.graal.hotspot.stubs.Stub;
 import com.oracle.graal.lir.*;
 import com.oracle.graal.lir.StandardOp.*;
@@ -189,7 +189,7 @@
         // Emit the prefix
 
         if (unverifiedStub != null) {
-            crb.recordMark(Marks.MARK_UNVERIFIED_ENTRY);
+            MarkId.recordMark(crb, MarkId.UNVERIFIED_ENTRY);
             // We need to use JavaCall here because we haven't entered the frame yet.
             CallingConvention cc = regConfig.getCallingConvention(JavaCall, null, new JavaType[]{getProviders().getMetaAccess().lookupJavaType(Object.class)}, getTarget(), false);
             Register inlineCacheKlass = g5; // see MacroAssembler::ic_call
@@ -204,8 +204,8 @@
         }
 
         masm.align(config.codeEntryAlignment);
-        crb.recordMark(Marks.MARK_OSR_ENTRY);
-        crb.recordMark(Marks.MARK_VERIFIED_ENTRY);
+        MarkId.recordMark(crb, MarkId.OSR_ENTRY);
+        MarkId.recordMark(crb, MarkId.VERIFIED_ENTRY);
 
         // Emit code for the LIR
         crb.emit(lir);
@@ -213,9 +213,9 @@
         HotSpotFrameContext frameContext = (HotSpotFrameContext) crb.frameContext;
         HotSpotForeignCallsProvider foreignCalls = getProviders().getForeignCalls();
         if (!frameContext.isStub) {
-            crb.recordMark(Marks.MARK_EXCEPTION_HANDLER_ENTRY);
+            MarkId.recordMark(crb, MarkId.EXCEPTION_HANDLER_ENTRY);
             SPARCCall.directCall(crb, masm, foreignCalls.lookupForeignCall(EXCEPTION_HANDLER), null, false, null);
-            crb.recordMark(Marks.MARK_DEOPT_HANDLER_ENTRY);
+            MarkId.recordMark(crb, MarkId.DEOPT_HANDLER_ENTRY);
             SPARCCall.directCall(crb, masm, foreignCalls.lookupForeignCall(DEOPT_HANDLER), null, false, null);
         } else {
             // No need to emit the stubs for entries back into the method since
--- a/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotBackendFactory.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotBackendFactory.java	Tue Mar 18 11:51:37 2014 -0700
@@ -42,7 +42,7 @@
         final int stackFrameAlignment = 16;
         final int implicitNullCheckLimit = 4096;
         final boolean inlineObjects = true;
-        return new TargetDescription(createArchitecture(), true, stackFrameAlignment, implicitNullCheckLimit, inlineObjects);
+        return new HotSpotTargetDescription(createArchitecture(), true, stackFrameAlignment, implicitNullCheckLimit, inlineObjects, Kind.Int);
     }
 
     public HotSpotBackend createBackend(HotSpotGraalRuntime runtime, HotSpotBackend host) {
--- a/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotCodeCacheProvider.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotCodeCacheProvider.java	Tue Mar 18 11:51:37 2014 -0700
@@ -34,6 +34,6 @@
 
     @Override
     protected RegisterConfig createRegisterConfig() {
-        return new SPARCHotSpotRegisterConfig(getTarget().arch, runtime.getConfig());
+        return new SPARCHotSpotRegisterConfig(getTarget(), runtime.getConfig());
     }
 }
--- a/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotRegisterConfig.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotRegisterConfig.java	Tue Mar 18 11:51:37 2014 -0700
@@ -130,10 +130,10 @@
         return registers;
     }
 
-    public SPARCHotSpotRegisterConfig(Architecture architecture, HotSpotVMConfig config) {
-        this.architecture = architecture;
+    public SPARCHotSpotRegisterConfig(TargetDescription target, HotSpotVMConfig config) {
+        this.architecture = target.arch;
 
-        csl = new CalleeSaveLayout(architecture, -1, -1, architecture.getWordSize(), calleeSaveRegisters);
+        csl = new CalleeSaveLayout(target, -1, -1, target.arch.getWordSize(), calleeSaveRegisters);
         allocatable = initAllocatable(config.useCompressedOops);
         attributesMap = RegisterAttributes.createMap(this, SPARC.allRegisters);
     }
@@ -203,7 +203,7 @@
 
             if (locations[i] == null) {
                 locations[i] = StackSlot.get(kind.getStackKind(), currentStackOffset, !type.out);
-                currentStackOffset += Math.max(target.arch.getSizeInBytes(kind), target.wordSize);
+                currentStackOffset += Math.max(target.getSizeInBytes(kind), target.wordSize);
             }
         }
 
--- a/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotSafepointOp.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotSafepointOp.java	Tue Mar 18 11:51:37 2014 -0700
@@ -23,13 +23,13 @@
 package com.oracle.graal.hotspot.sparc;
 
 import static com.oracle.graal.asm.sparc.SPARCMacroAssembler.*;
-import static com.oracle.graal.hotspot.bridge.Marks.*;
 import static com.oracle.graal.sparc.SPARC.*;
 
 import com.oracle.graal.api.code.*;
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.asm.sparc.*;
 import com.oracle.graal.hotspot.*;
+import com.oracle.graal.hotspot.meta.HotSpotCodeCacheProvider.MarkId;
 import com.oracle.graal.lir.*;
 import com.oracle.graal.lir.sparc.*;
 import com.oracle.graal.lir.asm.*;
@@ -61,7 +61,7 @@
     public static void emitCode(CompilationResultBuilder crb, SPARCMacroAssembler masm, HotSpotVMConfig config, boolean atReturn, LIRFrameState state, Register scratch) {
         final int pos = masm.position();
         new Setx(config.safepointPollingAddress, scratch).emit(masm);
-        crb.recordMark(atReturn ? MARK_POLL_RETURN_FAR : MARK_POLL_FAR);
+        MarkId.recordMark(crb, atReturn ? MarkId.POLL_RETURN_FAR : MarkId.POLL_FAR);
         if (state != null) {
             crb.recordInfopoint(pos, state, InfopointReason.SAFEPOINT);
         }
--- a/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotspotDirectStaticCallOp.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotspotDirectStaticCallOp.java	Tue Mar 18 11:51:37 2014 -0700
@@ -28,7 +28,7 @@
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.asm.sparc.*;
 import com.oracle.graal.hotspot.*;
-import com.oracle.graal.hotspot.bridge.*;
+import com.oracle.graal.hotspot.meta.HotSpotCodeCacheProvider.MarkId;
 import com.oracle.graal.lir.*;
 import com.oracle.graal.lir.asm.*;
 import com.oracle.graal.lir.sparc.SPARCCall.DirectCallOp;
@@ -42,7 +42,6 @@
 @Opcode("CALL_DIRECT")
 final class SPARCHotspotDirectStaticCallOp extends DirectCallOp {
 
-    private static final long nonOopBits = HotSpotGraalRuntime.runtime().getConfig().nonOopBits;
     private final Constant metaspaceMethod;
     private final InvokeKind invokeKind;
 
@@ -58,9 +57,9 @@
         // The mark for an invocation that uses an inline cache must be placed at the
         // instruction that loads the Klass from the inline cache.
         SPARCMove.move(crb, masm, g5.asValue(Kind.Long), metaspaceMethod);
-        crb.recordMark(invokeKind == InvokeKind.Static ? Marks.MARK_INVOKESTATIC : Marks.MARK_INVOKESPECIAL);
+        MarkId.recordMark(crb, invokeKind == InvokeKind.Static ? MarkId.INVOKESTATIC : MarkId.INVOKESPECIAL);
         // SPARCMove.move(crb, masm, g3.asValue(Kind.Long), Constant.LONG_0);
-        new Setx(nonOopBits, g3, true).emit(masm);
+        new Setx(HotSpotGraalRuntime.runtime().getConfig().nonOopBits, g3, true).emit(masm);
         super.emitCode(crb, masm);
     }
 }
--- a/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotspotDirectVirtualCallOp.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotspotDirectVirtualCallOp.java	Tue Mar 18 11:51:37 2014 -0700
@@ -29,7 +29,7 @@
 import com.oracle.graal.asm.sparc.*;
 import com.oracle.graal.asm.sparc.SPARCMacroAssembler.*;
 import com.oracle.graal.hotspot.*;
-import com.oracle.graal.hotspot.bridge.*;
+import com.oracle.graal.hotspot.meta.HotSpotCodeCacheProvider.MarkId;
 import com.oracle.graal.lir.*;
 import com.oracle.graal.lir.sparc.SPARCCall.DirectCallOp;
 import com.oracle.graal.lir.asm.*;
@@ -54,7 +54,7 @@
     public void emitCode(CompilationResultBuilder crb, SPARCMacroAssembler masm) {
         // The mark for an invocation that uses an inline cache must be placed at the
         // instruction that loads the Klass from the inline cache.
-        crb.recordMark(invokeKind == Virtual ? Marks.MARK_INVOKEVIRTUAL : Marks.MARK_INVOKEINTERFACE);
+        MarkId.recordMark(crb, invokeKind == Virtual ? MarkId.INVOKEVIRTUAL : MarkId.INVOKEINTERFACE);
         new Setx(HotSpotGraalRuntime.runtime().getConfig().nonOopBits, g3, true).emit(masm);
         super.emitCode(crb, masm);
     }
--- a/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCIndirectCallOp.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCIndirectCallOp.java	Tue Mar 18 11:51:37 2014 -0700
@@ -29,7 +29,7 @@
 import com.oracle.graal.api.code.*;
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.asm.sparc.*;
-import com.oracle.graal.hotspot.bridge.*;
+import com.oracle.graal.hotspot.meta.HotSpotCodeCacheProvider.MarkId;
 import com.oracle.graal.lir.*;
 import com.oracle.graal.lir.sparc.*;
 import com.oracle.graal.lir.sparc.SPARCCall.IndirectCallOp;
@@ -58,7 +58,7 @@
 
     @Override
     public void emitCode(CompilationResultBuilder crb, SPARCMacroAssembler masm) {
-        crb.recordMark(Marks.MARK_INLINE_INVOKE);
+        MarkId.recordMark(crb, MarkId.INLINE_INVOKE);
         Register callReg = asRegister(targetAddress);
         assert !callReg.equals(METHOD);
         SPARCCall.indirectCall(crb, masm, callReg, callTarget, state);
--- a/graal/com.oracle.graal.hotspot.test/src/com/oracle/graal/hotspot/test/HotSpotCryptoSubstitutionTest.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot.test/src/com/oracle/graal/hotspot/test/HotSpotCryptoSubstitutionTest.java	Tue Mar 18 11:51:37 2014 -0700
@@ -49,7 +49,7 @@
     protected InstalledCode addMethod(ResolvedJavaMethod method, CompilationResult compResult) {
         HotSpotResolvedJavaMethod hsMethod = (HotSpotResolvedJavaMethod) method;
         HotSpotNmethod installedCode = new HotSpotNmethod(hsMethod, compResult.getName(), true);
-        HotSpotCompiledNmethod compiledNmethod = new HotSpotCompiledNmethod(runtime().getTarget().arch, hsMethod, compResult);
+        HotSpotCompiledNmethod compiledNmethod = new HotSpotCompiledNmethod(runtime().getTarget(), hsMethod, compResult);
         CodeInstallResult result = runtime().getCompilerToVM().installCode(compiledNmethod, installedCode, null);
         Assert.assertEquals("Error installing method " + method + ": " + result, result, CodeInstallResult.OK);
 
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/CompilationStatistics.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/CompilationStatistics.java	Tue Mar 18 11:51:37 2014 -0700
@@ -102,10 +102,10 @@
         }
     }
 
-    public void finish(HotSpotResolvedJavaMethod method) {
+    public void finish(HotSpotResolvedJavaMethod method, HotSpotInstalledCode code) {
         if (ENABLED) {
             duration = System.nanoTime() - startTime;
-            codeSize = method.getCompiledCodeSize();
+            codeSize = (int) code.getCodeSize();
             memoryUsed = getThreadAllocatedBytes() - threadAllocatedBytesStart;
             if (current.get().getLast() != this) {
                 throw new RuntimeException("mismatch in finish()");
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/CompilationTask.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/CompilationTask.java	Tue Mar 18 11:51:37 2014 -0700
@@ -54,6 +54,8 @@
 
 public class CompilationTask implements Runnable, Comparable {
 
+    private static final long TIMESTAMP_START = System.currentTimeMillis();
+
     // Keep static finals in a group with withinEnqueue as the last one. CompilationTask can be
     // called from within it's own clinit so it needs to be careful about accessing state. Once
     // withinEnqueue is non-null we assume that CompilationTask is fully initialized.
@@ -279,8 +281,12 @@
 
             try (TimerCloseable b = CodeInstallationTime.start()) {
                 installedCode = installMethod(result);
+                if (!isOSR) {
+                    ProfilingInfo profile = method.getProfilingInfo();
+                    profile.setCompilerIRSize(StructuredGraph.class, graph.getNodeCount());
+                }
             }
-            stats.finish(method);
+            stats.finish(method, installedCode);
         } catch (BailoutException bailout) {
             BAILOUTS.increment();
             if (ExitVMOnBailout.getValue()) {
@@ -326,7 +332,24 @@
     private void printCompilation() {
         final boolean isOSR = entryBCI != StructuredGraph.INVOCATION_ENTRY_BCI;
         final int mod = method.getModifiers();
-        TTY.println(String.format("%7d %4d %c%c%c%c%c       %s %s(%d bytes)", 0, id, isOSR ? '%' : ' ', Modifier.isSynchronized(mod) ? 's' : ' ', ' ', ' ', Modifier.isNative(mod) ? 'n' : ' ',
+        String compilerName = "";
+        if (HotSpotCIPrintCompilerName.getValue()) {
+            compilerName = "Graal:";
+        }
+        HotSpotVMConfig config = backend.getRuntime().getConfig();
+        int compLevel = config.compilationLevelFullOptimization;
+        char compLevelChar;
+        if (config.tieredCompilation) {
+            compLevelChar = '-';
+            if (compLevel != -1) {
+                compLevelChar = (char) ('0' + compLevel);
+            }
+        } else {
+            compLevelChar = ' ';
+        }
+        boolean hasExceptionHandlers = method.getExceptionHandlers().length > 0;
+        TTY.println(String.format("%s%7d %4d %c%c%c%c%c%c      %s %s(%d bytes)", compilerName, (System.currentTimeMillis() - TIMESTAMP_START), id, isOSR ? '%' : ' ',
+                        Modifier.isSynchronized(mod) ? 's' : ' ', hasExceptionHandlers ? '!' : ' ', blocking ? 'b' : ' ', Modifier.isNative(mod) ? 'n' : ' ', compLevelChar,
                         MetaUtil.format("%H::%n(%p)", method), isOSR ? "@ " + entryBCI + " " : "", method.getCodeSize()));
     }
 
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotBackend.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotBackend.java	Tue Mar 18 11:51:37 2014 -0700
@@ -27,7 +27,6 @@
 import com.oracle.graal.api.code.*;
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.compiler.target.*;
-import com.oracle.graal.hotspot.bridge.*;
 import com.oracle.graal.hotspot.meta.*;
 import com.oracle.graal.hotspot.stubs.*;
 import com.oracle.graal.lir.*;
@@ -51,7 +50,8 @@
 
     /**
      * Descriptor for {@link ExceptionHandlerStub}. This stub is called by the
-     * {@linkplain Marks#MARK_EXCEPTION_HANDLER_ENTRY exception handler} in a compiled method.
+     * {@linkplain HotSpotVMConfig#codeInstallerMarkIdExceptionHandlerEntry exception handler} in a
+     * compiled method.
      */
     public static final ForeignCallDescriptor EXCEPTION_HANDLER = new ForeignCallDescriptor("exceptionHandler", void.class, Object.class, Word.class);
 
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotCompiledCode.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotCompiledCode.java	Tue Mar 18 11:51:37 2014 -0700
@@ -22,21 +22,17 @@
  */
 package com.oracle.graal.hotspot;
 
-import java.nio.*;
 import java.util.*;
 
 import com.oracle.graal.api.code.*;
 import com.oracle.graal.api.code.CompilationResult.CodeAnnotation;
 import com.oracle.graal.api.code.CompilationResult.CodeComment;
-import com.oracle.graal.api.code.CompilationResult.Data;
-import com.oracle.graal.api.code.CompilationResult.DataPatch;
 import com.oracle.graal.api.code.CompilationResult.ExceptionHandler;
 import com.oracle.graal.api.code.CompilationResult.Infopoint;
 import com.oracle.graal.api.code.CompilationResult.JumpTable;
 import com.oracle.graal.api.code.CompilationResult.Mark;
 import com.oracle.graal.api.code.CompilationResult.Site;
-import com.oracle.graal.api.meta.*;
-import com.oracle.graal.asm.*;
+import com.oracle.graal.hotspot.data.*;
 
 /**
  * A {@link CompilationResult} with additional HotSpot-specific information required for installing
@@ -53,111 +49,6 @@
 
     public final DataSection dataSection;
 
-    /**
-     * Represents a reference to the data section. Before the code is installed, all {@link Data}
-     * items referenced by a {@link DataPatch} are put into the data section of the method, and
-     * replaced by {@link HotSpotData}.
-     */
-    public static final class HotSpotData extends Data {
-
-        /**
-         * The offset of the data item in the data section.
-         */
-        public int offset;
-
-        /**
-         * If the data item is an oop that needs to be patched by the runtime, this field contains
-         * the reference to the object.
-         */
-        public Constant constant;
-
-        public HotSpotData(int offset) {
-            super(0);
-            this.offset = offset;
-        }
-
-        @Override
-        public int getSize(Architecture arch) {
-            return 0;
-        }
-
-        @Override
-        public void emit(Architecture arch, ByteBuffer buffer) {
-        }
-    }
-
-    /**
-     * Represents the data section of a method.
-     */
-    public static final class DataSection {
-
-        /**
-         * The minimum alignment required for this data section.
-         */
-        public final int sectionAlignment;
-
-        /**
-         * The raw data contained in the data section.
-         */
-        public final byte[] data;
-
-        /**
-         * A list of locations where oop pointers need to be patched by the runtime.
-         */
-        public final HotSpotData[] patches;
-
-        public DataSection(Architecture arch, Site[] sites) {
-            int size = 0;
-            int patchCount = 0;
-            List<DataPatch> externalDataList = new ArrayList<>();
-
-            // find all external data items and determine total size of data section
-            for (Site site : sites) {
-                if (site instanceof DataPatch) {
-                    DataPatch dataPatch = (DataPatch) site;
-                    if (dataPatch.externalData != null) {
-                        Data d = dataPatch.externalData;
-                        size = NumUtil.roundUp(size, d.getAlignment());
-                        size += d.getSize(arch);
-                        externalDataList.add(dataPatch);
-                        if (dataPatch.getConstant() != null && dataPatch.getConstant().getKind() == Kind.Object) {
-                            patchCount++;
-                        }
-                    }
-                }
-            }
-
-            data = new byte[size];
-            patches = new HotSpotData[patchCount];
-            ByteBuffer buffer = ByteBuffer.wrap(data).order(ByteOrder.nativeOrder());
-            int index = 0;
-            int patchIndex = 0;
-            int alignment = 0;
-
-            // build data section
-            for (DataPatch dataPatch : externalDataList) {
-                Data d = dataPatch.externalData;
-
-                alignment = Math.max(alignment, d.getAlignment());
-                index = NumUtil.roundUp(index, d.getAlignment());
-                buffer.position(index);
-
-                HotSpotData hsData = new HotSpotData(index);
-                if (dataPatch.getConstant() != null && dataPatch.getConstant().getKind() == Kind.Object) {
-                    // record patch location for oop pointers
-                    hsData.constant = dataPatch.getConstant();
-                    patches[patchIndex++] = hsData;
-                }
-                dataPatch.externalData = hsData;
-
-                index += d.getSize(arch);
-                d.emit(arch, buffer);
-            }
-
-            this.sectionAlignment = alignment;
-        }
-    }
-
     public static class Comment {
 
         public final String text;
@@ -169,10 +60,10 @@
         }
     }
 
-    public HotSpotCompiledCode(Architecture arch, CompilationResult compResult) {
+    public HotSpotCompiledCode(TargetDescription target, CompilationResult compResult) {
         this.comp = compResult;
         sites = getSortedSites(compResult);
-        dataSection = new DataSection(arch, sites);
+        dataSection = new DataSection(target, sites);
         if (compResult.getExceptionHandlers().isEmpty()) {
             exceptionHandlers = null;
         } else {
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotCompiledNmethod.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotCompiledNmethod.java	Tue Mar 18 11:51:37 2014 -0700
@@ -35,8 +35,8 @@
     public final int entryBCI;
     public final int id;
 
-    public HotSpotCompiledNmethod(Architecture arch, HotSpotResolvedJavaMethod method, CompilationResult compResult) {
-        super(arch, compResult);
+    public HotSpotCompiledNmethod(TargetDescription target, HotSpotResolvedJavaMethod method, CompilationResult compResult) {
+        super(target, compResult);
         this.method = method;
         this.entryBCI = compResult.getEntryBCI();
         this.id = compResult.getId();
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotCompiledRuntimeStub.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotCompiledRuntimeStub.java	Tue Mar 18 11:51:37 2014 -0700
@@ -26,7 +26,7 @@
 import com.oracle.graal.api.code.CompilationResult.Call;
 import com.oracle.graal.api.code.CompilationResult.DataPatch;
 import com.oracle.graal.api.code.CompilationResult.Infopoint;
-import com.oracle.graal.api.meta.*;
+import com.oracle.graal.hotspot.data.*;
 import com.oracle.graal.hotspot.stubs.*;
 
 /**
@@ -38,8 +38,8 @@
 
     public final String stubName;
 
-    public HotSpotCompiledRuntimeStub(Architecture arch, Stub stub, CompilationResult compResult) {
-        super(arch, compResult);
+    public HotSpotCompiledRuntimeStub(TargetDescription target, Stub stub, CompilationResult compResult) {
+        super(target, compResult);
         assert checkStubInvariants(compResult);
         this.stubName = stub.toString();
     }
@@ -50,11 +50,7 @@
     private boolean checkStubInvariants(CompilationResult compResult) {
         assert compResult.getExceptionHandlers().isEmpty();
         for (DataPatch data : compResult.getDataReferences()) {
-            Constant constant = data.getConstant();
-            if (constant != null) {
-                assert constant.getKind() != Kind.Object : this + " cannot have embedded object constant: " + constant;
-                assert constant.getPrimitiveAnnotation() == null : this + " cannot have embedded metadata: " + constant;
-            }
+            assert !(data.data instanceof PatchedData) : this + " cannot have embedded object or metadata constant: " + data.data;
         }
         for (Infopoint infopoint : compResult.getInfopoints()) {
             assert infopoint instanceof Call : this + " cannot have non-call infopoint: " + infopoint;
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotGraalRuntime.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotGraalRuntime.java	Tue Mar 18 11:51:37 2014 -0700
@@ -235,6 +235,9 @@
         if (HotSpotPrintInlining.getValue() == false) {
             HotSpotPrintInlining.setValue(config.printInlining);
         }
+        if (HotSpotCIPrintCompilerName.getValue() == false) {
+            HotSpotCIPrintCompilerName.setValue(config.printCompilerName);
+        }
 
         if (Boolean.valueOf(System.getProperty("graal.printconfig"))) {
             printConfig(config);
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotReferenceMap.java	Tue Mar 18 11:51:37 2014 -0700
@@ -0,0 +1,114 @@
+/*
+ * Copyright (c) 2009, 2014, 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.hotspot;
+
+import java.io.*;
+import java.util.*;
+
+import com.oracle.graal.api.code.CodeUtil.RefMapFormatter;
+import com.oracle.graal.api.code.*;
+import com.oracle.graal.api.meta.*;
+import com.oracle.graal.hotspot.nodes.type.*;
+
+public class HotSpotReferenceMap implements ReferenceMap, Serializable {
+
+    private static final long serialVersionUID = -1052183095979496819L;
+
+    /**
+     * Contains 2 bits per register.
+     * <ul>
+     * <li>bit0 = 0: contains no references</li>
+     * <li>bit0 = 1, bit1 = 0: contains a wide oop</li>
+     * <li>bit0 = 1, bit1 = 1: contains a narrow oop</li>
+     * </ul>
+     */
+    private final BitSet registerRefMap;
+
+    /**
+     * Contains 3 bits per stack slot.
+     * <ul>
+     * <li>bit0 = 0: contains no references</li>
+     * <li>bit0 = 1, bit1+2 = 0: contains a wide oop</li>
+     * <li>bit0 = 1, bit1 = 1: contains a narrow oop in the lower half</li>
+     * <li>bit0 = 1, bit2 = 1: contains a narrow oop in the upper half</li>
+     * </ul>
+     */
+    private final BitSet frameRefMap;
+
+    private final int frameSlotSize;
+
+    public HotSpotReferenceMap(int registerCount, int frameSlotCount, int frameSlotSize) {
+        if (registerCount > 0) {
+            this.registerRefMap = new BitSet(registerCount * 2);
+        } else {
+            this.registerRefMap = null;
+        }
+        this.frameRefMap = new BitSet(frameSlotCount * 3);
+        this.frameSlotSize = frameSlotSize;
+    }
+
+    public void setRegister(int idx, PlatformKind kind) {
+        if (kind == Kind.Object) {
+            registerRefMap.set(2 * idx);
+        } else if (kind == NarrowOopStamp.NarrowOop) {
+            registerRefMap.set(2 * idx);
+            registerRefMap.set(2 * idx + 1);
+        }
+    }
+
+    public void setStackSlot(int offset, PlatformKind kind) {
+        int idx = offset / frameSlotSize;
+        if (kind == Kind.Object) {
+            assert offset % frameSlotSize == 0;
+            frameRefMap.set(3 * idx);
+        } else if (kind == NarrowOopStamp.NarrowOop) {
+            frameRefMap.set(3 * idx);
+            if (offset % frameSlotSize == 0) {
+                frameRefMap.set(3 * idx + 1);
+            } else {
+                assert offset % frameSlotSize == frameSlotSize / 2;
+                frameRefMap.set(3 * idx + 2);
+            }
+        }
+    }
+
+    public boolean hasRegisterRefMap() {
+        return registerRefMap != null && registerRefMap.size() > 0;
+    }
+
+    public boolean hasFrameRefMap() {
+        return frameRefMap != null && frameRefMap.size() > 0;
+    }
+
+    public void appendRegisterMap(StringBuilder sb, RefMapFormatter formatter) {
+        for (int reg = registerRefMap.nextSetBit(0); reg >= 0; reg = registerRefMap.nextSetBit(reg + 2)) {
+            sb.append(' ').append(formatter.formatRegister(reg / 2));
+        }
+    }
+
+    public void appendFrameMap(StringBuilder sb, RefMapFormatter formatter) {
+        for (int slot = frameRefMap.nextSetBit(0); slot >= 0; slot = frameRefMap.nextSetBit(slot + 3)) {
+            sb.append(' ').append(formatter.formatStackSlot(slot / 3));
+        }
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotTargetDescription.java	Tue Mar 18 11:51:37 2014 -0700
@@ -0,0 +1,51 @@
+/*
+ * Copyright (c) 2014, 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.hotspot;
+
+import com.oracle.graal.api.code.*;
+import com.oracle.graal.api.meta.*;
+import com.oracle.graal.hotspot.nodes.type.*;
+
+public class HotSpotTargetDescription extends TargetDescription {
+
+    private final PlatformKind rawNarrowOopKind;
+
+    public HotSpotTargetDescription(Architecture arch, boolean isMP, int stackAlignment, int implicitNullCheckLimit, boolean inlineObjects, PlatformKind rawNarrowOopKind) {
+        super(arch, isMP, stackAlignment, implicitNullCheckLimit, inlineObjects);
+        this.rawNarrowOopKind = rawNarrowOopKind;
+    }
+
+    @Override
+    public int getSizeInBytes(PlatformKind kind) {
+        if (kind == NarrowOopStamp.NarrowOop) {
+            return super.getSizeInBytes(rawNarrowOopKind);
+        } else {
+            return super.getSizeInBytes(kind);
+        }
+    }
+
+    @Override
+    public ReferenceMap createReferenceMap(boolean hasRegisters, int stackSlotCount) {
+        return new HotSpotReferenceMap(hasRegisters ? arch.getRegisterReferenceMapBitCount() : 0, stackSlotCount, wordSize);
+    }
+}
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMConfig.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/HotSpotVMConfig.java	Tue Mar 18 11:51:37 2014 -0700
@@ -709,10 +709,12 @@
     @HotSpotVMFlag(name = "DontCompileHugeMethods") @Stable public boolean dontCompileHugeMethods;
     @HotSpotVMFlag(name = "HugeMethodLimit") @Stable public int hugeMethodLimit;
     @HotSpotVMFlag(name = "PrintCompilation") @Stable public boolean printCompilation;
+    @HotSpotVMFlag(name = "CIPrintCompilerName") @Stable public boolean printCompilerName;
     @HotSpotVMFlag(name = "PrintInlining") @Stable public boolean printInlining;
     @HotSpotVMFlag(name = "GraalUseFastLocking") @Stable public boolean useFastLocking;
     @HotSpotVMFlag(name = "ForceUnreachable") @Stable public boolean forceUnreachable;
     @HotSpotVMFlag(name = "GPUOffload") @Stable public boolean gpuOffload;
+    @HotSpotVMFlag(name = "TieredCompilation") @Stable public boolean tieredCompilation;
 
     @HotSpotVMFlag(name = "UseTLAB") @Stable public boolean useTLAB;
     @HotSpotVMFlag(name = "UseBiasedLocking") @Stable public boolean useBiasedLocking;
@@ -1189,6 +1191,7 @@
     @HotSpotVMField(name = "MethodData::_data_size", type = "int", get = HotSpotVMField.Type.OFFSET) @Stable public int methodDataDataSize;
     @HotSpotVMField(name = "MethodData::_data[0]", type = "intptr_t", get = HotSpotVMField.Type.OFFSET) @Stable public int methodDataOopDataOffset;
     @HotSpotVMField(name = "MethodData::_trap_hist._array[0]", type = "u1", get = HotSpotVMField.Type.OFFSET) @Stable public int methodDataOopTrapHistoryOffset;
+    @HotSpotVMField(name = "MethodData::_graal_node_count", type = "int", get = HotSpotVMField.Type.OFFSET) @Stable public int methodDataGraalNodeCountOffset;
 
     @HotSpotVMField(name = "nmethod::_verified_entry_point", type = "address", get = HotSpotVMField.Type.OFFSET) @Stable public int nmethodEntryOffset;
     @HotSpotVMField(name = "nmethod::_comp_level", type = "int", get = HotSpotVMField.Type.OFFSET) @Stable public int nmethodCompLevelOffset;
@@ -1419,6 +1422,22 @@
     @HotSpotVMConstant(name = "CompilerToVM::KLASS_TAG") @Stable public int compilerToVMKlassTag;
     @HotSpotVMConstant(name = "CompilerToVM::SYMBOL_TAG") @Stable public int compilerToVMSymbolTag;
 
+    @HotSpotVMConstant(name = "CodeInstaller::VERIFIED_ENTRY") @Stable public int codeInstallerMarkIdVerifiedEntry;
+    @HotSpotVMConstant(name = "CodeInstaller::UNVERIFIED_ENTRY") @Stable public int codeInstallerMarkIdUnverifiedEntry;
+    @HotSpotVMConstant(name = "CodeInstaller::OSR_ENTRY") @Stable public int codeInstallerMarkIdOsrEntry;
+    @HotSpotVMConstant(name = "CodeInstaller::EXCEPTION_HANDLER_ENTRY") @Stable public int codeInstallerMarkIdExceptionHandlerEntry;
+    @HotSpotVMConstant(name = "CodeInstaller::DEOPT_HANDLER_ENTRY") @Stable public int codeInstallerMarkIdDeoptHandlerEntry;
+    @HotSpotVMConstant(name = "CodeInstaller::INVOKEINTERFACE") @Stable public int codeInstallerMarkIdInvokeinterface;
+    @HotSpotVMConstant(name = "CodeInstaller::INVOKEVIRTUAL") @Stable public int codeInstallerMarkIdInvokevirtual;
+    @HotSpotVMConstant(name = "CodeInstaller::INVOKESTATIC") @Stable public int codeInstallerMarkIdInvokestatic;
+    @HotSpotVMConstant(name = "CodeInstaller::INVOKESPECIAL") @Stable public int codeInstallerMarkIdInvokespecial;
+    @HotSpotVMConstant(name = "CodeInstaller::INLINE_INVOKE") @Stable public int codeInstallerMarkIdInlineInvoke;
+    @HotSpotVMConstant(name = "CodeInstaller::POLL_NEAR") @Stable public int codeInstallerMarkIdPollNear;
+    @HotSpotVMConstant(name = "CodeInstaller::POLL_RETURN_NEAR") @Stable public int codeInstallerMarkIdPollReturnNear;
+    @HotSpotVMConstant(name = "CodeInstaller::POLL_FAR") @Stable public int codeInstallerMarkIdPollFar;
+    @HotSpotVMConstant(name = "CodeInstaller::POLL_RETURN_FAR") @Stable public int codeInstallerMarkIdPollReturnFar;
+    @HotSpotVMConstant(name = "CodeInstaller::INVOKE_INVALID") @Stable public int codeInstallerMarkIdInvokeInvalid;
+
     public boolean check() {
         for (Field f : getClass().getDeclaredFields()) {
             int modifiers = f.getModifiers();
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/bridge/CompilerToVM.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/bridge/CompilerToVM.java	Tue Mar 18 11:51:37 2014 -0700
@@ -118,7 +118,9 @@
      */
     long lookupType(String name, Class<?> accessingClass, boolean resolve);
 
-    Object lookupConstantInPool(long metaspaceConstantPool, int cpi);
+    Object resolveConstantInPool(long metaspaceConstantPool, int cpi);
+
+    Object resolvePossiblyCachedConstantInPool(long metaspaceConstantPool, int cpi);
 
     int lookupNameAndTypeRefIndexInPool(long metaspaceConstantPool, int cpi);
 
@@ -128,6 +130,8 @@
 
     int lookupKlassRefIndexInPool(long metaspaceConstantPool, int cpi);
 
+    long constantPoolKlassAt(long metaspaceConstantPool, int cpi);
+
     /**
      * Looks up a class entry in a constant pool.
      * 
@@ -163,7 +167,7 @@
      */
     long resolveField(long metaspaceConstantPool, int cpi, byte opcode, long[] info);
 
-    void loadReferencedTypeInPool(long metaspaceConstantPool, int cpi, byte opcode);
+    int constantPoolRemapInstructionOperandFromCache(long metaspaceConstantPool, int cpi);
 
     Object lookupAppendixInPool(long metaspaceConstantPool, int cpi);
 
@@ -248,14 +252,6 @@
     boolean hasFinalizableSubclass(long metaspaceKlass);
 
     /**
-     * Gets the compiled code size for a method.
-     * 
-     * @param metaspaceMethod the metaspace Method object to query
-     * @return the compiled code size the method
-     */
-    int getCompiledCodeSize(long metaspaceMethod);
-
-    /**
      * Gets the metaspace Method object corresponding to a given {@link Class} object and slot
      * number.
      * 
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/bridge/CompilerToVMImpl.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/bridge/CompilerToVMImpl.java	Tue Mar 18 11:51:37 2014 -0700
@@ -63,8 +63,9 @@
     @Override
     public native long lookupType(String name, Class<?> accessingClass, boolean eagerResolve);
 
-    @Override
-    public native Object lookupConstantInPool(long metaspaceConstantPool, int cpi);
+    public native Object resolveConstantInPool(long metaspaceConstantPool, int cpi);
+
+    public native Object resolvePossiblyCachedConstantInPool(long metaspaceConstantPool, int cpi);
 
     @Override
     public native int lookupNameAndTypeRefIndexInPool(long metaspaceConstantPool, int cpi);
@@ -78,6 +79,8 @@
     @Override
     public native int lookupKlassRefIndexInPool(long metaspaceConstantPool, int cpi);
 
+    public native long constantPoolKlassAt(long metaspaceConstantPool, int cpi);
+
     @Override
     public native long lookupKlassInPool(long metaspaceConstantPool, int cpi);
 
@@ -87,8 +90,7 @@
     @Override
     public native long resolveField(long metaspaceConstantPool, int cpi, byte opcode, long[] info);
 
-    @Override
-    public native void loadReferencedTypeInPool(long metaspaceConstantPool, int cpi, byte opcode);
+    public native int constantPoolRemapInstructionOperandFromCache(long metaspaceConstantPool, int cpi);
 
     @Override
     public native Object lookupAppendixInPool(long metaspaceConstantPool, int cpi);
@@ -109,9 +111,6 @@
     public native long getClassInitializer(long metaspaceKlass);
 
     @Override
-    public native int getCompiledCodeSize(long metaspaceMethod);
-
-    @Override
     public native long getMaxCallTargetOffset(long address);
 
     // The HotSpot disassembler seems not to be thread safe so it's better to synchronize its usage
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/bridge/Marks.java	Tue Mar 18 11:07:47 2014 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,46 +0,0 @@
-/*
- * Copyright (c) 2012, 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.hotspot.bridge;
-
-/**
- * Constants used to mark special positions in code being installed into the code cache by Graal C++
- * code. These constants need to be kept in sync with those of the same name defined in
- * graalCodeInstaller.hpp.
- */
-public interface Marks {
-
-    int MARK_VERIFIED_ENTRY = 1;
-    int MARK_UNVERIFIED_ENTRY = 2;
-    int MARK_OSR_ENTRY = 3;
-    int MARK_EXCEPTION_HANDLER_ENTRY = 4;
-    int MARK_DEOPT_HANDLER_ENTRY = 5;
-    int MARK_INVOKEINTERFACE = 6;
-    int MARK_INVOKEVIRTUAL = 7;
-    int MARK_INVOKESTATIC = 8;
-    int MARK_INVOKESPECIAL = 9;
-    int MARK_INLINE_INVOKE = 10;
-    int MARK_POLL_NEAR = 11;
-    int MARK_POLL_RETURN_NEAR = 12;
-    int MARK_POLL_FAR = 13;
-    int MARK_POLL_RETURN_FAR = 14;
-}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/data/DataSection.java	Tue Mar 18 11:51:37 2014 -0700
@@ -0,0 +1,106 @@
+/*
+ * Copyright (c) 2014, 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.hotspot.data;
+
+import java.nio.*;
+import java.util.*;
+
+import com.oracle.graal.api.code.CompilationResult.Data;
+import com.oracle.graal.api.code.CompilationResult.DataPatch;
+import com.oracle.graal.api.code.CompilationResult.Site;
+import com.oracle.graal.api.code.*;
+import com.oracle.graal.asm.*;
+
+/**
+ * Represents the data section of a method.
+ */
+public final class DataSection {
+
+    /**
+     * The minimum alignment required for this data section.
+     */
+    public final int sectionAlignment;
+
+    /**
+     * The raw data contained in the data section.
+     */
+    public final byte[] data;
+
+    /**
+     * A list of locations where oop pointers need to be patched by the runtime.
+     */
+    public final DataPatch[] patches;
+
+    public DataSection(TargetDescription target, Site[] sites) {
+        int size = 0;
+        int patchCount = 0;
+        List<DataPatch> externalDataList = new ArrayList<>();
+
+        // find all external data items and determine total size of data section
+        for (Site site : sites) {
+            if (site instanceof DataPatch) {
+                DataPatch dataPatch = (DataPatch) site;
+                Data d = dataPatch.data;
+                if (dataPatch.inline) {
+                    assert d instanceof PatchedData : "unnecessary data patch";
+                } else {
+                    size = NumUtil.roundUp(size, d.getAlignment());
+                    size += d.getSize(target);
+                    externalDataList.add(dataPatch);
+                    if (d instanceof PatchedData) {
+                        patchCount++;
+                    }
+                }
+            }
+        }
+
+        data = new byte[size];
+        patches = new DataPatch[patchCount];
+        ByteBuffer buffer = ByteBuffer.wrap(data).order(ByteOrder.nativeOrder());
+        int index = 0;
+        int patchIndex = 0;
+        int alignment = 0;
+
+        // build data section
+        for (DataPatch dataPatch : externalDataList) {
+            assert !dataPatch.inline;
+            Data d = dataPatch.data;
+
+            alignment = Math.max(alignment, d.getAlignment());
+            index = NumUtil.roundUp(index, d.getAlignment());
+            buffer.position(index);
+
+            DataSectionReference reference = new DataSectionReference(index);
+            if (d instanceof PatchedData) {
+                // record patch location
+                patches[patchIndex++] = new DataPatch(index, d, true);
+            }
+            dataPatch.data = reference;
+
+            index += d.getSize(target);
+            d.emit(target, buffer);
+        }
+
+        this.sectionAlignment = alignment;
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/data/DataSectionReference.java	Tue Mar 18 11:51:37 2014 -0700
@@ -0,0 +1,60 @@
+/*
+ * Copyright (c) 2014, 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.hotspot.data;
+
+import java.nio.*;
+
+import com.oracle.graal.api.code.CompilationResult.Data;
+import com.oracle.graal.api.code.CompilationResult.DataPatch;
+import com.oracle.graal.api.code.*;
+import com.oracle.graal.api.meta.*;
+
+/**
+ * Represents a reference to the data section. Before the code is installed, all {@link Data} items
+ * referenced by a {@link DataPatch} are put into the data section of the method, and replaced by
+ * {@link DataSectionReference}.
+ */
+public class DataSectionReference extends Data {
+
+    public final int offset;
+
+    protected DataSectionReference(int offset) {
+        super(0);
+        this.offset = offset;
+    }
+
+    @Override
+    public int getSize(TargetDescription target) {
+        return 0;
+    }
+
+    @Override
+    public Kind getKind() {
+        return Kind.Illegal;
+    }
+
+    @Override
+    public void emit(TargetDescription target, ByteBuffer buffer) {
+    }
+
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/data/MetaspaceData.java	Tue Mar 18 11:51:37 2014 -0700
@@ -0,0 +1,80 @@
+/*
+ * Copyright (c) 2014, 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.hotspot.data;
+
+import java.nio.*;
+
+import com.oracle.graal.api.code.*;
+import com.oracle.graal.api.meta.*;
+import com.oracle.graal.graph.*;
+
+/**
+ * A data item that represents a metaspace pointer.
+ */
+public class MetaspaceData extends PatchedData {
+
+    public final long value;
+    public final Object annotation;
+    public final boolean compressed;
+
+    public MetaspaceData(int alignment, long value, Object annotation, boolean compressed) {
+        super(alignment);
+        assert annotation != null;
+        this.value = value;
+        this.annotation = annotation;
+        this.compressed = compressed;
+    }
+
+    @Override
+    public int getSize(TargetDescription target) {
+        if (compressed) {
+            return target.getSizeInBytes(Kind.Int);
+        } else {
+            return target.getSizeInBytes(target.wordKind);
+        }
+    }
+
+    @Override
+    public Kind getKind() {
+        return Kind.Long;
+    }
+
+    @Override
+    public void emit(TargetDescription target, ByteBuffer buffer) {
+        switch (getSize(target)) {
+            case 4:
+                buffer.putInt((int) value);
+                break;
+            case 8:
+                buffer.putLong(value);
+                break;
+            default:
+                throw GraalInternalError.shouldNotReachHere("unexpected metaspace pointer size");
+        }
+    }
+
+    @Override
+    public String toString() {
+        return (compressed ? "NarrowPointer[0x" + Integer.toHexString((int) value) : "Pointer[0x" + Long.toHexString(value)) + "]{" + annotation + "}";
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/data/OopData.java	Tue Mar 18 11:51:37 2014 -0700
@@ -0,0 +1,78 @@
+/*
+ * Copyright (c) 2014, 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.hotspot.data;
+
+import java.nio.*;
+
+import com.oracle.graal.api.code.*;
+import com.oracle.graal.api.meta.*;
+import com.oracle.graal.graph.*;
+import com.oracle.graal.hotspot.nodes.type.*;
+
+/**
+ * A data item that represents an oop value.
+ */
+public class OopData extends PatchedData {
+
+    public final Object object;
+    public final boolean compressed;
+
+    public OopData(int alignment, Object object, boolean compressed) {
+        super(alignment);
+        this.object = object;
+        this.compressed = compressed;
+    }
+
+    @Override
+    public int getSize(TargetDescription target) {
+        if (compressed) {
+            return target.getSizeInBytes(NarrowOopStamp.NarrowOop);
+        } else {
+            return target.getSizeInBytes(Kind.Object);
+        }
+    }
+
+    @Override
+    public Kind getKind() {
+        return Kind.Object;
+    }
+
+    @Override
+    public void emit(TargetDescription target, ByteBuffer buffer) {
+        switch (getSize(target)) {
+            case 4:
+                buffer.putInt(0xDEADDEAD);
+                break;
+            case 8:
+                buffer.putLong(0xDEADDEADDEADDEADL);
+                break;
+            default:
+                throw GraalInternalError.shouldNotReachHere("unexpected oop size");
+        }
+    }
+
+    @Override
+    public String toString() {
+        return (compressed ? "NarrowOop[" : "Oop[") + Kind.Object.format(object) + "]";
+    }
+}
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/data/PatchedData.java	Tue Mar 18 11:51:37 2014 -0700
@@ -0,0 +1,35 @@
+/*
+ * Copyright (c) 2014, 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.hotspot.data;
+
+import com.oracle.graal.api.code.CompilationResult.Data;
+
+/**
+ * Represents a data item that needs to be patched.
+ */
+public abstract class PatchedData extends Data {
+
+    protected PatchedData(int alignment) {
+        super(alignment);
+    }
+}
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/debug/BenchmarkCounters.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/debug/BenchmarkCounters.java	Tue Mar 18 11:51:37 2014 -0700
@@ -50,10 +50,10 @@
  * infrastructure is enabled by specifying either the GenericDynamicCounters or
  * BenchmarkDynamicCounters option.<br/>
  * 
- * The counters are kept in a special area in the native JavaThread object, and the number of
- * counters is configured in {@code thread.hpp (GRAAL_COUNTERS_SIZE)}. This file also contains an
- * option to exclude compiler threads ({@code GRAAL_COUNTERS_EXCLUDE_COMPILER_THREADS}, which
- * defaults to true).
+ * The counters are kept in a special area allocated for each native JavaThread object, and the
+ * number of counters is configured using {@code -XX:GraalCounterSize=value}.
+ * {@code -XX:+/-GraalCountersExcludeCompiler} configures whether to exclude compiler threads
+ * (defaults to true).
  * 
  * The subsystems that use the logging need to have their own options to turn on the counters, and
  * insert DynamicCounterNodes when they're enabled.
@@ -64,12 +64,10 @@
  * <h1>Example</h1> In order to create statistics about allocations within the DaCapo pmd benchmark
  * the following steps are necessary:
  * <ul>
- * <li>Modify {@code thread.hpp}: increase GRAAL_COUNTER_SIZE. The actual required value depends on
- * the granularity of the profiling, 10000 should be enough for most cases. This will increase the
- * JavaThread structure by 80kb.</li>
- * <li>Also in {@code thread.hpp}: GRAAL_COUNTERS_EXCLUDE_COMPILER_THREADS specifies whether the
- * numbers generated by compiler threads should be excluded (default: true).</li>
- * <li>Build the Graal VM.</li>
+ * <li>Set {@code -XX:GraalCounterSize=value}. The actual required value depends on the granularity
+ * of the profiling, 10000 should be enough for most cases.</li>
+ * <li>Also: {@code -XX:+/-GraalCountersExcludeCompiler} specifies whether the numbers generated by
+ * compiler threads should be excluded (default: true).</li>
  * <li>Start the DaCapo pmd benchmark with
  * {@code "-G:BenchmarkDynamicCounters=err, starting ====, PASSED in "} and
  * {@code -G:+ProfileAllocations}.</li>
@@ -330,7 +328,7 @@
 
             int index = BenchmarkCounters.getIndex(counter);
             if (index >= config.graalCountersSize) {
-                throw new GraalInternalError("too many counters, reduce number of counters or increase GRAAL_COUNTERS_SIZE (current value: " + config.graalCountersSize + ")");
+                throw new GraalInternalError("too many counters, reduce number of counters or increase -XX:GraalCounterSize=... (current value: " + config.graalCountersSize + ")");
             }
             ConstantLocationNode arrayLocation = ConstantLocationNode.create(LocationIdentity.ANY_LOCATION, Kind.Long, config.graalCountersThreadOffset, graph);
             ReadNode readArray = graph.add(new ReadNode(thread, arrayLocation, StampFactory.forKind(wordKind), BarrierType.NONE, false));
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotCodeCacheProvider.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotCodeCacheProvider.java	Tue Mar 18 11:51:37 2014 -0700
@@ -29,15 +29,20 @@
 import com.oracle.graal.api.code.CodeUtil.DefaultRefMapFormatter;
 import com.oracle.graal.api.code.CodeUtil.RefMapFormatter;
 import com.oracle.graal.api.code.CompilationResult.Call;
+import com.oracle.graal.api.code.CompilationResult.Data;
 import com.oracle.graal.api.code.CompilationResult.DataPatch;
 import com.oracle.graal.api.code.CompilationResult.Infopoint;
 import com.oracle.graal.api.code.CompilationResult.Mark;
+import com.oracle.graal.api.code.CompilationResult.PrimitiveData;
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.debug.*;
+import com.oracle.graal.graph.*;
 import com.oracle.graal.hotspot.*;
 import com.oracle.graal.hotspot.bridge.*;
 import com.oracle.graal.hotspot.bridge.CompilerToVM.CodeInstallResult;
+import com.oracle.graal.hotspot.data.*;
 import com.oracle.graal.java.*;
+import com.oracle.graal.lir.asm.*;
 import com.oracle.graal.printer.*;
 
 /**
@@ -57,6 +62,54 @@
 
     protected abstract RegisterConfig createRegisterConfig();
 
+    /**
+     * Constants used to mark special positions in code being installed into the code cache by Graal
+     * C++ code.
+     */
+    public enum MarkId {
+        VERIFIED_ENTRY(config().codeInstallerMarkIdVerifiedEntry),
+        UNVERIFIED_ENTRY(config().codeInstallerMarkIdUnverifiedEntry),
+        OSR_ENTRY(config().codeInstallerMarkIdOsrEntry),
+        EXCEPTION_HANDLER_ENTRY(config().codeInstallerMarkIdExceptionHandlerEntry),
+        DEOPT_HANDLER_ENTRY(config().codeInstallerMarkIdDeoptHandlerEntry),
+        INVOKEINTERFACE(config().codeInstallerMarkIdInvokeinterface),
+        INVOKEVIRTUAL(config().codeInstallerMarkIdInvokevirtual),
+        INVOKESTATIC(config().codeInstallerMarkIdInvokestatic),
+        INVOKESPECIAL(config().codeInstallerMarkIdInvokespecial),
+        INLINE_INVOKE(config().codeInstallerMarkIdInlineInvoke),
+        POLL_NEAR(config().codeInstallerMarkIdPollNear),
+        POLL_RETURN_NEAR(config().codeInstallerMarkIdPollReturnNear),
+        POLL_FAR(config().codeInstallerMarkIdPollFar),
+        POLL_RETURN_FAR(config().codeInstallerMarkIdPollReturnFar);
+
+        private final int value;
+
+        private MarkId(int value) {
+            this.value = value;
+        }
+
+        private static HotSpotVMConfig config() {
+            return HotSpotGraalRuntime.runtime().getConfig();
+        }
+
+        public static MarkId getEnum(int value) {
+            for (MarkId e : values()) {
+                if (e.value == value) {
+                    return e;
+                }
+            }
+            throw GraalInternalError.shouldNotReachHere("unknown enum value " + value);
+        }
+
+        /**
+         * Helper method to {@link CompilationResultBuilder#recordMark(Object) record a mark} with a
+         * {@link CompilationResultBuilder}.
+         */
+        public static void recordMark(CompilationResultBuilder crb, MarkId mark) {
+            crb.recordMark(mark.value);
+        }
+    }
+
     @Override
     public String disassemble(CompilationResult compResult, InstalledCode installedCode) {
         byte[] code = installedCode == null ? Arrays.copyOf(compResult.getTargetCode(), compResult.getTargetCodeSize()) : installedCode.getCode();
@@ -82,10 +135,10 @@
                 }
             }
             for (DataPatch site : compResult.getDataReferences()) {
-                hcf.addOperandComment(site.pcOffset, "{" + site.getDataString() + "}");
+                hcf.addOperandComment(site.pcOffset, "{" + site.data.toString() + "}");
             }
             for (Mark mark : compResult.getMarks()) {
-                hcf.addComment(mark.pcOffset, getMarkName(mark));
+                hcf.addComment(mark.pcOffset, MarkId.getEnum((int) mark.id).toString());
             }
         }
         return hcf.toEmbeddedString();
@@ -111,25 +164,6 @@
         return String.valueOf(call.target);
     }
 
-    /**
-     * Decodes a mark to a mnemonic if possible.
-     */
-    private static String getMarkName(Mark mark) {
-        Field[] fields = Marks.class.getDeclaredFields();
-        for (Field f : fields) {
-            if (Modifier.isStatic(f.getModifiers()) && f.getName().startsWith("MARK_")) {
-                f.setAccessible(true);
-                try {
-                    if (f.get(null).equals(mark.id)) {
-                        return f.getName();
-                    }
-                } catch (Exception e) {
-                }
-            }
-        }
-        return "MARK:" + mark.id;
-    }
-
     private static void addExceptionHandlersComment(CompilationResult compResult, HexCodeFile hcf) {
         if (!compResult.getExceptionHandlers().isEmpty()) {
             String nl = HexCodeFile.NEW_LINE;
@@ -173,7 +207,7 @@
             compResult.setId(method.allocateCompileId(compResult.getEntryBCI()));
         }
         HotSpotInstalledCode installedCode = new HotSpotNmethod(method, compResult.getName(), true);
-        runtime.getCompilerToVM().installCode(new HotSpotCompiledNmethod(target.arch, method, compResult), installedCode, method.getSpeculationLog());
+        runtime.getCompilerToVM().installCode(new HotSpotCompiledNmethod(target, method, compResult), installedCode, method.getSpeculationLog());
         return logOrDump(installedCode, compResult);
     }
 
@@ -184,7 +218,7 @@
             compResult.setId(hotspotMethod.allocateCompileId(compResult.getEntryBCI()));
         }
         HotSpotInstalledCode code = new HotSpotNmethod(hotspotMethod, compResult.getName(), false);
-        CodeInstallResult result = runtime.getCompilerToVM().installCode(new HotSpotCompiledNmethod(target.arch, hotspotMethod, compResult), code, log);
+        CodeInstallResult result = runtime.getCompilerToVM().installCode(new HotSpotCompiledNmethod(target, hotspotMethod, compResult), code, log);
         if (result != CodeInstallResult.OK) {
             return null;
         }
@@ -203,7 +237,7 @@
             compResult.setId(javaMethod.allocateCompileId(compResult.getEntryBCI()));
         }
         HotSpotNmethod code = new HotSpotNmethod(javaMethod, compResult.getName(), false, true);
-        HotSpotCompiledNmethod compiled = new HotSpotCompiledNmethod(target.arch, javaMethod, compResult);
+        HotSpotCompiledNmethod compiled = new HotSpotCompiledNmethod(target, javaMethod, compResult);
         CompilerToVM vm = runtime.getCompilerToVM();
         CodeInstallResult result = vm.installCode(compiled, code, null);
         if (result != CodeInstallResult.OK) {
@@ -216,6 +250,16 @@
         return constant.getPrimitiveAnnotation() != null;
     }
 
+    public Data createDataItem(Constant constant, int alignment) {
+        if (constant.getPrimitiveAnnotation() != null) {
+            return new MetaspaceData(alignment, constant.asLong(), constant.getPrimitiveAnnotation(), false);
+        } else if (constant.getKind().isObject()) {
+            return new OopData(alignment, constant.asObject(), false);
+        } else {
+            return new PrimitiveData(constant, alignment);
+        }
+    }
+
     @Override
     public TargetDescription getTarget() {
         return target;
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotConstantPool.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotConstantPool.java	Tue Mar 18 11:51:37 2014 -0700
@@ -40,6 +40,51 @@
     private static final long serialVersionUID = -5443206401485234850L;
 
     /**
+     * Enum of all {@code JVM_CONSTANT} constants used in the VM. This includes the public and
+     * internal ones.
+     */
+    private enum JVM_CONSTANT {
+        // @formatter:off
+        Utf8(config().jvmConstantUtf8),
+        Integer(config().jvmConstantInteger),
+        Long(config().jvmConstantLong),
+        Float(config().jvmConstantFloat),
+        Double(config().jvmConstantDouble),
+        Class(config().jvmConstantClass),
+        UnresolvedClass(config().jvmConstantUnresolvedClass),
+        UnresolvedClassInError(config().jvmConstantUnresolvedClassInError),
+        String(config().jvmConstantString),
+        Fieldref(config().jvmConstantFieldref),
+        MethodRef(config().jvmConstantMethodref),
+        InterfaceMethodref(config().jvmConstantInterfaceMethodref),
+        NameAndType(config().jvmConstantNameAndType),
+        MethodHandle(config().jvmConstantMethodHandle),
+        MethodHandleInError(config().jvmConstantMethodHandleInError),
+        MethodType(config().jvmConstantMethodType),
+        MethodTypeInError(config().jvmConstantMethodTypeInError);
+        // @formatter:on
+
+        private final int value;
+
+        private JVM_CONSTANT(int value) {
+            this.value = value;
+        }
+
+        private static HotSpotVMConfig config() {
+            return runtime().getConfig();
+        }
+
+        public static JVM_CONSTANT getEnum(int value) {
+            for (JVM_CONSTANT e : values()) {
+                if (e.value == value) {
+                    return e;
+                }
+            }
+            throw GraalInternalError.shouldNotReachHere("unknown enum value " + value);
+        }
+    }
+
+    /**
      * Reference to the C++ ConstantPool object.
      */
     private final long metaspaceConstantPool;
@@ -86,11 +131,12 @@
      * @param index constant pool index
      * @return constant pool tag
      */
-    private int getTagAt(int index) {
+    private JVM_CONSTANT getTagAt(int index) {
         assertBounds(index);
         HotSpotVMConfig config = runtime().getConfig();
-        long tags = unsafe.getAddress(metaspaceConstantPool + config.constantPoolTagsOffset);
-        return unsafe.getByteVolatile(null, tags + config.arrayU1DataOffset + index);
+        final long metaspaceConstantPoolTags = unsafe.getAddress(metaspaceConstantPool + config.constantPoolTagsOffset);
+        final int tag = unsafe.getByteVolatile(null, metaspaceConstantPoolTags + config.arrayU1DataOffset + index);
+        return JVM_CONSTANT.getEnum(tag);
     }
 
     /**
@@ -101,8 +147,7 @@
      */
     private long getEntryAt(int index) {
         assertBounds(index);
-        HotSpotVMConfig config = runtime().getConfig();
-        return unsafe.getAddress(metaspaceConstantPool + config.constantPoolSize + index * runtime().getTarget().wordSize);
+        return unsafe.getAddress(metaspaceConstantPool + runtime().getConfig().constantPoolSize + index * runtime().getTarget().wordSize);
     }
 
     /**
@@ -112,9 +157,8 @@
      * @return integer constant pool entry at index
      */
     private int getIntAt(int index) {
-        HotSpotVMConfig config = runtime().getConfig();
-        assertTag(index, config.jvmConstantInteger);
-        return unsafe.getInt(metaspaceConstantPool + config.constantPoolSize + index * runtime().getTarget().wordSize);
+        assertTag(index, JVM_CONSTANT.Integer);
+        return unsafe.getInt(metaspaceConstantPool + runtime().getConfig().constantPoolSize + index * runtime().getTarget().wordSize);
     }
 
     /**
@@ -124,9 +168,8 @@
      * @return long constant pool entry
      */
     private long getLongAt(int index) {
-        HotSpotVMConfig config = runtime().getConfig();
-        assertTag(index, config.jvmConstantLong);
-        return unsafe.getLong(metaspaceConstantPool + config.constantPoolSize + index * runtime().getTarget().wordSize);
+        assertTag(index, JVM_CONSTANT.Long);
+        return unsafe.getLong(metaspaceConstantPool + runtime().getConfig().constantPoolSize + index * runtime().getTarget().wordSize);
     }
 
     /**
@@ -136,9 +179,8 @@
      * @return float constant pool entry
      */
     private float getFloatAt(int index) {
-        HotSpotVMConfig config = runtime().getConfig();
-        assertTag(index, config.jvmConstantFloat);
-        return unsafe.getFloat(metaspaceConstantPool + config.constantPoolSize + index * runtime().getTarget().wordSize);
+        assertTag(index, JVM_CONSTANT.Float);
+        return unsafe.getFloat(metaspaceConstantPool + runtime().getConfig().constantPoolSize + index * runtime().getTarget().wordSize);
     }
 
     /**
@@ -148,9 +190,8 @@
      * @return float constant pool entry
      */
     private double getDoubleAt(int index) {
-        HotSpotVMConfig config = runtime().getConfig();
-        assertTag(index, config.jvmConstantDouble);
-        return unsafe.getDouble(metaspaceConstantPool + config.constantPoolSize + index * runtime().getTarget().wordSize);
+        assertTag(index, JVM_CONSTANT.Double);
+        return unsafe.getDouble(metaspaceConstantPool + runtime().getConfig().constantPoolSize + index * runtime().getTarget().wordSize);
     }
 
     /**
@@ -160,9 +201,8 @@
      * @return {@code JVM_CONSTANT_NameAndType} constant pool entry
      */
     private int getNameAndTypeAt(int index) {
-        HotSpotVMConfig config = runtime().getConfig();
-        assertTag(index, config.jvmConstantNameAndType);
-        return unsafe.getInt(metaspaceConstantPool + config.constantPoolSize + index * runtime().getTarget().wordSize);
+        assertTag(index, JVM_CONSTANT.NameAndType);
+        return unsafe.getInt(metaspaceConstantPool + runtime().getConfig().constantPoolSize + index * runtime().getTarget().wordSize);
     }
 
     /**
@@ -239,6 +279,20 @@
     }
 
     /**
+     * Gets the uncached klass reference index constant pool entry at index {@code index}. See:
+     * {@code ConstantPool::uncached_klass_ref_index_at}.
+     * 
+     * @param index constant pool index
+     * @return klass reference index
+     */
+    private int getUncachedKlassRefIndexAt(int index) {
+        assert getTagAt(index) == JVM_CONSTANT.Fieldref || getTagAt(index) == JVM_CONSTANT.MethodRef || getTagAt(index) == JVM_CONSTANT.InterfaceMethodref;
+        final int refIndex = unsafe.getInt(metaspaceConstantPool + runtime().getConfig().constantPoolSize + index * runtime().getTarget().wordSize);
+        // klass ref index is in the low 16-bits.
+        return refIndex & 0xFFFF;
+    }
+
+    /**
      * Asserts that the constant pool index {@code index} is in the bounds of the constant pool.
      * 
      * @param index constant pool index
@@ -253,115 +307,52 @@
      * @param index constant pool index
      * @param tag expected tag
      */
-    private void assertTag(int index, int tag) {
-        assert getTagAt(index) == tag : "constant pool tag at index " + index + " is " + getNameForTag(getTagAt(index)) + " but expected " + getNameForTag(tag);
-    }
-
-    private static String getNameForTag(int tag) {
-        HotSpotVMConfig config = runtime().getConfig();
-        if (tag == config.jvmConstantUtf8) {
-            return "JVM_CONSTANT_Utf8";
-        }
-        if (tag == config.jvmConstantInteger) {
-            return "JVM_CONSTANT_Integer";
-        }
-        if (tag == config.jvmConstantLong) {
-            return "JVM_CONSTANT_Long";
-        }
-        if (tag == config.jvmConstantFloat) {
-            return "JVM_CONSTANT_Float";
-        }
-        if (tag == config.jvmConstantDouble) {
-            return "JVM_CONSTANT_Double";
-        }
-        if (tag == config.jvmConstantClass) {
-            return "JVM_CONSTANT_Class";
-        }
-        if (tag == config.jvmConstantUnresolvedClass) {
-            return "JVM_CONSTANT_UnresolvedClass";
-        }
-        if (tag == config.jvmConstantUnresolvedClassInError) {
-            return "JVM_CONSTANT_UnresolvedClassInError";
-        }
-        if (tag == config.jvmConstantString) {
-            return "JVM_CONSTANT_String";
-        }
-        if (tag == config.jvmConstantFieldref) {
-            return "JVM_CONSTANT_Fieldref";
-        }
-        if (tag == config.jvmConstantMethodref) {
-            return "JVM_CONSTANT_Methodref";
-        }
-        if (tag == config.jvmConstantInterfaceMethodref) {
-            return "JVM_CONSTANT_InterfaceMethodref";
-        }
-        if (tag == config.jvmConstantNameAndType) {
-            return "JVM_CONSTANT_NameAndType";
-        }
-        if (tag == config.jvmConstantMethodHandle) {
-            return "JVM_CONSTANT_MethodHandle";
-        }
-        if (tag == config.jvmConstantMethodHandleInError) {
-            return "JVM_CONSTANT_MethodHandleInError";
-        }
-        if (tag == config.jvmConstantMethodType) {
-            return "JVM_CONSTANT_MethodType";
-        }
-        if (tag == config.jvmConstantMethodTypeInError) {
-            return "JVM_CONSTANT_MethodTypeInError";
-        }
-        return "unknown constant tag " + tag;
+    private void assertTag(int index, JVM_CONSTANT tag) {
+        assert getTagAt(index) == tag : "constant pool tag at index " + index + " is " + getTagAt(index) + " but expected " + tag;
     }
 
     @Override
     public int length() {
-        HotSpotVMConfig config = runtime().getConfig();
-        return unsafe.getInt(metaspaceConstantPool + config.constantPoolLengthOffset);
+        return unsafe.getInt(metaspaceConstantPool + runtime().getConfig().constantPoolLengthOffset);
     }
 
     @Override
     public Object lookupConstant(int cpi) {
         assert cpi != 0;
-
-        HotSpotVMConfig config = runtime().getConfig();
-        final int tag = getTagAt(cpi);
-
-        // Handle primitive constant pool entries directly.
-        if (tag == config.jvmConstantInteger) {
-            return Constant.forInt(getIntAt(cpi));
-        }
-        if (tag == config.jvmConstantLong) {
-            return Constant.forLong(getLongAt(cpi));
-        }
-        if (tag == config.jvmConstantFloat) {
-            return Constant.forFloat(getFloatAt(cpi));
-        }
-        if (tag == config.jvmConstantDouble) {
-            return Constant.forDouble(getDoubleAt(cpi));
+        final JVM_CONSTANT tag = getTagAt(cpi);
+        switch (tag) {
+            case Integer:
+                return Constant.forInt(getIntAt(cpi));
+            case Long:
+                return Constant.forLong(getLongAt(cpi));
+            case Float:
+                return Constant.forFloat(getFloatAt(cpi));
+            case Double:
+                return Constant.forDouble(getDoubleAt(cpi));
+            case Class:
+            case UnresolvedClass:
+            case UnresolvedClassInError:
+                final int opcode = -1;  // opcode is not used
+                return lookupType(cpi, opcode);
+            case String:
+                Object string = runtime().getCompilerToVM().resolvePossiblyCachedConstantInPool(metaspaceConstantPool, cpi);
+                return Constant.forObject(string);
+            case MethodHandle:
+            case MethodHandleInError:
+            case MethodType:
+            case MethodTypeInError:
+                Object obj = runtime().getCompilerToVM().resolveConstantInPool(metaspaceConstantPool, cpi);
+                return Constant.forObject(obj);
+            default:
+                throw GraalInternalError.shouldNotReachHere("unknown constant pool tag " + tag);
         }
-
-        // All the other constant pool entries need special attention so we call down into the VM.
-        if (tag == config.jvmConstantClass || tag == config.jvmConstantUnresolvedClass || tag == config.jvmConstantUnresolvedClassInError) {
-            final int opcode = -1;  // opcode is not used
-            return lookupType(cpi, opcode);
-        }
-        if (tag == config.jvmConstantString) {
-            Object string = runtime().getCompilerToVM().lookupConstantInPool(metaspaceConstantPool, cpi);
-            return Constant.forObject(string);
-        }
-        if (tag == config.jvmConstantMethodHandle || tag == config.jvmConstantMethodHandleInError || tag == config.jvmConstantMethodType || tag == config.jvmConstantMethodTypeInError) {
-            Object obj = runtime().getCompilerToVM().lookupConstantInPool(metaspaceConstantPool, cpi);
-            return Constant.forObject(obj);
-        }
-
-        throw GraalInternalError.shouldNotReachHere("unknown constant pool tag " + tag);
     }
 
     @Override
     public String lookupUtf8(int cpi) {
-        assertTag(cpi, runtime().getConfig().jvmConstantUtf8);
-        long signature = getEntryAt(cpi);
-        HotSpotSymbol symbol = new HotSpotSymbol(signature);
+        assertTag(cpi, JVM_CONSTANT.Utf8);
+        final long metaspaceSymbol = getEntryAt(cpi);
+        HotSpotSymbol symbol = new HotSpotSymbol(metaspaceSymbol);
         return symbol.asString();
     }
 
@@ -473,7 +464,37 @@
                 break;
             default:
                 index = toConstantPoolIndex(cpi, opcode);
+                index = runtime().getCompilerToVM().constantPoolRemapInstructionOperandFromCache(metaspaceConstantPool, index);
         }
-        runtime().getCompilerToVM().loadReferencedTypeInPool(metaspaceConstantPool, index, (byte) opcode);
+
+        JVM_CONSTANT tag = getTagAt(index);
+        switch (tag) {
+            case Fieldref:
+            case MethodRef:
+            case InterfaceMethodref:
+                index = getUncachedKlassRefIndexAt(index);
+                tag = getTagAt(index);
+                assert tag == JVM_CONSTANT.Class || tag == JVM_CONSTANT.UnresolvedClass || tag == JVM_CONSTANT.UnresolvedClassInError : tag;
+                break;
+            default:
+                // nothing
+                break;
+        }
+
+        switch (tag) {
+            case Class:
+            case UnresolvedClass:
+            case UnresolvedClassInError:
+                final long metaspaceKlass = runtime().getCompilerToVM().constantPoolKlassAt(metaspaceConstantPool, index);
+                HotSpotResolvedObjectType type = (HotSpotResolvedObjectType) HotSpotResolvedObjectType.fromMetaspaceKlass(metaspaceKlass);
+                Class<?> klass = type.mirror();
+                if (!klass.isPrimitive() && !klass.isArray()) {
+                    unsafe.ensureClassInitialized(klass);
+                }
+                break;
+            default:
+                // nothing
+                break;
+        }
     }
 }
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotLoweringProvider.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotLoweringProvider.java	Tue Mar 18 11:51:37 2014 -0700
@@ -700,9 +700,9 @@
 
     public int getScalingFactor(Kind kind) {
         if (useCompressedOops() && kind == Kind.Object) {
-            return this.runtime.getTarget().arch.getSizeInBytes(Kind.Int);
+            return this.runtime.getTarget().getSizeInBytes(Kind.Int);
         } else {
-            return this.runtime.getTarget().arch.getSizeInBytes(kind);
+            return this.runtime.getTarget().getSizeInBytes(kind);
         }
     }
 
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotMetaAccessProvider.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotMetaAccessProvider.java	Tue Mar 18 11:51:37 2014 -0700
@@ -299,7 +299,7 @@
                     ResolvedJavaType elementType = lookupJavaType.getComponentType();
                     Kind elementKind = elementType.getKind();
                     final int headerSize = HotSpotGraalRuntime.getArrayBaseOffset(elementKind);
-                    int sizeOfElement = HotSpotGraalRuntime.runtime().getTarget().arch.getSizeInBytes(elementKind);
+                    int sizeOfElement = HotSpotGraalRuntime.runtime().getTarget().getSizeInBytes(elementKind);
                     int alignment = HotSpotGraalRuntime.runtime().getTarget().wordSize;
                     int log2ElementSize = CodeUtil.log2(sizeOfElement);
                     return NewObjectSnippets.computeArrayAllocationSize(length, alignment, headerSize, log2ElementSize);
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotMethodData.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotMethodData.java	Tue Mar 18 11:51:37 2014 -0700
@@ -825,4 +825,12 @@
             super(runtime().getConfig().dataLayoutArgInfoDataTag, ARG_INFO_DATA_SIZE);
         }
     }
+
+    public void setCompiledGraphSize(int nodeCount) {
+        unsafe.putInt(metaspaceMethodData + config.methodDataGraalNodeCountOffset, nodeCount);
+    }
+
+    public int getCompiledGraphSize() {
+        return unsafe.getInt(metaspaceMethodData + config.methodDataGraalNodeCountOffset);
+    }
 }
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotNmethod.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotNmethod.java	Tue Mar 18 11:51:37 2014 -0700
@@ -43,7 +43,12 @@
 
     private static final long serialVersionUID = -1784683588947054103L;
 
+    /**
+     * This (indirect) Method* reference is safe since class redefinition preserves all methods
+     * associated with nmethods in the code cache.
+     */
     private final HotSpotResolvedJavaMethod method;
+
     private final boolean isDefault;
     private final boolean isExternal;
     private final String name;
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotProfilingInfo.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotProfilingInfo.java	Tue Mar 18 11:51:37 2014 -0700
@@ -25,6 +25,7 @@
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.debug.*;
 import com.oracle.graal.hotspot.*;
+import com.oracle.graal.nodes.*;
 
 public final class HotSpotProfilingInfo extends CompilerObject implements ProfilingInfo {
 
@@ -205,4 +206,21 @@
     public void setMature() {
         isMature = true;
     }
+
+    @Override
+    public boolean setCompilerIRSize(Class<?> irType, int size) {
+        if (irType == StructuredGraph.class) {
+            methodData.setCompiledGraphSize(size);
+            return true;
+        }
+        return false;
+    }
+
+    @Override
+    public int getCompilerIRSize(Class<?> irType) {
+        if (irType == StructuredGraph.class) {
+            return methodData.getCompiledGraphSize();
+        }
+        return -1;
+    }
 }
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotResolvedJavaMethod.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/meta/HotSpotResolvedJavaMethod.java	Tue Mar 18 11:51:37 2014 -0700
@@ -28,8 +28,6 @@
 
 import java.lang.annotation.*;
 import java.lang.reflect.*;
-import java.util.*;
-import java.util.concurrent.*;
 
 import com.oracle.graal.api.code.*;
 import com.oracle.graal.api.meta.*;
@@ -59,7 +57,6 @@
     private boolean forceInline;
     private boolean dontInline;
     private boolean ignoredBySecurityStackWalk;
-    private Map<Object, Object> compilerStorage;
     private HotSpotMethodData methodData;
     private byte[] code;
     private SpeculationLog speculationLog;
@@ -356,10 +353,6 @@
         return signature;
     }
 
-    public int getCompiledCodeSize() {
-        return runtime().getCompilerToVM().getCompiledCodeSize(metaspaceMethod);
-    }
-
     /**
      * Gets the value of {@code Method::_code}.
      * 
@@ -433,14 +426,6 @@
     }
 
     @Override
-    public Map<Object, Object> getCompilerStorage() {
-        if (compilerStorage == null) {
-            compilerStorage = new ConcurrentHashMap<>();
-        }
-        return compilerStorage;
-    }
-
-    @Override
     public ConstantPool getConstantPool() {
         return constantPool;
     }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/nodes/type/NarrowOopStamp.java	Tue Mar 18 11:51:37 2014 -0700
@@ -0,0 +1,148 @@
+/*
+ * Copyright (c) 2014, 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.hotspot.nodes.type;
+
+import com.oracle.graal.api.meta.*;
+import com.oracle.graal.hotspot.HotSpotVMConfig.CompressEncoding;
+import com.oracle.graal.nodes.spi.*;
+import com.oracle.graal.nodes.type.*;
+
+public class NarrowOopStamp extends ObjectStamp {
+
+    public static final PlatformKind NarrowOop = new PlatformKind() {
+
+        public String name() {
+            return "NarrowOop";
+        }
+
+        @Override
+        public String toString() {
+            return name();
+        }
+    };
+
+    private final CompressEncoding encoding;
+
+    public NarrowOopStamp(ObjectStamp stamp, CompressEncoding encoding) {
+        this(stamp.type(), stamp.isExactType(), stamp.nonNull(), stamp.alwaysNull(), encoding);
+    }
+
+    public NarrowOopStamp(ResolvedJavaType type, boolean exactType, boolean nonNull, boolean alwaysNull, CompressEncoding encoding) {
+        super(type, exactType, nonNull, alwaysNull);
+        this.encoding = encoding;
+    }
+
+    public Stamp uncompressed() {
+        return new ObjectStamp(type(), isExactType(), nonNull(), alwaysNull());
+    }
+
+    public CompressEncoding getEncoding() {
+        return encoding;
+    }
+
+    @Override
+    public Stamp unrestricted() {
+        return new NarrowOopStamp((ObjectStamp) super.unrestricted(), encoding);
+    }
+
+    @Override
+    public Kind getStackKind() {
+        return Kind.Object;
+    }
+
+    @Override
+    public PlatformKind getPlatformKind(LIRTypeTool tool) {
+        return NarrowOop;
+    }
+
+    @Override
+    public String toString() {
+        StringBuilder str = new StringBuilder();
+        str.append('n');
+        str.append(super.toString());
+        return str.toString();
+    }
+
+    @Override
+    public Stamp meet(Stamp otherStamp) {
+        if (this == otherStamp) {
+            return this;
+        }
+        if (otherStamp instanceof IllegalStamp) {
+            return otherStamp.meet(this);
+        }
+        if (!isCompatible(otherStamp)) {
+            return StampFactory.illegal(Kind.Illegal);
+        }
+        return new NarrowOopStamp((ObjectStamp) super.meet(otherStamp), encoding);
+    }
+
+    @Override
+    public Stamp join(Stamp otherStamp) {
+        if (this == otherStamp) {
+            return this;
+        }
+        if (otherStamp instanceof IllegalStamp) {
+            return otherStamp.join(this);
+        }
+        if (!isCompatible(otherStamp)) {
+            return StampFactory.illegal(Kind.Illegal);
+        }
+        return new NarrowOopStamp((ObjectStamp) super.join(otherStamp), encoding);
+    }
+
+    @Override
+    public boolean isCompatible(Stamp other) {
+        if (this == other) {
+            return true;
+        }
+        if (other instanceof NarrowOopStamp) {
+            NarrowOopStamp narrow = (NarrowOopStamp) other;
+            return encoding.equals(narrow.encoding);
+        }
+        return false;
+    }
+
+    @Override
+    public int hashCode() {
+        final int prime = 31;
+        int result = super.hashCode();
+        result = prime * result + encoding.hashCode();
+        return result;
+    }
+
+    @Override
+    public boolean equals(Object obj) {
+        if (this == obj) {
+            return true;
+        }
+        if (obj == null || getClass() != obj.getClass()) {
+            return false;
+        }
+        NarrowOopStamp other = (NarrowOopStamp) obj;
+        if (!encoding.equals(other.encoding)) {
+            return false;
+        }
+        return super.equals(other);
+    }
+}
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/phases/WriteBarrierVerificationPhase.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/phases/WriteBarrierVerificationPhase.java	Tue Mar 18 11:51:37 2014 -0700
@@ -73,11 +73,11 @@
             Node currentNode = iterator.next();
             assert !isSafepoint(currentNode) : "Write barrier must be present " + write;
             if (useG1GC()) {
-                if (!(currentNode instanceof G1PostWriteBarrier) || ((currentNode instanceof G1PostWriteBarrier) && !validateBarrier((FixedAccessNode) write, (WriteBarrier) currentNode))) {
+                if (!(currentNode instanceof G1PostWriteBarrier) || (!validateBarrier((FixedAccessNode) write, (WriteBarrier) currentNode))) {
                     expandFrontier(frontier, currentNode);
                 }
             } else {
-                if (!(currentNode instanceof SerialWriteBarrier) || ((currentNode instanceof SerialWriteBarrier) && !validateBarrier((FixedAccessNode) write, (WriteBarrier) currentNode)) ||
+                if (!(currentNode instanceof SerialWriteBarrier) || (!validateBarrier((FixedAccessNode) write, (WriteBarrier) currentNode)) ||
                                 ((currentNode instanceof SerialWriteBarrier) && !validateBarrier((FixedAccessNode) write, (WriteBarrier) currentNode))) {
                     expandFrontier(frontier, currentNode);
                 }
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/stubs/ExceptionHandlerStub.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/stubs/ExceptionHandlerStub.java	Tue Mar 18 11:51:37 2014 -0700
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2012, 2014, 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
@@ -31,16 +31,16 @@
 import com.oracle.graal.graph.Node.ConstantNodeParameter;
 import com.oracle.graal.graph.Node.NodeIntrinsic;
 import com.oracle.graal.hotspot.*;
-import com.oracle.graal.hotspot.bridge.*;
 import com.oracle.graal.hotspot.meta.*;
+import com.oracle.graal.hotspot.meta.HotSpotCodeCacheProvider.MarkId;
 import com.oracle.graal.hotspot.nodes.*;
 import com.oracle.graal.replacements.*;
 import com.oracle.graal.replacements.Snippet.*;
 import com.oracle.graal.word.*;
 
 /**
- * Stub called by the {@linkplain Marks#MARK_EXCEPTION_HANDLER_ENTRY exception handler entry point}
- * in a compiled method. This entry point is used when returning to a method to handle an exception
+ * Stub called by the {@linkplain MarkId#EXCEPTION_HANDLER_ENTRY exception handler entry point} in a
+ * compiled method. This entry point is used when returning to a method to handle an exception
  * thrown by a callee. It is not used for routing implicit exceptions. Therefore, it does not need
  * to save any registers as HotSpot uses a caller save convention.
  * <p>
--- a/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/stubs/Stub.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hotspot/src/com/oracle/graal/hotspot/stubs/Stub.java	Tue Mar 18 11:51:37 2014 -0700
@@ -153,7 +153,7 @@
                 try (Scope s = Debug.scope("CodeInstall")) {
                     Stub stub = Stub.this;
                     HotSpotRuntimeStub installedCode = new HotSpotRuntimeStub(stub);
-                    HotSpotCompiledCode hsCompResult = new HotSpotCompiledRuntimeStub(backend.getTarget().arch, stub, compResult);
+                    HotSpotCompiledCode hsCompResult = new HotSpotCompiledRuntimeStub(backend.getTarget(), stub, compResult);
 
                     CodeInstallResult result = runtime().getCompilerToVM().installCode(hsCompResult, installedCode, null);
                     if (result != CodeInstallResult.OK) {
--- a/graal/com.oracle.graal.hsail/src/com/oracle/graal/hsail/HSAIL.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hsail/src/com/oracle/graal/hsail/HSAIL.java	Tue Mar 18 11:51:37 2014 -0700
@@ -168,7 +168,7 @@
         Kind kind = arg.getKind();
         if (kind == Kind.Double || kind == Kind.Long) {
             regPrefix = "$d";
-        } else if (kind == Kind.Int || kind == Kind.Float || kind == Kind.NarrowOop) {
+        } else if (kind == Kind.Int || kind == Kind.Float) {
             regPrefix = "$s";
         } else {
             regPrefix = "$d";
@@ -193,7 +193,6 @@
                 case Int:
                 case Long:
                 case Object:
-                case NarrowOop:
                     return true;
             }
         } else if (category == FPU) {
--- a/graal/com.oracle.graal.hsail/src/com/oracle/graal/hsail/HSAILRegisterConfig.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.hsail/src/com/oracle/graal/hsail/HSAILRegisterConfig.java	Tue Mar 18 11:51:37 2014 -0700
@@ -123,7 +123,7 @@
 
             if (locations[i] == null) {
                 locations[i] = StackSlot.get(kind.getStackKind(), currentStackOffset, !type.out);
-                currentStackOffset += Math.max(target.arch.getSizeInBytes(kind), target.wordSize);
+                currentStackOffset += Math.max(target.getSizeInBytes(kind), target.wordSize);
             }
         }
 
@@ -150,7 +150,6 @@
             case Short:
             case Byte:
             case Float:
-            case NarrowOop:
                 return regBitness32.clone();
             case Long:
             case Double:
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.java.decompiler.test/src/com/oracle/graal/java/decompiler/test/DecompilerTest.java	Tue Mar 18 11:51:37 2014 -0700
@@ -0,0 +1,111 @@
+/*
+ * 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.java.decompiler.test;
+
+import java.lang.reflect.*;
+
+import org.junit.*;
+
+import com.oracle.graal.api.meta.*;
+import com.oracle.graal.api.runtime.*;
+import com.oracle.graal.java.decompiler.test.example.*;
+import com.oracle.graal.printer.*;
+import com.oracle.graal.runtime.*;
+
+@Ignore
+public class DecompilerTest {
+
+    public static void doTest(String name) {
+        try {
+            DebugEnvironment.initialize(System.out);
+            MetaAccessProvider metaAccess = Graal.getRequiredCapability(RuntimeProvider.class).getHostBackend().getProviders().getMetaAccess();
+            Method method = Example.class.getDeclaredMethod(name, new Class[]{int.class, int.class});
+            final ResolvedJavaMethod javaMethod = metaAccess.lookupJavaMethod(method);
+            TestUtil.compileMethod(javaMethod);
+        } catch (NoSuchMethodException e) {
+            Assert.fail();
+        } catch (SecurityException e) {
+            Assert.fail();
+        }
+    }
+
+    @Test
+    public void test01() {
+        doTest("loop7");
+    }
+
+    @Test
+    public void test02() {
+        doTest("loop6");
+    }
+
+    @Test
+    public void test03() {
+        doTest("loop5");
+    }
+
+    @Test
+    public void test04() {
+        doTest("loop4");
+    }
+
+    @Test
+    public void test05() {
+        doTest("loop3");
+    }
+
+    @Test
+    public void test06() {
+        doTest("loop2");
+    }
+
+    @Test
+    public void test07() {
+        doTest("loop");
+    }
+
+    @Test
+    public void test08() {
+        doTest("if0");
+    }
+
+    @Test
+    public void test09() {
+        doTest("if1");
+    }
+
+    @Test
+    public void test10() {
+        doTest("if2");
+    }
+
+    @Test
+    public void test11() {
+        doTest("if3");
+    }
+
+    @Test
+    public void test12() {
+        doTest("if4");
+    }
+}
--- a/graal/com.oracle.graal.java.decompiler.test/src/com/oracle/graal/java/decompiler/test/Test.java	Tue Mar 18 11:07:47 2014 -0700
+++ /dev/null	Thu Jan 01 00:00:00 1970 +0000
@@ -1,47 +0,0 @@
-/*
- * 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.java.decompiler.test;
-
-import java.lang.reflect.*;
-
-import com.oracle.graal.api.meta.*;
-import com.oracle.graal.api.runtime.*;
-import com.oracle.graal.java.decompiler.test.example.*;
-import com.oracle.graal.printer.*;
-import com.oracle.graal.runtime.*;
-
-public class Test {
-
-    /**
-     * @param args
-     * @throws SecurityException
-     * @throws NoSuchMethodException
-     */
-    public static void main(String[] args) throws NoSuchMethodException, SecurityException {
-        DebugEnvironment.initialize(System.out);
-        MetaAccessProvider metaAccess = Graal.getRequiredCapability(RuntimeProvider.class).getHostBackend().getProviders().getMetaAccess();
-        Method method = Example.class.getDeclaredMethod("loop7", new Class[]{int.class, int.class});
-        final ResolvedJavaMethod javaMethod = metaAccess.lookupJavaMethod(method);
-        TestUtil.compileMethod(javaMethod);
-    }
-}
--- a/graal/com.oracle.graal.java.decompiler.test/src/com/oracle/graal/java/decompiler/test/TestUtil.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.java.decompiler.test/src/com/oracle/graal/java/decompiler/test/TestUtil.java	Tue Mar 18 11:51:37 2014 -0700
@@ -24,6 +24,7 @@
 
 import static com.oracle.graal.api.code.CodeUtil.*;
 import static com.oracle.graal.compiler.GraalCompiler.*;
+
 import com.oracle.graal.api.code.*;
 import com.oracle.graal.api.code.CallingConvention.Type;
 import com.oracle.graal.api.meta.*;
--- a/graal/com.oracle.graal.java.decompiler/src/com/oracle/graal/java/decompiler/DecompilerIfSimplify.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.java.decompiler/src/com/oracle/graal/java/decompiler/DecompilerIfSimplify.java	Tue Mar 18 11:51:37 2014 -0700
@@ -68,7 +68,7 @@
                         // TODO(mg)
                         // thenBlocks and elseBlocks can be both empty --> causes an AssertionError
                         DecompilerIfBlock ifBlock = new DecompilerIfBlock(block.getBlock(), decompiler, thenBlocks, elseBlocks, infoStream);
-                        if (thenBlocks.contains(block.getBlock()) || elseBlocks.contains(block.getBlock())) {
+                        if (thenBlocks.contains(block) || elseBlocks.contains(block)) {
                             throw new AssertionError();
                         }
                         blocks.add(ifBlock);
--- a/graal/com.oracle.graal.java.decompiler/src/com/oracle/graal/java/decompiler/block/DecompilerIfBlock.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.java.decompiler/src/com/oracle/graal/java/decompiler/block/DecompilerIfBlock.java	Tue Mar 18 11:51:37 2014 -0700
@@ -158,7 +158,20 @@
 
     @Override
     public boolean contains(Block b) {
-        return b == block || thenBranch.contains(b) || elseBranch.contains(b);
+        if (b == block) {
+            return true;
+        }
+        for (DecompilerBlock i : thenBranch) {
+            if (i.block == b) {
+                return true;
+            }
+        }
+        for (DecompilerBlock i : elseBranch) {
+            if (i.block == b) {
+                return true;
+            }
+        }
+        return false;
     }
 
     @Override
--- a/graal/com.oracle.graal.java/src/com/oracle/graal/java/BciBlockMapping.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.java/src/com/oracle/graal/java/BciBlockMapping.java	Tue Mar 18 11:51:37 2014 -0700
@@ -99,11 +99,6 @@
         public Block retSuccessor;
         public boolean endsWithRet = false;
 
-        public BitSet localsLiveIn;
-        public BitSet localsLiveOut;
-        private BitSet localsLiveGen;
-        private BitSet localsLiveKill;
-
         public Block exceptionDispatchBlock() {
             if (successors.size() > 0 && successors.get(successors.size() - 1) instanceof ExceptionDispatchBlock) {
                 return successors.get(successors.size() - 1);
@@ -167,6 +162,8 @@
     private Block[] blockMap;
     public Block[] loopHeaders;
 
+    public LocalLiveness liveness;
+
     /**
      * Creates a new BlockMap instance from bytecode of the given method .
      * 
@@ -212,7 +209,8 @@
         }
         if (OptLivenessAnalysis.getValue()) {
             try (Scope s = Debug.scope("LivenessAnalysis")) {
-                computeLiveness();
+                liveness = method.getMaxLocals() <= 64 ? new SmallLocalLiveness() : new LargeLocalLiveness();
+                liveness.computeLiveness();
             } catch (Throwable e) {
                 throw Debug.handle(e);
             }
@@ -729,153 +727,225 @@
         return loops;
     }
 
-    private void computeLiveness() {
-        for (Block block : blocks) {
-            computeLocalLiveness(block);
-        }
+    /**
+     * Encapsulates the liveness calculation, so that subclasses for locals <= 64 and locals > 64
+     * can be implemented.
+     */
+    public abstract class LocalLiveness {
+
+        private void computeLiveness() {
+            for (Block block : blocks) {
+                computeLocalLiveness(block);
+            }
 
-        boolean changed;
-        int iteration = 0;
-        do {
-            Debug.log("Iteration %d", iteration);
-            changed = false;
-            for (int i = blocks.size() - 1; i >= 0; i--) {
-                Block block = blocks.get(i);
-                Debug.log("  start B%d  [%d, %d]  in: %s  out: %s  gen: %s  kill: %s", block.blockID, block.startBci, block.endBci, block.localsLiveIn, block.localsLiveOut, block.localsLiveGen,
-                                block.localsLiveKill);
+            boolean changed;
+            int iteration = 0;
+            do {
+                Debug.log("Iteration %d", iteration);
+                changed = false;
+                for (int i = blocks.size() - 1; i >= 0; i--) {
+                    Block block = blocks.get(i);
+                    int blockID = block.blockID;
+                    // log statements in IFs because debugLiveX creates a new String
+                    if (Debug.isLogEnabled()) {
+                        Debug.log("  start B%d  [%d, %d]  in: %s  out: %s  gen: %s  kill: %s", block.blockID, block.startBci, block.endBci, debugLiveIn(blockID), debugLiveOut(blockID),
+                                        debugLiveGen(blockID), debugLiveKill(blockID));
+                    }
 
-                boolean blockChanged = (iteration == 0);
-                if (block.successors.size() > 0) {
-                    int oldCardinality = block.localsLiveOut.cardinality();
-                    for (Block sux : block.successors) {
-                        Debug.log("    Successor B%d: %s", sux.blockID, sux.localsLiveIn);
-                        block.localsLiveOut.or(sux.localsLiveIn);
+                    boolean blockChanged = (iteration == 0);
+                    if (block.successors.size() > 0) {
+                        int oldCardinality = liveOutCardinality(blockID);
+                        for (Block sux : block.successors) {
+                            if (Debug.isLogEnabled()) {
+                                Debug.log("    Successor B%d: %s", sux.blockID, debugLiveIn(sux.blockID));
+                            }
+                            propagateLiveness(blockID, sux.blockID);
+                        }
+                        blockChanged |= (oldCardinality != liveOutCardinality(blockID));
                     }
-                    blockChanged |= (oldCardinality != block.localsLiveOut.cardinality());
+
+                    if (blockChanged) {
+                        updateLiveness(blockID);
+                        if (Debug.isLogEnabled()) {
+                            Debug.log("  end   B%d  [%d, %d]  in: %s  out: %s  gen: %s  kill: %s", block.blockID, block.startBci, block.endBci, debugLiveIn(blockID), debugLiveOut(blockID),
+                                            debugLiveGen(blockID), debugLiveKill(blockID));
+                        }
+                    }
+                    changed |= blockChanged;
                 }
-
-                if (blockChanged) {
-                    block.localsLiveIn.clear();
-                    block.localsLiveIn.or(block.localsLiveOut);
-                    block.localsLiveIn.andNot(block.localsLiveKill);
-                    block.localsLiveIn.or(block.localsLiveGen);
-                    Debug.log("  end   B%d  [%d, %d]  in: %s  out: %s  gen: %s  kill: %s", block.blockID, block.startBci, block.endBci, block.localsLiveIn, block.localsLiveOut, block.localsLiveGen,
-                                    block.localsLiveKill);
-                }
-                changed |= blockChanged;
-            }
-            iteration++;
-        } while (changed);
-    }
-
-    private void computeLocalLiveness(Block block) {
-        block.localsLiveIn = new BitSet(method.getMaxLocals());
-        block.localsLiveOut = new BitSet(method.getMaxLocals());
-        block.localsLiveGen = new BitSet(method.getMaxLocals());
-        block.localsLiveKill = new BitSet(method.getMaxLocals());
-
-        if (block.startBci < 0 || block.endBci < 0) {
-            return;
+                iteration++;
+            } while (changed);
         }
 
-        stream.setBCI(block.startBci);
-        while (stream.currentBCI() <= block.endBci) {
-            switch (stream.currentBC()) {
-                case LLOAD:
-                case DLOAD:
-                    loadTwo(block, stream.readLocalIndex());
-                    break;
-                case LLOAD_0:
-                case DLOAD_0:
-                    loadTwo(block, 0);
-                    break;
-                case LLOAD_1:
-                case DLOAD_1:
-                    loadTwo(block, 1);
-                    break;
-                case LLOAD_2:
-                case DLOAD_2:
-                    loadTwo(block, 2);
-                    break;
-                case LLOAD_3:
-                case DLOAD_3:
-                    loadTwo(block, 3);
-                    break;
-                case ILOAD:
-                case IINC:
-                case FLOAD:
-                case ALOAD:
-                case RET:
-                    loadOne(block, stream.readLocalIndex());
-                    break;
-                case ILOAD_0:
-                case FLOAD_0:
-                case ALOAD_0:
-                    loadOne(block, 0);
-                    break;
-                case ILOAD_1:
-                case FLOAD_1:
-                case ALOAD_1:
-                    loadOne(block, 1);
-                    break;
-                case ILOAD_2:
-                case FLOAD_2:
-                case ALOAD_2:
-                    loadOne(block, 2);
-                    break;
-                case ILOAD_3:
-                case FLOAD_3:
-                case ALOAD_3:
-                    loadOne(block, 3);
-                    break;
+        /**
+         * Returns whether the local is live at the beginning of the given block.
+         */
+        public abstract boolean localIsLiveIn(Block block, int local);
+
+        /**
+         * Returns whether the local is live at the end of the given block.
+         */
+        public abstract boolean localIsLiveOut(Block block, int local);
+
+        /**
+         * Returns a string representation of the liveIn values of the given block.
+         */
+        protected abstract String debugLiveIn(int blockID);
+
+        /**
+         * Returns a string representation of the liveOut values of the given block.
+         */
+        protected abstract String debugLiveOut(int blockID);
+
+        /**
+         * Returns a string representation of the liveGen values of the given block.
+         */
+        protected abstract String debugLiveGen(int blockID);
+
+        /**
+         * Returns a string representation of the liveKill values of the given block.
+         */
+        protected abstract String debugLiveKill(int blockID);
+
+        /**
+         * Returns the number of live locals at the end of the given block.
+         */
+        protected abstract int liveOutCardinality(int blockID);
+
+        /**
+         * Adds all locals the are in the liveIn of the successor to the liveOut of the block.
+         */
+        protected abstract void propagateLiveness(int blockID, int successorID);
+
+        /**
+         * Calculates a new liveIn for the given block from liveOut, liveKill and liveGen.
+         */
+        protected abstract void updateLiveness(int blockID);
+
+        /**
+         * Adds the local to liveGen if it wasn't already killed in this block.
+         */
+        protected abstract void loadOne(int blockID, int local);
+
+        /**
+         * Add this local to liveKill if it wasn't already generated in this block.
+         */
+        protected abstract void storeOne(int blockID, int local);
 
-                case LSTORE:
-                case DSTORE:
-                    storeTwo(block, stream.readLocalIndex());
-                    break;
-                case LSTORE_0:
-                case DSTORE_0:
-                    storeTwo(block, 0);
-                    break;
-                case LSTORE_1:
-                case DSTORE_1:
-                    storeTwo(block, 1);
-                    break;
-                case LSTORE_2:
-                case DSTORE_2:
-                    storeTwo(block, 2);
-                    break;
-                case LSTORE_3:
-                case DSTORE_3:
-                    storeTwo(block, 3);
-                    break;
-                case ISTORE:
-                case FSTORE:
-                case ASTORE:
-                    storeOne(block, stream.readLocalIndex());
-                    break;
-                case ISTORE_0:
-                case FSTORE_0:
-                case ASTORE_0:
-                    storeOne(block, 0);
-                    break;
-                case ISTORE_1:
-                case FSTORE_1:
-                case ASTORE_1:
-                    storeOne(block, 1);
-                    break;
-                case ISTORE_2:
-                case FSTORE_2:
-                case ASTORE_2:
-                    storeOne(block, 2);
-                    break;
-                case ISTORE_3:
-                case FSTORE_3:
-                case ASTORE_3:
-                    storeOne(block, 3);
-                    break;
+        private void computeLocalLiveness(Block block) {
+            if (block.startBci < 0 || block.endBci < 0) {
+                return;
             }
-            stream.next();
+            int blockID = block.blockID;
+            stream.setBCI(block.startBci);
+            while (stream.currentBCI() <= block.endBci) {
+                switch (stream.currentBC()) {
+                    case LLOAD:
+                    case DLOAD:
+                        loadTwo(blockID, stream.readLocalIndex());
+                        break;
+                    case LLOAD_0:
+                    case DLOAD_0:
+                        loadTwo(blockID, 0);
+                        break;
+                    case LLOAD_1:
+                    case DLOAD_1:
+                        loadTwo(blockID, 1);
+                        break;
+                    case LLOAD_2:
+                    case DLOAD_2:
+                        loadTwo(blockID, 2);
+                        break;
+                    case LLOAD_3:
+                    case DLOAD_3:
+                        loadTwo(blockID, 3);
+                        break;
+                    case ILOAD:
+                    case IINC:
+                    case FLOAD:
+                    case ALOAD:
+                    case RET:
+                        loadOne(blockID, stream.readLocalIndex());
+                        break;
+                    case ILOAD_0:
+                    case FLOAD_0:
+                    case ALOAD_0:
+                        loadOne(blockID, 0);
+                        break;
+                    case ILOAD_1:
+                    case FLOAD_1:
+                    case ALOAD_1:
+                        loadOne(blockID, 1);
+                        break;
+                    case ILOAD_2:
+                    case FLOAD_2:
+                    case ALOAD_2:
+                        loadOne(blockID, 2);
+                        break;
+                    case ILOAD_3:
+                    case FLOAD_3:
+                    case ALOAD_3:
+                        loadOne(blockID, 3);
+                        break;
+
+                    case LSTORE:
+                    case DSTORE:
+                        storeTwo(blockID, stream.readLocalIndex());
+                        break;
+                    case LSTORE_0:
+                    case DSTORE_0:
+                        storeTwo(blockID, 0);
+                        break;
+                    case LSTORE_1:
+                    case DSTORE_1:
+                        storeTwo(blockID, 1);
+                        break;
+                    case LSTORE_2:
+                    case DSTORE_2:
+                        storeTwo(blockID, 2);
+                        break;
+                    case LSTORE_3:
+                    case DSTORE_3:
+                        storeTwo(blockID, 3);
+                        break;
+                    case ISTORE:
+                    case FSTORE:
+                    case ASTORE:
+                        storeOne(blockID, stream.readLocalIndex());
+                        break;
+                    case ISTORE_0:
+                    case FSTORE_0:
+                    case ASTORE_0:
+                        storeOne(blockID, 0);
+                        break;
+                    case ISTORE_1:
+                    case FSTORE_1:
+                    case ASTORE_1:
+                        storeOne(blockID, 1);
+                        break;
+                    case ISTORE_2:
+                    case FSTORE_2:
+                    case ASTORE_2:
+                        storeOne(blockID, 2);
+                        break;
+                    case ISTORE_3:
+                    case FSTORE_3:
+                    case ASTORE_3:
+                        storeOne(blockID, 3);
+                        break;
+                }
+                stream.next();
+            }
+        }
+
+        private void loadTwo(int blockID, int local) {
+            loadOne(blockID, local);
+            loadOne(blockID, local + 1);
+        }
+
+        private void storeTwo(int blockID, int local) {
+            storeOne(blockID, local);
+            storeOne(blockID, local + 1);
         }
     }
 
@@ -889,25 +959,182 @@
         return map;
     }
 
-    private static void loadTwo(Block block, int local) {
-        loadOne(block, local);
-        loadOne(block, local + 1);
-    }
+    public final class SmallLocalLiveness extends LocalLiveness {
+        /*
+         * local n is represented by the bit accessible as (1 << n)
+         */
+
+        private final long[] localsLiveIn;
+        private final long[] localsLiveOut;
+        private final long[] localsLiveGen;
+        private final long[] localsLiveKill;
+
+        public SmallLocalLiveness() {
+            localsLiveIn = new long[blocks.size()];
+            localsLiveOut = new long[blocks.size()];
+            localsLiveGen = new long[blocks.size()];
+            localsLiveKill = new long[blocks.size()];
+        }
+
+        private String debugString(long value) {
+            StringBuilder str = new StringBuilder("{");
+            long current = value;
+            for (int i = 0; i < method.getMaxLocals(); i++) {
+                if ((current & 1L) == 1L) {
+                    if (str.length() > 1) {
+                        str.append(", ");
+                    }
+                    str.append(i);
+                }
+                current >>= 1;
+            }
+            return str.append('}').toString();
+        }
+
+        @Override
+        protected String debugLiveIn(int blockID) {
+            return debugString(localsLiveIn[blockID]);
+        }
+
+        @Override
+        protected String debugLiveOut(int blockID) {
+            return debugString(localsLiveOut[blockID]);
+        }
+
+        @Override
+        protected String debugLiveGen(int blockID) {
+            return debugString(localsLiveGen[blockID]);
+        }
 
-    private static void loadOne(Block block, int local) {
-        if (!block.localsLiveKill.get(local)) {
-            block.localsLiveGen.set(local);
+        @Override
+        protected String debugLiveKill(int blockID) {
+            return debugString(localsLiveKill[blockID]);
+        }
+
+        @Override
+        protected int liveOutCardinality(int blockID) {
+            return Long.bitCount(localsLiveOut[blockID]);
+        }
+
+        @Override
+        protected void propagateLiveness(int blockID, int successorID) {
+            localsLiveOut[blockID] |= localsLiveIn[successorID];
+        }
+
+        @Override
+        protected void updateLiveness(int blockID) {
+            localsLiveIn[blockID] = (localsLiveOut[blockID] & ~localsLiveKill[blockID]) | localsLiveGen[blockID];
+        }
+
+        @Override
+        protected void loadOne(int blockID, int local) {
+            long bit = 1L << local;
+            if ((localsLiveKill[blockID] & bit) == 0L) {
+                localsLiveGen[blockID] |= bit;
+            }
+        }
+
+        @Override
+        protected void storeOne(int blockID, int local) {
+            long bit = 1L << local;
+            if ((localsLiveGen[blockID] & bit) == 0L) {
+                localsLiveKill[blockID] |= bit;
+            }
+        }
+
+        @Override
+        public boolean localIsLiveIn(Block block, int local) {
+            int blockID = block.blockID;
+            return blockID >= Integer.MAX_VALUE ? false : (localsLiveIn[blockID] & (1L << local)) != 0L;
+        }
+
+        @Override
+        public boolean localIsLiveOut(Block block, int local) {
+            int blockID = block.blockID;
+            return blockID >= Integer.MAX_VALUE ? false : (localsLiveOut[blockID] & (1L << local)) != 0L;
         }
     }
 
-    private static void storeTwo(Block block, int local) {
-        storeOne(block, local);
-        storeOne(block, local + 1);
-    }
+    public final class LargeLocalLiveness extends LocalLiveness {
+        private BitSet[] localsLiveIn;
+        private BitSet[] localsLiveOut;
+        private BitSet[] localsLiveGen;
+        private BitSet[] localsLiveKill;
+
+        public LargeLocalLiveness() {
+            localsLiveIn = new BitSet[blocks.size()];
+            localsLiveOut = new BitSet[blocks.size()];
+            localsLiveGen = new BitSet[blocks.size()];
+            localsLiveKill = new BitSet[blocks.size()];
+            for (int i = 0; i < blocks.size(); i++) {
+                localsLiveIn[i] = new BitSet(method.getMaxLocals());
+                localsLiveOut[i] = new BitSet(method.getMaxLocals());
+                localsLiveGen[i] = new BitSet(method.getMaxLocals());
+                localsLiveKill[i] = new BitSet(method.getMaxLocals());
+            }
+        }
+
+        @Override
+        protected String debugLiveIn(int blockID) {
+            return localsLiveIn[blockID].toString();
+        }
+
+        @Override
+        protected String debugLiveOut(int blockID) {
+            return localsLiveOut[blockID].toString();
+        }
+
+        @Override
+        protected String debugLiveGen(int blockID) {
+            return localsLiveGen[blockID].toString();
+        }
+
+        @Override
+        protected String debugLiveKill(int blockID) {
+            return localsLiveKill[blockID].toString();
+        }
 
-    private static void storeOne(Block block, int local) {
-        if (!block.localsLiveGen.get(local)) {
-            block.localsLiveKill.set(local);
+        @Override
+        protected int liveOutCardinality(int blockID) {
+            return localsLiveOut[blockID].cardinality();
+        }
+
+        @Override
+        protected void propagateLiveness(int blockID, int successorID) {
+            localsLiveOut[blockID].or(localsLiveIn[successorID]);
+        }
+
+        @Override
+        protected void updateLiveness(int blockID) {
+            BitSet liveIn = localsLiveIn[blockID];
+            liveIn.clear();
+            liveIn.or(localsLiveOut[blockID]);
+            liveIn.andNot(localsLiveKill[blockID]);
+            liveIn.or(localsLiveGen[blockID]);
+        }
+
+        @Override
+        protected void loadOne(int blockID, int local) {
+            if (!localsLiveKill[blockID].get(local)) {
+                localsLiveGen[blockID].set(local);
+            }
+        }
+
+        @Override
+        protected void storeOne(int blockID, int local) {
+            if (!localsLiveGen[blockID].get(local)) {
+                localsLiveKill[blockID].set(local);
+            }
+        }
+
+        @Override
+        public boolean localIsLiveIn(Block block, int local) {
+            return block.blockID >= Integer.MAX_VALUE ? true : localsLiveIn[block.blockID].get(local);
+        }
+
+        @Override
+        public boolean localIsLiveOut(Block block, int local) {
+            return block.blockID >= Integer.MAX_VALUE ? true : localsLiveOut[block.blockID].get(local);
         }
     }
 }
--- a/graal/com.oracle.graal.java/src/com/oracle/graal/java/FrameStateBuilder.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.java/src/com/oracle/graal/java/FrameStateBuilder.java	Tue Mar 18 11:51:37 2014 -0700
@@ -32,6 +32,8 @@
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.debug.*;
 import com.oracle.graal.graph.Node.Verbosity;
+import com.oracle.graal.java.BciBlockMapping.Block;
+import com.oracle.graal.java.BciBlockMapping.LocalLiveness;
 import com.oracle.graal.nodes.*;
 import com.oracle.graal.nodes.calc.*;
 import com.oracle.graal.nodes.java.*;
@@ -203,7 +205,7 @@
                 return null;
             }
 
-            PhiNode phi = graph.addWithoutUnique(new PhiNode(currentValue.kind(), block));
+            PhiNode phi = graph.addWithoutUnique(new PhiNode(currentValue.stamp().unrestricted(), block));
             for (int i = 0; i < block.phiPredecessorCount(); i++) {
                 phi.addInput(currentValue);
             }
@@ -301,7 +303,7 @@
         }
         assert !block.isPhiAtMerge(value) : "phi function for this block already created";
 
-        PhiNode phi = graph.addWithoutUnique(new PhiNode(value.kind(), block));
+        PhiNode phi = graph.addWithoutUnique(new PhiNode(value.stamp().unrestricted(), block));
         phi.addInput(value);
         return phi;
     }
@@ -315,13 +317,21 @@
         }
     }
 
-    public void clearNonLiveLocals(BitSet liveness) {
+    public void clearNonLiveLocals(Block block, LocalLiveness liveness, boolean liveIn) {
         if (liveness == null) {
             return;
         }
-        for (int i = 0; i < locals.length; i++) {
-            if (!liveness.get(i)) {
-                locals[i] = null;
+        if (liveIn) {
+            for (int i = 0; i < locals.length; i++) {
+                if (!liveness.localIsLiveIn(block, i)) {
+                    locals[i] = null;
+                }
+            }
+        } else {
+            for (int i = 0; i < locals.length; i++) {
+                if (!liveness.localIsLiveOut(block, i)) {
+                    locals[i] = null;
+                }
             }
         }
     }
--- a/graal/com.oracle.graal.java/src/com/oracle/graal/java/GraphBuilderPhase.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.java/src/com/oracle/graal/java/GraphBuilderPhase.java	Tue Mar 18 11:51:37 2014 -0700
@@ -42,6 +42,7 @@
 import com.oracle.graal.graph.*;
 import com.oracle.graal.java.BciBlockMapping.Block;
 import com.oracle.graal.java.BciBlockMapping.ExceptionDispatchBlock;
+import com.oracle.graal.java.BciBlockMapping.LocalLiveness;
 import com.oracle.graal.nodes.*;
 import com.oracle.graal.nodes.calc.*;
 import com.oracle.graal.nodes.calc.FloatConvertNode.FloatConvert;
@@ -69,7 +70,7 @@
     public static final class RuntimeCalls {
 
         public static final ForeignCallDescriptor CREATE_NULL_POINTER_EXCEPTION = new ForeignCallDescriptor("createNullPointerException", NullPointerException.class);
-        public static final ForeignCallDescriptor CREATE_OUT_OF_BOUNDS_EXCEPTION = new ForeignCallDescriptor("createOutOfBoundsException", IndexOutOfBoundsException.class, int.class);
+        public static final ForeignCallDescriptor CREATE_OUT_OF_BOUNDS_EXCEPTION = new ForeignCallDescriptor("createOutOfBoundsException", ArrayIndexOutOfBoundsException.class, int.class);
     }
 
     /**
@@ -159,6 +160,7 @@
         }
 
         private Block[] loopHeaders;
+        private LocalLiveness liveness;
 
         /**
          * Gets the current frame state being processed by this builder.
@@ -225,6 +227,7 @@
             // compute the block map, setup exception handlers and get the entrypoint(s)
             BciBlockMapping blockMap = BciBlockMapping.create(method);
             loopHeaders = blockMap.loopHeaders;
+            liveness = blockMap.liveness;
 
             lastInstr = currentGraph.start();
             if (isSynchronized(method.getModifiers())) {
@@ -233,7 +236,7 @@
                 methodSynchronizedObject = synchronizedObject(frameState, method);
                 lastInstr = genMonitorEnter(methodSynchronizedObject);
             }
-            frameState.clearNonLiveLocals(blockMap.startBlock.localsLiveIn);
+            frameState.clearNonLiveLocals(blockMap.startBlock, liveness, true);
             ((StateSplit) lastInstr).setStateAfter(frameState.create(0));
 
             if (graphBuilderConfig.eagerInfopointMode()) {
@@ -1228,7 +1231,7 @@
                 createInvoke(callTarget, resultType);
             } else {
                 assert bci() == currentBlock.endBci;
-                frameState.clearNonLiveLocals(currentBlock.localsLiveOut);
+                frameState.clearNonLiveLocals(currentBlock, liveness, false);
 
                 InvokeWithExceptionNode invoke = createInvokeWithException(callTarget, resultType);
 
@@ -1544,7 +1547,7 @@
                 Target target = checkLoopExit(block.firstInstruction, block, state);
                 FixedNode result = target.fixed;
                 block.entryState = target.state == state ? state.copy() : target.state;
-                block.entryState.clearNonLiveLocals(block.localsLiveIn);
+                block.entryState.clearNonLiveLocals(block, liveness, true);
 
                 Debug.log("createTarget %s: first visit, result: %s", block, block.firstInstruction);
                 return result;
@@ -1823,7 +1826,7 @@
                 bci = stream.currentBCI();
 
                 if (bci > block.endBci) {
-                    frameState.clearNonLiveLocals(currentBlock.localsLiveOut);
+                    frameState.clearNonLiveLocals(currentBlock, liveness, false);
                 }
                 if (lastInstr instanceof StateSplit) {
                     if (lastInstr.getClass() == AbstractBeginNode.class) {
--- a/graal/com.oracle.graal.jtt/src/com/oracle/graal/jtt/loop/LoopParseLong.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.jtt/src/com/oracle/graal/jtt/loop/LoopParseLong.java	Tue Mar 18 11:51:37 2014 -0700
@@ -27,6 +27,25 @@
 
 public class LoopParseLong extends JTTTest {
 
+    @SuppressWarnings("unused")
+    public static long testShortened(String s, int radix) throws NumberFormatException {
+        long result = 0;
+        boolean negative = false;
+        int len = s.length();
+        char firstChar = s.charAt(0);
+        if (firstChar < '0') {
+            if (firstChar == '-') {
+                negative = true;
+            } else if (firstChar != '+') {
+                throw new NumberFormatException();
+            }
+            if (len == 1) {
+                throw new NumberFormatException();
+            }
+        }
+        return result;
+    }
+
     public static long test(String s, int radix) throws NumberFormatException {
         if (s == null) {
             throw new NumberFormatException("null");
@@ -81,6 +100,8 @@
 
     @LongTest
     public void run0() throws Throwable {
+        runTest("testShortened", "7", 10);
+        runTest("testShortened", "-100", 10);
         runTest("test", "7", 10);
         runTest("test", "-100", 10);
     }
--- a/graal/com.oracle.graal.lir.hsail/src/com/oracle/graal/lir/hsail/HSAILMove.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.lir.hsail/src/com/oracle/graal/lir/hsail/HSAILMove.java	Tue Mar 18 11:51:37 2014 -0700
@@ -237,13 +237,6 @@
                         throw GraalInternalError.shouldNotReachHere("Cannot store 64-bit constants to object ref");
                     }
                     break;
-                case NarrowOop:
-                    if (input.isNull()) {
-                        masm.emitStoreImmediate(kind, 0L, address.toAddress());
-                    } else {
-                        throw GraalInternalError.shouldNotReachHere("Cannot store 64-bit constants to object ref");
-                    }
-                    break;
                 default:
                     throw GraalInternalError.shouldNotReachHere();
             }
--- a/graal/com.oracle.graal.lir/src/com/oracle/graal/lir/FrameMap.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.lir/src/com/oracle/graal/lir/FrameMap.java	Tue Mar 18 11:51:37 2014 -0700
@@ -170,7 +170,7 @@
             // Without this, frameNeedsAllocating() would never return true.
             int total = 0;
             for (StackSlot s : freedSlots) {
-                total += target.arch.getSizeInBytes(s.getKind());
+                total += target.getSizeInBytes(s.getKind());
             }
             if (total == spillSize - initialSpillSize) {
                 // reset spill area size
@@ -256,7 +256,7 @@
      * @return the size in bytes
      */
     protected int spillSlotSize(PlatformKind kind) {
-        return target.arch.getSizeInBytes(kind);
+        return target.getSizeInBytes(kind);
     }
 
     /**
@@ -347,8 +347,8 @@
         }
     }
 
-    public ReferenceMap initReferenceMap(boolean canHaveRegisters) {
-        ReferenceMap refMap = new ReferenceMap(canHaveRegisters ? target.arch.getRegisterReferenceMapBitCount() : 0, frameSize() / target.wordSize);
+    public ReferenceMap initReferenceMap(boolean hasRegisters) {
+        ReferenceMap refMap = target.createReferenceMap(hasRegisters, frameSize() / target.wordSize);
         for (StackSlot slot : objectStackSlots) {
             setReference(slot, refMap);
         }
@@ -364,22 +364,14 @@
      * @param refMap A reference map, as created by {@link #initReferenceMap(boolean)}.
      */
     public void setReference(Value location, ReferenceMap refMap) {
-        Kind kind = location.getKind();
-        if (kind == Kind.Object || kind == Kind.NarrowOop) {
-            if (isRegister(location)) {
-                refMap.setRegister(asRegister(location).number, kind == Kind.NarrowOop);
-            } else if (isStackSlot(location)) {
-                if (kind == Kind.NarrowOop) {
-                    int offset = offsetForStackSlot(asStackSlot(location));
-                    assert offset % target.wordSize == 0 || offset % target.wordSize == target.wordSize / 2;
-                    refMap.setStackSlot(offset / target.wordSize, offset % target.wordSize == 0, offset % target.wordSize != 0);
-                } else {
-                    int index = indexForStackSlot(asStackSlot(location));
-                    refMap.setStackSlot(index, false, false);
-                }
-            } else {
-                assert isConstant(location);
-            }
+        PlatformKind kind = location.getPlatformKind();
+        if (isRegister(location)) {
+            refMap.setRegister(asRegister(location).number, kind);
+        } else if (isStackSlot(location)) {
+            int offset = offsetForStackSlot(asStackSlot(location));
+            refMap.setStackSlot(offset, kind);
+        } else {
+            assert isConstant(location);
         }
     }
 }
--- a/graal/com.oracle.graal.lir/src/com/oracle/graal/lir/asm/CompilationResultBuilder.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.lir/src/com/oracle/graal/lir/asm/CompilationResultBuilder.java	Tue Mar 18 11:51:37 2014 -0700
@@ -27,7 +27,6 @@
 import java.util.*;
 
 import com.oracle.graal.api.code.*;
-import com.oracle.graal.api.code.CompilationResult.ConstantData;
 import com.oracle.graal.api.code.CompilationResult.Data;
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.asm.*;
@@ -157,6 +156,10 @@
     }
 
     public void recordInlineDataInCode(Constant data) {
+        recordInlineDataInCode(codeCache.createDataItem(data, 0));
+    }
+
+    public void recordInlineDataInCode(Data data) {
         assert data != null;
         int pos = asm.position();
         Debug.log("Inline data in code: pos = %d, data = %s", pos, data);
@@ -165,7 +168,7 @@
 
     public AbstractAddress recordDataReferenceInCode(Constant data, int alignment) {
         assert data != null;
-        return recordDataReferenceInCode(new ConstantData(data, alignment));
+        return recordDataReferenceInCode(codeCache.createDataItem(data, alignment));
     }
 
     public AbstractAddress recordDataReferenceInCode(Data data) {
--- a/graal/com.oracle.graal.loop/src/com/oracle/graal/loop/LoopFragment.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.loop/src/com/oracle/graal/loop/LoopFragment.java	Tue Mar 18 11:51:37 2014 -0700
@@ -332,7 +332,7 @@
                     PhiNode phi;
                     switch (vpn.type()) {
                         case Value:
-                            phi = graph.addWithoutUnique(new PhiNode(vpn.kind(), merge));
+                            phi = graph.addWithoutUnique(new PhiNode(vpn.stamp(), merge));
                             break;
                         case Guard:
                             phi = graph.addWithoutUnique(new PhiNode(vpn.type(), merge));
--- a/graal/com.oracle.graal.loop/src/com/oracle/graal/loop/LoopFragmentInside.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.loop/src/com/oracle/graal/loop/LoopFragmentInside.java	Tue Mar 18 11:51:37 2014 -0700
@@ -170,7 +170,7 @@
         PhiNode ret;
         switch (phi.type()) {
             case Value:
-                ret = new PhiNode(phi.kind(), merge);
+                ret = new PhiNode(phi.stamp(), merge);
                 break;
             case Guard:
                 ret = new PhiNode(PhiType.Guard, merge);
--- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/IfNode.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/IfNode.java	Tue Mar 18 11:51:37 2014 -0700
@@ -222,7 +222,8 @@
                 }
             } else if (b instanceof InstanceOfNode) {
                 InstanceOfNode instanceOfB = (InstanceOfNode) b;
-                if (instanceOfA.object() == instanceOfB.object() && !instanceOfA.type().isAssignableFrom(instanceOfB.type()) && !instanceOfB.type().isAssignableFrom(instanceOfA.type())) {
+                if (instanceOfA.object() == instanceOfB.object() && !instanceOfA.type().isInterface() && !instanceOfB.type().isInterface() &&
+                                !instanceOfA.type().isAssignableFrom(instanceOfB.type()) && !instanceOfB.type().isAssignableFrom(instanceOfA.type())) {
                     // Two instanceof on the same value with mutually exclusive types.
                     JavaTypeProfile profileA = instanceOfA.profile();
                     JavaTypeProfile profileB = instanceOfB.profile();
--- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/PhiNode.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/PhiNode.java	Tue Mar 18 11:51:37 2014 -0700
@@ -22,7 +22,6 @@
  */
 package com.oracle.graal.nodes;
 
-import com.oracle.graal.api.meta.*;
 import com.oracle.graal.graph.*;
 import com.oracle.graal.graph.spi.*;
 import com.oracle.graal.nodes.calc.*;
@@ -53,15 +52,11 @@
     private final PhiType type;
 
     /**
-     * Create a value phi ({@link PhiType#Value}) with the specified kind.
+     * Create a value phi ({@link PhiType#Value}) with the specified stamp.
      * 
-     * @param kind the kind of the value
+     * @param stamp the stamp of the value
      * @param merge the merge that the new phi belongs to
      */
-    public PhiNode(Kind kind, MergeNode merge) {
-        this(StampFactory.forKind(kind), merge);
-    }
-
     public PhiNode(Stamp stamp, MergeNode merge) {
         super(stamp);
         assert stamp != StampFactory.forVoid();
@@ -186,7 +181,7 @@
 
     public void addInput(ValueNode x) {
         assert !(x instanceof PhiNode) || ((PhiNode) x).merge() instanceof LoopBeginNode || ((PhiNode) x).merge() != this.merge();
-        assert x.kind() == kind() || type != PhiType.Value;
+        assert x.stamp().isCompatible(stamp()) || type != PhiType.Value;
         values.add(x);
     }
 
--- a/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/type/IllegalStamp.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.nodes/src/com/oracle/graal/nodes/type/IllegalStamp.java	Tue Mar 18 11:51:37 2014 -0700
@@ -85,8 +85,9 @@
         if (stamp instanceof IllegalStamp) {
             IllegalStamp other = (IllegalStamp) stamp;
             return kind == other.kind;
+        } else {
+            return stamp.isCompatible(this);
         }
-        return false;
     }
 
     @Override
--- a/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/DeoptimizationGroupingPhase.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/DeoptimizationGroupingPhase.java	Tue Mar 18 11:51:37 2014 -0700
@@ -27,6 +27,7 @@
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.nodes.*;
 import com.oracle.graal.nodes.cfg.*;
+import com.oracle.graal.nodes.type.*;
 import com.oracle.graal.phases.*;
 import com.oracle.graal.phases.tiers.*;
 
@@ -55,8 +56,8 @@
                     if (target instanceof AbstractDeoptimizeNode) {
                         merge = graph.add(new MergeNode());
                         EndNode firstEnd = graph.add(new EndNode());
-                        reasonActionPhi = graph.addWithoutUnique(new PhiNode(Kind.Int, merge));
-                        speculationPhi = graph.addWithoutUnique(new PhiNode(Kind.Object, merge));
+                        reasonActionPhi = graph.addWithoutUnique(new PhiNode(StampFactory.forKind(Kind.Int), merge));
+                        speculationPhi = graph.addWithoutUnique(new PhiNode(StampFactory.forKind(Kind.Object), merge));
                         merge.addForwardEnd(firstEnd);
                         reasonActionPhi.addInput(((AbstractDeoptimizeNode) target).getActionAndReason(context.getMetaAccess()));
                         speculationPhi.addInput(((AbstractDeoptimizeNode) target).getSpeculation(context.getMetaAccess()));
--- a/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/FrameStateAssignmentPhase.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/FrameStateAssignmentPhase.java	Tue Mar 18 11:51:37 2014 -0700
@@ -59,8 +59,9 @@
 
             if (node instanceof StateSplit) {
                 StateSplit stateSplit = (StateSplit) node;
-                if (stateSplit.stateAfter() != null) {
-                    FrameState newState = stateSplit.stateAfter();
+                FrameState stateAfter = stateSplit.stateAfter();
+                if (stateAfter != null) {
+                    FrameState newState = stateAfter;
                     stateSplit.setStateAfter(null);
                     return newState;
                 }
--- a/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/InliningPhase.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/InliningPhase.java	Tue Mar 18 11:51:37 2014 -0700
@@ -91,14 +91,6 @@
         return inliningCount;
     }
 
-    public static void storeStatisticsAfterLowTier(StructuredGraph graph) {
-        ResolvedJavaMethod method = graph.method();
-        if (method != null) {
-            CompiledMethodInfo info = compiledMethodInfo(graph.method());
-            info.setLowLevelNodeCount(graph.getNodeCount());
-        }
-    }
-
     @Override
     protected void run(final StructuredGraph graph, final HighTierContext context) {
         final InliningData data = new InliningData(graph, context.getAssumptions());
@@ -310,15 +302,6 @@
         return newGraph;
     }
 
-    private static synchronized CompiledMethodInfo compiledMethodInfo(ResolvedJavaMethod m) {
-        CompiledMethodInfo info = (CompiledMethodInfo) m.getCompilerStorage().get(CompiledMethodInfo.class);
-        if (info == null) {
-            info = new CompiledMethodInfo();
-            m.getCompilerStorage().put(CompiledMethodInfo.class, info);
-        }
-        return info;
-    }
-
     private abstract static class AbstractInliningPolicy implements InliningPolicy {
 
         protected final Map<Invoke, Double> hints;
@@ -371,7 +354,12 @@
         protected static int previousLowLevelGraphSize(InlineInfo info) {
             int size = 0;
             for (int i = 0; i < info.numberOfMethods(); i++) {
-                size += compiledMethodInfo(info.methodAt(i)).lowLevelNodeCount();
+                ResolvedJavaMethod m = info.methodAt(i);
+                ProfilingInfo profile = m.getProfilingInfo();
+                int compiledGraphSize = profile.getCompilerIRSize(StructuredGraph.class);
+                if (compiledGraphSize > 0) {
+                    size += compiledGraphSize;
+                }
             }
             return size;
         }
@@ -864,21 +852,4 @@
             return (graph != null ? MetaUtil.format("%H.%n(%p)", method()) : "<null method>") + remainingInvokes;
         }
     }
-
-    private static class CompiledMethodInfo {
-
-        private int lowLevelNodes;
-
-        public CompiledMethodInfo() {
-        }
-
-        public int lowLevelNodeCount() {
-            return lowLevelNodes;
-        }
-
-        public void setLowLevelNodeCount(int lowLevelNodes) {
-            this.lowLevelNodes = lowLevelNodes;
-        }
-
-    }
 }
--- a/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/InliningUtil.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/InliningUtil.java	Tue Mar 18 11:51:37 2014 -0700
@@ -625,7 +625,7 @@
 
             PhiNode returnValuePhi = null;
             if (invoke.asNode().kind() != Kind.Void) {
-                returnValuePhi = graph.addWithoutUnique(new PhiNode(invoke.asNode().kind(), returnMerge));
+                returnValuePhi = graph.addWithoutUnique(new PhiNode(invoke.asNode().stamp().unrestricted(), returnMerge));
             }
 
             MergeNode exceptionMerge = null;
@@ -638,7 +638,7 @@
 
                 FixedNode exceptionSux = exceptionEdge.next();
                 graph.addBeforeFixed(exceptionSux, exceptionMerge);
-                exceptionObjectPhi = graph.addWithoutUnique(new PhiNode(Kind.Object, exceptionMerge));
+                exceptionObjectPhi = graph.addWithoutUnique(new PhiNode(StampFactory.forKind(Kind.Object), exceptionMerge));
                 exceptionMerge.setStateAfter(exceptionEdge.stateAfter().duplicateModified(invoke.stateAfter().bci, true, Kind.Object, exceptionObjectPhi));
             }
 
@@ -1486,7 +1486,7 @@
 
             if (returnNode.result() != null) {
                 if (returnValuePhi == null) {
-                    returnValuePhi = merge.graph().addWithoutUnique(new PhiNode(returnNode.result().kind(), merge));
+                    returnValuePhi = merge.graph().addWithoutUnique(new PhiNode(returnNode.result().stamp().unrestricted(), merge));
                 }
                 returnValuePhi.addInput(returnNode.result());
             }
--- a/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/LoweringPhase.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/LoweringPhase.java	Tue Mar 18 11:51:37 2014 -0700
@@ -312,6 +312,8 @@
                     Mark preLoweringMark = node.graph().getMark();
                     ((Lowerable) node).lower(loweringTool);
                     if (loweringTool.guardAnchor.asNode().isDeleted()) {
+                        // TODO nextNode could be deleted but this is not currently supported
+                        assert nextNode.isAlive();
                         loweringTool.guardAnchor = BeginNode.prevBegin(nextNode);
                     }
                     assert checkPostNodeLowering(node, loweringTool, preLoweringMark, unscheduledUsages);
--- a/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/ReadEliminationPhase.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/ReadEliminationPhase.java	Tue Mar 18 11:51:37 2014 -0700
@@ -87,7 +87,7 @@
         }
         if (lastLocationAccess instanceof PhiNode) {
             PhiNode phi = (PhiNode) lastLocationAccess;
-            PhiNode newPhi = phi.graph().addWithoutUnique(new PhiNode(n.kind(), phi.merge()));
+            PhiNode newPhi = phi.graph().addWithoutUnique(new PhiNode(n.stamp().unrestricted(), phi.merge()));
             nodeMap.set(phi, newPhi);
             for (ValueNode value : phi.values()) {
                 newPhi.addInput(getValue(n, (MemoryNode) value, nodeMap));
--- a/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/TailDuplicationPhase.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.phases.common/src/com/oracle/graal/phases/common/TailDuplicationPhase.java	Tue Mar 18 11:51:37 2014 -0700
@@ -486,7 +486,7 @@
                             // introduce a new phi
                             PhiNode newPhi = bottomPhis.get(node);
                             if (newPhi == null) {
-                                newPhi = graph.addWithoutUnique(new PhiNode(node.kind(), newBottomMerge));
+                                newPhi = graph.addWithoutUnique(new PhiNode(node.stamp().unrestricted(), newBottomMerge));
                                 bottomPhis.put(node, newPhi);
                                 newPhi.addInput(node);
                             }
--- a/graal/com.oracle.graal.phases/src/com/oracle/graal/phases/BasePhase.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.phases/src/com/oracle/graal/phases/BasePhase.java	Tue Mar 18 11:51:37 2014 -0700
@@ -36,7 +36,35 @@
  */
 public abstract class BasePhase<C> {
 
-    private final String name;
+    /**
+     * Phase name lazily computed from the phase class.
+     */
+    class Name extends LazyName {
+
+        @Override
+        public String createString() {
+            String s = BasePhase.this.getClass().getSimpleName();
+            return s.substring(0, s.length() - "Phase".length());
+        }
+    }
+
+    /**
+     * Lazily computed debug value name composed of a prefix and a phase's name.
+     */
+    class DebugValueName extends LazyName {
+        final String prefix;
+
+        public DebugValueName(String prefix) {
+            this.prefix = prefix;
+        }
+
+        @Override
+        public String createString() {
+            return prefix + name;
+        }
+    }
+
+    private final CharSequence name;
 
     private final DebugTimer phaseTimer;
     private final DebugMetric phaseMetric;
@@ -49,25 +77,20 @@
     }
 
     protected BasePhase() {
-        String nm = this.getClass().getSimpleName();
-        if (nm.endsWith("Phase")) {
-            name = nm.substring(0, nm.length() - "Phase".length());
-        } else {
-            name = nm;
-        }
-        assert checkName(name);
-        phaseTimer = Debug.timer("PhaseTime_" + name);
-        phaseMetric = Debug.metric("PhaseCount_" + name);
+        name = new Name();
+        assert checkName(name.toString());
+        phaseTimer = Debug.timer(new DebugValueName("PhaseTime_"));
+        phaseMetric = Debug.metric(new DebugValueName("PhaseCount_"));
     }
 
     protected BasePhase(String name) {
         assert checkName(name);
         this.name = name;
-        phaseTimer = Debug.timer("PhaseTime_" + name);
-        phaseMetric = Debug.metric("PhaseCount_" + name);
+        phaseTimer = Debug.timer(new DebugValueName("PhaseTime_"));
+        phaseMetric = Debug.metric(new DebugValueName("PhaseCount_"));
     }
 
-    protected String getDetailedName() {
+    protected CharSequence getDetailedName() {
         return getName();
     }
 
@@ -88,7 +111,7 @@
         }
     }
 
-    public final String getName() {
+    public final CharSequence getName() {
         return name;
     }
 
--- a/graal/com.oracle.graal.phases/src/com/oracle/graal/phases/GraalOptions.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.phases/src/com/oracle/graal/phases/GraalOptions.java	Tue Mar 18 11:51:37 2014 -0700
@@ -177,6 +177,8 @@
     @Option(help = "")
     public static final OptionValue<Boolean> HotSpotPrintCompilation = new OptionValue<>(false);
     @Option(help = "")
+    public static final OptionValue<Boolean> HotSpotCIPrintCompilerName = new OptionValue<>(false);
+    @Option(help = "")
     public static final OptionValue<Boolean> HotSpotPrintInlining = new OptionValue<>(false);
 
     // Register allocator debugging
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.phases/src/com/oracle/graal/phases/LazyName.java	Tue Mar 18 11:51:37 2014 -0700
@@ -0,0 +1,60 @@
+/*
+ * Copyright (c) 2014, 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;
+
+import com.oracle.graal.debug.*;
+
+/**
+ * A name whose {@link String} value is computed only when it is needed. This is useful in
+ * combination with debugging facilities such as {@link Debug#scope(CharSequence, Object...)} where
+ * the {@link String} value of a name is only needed if debugging is enabled.
+ */
+public abstract class LazyName implements CharSequence {
+
+    private String value;
+
+    public int length() {
+        return toString().length();
+    }
+
+    public char charAt(int index) {
+        return toString().charAt(index);
+    }
+
+    public CharSequence subSequence(int start, int end) {
+        return toString().subSequence(start, end);
+    }
+
+    @Override
+    public final String toString() {
+        if (value == null) {
+            value = createString();
+        }
+        return value;
+    }
+
+    /**
+     * Creates the {@link String} value of this name.
+     */
+    protected abstract String createString();
+}
--- a/graal/com.oracle.graal.phases/src/com/oracle/graal/phases/schedule/SchedulePhase.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.phases/src/com/oracle/graal/phases/schedule/SchedulePhase.java	Tue Mar 18 11:51:37 2014 -0700
@@ -292,7 +292,7 @@
     }
 
     private void printSchedule(String desc) {
-        if (Debug.isEnabled()) {
+        if (Debug.isLogEnabled()) {
             Debug.printf("=== %s / %s / %s (%s) ===\n", getCFG().getStartBlock().getBeginNode().graph(), selectedStrategy, memsched, desc);
             for (Block b : getCFG().getBlocks()) {
                 Debug.printf("==== b: %s (loopDepth: %s). ", b, b.getLoopDepth());
@@ -388,8 +388,7 @@
     private void assignBlockToNode(ScheduledNode node, SchedulingStrategy strategy) {
         assert !node.isDeleted();
 
-        Block prevBlock = cfg.getNodeToBlock().get(node);
-        if (prevBlock != null) {
+        if (cfg.getNodeToBlock().containsKey(node)) {
             return;
         }
         // PhiNodes, ProxyNodes and FixedNodes should already have been placed in blocks by
@@ -418,6 +417,7 @@
                     block = latestBlock(node, strategy);
                 }
                 if (block == null) {
+                    // handle nodes without usages
                     block = earliestBlock;
                 } else if (strategy == SchedulingStrategy.LATEST_OUT_OF_LOOPS && !(node instanceof VirtualObjectNode)) {
                     // schedule at the latest position possible in the outermost loop possible
@@ -752,10 +752,14 @@
                     if (!(usage instanceof FrameState)) {
                         throw new SchedulingError(usage.toString());
                     }
-                    // If a FrameState belongs to a BeginNode then it's inputs will be placed at the
-                    // common dominator of all EndNodes.
-                    for (Node pred : unscheduledUsage.cfgPredecessors()) {
-                        closure.apply(cfg.getNodeToBlock().get(pred));
+                    if (unscheduledUsage instanceof StartNode) {
+                        closure.apply(cfg.getNodeToBlock().get(unscheduledUsage));
+                    } else {
+                        // If a FrameState belongs to a BeginNode then it's inputs will be placed at
+                        // the common dominator of all EndNodes.
+                        for (Node pred : unscheduledUsage.cfgPredecessors()) {
+                            closure.apply(cfg.getNodeToBlock().get(pred));
+                        }
                     }
                 } else {
                     // For the time being, FrameStates can only be connected to NodeWithState.
--- a/graal/com.oracle.graal.phases/src/com/oracle/graal/phases/util/GraphOrder.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.phases/src/com/oracle/graal/phases/util/GraphOrder.java	Tue Mar 18 11:51:37 2014 -0700
@@ -26,7 +26,12 @@
 
 import com.oracle.graal.graph.*;
 import com.oracle.graal.nodes.*;
+import com.oracle.graal.nodes.VirtualState.NodeClosure;
+import com.oracle.graal.nodes.cfg.*;
 import com.oracle.graal.phases.graph.*;
+import com.oracle.graal.phases.graph.ReentrantBlockIterator.*;
+import com.oracle.graal.phases.schedule.*;
+import com.oracle.graal.phases.schedule.SchedulePhase.*;
 
 public final class GraphOrder {
 
@@ -34,9 +39,9 @@
     }
 
     /**
-     * Asserts that there are no (invalid) cycles in the given graph. First, an ordered list of all
-     * nodes in the graph (a total ordering) is created. A second run over this list checks whether
-     * inputs are scheduled before their usages.
+     * Quick (and imprecise) assertion that there are no (invalid) cycles in the given graph. First,
+     * an ordered list of all nodes in the graph (a total ordering) is created. A second run over
+     * this list checks whether inputs are scheduled before their usages.
      * 
      * @param graph the graph to be checked.
      * @throws AssertionError if a cycle was detected.
@@ -62,7 +67,6 @@
             }
             visited.mark(node);
         }
-
         return true;
     }
 
@@ -80,34 +84,161 @@
     }
 
     private static void visitForward(ArrayList<Node> nodes, NodeBitMap visited, Node node, boolean floatingOnly) {
-        if (node != null && !visited.isMarked(node)) {
-            assert !floatingOnly || !(node instanceof FixedNode) : "unexpected reference to fixed node: " + node + " (this indicates an unexpected cycle)";
-            visited.mark(node);
-            FrameState stateAfter = null;
-            if (node instanceof StateSplit) {
-                stateAfter = ((StateSplit) node).stateAfter();
-            }
-            for (Node input : node.inputs()) {
-                if (input != stateAfter) {
-                    visitForward(nodes, visited, input, true);
+        try {
+            assert node == null || node.isAlive() : node + " not alive";
+            if (node != null && !visited.isMarked(node)) {
+                if (floatingOnly && node instanceof FixedNode) {
+                    throw new GraalInternalError("unexpected reference to fixed node: %s (this indicates an unexpected cycle)", node);
+                }
+                visited.mark(node);
+                FrameState stateAfter = null;
+                if (node instanceof StateSplit) {
+                    stateAfter = ((StateSplit) node).stateAfter();
+                }
+                for (Node input : node.inputs()) {
+                    if (input != stateAfter) {
+                        visitForward(nodes, visited, input, true);
+                    }
+                }
+                if (node instanceof EndNode) {
+                    EndNode end = (EndNode) node;
+                    for (PhiNode phi : end.merge().phis()) {
+                        visitForward(nodes, visited, phi.valueAt(end), true);
+                    }
+                }
+                nodes.add(node);
+                if (node instanceof MergeNode) {
+                    for (PhiNode phi : ((MergeNode) node).phis()) {
+                        visited.mark(phi);
+                        nodes.add(phi);
+                    }
+                }
+                if (stateAfter != null) {
+                    visitForward(nodes, visited, stateAfter, true);
                 }
             }
-            if (node instanceof EndNode) {
-                EndNode end = (EndNode) node;
-                for (PhiNode phi : end.merge().phis()) {
-                    visitForward(nodes, visited, phi.valueAt(end), true);
-                }
-            }
-            nodes.add(node);
-            if (node instanceof MergeNode) {
-                for (PhiNode phi : ((MergeNode) node).phis()) {
-                    visited.mark(phi);
-                    nodes.add(phi);
-                }
-            }
-            if (stateAfter != null) {
-                visitForward(nodes, visited, stateAfter, true);
-            }
+        } catch (GraalInternalError e) {
+            e.addContext(node);
+            throw e;
         }
     }
+
+    /**
+     * This method schedules the graph and makes sure that, for every node, all inputs are available
+     * at the position where it is scheduled. This is a very expensive assertion.
+     * 
+     * Also, this phase assumes ProxyNodes to exist at LoopExitNodes, so that it cannot be run after
+     * phases that remove loop proxies or move proxies to BeginNodes.
+     */
+    public static boolean assertSchedulableGraph(final StructuredGraph graph) {
+        try {
+            final SchedulePhase schedule = new SchedulePhase(SchedulingStrategy.LATEST_OUT_OF_LOOPS, MemoryScheduling.NONE);
+            final IdentityHashMap<LoopBeginNode, NodeBitMap> loopEntryStates = new IdentityHashMap<>();
+            schedule.apply(graph, false);
+
+            BlockIteratorClosure<NodeBitMap> closure = new BlockIteratorClosure<NodeBitMap>() {
+
+                @Override
+                protected List<NodeBitMap> processLoop(Loop loop, NodeBitMap initialState) {
+                    return ReentrantBlockIterator.processLoop(this, loop, initialState).exitStates;
+                }
+
+                @Override
+                protected NodeBitMap processBlock(final Block block, final NodeBitMap currentState) {
+                    final List<ScheduledNode> list = schedule.getBlockToNodesMap().get(block);
+
+                    /*
+                     * A stateAfter is not valid directly after its associated state split, but
+                     * right before the next fixed node. Therefore a pending stateAfter is kept that
+                     * will be checked at the correct position.
+                     */
+                    FrameState pendingStateAfter = null;
+                    for (final ScheduledNode node : list) {
+                        FrameState stateAfter = node instanceof StateSplit ? ((StateSplit) node).stateAfter() : null;
+
+                        if (pendingStateAfter != null && node instanceof FixedNode) {
+                            pendingStateAfter.applyToNonVirtual(new NodeClosure<Node>() {
+                                public void apply(Node usage, Node nonVirtualNode) {
+                                    assert currentState.isMarked(nonVirtualNode) : nonVirtualNode + " not available at virtualstate " + usage + " before " + node + " in block " + block + " \n" + list;
+                                }
+                            });
+                            pendingStateAfter = null;
+                        }
+
+                        if (node instanceof MergeNode) {
+                            // phis aren't scheduled, so they need to be added explicitly
+                            currentState.markAll(((MergeNode) node).phis());
+                            if (node instanceof LoopBeginNode) {
+                                // remember the state at the loop entry, it's restored at exits
+                                loopEntryStates.put((LoopBeginNode) node, currentState.copy());
+                            }
+                        } else if (node instanceof ProxyNode) {
+                            for (Node input : node.inputs()) {
+                                if (input != ((ProxyNode) node).proxyPoint()) {
+                                    assert currentState.isMarked(input) : input + " not available at " + node + " in block " + block + "\n" + list;
+                                }
+                            }
+                        } else if (node instanceof LoopExitNode) {
+                            // the contents of the loop are only accessible via proxies at the exit
+                            currentState.clearAll();
+                            currentState.markAll(loopEntryStates.get(((LoopExitNode) node).loopBegin()));
+                            // Loop proxies aren't scheduled, so they need to be added explicitly
+                            currentState.markAll(((LoopExitNode) node).proxies());
+                        } else {
+                            for (Node input : node.inputs()) {
+                                if (input != stateAfter) {
+                                    assert currentState.isMarked(input) : input + " not available at " + node + " in block " + block + "\n" + list;
+                                }
+                            }
+                        }
+                        if (node instanceof AbstractEndNode) {
+                            MergeNode merge = ((AbstractEndNode) node).merge();
+                            for (PhiNode phi : merge.phis()) {
+                                assert currentState.isMarked(phi.valueAt((AbstractEndNode) node)) : phi.valueAt((AbstractEndNode) node) + " not available at phi " + phi + " / end " + node +
+                                                " in block " + block;
+                            }
+                        }
+                        if (stateAfter != null) {
+                            assert pendingStateAfter == null;
+                            pendingStateAfter = stateAfter;
+                        }
+                        currentState.mark(node);
+                    }
+                    if (pendingStateAfter != null) {
+                        pendingStateAfter.applyToNonVirtual(new NodeClosure<Node>() {
+                            public void apply(Node usage, Node nonVirtualNode) {
+                                assert currentState.isMarked(nonVirtualNode) : nonVirtualNode + " not available at virtualstate " + usage + " at end of block " + block + " \n" + list;
+                            }
+                        });
+                    }
+                    return currentState;
+                }
+
+                @Override
+                protected NodeBitMap merge(Block merge, List<NodeBitMap> states) {
+                    NodeBitMap result = states.get(0);
+                    for (int i = 1; i < states.size(); i++) {
+                        result.intersect(states.get(i));
+                    }
+                    return result;
+                }
+
+                @Override
+                protected NodeBitMap getInitialState() {
+                    return graph.createNodeBitMap();
+                }
+
+                @Override
+                protected NodeBitMap cloneState(NodeBitMap oldState) {
+                    return oldState.copy();
+                }
+            };
+
+            ReentrantBlockIterator.apply(closure, schedule.getCFG().getStartBlock());
+
+        } catch (Throwable t) {
+            throw new AssertionError("unschedulable graph", t);
+        }
+        return true;
+    }
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.phases/src/com/oracle/graal/phases/util/MethodDebugValueName.java	Tue Mar 18 11:51:37 2014 -0700
@@ -0,0 +1,45 @@
+/*
+ * Copyright (c) 2014, 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.util;
+
+import com.oracle.graal.api.meta.*;
+import com.oracle.graal.phases.*;
+
+/**
+ * Lazily computed debug value name composed of a prefix and a {@linkplain JavaMethod#getName()
+ * method name}.
+ */
+public class MethodDebugValueName extends LazyName {
+    final String prefix;
+    final JavaMethod method;
+
+    public MethodDebugValueName(String prefix, JavaMethod method) {
+        this.prefix = prefix;
+        this.method = method;
+    }
+
+    @Override
+    public String createString() {
+        return prefix + "[" + method.getName() + "]";
+    }
+}
--- a/graal/com.oracle.graal.printer/src/com/oracle/graal/printer/CompilationPrinter.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.printer/src/com/oracle/graal/printer/CompilationPrinter.java	Tue Mar 18 11:51:37 2014 -0700
@@ -134,16 +134,17 @@
      */
     protected String debugInfoToString(BytecodePosition codePos, ReferenceMap refMap, RegisterSaveLayout calleeSaveInfo, Architecture arch) {
         StringBuilder sb = new StringBuilder();
+        RefMapFormatter formatter = new CodeUtil.NumberedRefMapFormatter();
 
         if (refMap != null && refMap.hasRegisterRefMap()) {
             sb.append("reg-ref-map:");
-            refMap.appendRegisterMap(sb, arch != null ? new ArchitectureRegFormatter(arch) : null);
+            refMap.appendRegisterMap(sb, arch != null ? new ArchitectureRegFormatter(arch) : formatter);
             sb.append("\n");
         }
 
         if (refMap != null && refMap.hasFrameRefMap()) {
             sb.append("frame-ref-map:");
-            refMap.appendFrameMap(sb, null);
+            refMap.appendFrameMap(sb, formatter);
             sb.append("\n");
         }
 
--- a/graal/com.oracle.graal.printer/src/com/oracle/graal/printer/DecompilerDebugDumpHandler.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.printer/src/com/oracle/graal/printer/DecompilerDebugDumpHandler.java	Tue Mar 18 11:51:37 2014 -0700
@@ -35,6 +35,7 @@
 
 public class DecompilerDebugDumpHandler implements DebugDumpHandler {
 
+    public static boolean printToNowhere;
     private final PrintStream infoPrintStream = System.out;
     private File file;
     private FileOutputStream fos;
@@ -55,6 +56,15 @@
                 filter = filter.substring(0, filter.indexOf("Phase"));
             }
 
+            if (printToNowhere) {
+                printStream = new PrintStream(new OutputStream() {
+                    @Override
+                    public void write(int b) throws IOException {
+                        // DO NOTHING
+                    }
+                });
+            }
+
             if (printStream == null) {
                 fileName = "decompilerDump_" + uniqueId.incrementAndGet() + "_" + System.currentTimeMillis() + ".txt";
                 file = new File(fileName);
--- a/graal/com.oracle.graal.printer/src/com/oracle/graal/printer/GraphPrinterDumpHandler.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.printer/src/com/oracle/graal/printer/GraphPrinterDumpHandler.java	Tue Mar 18 11:51:37 2014 -0700
@@ -202,7 +202,7 @@
         for (Object o : Debug.context()) {
             JavaMethod method = asJavaMethod(o);
             if (method != null) {
-                if (lastMethodOrGraph == null || !asJavaMethod(lastMethodOrGraph).equals(method)) {
+                if (lastMethodOrGraph == null || asJavaMethod(lastMethodOrGraph) == null || !asJavaMethod(lastMethodOrGraph).equals(method)) {
                     result.add(MetaUtil.format("%H::%n(%p)", method));
                 } else {
                     // This prevents multiple adjacent method context objects for the same method
--- a/graal/com.oracle.graal.replacements.test/src/com/oracle/graal/replacements/test/ArraysSubstitutionsTest.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.replacements.test/src/com/oracle/graal/replacements/test/ArraysSubstitutionsTest.java	Tue Mar 18 11:51:37 2014 -0700
@@ -329,4 +329,25 @@
         return Arrays.equals(a, b);
     }
 
+    @Test
+    public void testEqualsNodeGVN() {
+        test("testEqualsNodeGVNSnippet", true);
+    }
+
+    public static int[] intArrayCompare = new int[]{1, 2, 3, 4, 5, 6, 7, 8, 9};
+    public static int[] intArray;
+
+    public static boolean testEqualsNodeGVNSnippet(boolean b) {
+        int[] newIntArray = new int[]{0, 2, 3, 4, 5, 6, 7, 8, 9};
+        intArray = newIntArray;
+
+        if (b) {
+            newIntArray[0] = 1;
+            return Arrays.equals(newIntArray, intArrayCompare);
+        } else {
+            newIntArray[0] = 1;
+            return Arrays.equals(newIntArray, intArrayCompare);
+        }
+    }
+
 }
--- a/graal/com.oracle.graal.replacements/src/com/oracle/graal/replacements/ReplacementsImpl.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.replacements/src/com/oracle/graal/replacements/ReplacementsImpl.java	Tue Mar 18 11:51:37 2014 -0700
@@ -99,7 +99,7 @@
                 FrameStateProcessing frameStateProcessing = method.getAnnotation(Snippet.class).removeAllFrameStates() ? FrameStateProcessing.Removal
                                 : FrameStateProcessing.CollapseFrameForSingleSideEffect;
                 StructuredGraph newGraph = makeGraph(method, recursiveEntry, recursiveEntry, inliningPolicy(method), frameStateProcessing);
-                Debug.metric("SnippetNodeCount[" + method.getName() + "]").add(newGraph.getNodeCount());
+                Debug.metric(new MethodDebugValueName("SnippetNodeCount", method)).add(newGraph.getNodeCount());
                 if (!UseSnippetGraphCache) {
                     return newGraph;
                 }
@@ -201,8 +201,8 @@
                     }
                 }
             }
-            // We don't have per method guards for macro substitutions but at least respect the
-            // defaultGuard if there is one.
+            // We don't have per method guards for macro substitutions but at
+            // least respect the defaultGuard if there is one.
             if (macroSubstitution != null && (defaultGuard == null || defaultGuard.execute())) {
                 String originalName = originalName(substituteMethod, macroSubstitution.value());
                 JavaSignature originalSignature = originalSignature(substituteMethod, macroSubstitution.signature(), macroSubstitution.isStatic());
--- a/graal/com.oracle.graal.replacements/src/com/oracle/graal/replacements/SnippetTemplate.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.replacements/src/com/oracle/graal/replacements/SnippetTemplate.java	Tue Mar 18 11:51:37 2014 -0700
@@ -97,8 +97,8 @@
 
         protected SnippetInfo(ResolvedJavaMethod method) {
             this.method = method;
-            instantiationCounter = Debug.metric("SnippetInstantiationCount[" + method.getName() + "]");
-            instantiationTimer = Debug.timer("SnippetInstantiationTime[" + method.getName() + "]");
+            instantiationCounter = Debug.metric(new MethodDebugValueName("SnippetInstantiationCount", method));
+            instantiationTimer = Debug.timer(new MethodDebugValueName("SnippetInstantiationTime", method));
             assert Modifier.isStatic(method.getModifiers()) : "snippet method must be static: " + MetaUtil.format("%H.%n", method);
             int count = method.getSignature().getParameterCount(false);
             constantParameters = new boolean[count];
@@ -876,10 +876,11 @@
 
         @Override
         public void replace(ValueNode oldNode, ValueNode newNode, MemoryMapNode mmap) {
-            if (mmap != null && newNode != null) {
+            if (mmap != null) {
                 for (Node usage : oldNode.usages().snapshot()) {
                     LocationIdentity identity = getLocationIdentity(usage);
-                    if (identity != null && identity != LocationIdentity.FINAL_LOCATION) {
+                    boolean usageReplaced = false;
+                    if (identity != null && identity != FINAL_LOCATION) {
                         // lastLocationAccess points into the snippet graph. find a proper
                         // MemoryCheckPoint inside the snippet graph
                         MemoryNode lastAccess = mmap.getLastLocationAccess(identity);
@@ -888,17 +889,26 @@
                         if (usage instanceof MemoryAccess) {
                             MemoryAccess access = (MemoryAccess) usage;
                             if (access.getLastLocationAccess() == oldNode) {
-                                assert newNode.graph().isAfterFloatingReadPhase();
+                                assert oldNode.graph().isAfterFloatingReadPhase();
                                 access.setLastLocationAccess(lastAccess);
+                                usageReplaced = true;
                             }
                         } else {
                             assert usage instanceof MemoryProxy || usage instanceof MemoryPhiNode;
                             usage.replaceFirstInput(oldNode, lastAccess.asNode());
+                            usageReplaced = true;
                         }
                     }
+                    if (!usageReplaced) {
+                        assert newNode != null : "this branch is only valid if we have a newNode for replacement";
+                    }
                 }
             }
-            oldNode.replaceAtUsages(newNode);
+            if (newNode == null) {
+                assert oldNode.usages().isEmpty();
+            } else {
+                oldNode.replaceAtUsages(newNode);
+            }
         }
     };
 
@@ -1002,12 +1012,6 @@
             // Re-wire the control flow graph around the replacee
             FixedNode firstCFGNodeDuplicate = (FixedNode) duplicates.get(firstCFGNode);
             replacee.replaceAtPredecessor(firstCFGNodeDuplicate);
-            FixedNode next = null;
-            if (replacee instanceof FixedWithNextNode) {
-                FixedWithNextNode fwn = (FixedWithNextNode) replacee;
-                next = fwn.next();
-                fwn.setNext(null);
-            }
 
             if (replacee instanceof StateSplit) {
                 for (StateSplit sideEffectNode : sideEffectNodes) {
@@ -1036,12 +1040,18 @@
                 returnValue = returnDuplicate.result();
                 MemoryMapNode mmap = new DuplicateMapper(duplicates, replaceeGraph.start());
                 if (returnValue == null && replacee.usages().isNotEmpty() && replacee instanceof MemoryCheckpoint) {
-                    replacer.replace(replacee, (ValueNode) returnDuplicate.predecessor(), mmap);
+                    replacer.replace(replacee, null, mmap);
                 } else {
                     assert returnValue != null || replacee.usages().isEmpty();
                     replacer.replace(replacee, returnValue, mmap);
                 }
                 if (returnDuplicate.isAlive()) {
+                    FixedNode next = null;
+                    if (replacee instanceof FixedWithNextNode) {
+                        FixedWithNextNode fwn = (FixedWithNextNode) replacee;
+                        next = fwn.next();
+                        fwn.setNext(null);
+                    }
                     returnDuplicate.clearInputs();
                     returnDuplicate.replaceAndDelete(next);
                 }
--- a/graal/com.oracle.graal.replacements/src/com/oracle/graal/replacements/nodes/ArrayEqualsNode.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.replacements/src/com/oracle/graal/replacements/nodes/ArrayEqualsNode.java	Tue Mar 18 11:51:37 2014 -0700
@@ -31,13 +31,12 @@
 import com.oracle.graal.graph.spi.*;
 import com.oracle.graal.lir.*;
 import com.oracle.graal.nodes.*;
-import com.oracle.graal.nodes.calc.*;
 import com.oracle.graal.nodes.type.*;
 
 /**
  * Compares two arrays with the same length.
  */
-public class ArrayEqualsNode extends FloatingNode implements LIRGenLowerable, Canonicalizable {
+public class ArrayEqualsNode extends FixedWithNextNode implements LIRGenLowerable, Canonicalizable {
 
     /** {@link Kind} of the arrays to compare. */
     private final Kind kind;
--- a/graal/com.oracle.graal.sparc/src/com/oracle/graal/sparc/SPARC.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.sparc/src/com/oracle/graal/sparc/SPARC.java	Tue Mar 18 11:51:37 2014 -0700
@@ -162,7 +162,6 @@
                 case Int:
                 case Long:
                 case Object:
-                case NarrowOop:
                     return true;
             }
         } else if (category == FPU) {
--- a/graal/com.oracle.graal.truffle.hotspot/src/com/oracle/graal/truffle/hotspot/OptimizedCallTargetInstrumentation.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.truffle.hotspot/src/com/oracle/graal/truffle/hotspot/OptimizedCallTargetInstrumentation.java	Tue Mar 18 11:51:37 2014 -0700
@@ -29,8 +29,8 @@
 import com.oracle.graal.asm.*;
 import com.oracle.graal.graph.*;
 import com.oracle.graal.hotspot.*;
-import com.oracle.graal.hotspot.bridge.*;
 import com.oracle.graal.hotspot.meta.*;
+import com.oracle.graal.hotspot.meta.HotSpotCodeCacheProvider.MarkId;
 import com.oracle.graal.lir.*;
 import com.oracle.graal.lir.asm.*;
 import com.oracle.graal.truffle.*;
@@ -51,10 +51,9 @@
     @Override
     public Mark recordMark(Object id) {
         Mark mark = super.recordMark(id);
-        if (Integer.valueOf(Marks.MARK_VERIFIED_ENTRY).equals(id)) {
-            HotSpotVMConfig config = HotSpotGraalRuntime.runtime().getConfig();
+        if (MarkId.getEnum((int) id) == MarkId.VERIFIED_ENTRY) {
             HotSpotRegistersProvider registers = HotSpotGraalRuntime.runtime().getHostProviders().getRegisters();
-            injectTailCallCode(config, registers);
+            injectTailCallCode(HotSpotGraalRuntime.runtime().getConfig(), registers);
         }
         return mark;
     }
--- a/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/OptimizedCallNode.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/OptimizedCallNode.java	Tue Mar 18 11:51:37 2014 -0700
@@ -28,7 +28,7 @@
 import com.oracle.truffle.api.frame.*;
 import com.oracle.truffle.api.impl.*;
 import com.oracle.truffle.api.nodes.*;
-import com.oracle.truffle.api.nodes.NodeInfo.Kind;
+import com.oracle.truffle.api.nodes.NodeUtil.NodeCountFilter;
 
 /**
  * Call target that is optimized by Graal upon surpassing a specific invocation threshold.
@@ -60,7 +60,7 @@
     }
 
     @SuppressWarnings("unused")
-    public void nodeReplaced(Node oldNode, Node newNode, String reason) {
+    public void nodeReplaced(Node oldNode, Node newNode, CharSequence reason) {
     }
 
     @Override
@@ -85,6 +85,11 @@
         return new DefaultOptimizedCallNode(target);
     }
 
+    @Override
+    public boolean isInlinable() {
+        return true;
+    }
+
     private static final class DefaultOptimizedCallNode extends OptimizedCallNode {
 
         private boolean trySplit = true;
@@ -135,16 +140,11 @@
             if (isMaxSingleCall()) {
                 return true;
             }
-            return countPolymorphic() >= 1 || countGeneric() > 0;
+            return countPolymorphic() >= 1;
         }
 
         @Override
-        public void nodeReplaced(Node oldNode, Node newNode, String reason) {
-            trySplit = true;
-        }
-
-        @Override
-        protected void notifyCallNodeAdded() {
+        public void nodeReplaced(Node oldNode, Node newNode, CharSequence reason) {
             trySplit = true;
         }
 
@@ -163,11 +163,12 @@
         }
 
         private int countPolymorphic() {
-            return NodeUtil.countNodes(getCallTarget().getRootNode(), null, Kind.POLYMORPHIC, false);
-        }
-
-        private int countGeneric() {
-            return NodeUtil.countNodes(getCallTarget().getRootNode(), null, Kind.GENERIC, false);
+            return NodeUtil.countNodes(getCallTarget().getRootNode(), new NodeCountFilter() {
+                public boolean isCounted(Node node) {
+                    NodeCost cost = node.getCost();
+                    return cost == NodeCost.POLYMORPHIC || cost == NodeCost.MEGAMORPHIC;
+                }
+            });
         }
 
         @Override
--- a/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/OptimizedCallTarget.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.truffle/src/com/oracle/graal/truffle/OptimizedCallTarget.java	Tue Mar 18 11:51:37 2014 -0700
@@ -34,7 +34,7 @@
 import com.oracle.truffle.api.frame.*;
 import com.oracle.truffle.api.impl.*;
 import com.oracle.truffle.api.nodes.*;
-import com.oracle.truffle.api.nodes.NodeInfo.Kind;
+import com.oracle.truffle.api.nodes.NodeUtil.NodeCountFilter;
 
 /**
  * Call target that is optimized by Graal upon surpassing a specific invocation threshold.
@@ -136,7 +136,7 @@
         return call(caller, args);
     }
 
-    private void invalidate(Node oldNode, Node newNode, String reason) {
+    private void invalidate(Node oldNode, Node newNode, CharSequence reason) {
         InstalledCode m = this.installedCode;
         if (m != null) {
             CompilerAsserts.neverPartOfCompilation();
@@ -147,7 +147,7 @@
         cancelInstalledTask(oldNode, newNode, reason);
     }
 
-    private void cancelInstalledTask(Node oldNode, Node newNode, String reason) {
+    private void cancelInstalledTask(Node oldNode, Node newNode, CharSequence reason) {
         Future<InstalledCode> task = this.installedCodeTask;
         if (task != null) {
             task.cancel(true);
@@ -298,7 +298,7 @@
     }
 
     @Override
-    public void nodeReplaced(Node oldNode, Node newNode, String reason) {
+    public void nodeReplaced(Node oldNode, Node newNode, CharSequence reason) {
         compilationProfile.reportNodeReplaced();
         invalidate(oldNode, newNode, reason);
 
@@ -382,7 +382,7 @@
         }
     }
 
-    private static void logOptimizingUnqueued(OptimizedCallTarget target, Node oldNode, Node newNode, String reason) {
+    private static void logOptimizingUnqueued(OptimizedCallTarget target, Node oldNode, Node newNode, CharSequence reason) {
         if (TraceTruffleCompilationDetails.getValue()) {
             Map<String, Object> properties = new LinkedHashMap<>();
             addReplaceProperties(properties, oldNode, newNode);
@@ -405,7 +405,7 @@
         }
     }
 
-    private static void logOptimizedInvalidated(OptimizedCallTarget target, Node oldNode, Node newNode, String reason) {
+    private static void logOptimizedInvalidated(OptimizedCallTarget target, Node oldNode, Node newNode, CharSequence reason) {
         if (TraceTruffleCompilation.getValue()) {
             Map<String, Object> properties = new LinkedHashMap<>();
             addReplaceProperties(properties, oldNode, newNode);
@@ -414,7 +414,7 @@
         }
     }
 
-    private static void logOptimizingFailed(OptimizedCallTarget callSite, String reason) {
+    private static void logOptimizingFailed(OptimizedCallTarget callSite, CharSequence reason) {
         Map<String, Object> properties = new LinkedHashMap<>();
         properties.put("Reason", reason);
         log(0, "opt fail", callSite.toString(), properties);
@@ -428,11 +428,11 @@
 
             target.getRootNode().accept(new NodeVisitor() {
                 public boolean visit(Node node) {
-                    Kind kind = node.getKind();
-                    if (kind == Kind.POLYMORPHIC || kind == Kind.GENERIC) {
+                    NodeCost kind = node.getCost();
+                    if (kind == NodeCost.POLYMORPHIC || kind == NodeCost.MEGAMORPHIC) {
                         Map<String, Object> props = new LinkedHashMap<>();
                         props.put("simpleName", node.getClass().getSimpleName());
-                        String msg = kind == Kind.GENERIC ? "generic" : "polymorphic";
+                        String msg = kind == NodeCost.MEGAMORPHIC ? "megamorphic" : "polymorphic";
                         log(0, msg, node.toString(), props);
                     }
                     if (node instanceof CallNode) {
@@ -461,8 +461,20 @@
     }
 
     static void addASTSizeProperty(RootNode target, Map<String, Object> properties) {
+        int polymorphicCount = NodeUtil.countNodes(target.getRootNode(), new NodeCountFilter() {
+            public boolean isCounted(Node node) {
+                return node.getCost() == NodeCost.POLYMORPHIC;
+            }
+        }, true);
+
+        int megamorphicCount = NodeUtil.countNodes(target.getRootNode(), new NodeCountFilter() {
+            public boolean isCounted(Node node) {
+                return node.getCost() == NodeCost.MEGAMORPHIC;
+            }
+        }, true);
+
         String value = String.format("%4d (%d/%d)", NodeUtil.countNodes(target.getRootNode(), null, true), //
-                        NodeUtil.countNodes(target.getRootNode(), null, Kind.POLYMORPHIC, true), NodeUtil.countNodes(target.getRootNode(), null, Kind.GENERIC, true)); //
+                        polymorphicCount, megamorphicCount); //
 
         properties.put("ASTSize", value);
     }
--- a/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/EffectsPhase.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/EffectsPhase.java	Tue Mar 18 11:51:37 2014 -0700
@@ -78,7 +78,9 @@
                 graph.stopTrackingInputChange();
                 graph.stopTrackingUsagesDroppedZero();
 
-                Debug.dump(graph, "after " + getName() + " iteration");
+                if (Debug.isDumpEnabled()) {
+                    Debug.dump(graph, "after " + getName() + " iteration");
+                }
 
                 new DeadCodeEliminationPhase().apply(graph);
 
--- a/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/PEReadEliminationClosure.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/PEReadEliminationClosure.java	Tue Mar 18 11:51:37 2014 -0700
@@ -162,7 +162,7 @@
                     }
                 }
                 if (phi) {
-                    PhiNode phiNode = getCachedPhi(entry, value.kind());
+                    PhiNode phiNode = getCachedPhi(entry, value.stamp().unrestricted());
                     mergeEffects.addFloatingNode(phiNode, "mergeReadCache");
                     for (int i = 0; i < states.size(); i++) {
                         afterMergeEffects.addPhiInput(phiNode, states.get(i).getReadCache(key.object, key.identity, PEReadEliminationClosure.this));
@@ -194,7 +194,7 @@
                 values[i] = value;
             }
 
-            PhiNode phiNode = getCachedPhi(new ReadCacheEntry(identity, phi), values[0].kind());
+            PhiNode phiNode = getCachedPhi(new ReadCacheEntry(identity, phi), values[0].stamp().unrestricted());
             mergeEffects.addFloatingNode(phiNode, "mergeReadCachePhi");
             for (int i = 0; i < values.length; i++) {
                 afterMergeEffects.addPhiInput(phiNode, values[i]);
--- a/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/PartialEscapeClosure.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/PartialEscapeClosure.java	Tue Mar 18 11:51:37 2014 -0700
@@ -35,6 +35,7 @@
 import com.oracle.graal.nodes.java.*;
 import com.oracle.graal.nodes.spi.*;
 import com.oracle.graal.nodes.spi.Virtualizable.EscapeState;
+import com.oracle.graal.nodes.type.*;
 import com.oracle.graal.nodes.virtual.*;
 import com.oracle.graal.phases.schedule.*;
 import com.oracle.graal.phases.util.*;
@@ -284,10 +285,10 @@
             super(mergeBlock);
         }
 
-        protected <T> PhiNode getCachedPhi(T virtual, Kind kind) {
+        protected <T> PhiNode getCachedPhi(T virtual, Stamp stamp) {
             PhiNode result = materializedPhis.get(virtual);
             if (result == null) {
-                result = new PhiNode(kind, merge);
+                result = new PhiNode(stamp, merge);
                 materializedPhis.put(virtual, result);
             }
             return result;
@@ -334,6 +335,13 @@
             ObjectState[] objStates = new ObjectState[states.size()];
             boolean materialized;
             do {
+                Iterator<Map.Entry<VirtualObjectNode, ObjectState>> iter = newState.objectStates.entrySet().iterator();
+                while (iter.hasNext()) {
+                    Map.Entry<VirtualObjectNode, ObjectState> entry = iter.next();
+                    if (!virtualObjTemp.contains(entry.getValue())) {
+                        iter.remove();
+                    }
+                }
                 mergeEffects.clear();
                 afterMergeEffects.clear();
                 materialized = false;
@@ -363,7 +371,7 @@
                         if (uniqueMaterializedValue != null) {
                             newState.addObject(object, new ObjectState(object, uniqueMaterializedValue, EscapeState.Materialized, null));
                         } else {
-                            PhiNode materializedValuePhi = getCachedPhi(object, Kind.Object);
+                            PhiNode materializedValuePhi = getCachedPhi(object, StampFactory.forKind(Kind.Object));
                             mergeEffects.addFloatingNode(materializedValuePhi, "materializedPhi");
                             for (int i = 0; i < objStates.length; i++) {
                                 ObjectState obj = objStates[i];
@@ -458,7 +466,7 @@
                     for (int i = 1; i < objStates.length; i++) {
                         ValueNode[] fields = objStates[i].getEntries();
                         if (phis[valueIndex] == null && values[valueIndex] != fields[valueIndex]) {
-                            phis[valueIndex] = new PhiNode(values[valueIndex].kind(), merge);
+                            phis[valueIndex] = new PhiNode(values[valueIndex].stamp().unrestricted(), merge);
                         }
                     }
                     if (twoSlotKinds != null && twoSlotKinds[valueIndex] != null) {
@@ -487,7 +495,7 @@
                 return materialized;
             } else {
                 // not compatible: materialize in all predecessors
-                PhiNode materializedValuePhi = getCachedPhi(object, Kind.Object);
+                PhiNode materializedValuePhi = getCachedPhi(object, StampFactory.forKind(Kind.Object));
                 for (int i = 0; i < blockStates.size(); i++) {
                     ObjectState obj = objStates[i];
                     Block predecessor = mergeBlock.getPredecessors().get(i);
--- a/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/ReadEliminationClosure.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.virtual/src/com/oracle/graal/virtual/phases/ea/ReadEliminationClosure.java	Tue Mar 18 11:51:37 2014 -0700
@@ -33,6 +33,7 @@
 import com.oracle.graal.nodes.cfg.*;
 import com.oracle.graal.nodes.extended.*;
 import com.oracle.graal.nodes.java.*;
+import com.oracle.graal.nodes.type.*;
 import com.oracle.graal.nodes.util.*;
 import com.oracle.graal.phases.schedule.*;
 import com.oracle.graal.virtual.phases.ea.ReadEliminationBlockState.CacheEntry;
@@ -196,10 +197,10 @@
             super(mergeBlock);
         }
 
-        protected <T> PhiNode getCachedPhi(T virtual, Kind kind) {
+        protected <T> PhiNode getCachedPhi(T virtual, Stamp stamp) {
             PhiNode result = materializedPhis.get(virtual);
             if (result == null) {
-                result = new PhiNode(kind, merge);
+                result = new PhiNode(stamp, merge);
                 materializedPhis.put(virtual, result);
             }
             return result;
@@ -229,7 +230,7 @@
                     }
                 }
                 if (phi) {
-                    PhiNode phiNode = getCachedPhi(entry, value.kind());
+                    PhiNode phiNode = getCachedPhi(entry, value.stamp().unrestricted());
                     mergeEffects.addFloatingNode(phiNode, "mergeReadCache");
                     for (int i = 0; i < states.size(); i++) {
                         afterMergeEffects.addPhiInput(phiNode, states.get(i).getCacheEntry(key));
@@ -262,7 +263,7 @@
             }
 
             CacheEntry<?> newIdentifier = identifier.duplicateWithObject(phi);
-            PhiNode phiNode = getCachedPhi(newIdentifier, values[0].kind());
+            PhiNode phiNode = getCachedPhi(newIdentifier, values[0].stamp().unrestricted());
             mergeEffects.addFloatingNode(phiNode, "mergeReadCachePhi");
             for (int i = 0; i < values.length; i++) {
                 afterMergeEffects.addPhiInput(phiNode, values[i]);
--- a/graal/com.oracle.graal.word/src/com/oracle/graal/word/nodes/WordCastNode.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.graal.word/src/com/oracle/graal/word/nodes/WordCastNode.java	Tue Mar 18 11:51:37 2014 -0700
@@ -69,7 +69,7 @@
     @Override
     public void generate(LIRGeneratorTool generator) {
         assert kind() != input.kind();
-        assert generator.target().arch.getSizeInBytes(kind()) == generator.target().arch.getSizeInBytes(input.kind());
+        assert generator.target().getSizeInBytes(kind()) == generator.target().getSizeInBytes(input.kind());
 
         AllocatableValue result = generator.newVariable(kind());
         generator.emitMove(result, generator.operand(input));
--- a/graal/com.oracle.truffle.api.dsl.test/src/com/oracle/truffle/api/dsl/test/PolymorphicTest.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.api.dsl.test/src/com/oracle/truffle/api/dsl/test/PolymorphicTest.java	Tue Mar 18 11:51:37 2014 -0700
@@ -33,7 +33,6 @@
 import com.oracle.truffle.api.dsl.test.TypeSystemTest.TestRootNode;
 import com.oracle.truffle.api.dsl.test.TypeSystemTest.ValueNode;
 import com.oracle.truffle.api.nodes.*;
-import com.oracle.truffle.api.nodes.NodeInfo.Kind;
 
 public class PolymorphicTest {
 
@@ -55,7 +54,7 @@
         assertEquals("(boolean,boolean)", executeWith(node, false, false));
         assertEquals("(int,boolean)", executeWith(node, 42, false));
         assertEquals("(boolean,int)", executeWith(node, false, 42));
-        assertEquals(Kind.SPECIALIZED, node.getNode().getClass().getAnnotation(NodeInfo.class).kind());
+        assertEquals(NodeCost.MONOMORPHIC, node.getNode().getCost());
         assertParent(node.getNode(), node.getNode().getLeft());
         assertParent(node.getNode(), node.getNode().getRight());
     }
@@ -65,7 +64,7 @@
         TestRootNode<Node1> node = TestHelper.createRoot(Node1Factory.getInstance());
         assertEquals("(int,boolean)", executeWith(node, 42, false));
         assertEquals("(int,int)", executeWith(node, 42, 42));
-        assertEquals(Kind.POLYMORPHIC, node.getNode().getClass().getAnnotation(NodeInfo.class).kind());
+        assertEquals(NodeCost.NONE, node.getNode().getCost());
         assertParent(node.getNode(), node.getNode().getLeft());
         assertParent(node.getNode(), node.getNode().getRight());
     }
@@ -76,7 +75,7 @@
         assertEquals("(int,boolean)", executeWith(node, 42, false));
         assertEquals("(boolean,boolean)", executeWith(node, true, false));
         assertEquals("(int,int)", executeWith(node, 42, 42));
-        assertEquals(Kind.POLYMORPHIC, node.getNode().getClass().getAnnotation(NodeInfo.class).kind());
+        assertEquals(NodeCost.NONE, node.getNode().getCost());
         assertParent(node.getNode(), node.getNode().getLeft());
         assertParent(node.getNode(), node.getNode().getRight());
     }
@@ -88,7 +87,7 @@
         assertEquals("(int,boolean)", executeWith(node, 42, false));
         assertEquals("(boolean,boolean)", executeWith(node, true, false));
         assertEquals("(int,int)", executeWith(node, 42, 42));
-        assertEquals(Kind.GENERIC, node.getNode().getClass().getAnnotation(NodeInfo.class).kind());
+        assertEquals(NodeCost.MEGAMORPHIC, node.getNode().getCost());
         assertParent(node.getNode(), node.getNode().getLeft());
         assertParent(node.getNode(), node.getNode().getRight());
     }
@@ -97,7 +96,7 @@
     public void testGenericInitial() {
         TestRootNode<Node1> node = TestHelper.createRoot(Node1Factory.getInstance());
         assertEquals("(generic,generic)", executeWith(node, "1", "1"));
-        assertEquals(Kind.GENERIC, node.getNode().getClass().getAnnotation(NodeInfo.class).kind());
+        assertEquals(NodeCost.MEGAMORPHIC, node.getNode().getCost());
         assertParent(node.getNode(), node.getNode().getLeft());
         assertParent(node.getNode(), node.getNode().getRight());
     }
@@ -108,7 +107,7 @@
         assertEquals("(boolean,int)", executeWith(node, false, 42));
         assertEquals("(boolean,boolean)", executeWith(node, false, false));
         assertEquals("(generic,generic)", executeWith(node, "", ""));
-        assertEquals(Kind.GENERIC, node.getNode().getClass().getAnnotation(NodeInfo.class).kind());
+        assertEquals(NodeCost.MEGAMORPHIC, node.getNode().getCost());
         /* Assertions for bug GRAAL-425 */
         assertParent(node.getNode(), node.getNode().getLeft());
         assertParent(node.getNode(), node.getNode().getRight());
--- a/graal/com.oracle.truffle.api.dsl.test/src/com/oracle/truffle/api/dsl/test/PolymorphicTest2.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.api.dsl.test/src/com/oracle/truffle/api/dsl/test/PolymorphicTest2.java	Tue Mar 18 11:51:37 2014 -0700
@@ -32,7 +32,6 @@
 import com.oracle.truffle.api.dsl.test.PolymorphicTest2Factory.Node1Factory;
 import com.oracle.truffle.api.dsl.test.TypeSystemTest.TestRootNode;
 import com.oracle.truffle.api.nodes.*;
-import com.oracle.truffle.api.nodes.NodeInfo.Kind;
 
 public class PolymorphicTest2 {
 
@@ -43,7 +42,7 @@
         assertEquals(21, executeWith(node, false, false));
         assertEquals(42, executeWith(node, 21, 21));
         assertEquals("(boolean,int)", executeWith(node, false, 42));
-        assertEquals(Kind.POLYMORPHIC, node.getNode().getClass().getAnnotation(NodeInfo.class).kind());
+        assertEquals(NodeCost.NONE, node.getNode().getCost());
     }
 
     @SuppressWarnings("unused")
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/ReplaceObserver.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/ReplaceObserver.java	Tue Mar 18 11:51:37 2014 -0700
@@ -31,5 +31,5 @@
  */
 public interface ReplaceObserver {
 
-    void nodeReplaced(Node oldNode, Node newNode, String reason);
+    void nodeReplaced(Node oldNode, Node newNode, CharSequence reason);
 }
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/TruffleOptions.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/TruffleOptions.java	Tue Mar 18 11:51:37 2014 -0700
@@ -25,7 +25,6 @@
 package com.oracle.truffle.api;
 
 import com.oracle.truffle.api.nodes.*;
-import com.oracle.truffle.api.nodes.NodeInfo.Kind;
 
 /**
  * Class containing general Truffle options.
@@ -56,29 +55,29 @@
     public static String TraceRewritesFilterClass = System.getProperty("truffle.TraceRewritesFilterClass");
 
     /**
-     * Filters rewrites which does not contain the {@link Kind} in its source {@link NodeInfo}. If
-     * no {@link NodeInfo} is defined the element is filtered if the filter value is set.
+     * Filters rewrites which does not contain the {@link NodeCost} in its source {@link NodeInfo}.
+     * If no {@link NodeInfo} is defined the element is filtered if the filter value is set.
      * <p>
      * Can be set with
-     * {@code -Dtruffle.TraceRewritesFilterFromKind=UNINITIALIZED|SPECIALIZED|POLYMORPHIC|GENERIC}.
+     * {@code -Dtruffle.TraceRewritesFilterFromCost=NONE|MONOMORPHIC|POLYMORPHIC|MEGAMORPHIC}.
      */
-    public static NodeInfo.Kind TraceRewritesFilterFromKind = parseNodeInfoKind(System.getProperty("truffle.TraceRewritesFilterFromKind"));
+    public static NodeCost TraceRewritesFilterFromCost = parseNodeInfoKind(System.getProperty("truffle.TraceRewritesFilterFromCost"));
 
     /**
-     * Filters rewrites which does not contain the {@link Kind} in its target {@link NodeInfo}. If
-     * no {@link NodeInfo} is defined the element is filtered if the filter value is set.
+     * Filters rewrites which does not contain the {@link NodeCost} in its target {@link NodeInfo}.
+     * If no {@link NodeInfo} is defined the element is filtered if the filter value is set.
      * <p>
      * Can be set with
      * {@code -Dtruffle.TraceRewritesFilterToKind=UNINITIALIZED|SPECIALIZED|POLYMORPHIC|GENERIC}.
      */
-    public static NodeInfo.Kind TraceRewritesFilterToKind = parseNodeInfoKind(System.getProperty("truffle.TraceRewritesFilterToKind"));
+    public static NodeCost TraceRewritesFilterToCost = parseNodeInfoKind(System.getProperty("truffle.TraceRewritesFilterToCost"));
 
-    private static NodeInfo.Kind parseNodeInfoKind(String kind) {
+    private static NodeCost parseNodeInfoKind(String kind) {
         if (kind == null) {
             return null;
         }
 
-        return NodeInfo.Kind.valueOf(kind);
+        return NodeCost.valueOf(kind);
     }
 
 }
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/debug/KillException.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/debug/KillException.java	Tue Mar 18 11:51:37 2014 -0700
@@ -26,7 +26,6 @@
 
 import com.oracle.truffle.api.nodes.*;
 
-// TODO (mlvdv) does this need to extend ControlFlowException?  It was originally part of the Ruby Shell.
 /**
  * Controls breaking out of an execution context, such as a shell or eval.
  */
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/debug/QuitException.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/debug/QuitException.java	Tue Mar 18 11:51:37 2014 -0700
@@ -26,7 +26,6 @@
 
 import com.oracle.truffle.api.nodes.*;
 
-//TODO (mlvdv) does this need to extend ControlFlowException?  It was originally part of the Ruby execution environment.
 /**
  * Controls breaking out of all executions and ending Truffle execution.
  */
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/impl/DefaultCallNode.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/impl/DefaultCallNode.java	Tue Mar 18 11:51:37 2014 -0700
@@ -64,6 +64,11 @@
     }
 
     @Override
+    public boolean isInlinable() {
+        return false;
+    }
+
+    @Override
     public String toString() {
         return getParent() != null ? getParent().toString() : super.toString();
     }
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/CallNode.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/CallNode.java	Tue Mar 18 11:51:37 2014 -0700
@@ -28,13 +28,18 @@
 import com.oracle.truffle.api.frame.*;
 
 /**
- * This node represents a call to a static {@link CallTarget}. This node should be used whenever a
- * {@link CallTarget} is considered constant at a certain location in the tree. This enables the
- * Truffle runtime to perform inlining or other optimizations for this call-site. This class is
- * intended to be implemented by truffle runtime implementors and not by guest language
- * implementors.
+ * Represents a call to a {@link CallTarget} in the Truffle AST. Addtionally to calling the
+ * {@link CallTarget} this {@link Node} enables the runtime system to implement further
+ * optimizations. Optimizations that can possibly applied to a {@link CallNode} are inlining and
+ * splitting. Inlining inlines this call site into the call graph of the parent {@link CallTarget}.
+ * Splitting duplicates the {@link CallTarget} using {@link RootNode#split()} to collect call site
+ * sensitive profiling information.
  * 
- * @see #create(CallTarget) to create a CallNode instance.
+ * Please note: This class is not intended to be subclassed by guest language implementations.
+ * 
+ * @see TruffleRuntime#createCallNode(CallTarget)
+ * @see #inline()
+ * @see #split()
  */
 public abstract class CallNode extends Node {
 
@@ -45,7 +50,7 @@
     }
 
     /**
-     * Calls this constant target passing a caller frame and arguments.
+     * Calls the inner {@link CallTarget} returned by {@link #getCurrentCallTarget()}.
      * 
      * @param caller the caller frame
      * @param arguments the arguments that should be passed to the callee
@@ -65,27 +70,63 @@
     }
 
     /**
-     * @return true if this {@link CallNode} was already inlined.
+     * Returns <code>true</code> if the underlying runtime system supports inlining for the
+     * {@link CallTarget} in this {@link CallNode}.
+     * 
+     * @return true if inlining is supported.
+     */
+    public abstract boolean isInlinable();
+
+    /**
+     * Returns <code>true</code> if the {@link CallTarget} in this {@link CallNode} is inlined. A
+     * {@link CallNode} can either be inlined manually by invoking {@link #inline()} or by the
+     * runtime system which may at any point decide to inline.
+     * 
+     * @return true if this method was inlined else false.
      */
     public abstract boolean isInlined();
 
+    /**
+     * Enforces the runtime system to inline the {@link CallTarget} at this call site. If the
+     * runtime system does not support inlining or it is already inlined this method has no effect.
+     */
     public abstract void inline();
 
+    /**
+     * Returns <code>true</code> if this {@link CallNode} can be split. A {@link CallNode} can only
+     * be split if the runtime system supports splitting and if the {@link RootNode} contained the
+     * {@link CallTarget} returns <code>true</code> for {@link RootNode#isSplittable()}.
+     * 
+     * @return <code>true</code> if the target can be split
+     */
     public abstract boolean isSplittable();
 
+    /**
+     * Enforces the runtime system to split the {@link CallTarget}. If the {@link CallNode} is not
+     * splittable this methods has no effect.
+     */
     public abstract boolean split();
 
+    /**
+     * Returns <code>true</code> if the target of the {@link CallNode} was split.
+     * 
+     * @return if the target was split
+     */
     public final boolean isSplit() {
         return getSplitCallTarget() != null;
     }
 
+    /**
+     * Returns the splitted {@link CallTarget} if this method is split.
+     * 
+     * @return the split {@link CallTarget}
+     */
     public abstract CallTarget getSplitCallTarget();
 
     /**
      * Returns the used call target when {@link #call(PackedFrame, Arguments)} is invoked. If the
-     * {@link CallNode} was split this method returns the {@link CallTarget} returned by
-     * {@link #getSplitCallTarget()}. If not split this method returns the original supplied
-     * {@link CallTarget}.
+     * {@link CallTarget} was split this method returns the {@link CallTarget} returned by
+     * {@link #getSplitCallTarget()}.
      * 
      * @return the used {@link CallTarget} when node is called
      */
@@ -98,8 +139,24 @@
         }
     }
 
+    /**
+     * Returns the {@link RootNode} associated with {@link CallTarget} returned by
+     * {@link #getCurrentCallTarget()}. If the stored {@link CallTarget} does not contain a
+     * {@link RootNode} this method returns <code>null</code>.
+     * 
+     * @see #getCurrentCallTarget()
+     * @return the root node of the used call target
+     */
+    public final RootNode getCurrentRootNode() {
+        CallTarget target = getCurrentCallTarget();
+        if (target instanceof RootCallTarget) {
+            return ((RootCallTarget) target).getRootNode();
+        }
+        return null;
+    }
+
     @Override
-    protected void onReplace(Node newNode, String reason) {
+    protected void onReplace(Node newNode, CharSequence reason) {
         super.onReplace(newNode, reason);
 
         /*
@@ -114,6 +171,9 @@
         registerCallTarget((CallNode) newNode);
     }
 
+    /**
+     * Internal API for the runtime system.
+     */
     protected static final void registerCallTarget(CallNode newNode) {
         RootNode newRoot = newNode.getCurrentRootNode();
         if (newRoot != null) {
@@ -121,51 +181,4 @@
         }
     }
 
-    protected void notifyCallNodeAdded() {
-
-    }
-
-    /**
-     * Returns the {@link RootNode} associated with {@link CallTarget} returned by
-     * {@link #getCurrentCallTarget()}.
-     * 
-     * @see #getCurrentCallTarget()
-     * @return the root node of the used call target
-     */
-    public final RootNode getCurrentRootNode() {
-        CallTarget target = getCurrentCallTarget();
-        if (target instanceof RootCallTarget) {
-            return ((RootCallTarget) target).getRootNode();
-        }
-        return null;
-    }
-
-    /**
-     * @deprecated always returns <code>true</code> now.
-     */
-    @Deprecated
-    public boolean isInlinable() {
-        return true;
-    }
-
-    /**
-     * @deprecated instead use {@link #getCurrentRootNode()} and check for {@link #isInlined()} for
-     *             true.
-     */
-    @Deprecated
-    public RootNode getInlinedRoot() {
-        if (!isInlined()) {
-            return null;
-        }
-        return getCurrentRootNode();
-    }
-
-    /**
-     * @deprecated use {@link TruffleRuntime#createCallNode(CallTarget)} instead
-     */
-    @Deprecated
-    public static CallNode create(CallTarget target) {
-        return Truffle.getRuntime().createCallNode(target);
-    }
-
 }
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/GraphPrintVisitor.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/GraphPrintVisitor.java	Tue Mar 18 11:51:37 2014 -0700
@@ -214,7 +214,7 @@
             setNodeProperty(node, "name", node.getClass().getSimpleName().replaceFirst("Node$", ""));
             NodeInfo nodeInfo = node.getClass().getAnnotation(NodeInfo.class);
             if (nodeInfo != null) {
-                setNodeProperty(node, "kind", nodeInfo.kind());
+                setNodeProperty(node, "cost", nodeInfo.cost());
                 if (!nodeInfo.shortName().isEmpty()) {
                     setNodeProperty(node, "shortName", nodeInfo.shortName());
                 }
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/Node.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/Node.java	Tue Mar 18 11:51:37 2014 -0700
@@ -29,7 +29,6 @@
 import java.util.*;
 
 import com.oracle.truffle.api.*;
-import com.oracle.truffle.api.nodes.NodeInfo.Kind;
 
 /**
  * Abstract base class for all Truffle nodes.
@@ -82,12 +81,20 @@
         this.sourceSection = section;
     }
 
-    public Kind getKind() {
+    /**
+     * Returns a rough estimate for the cost of this {@link Node}. This estimate can be used by
+     * runtime systems or guest languages to implement heuristics based on Truffle ASTs. This method
+     * is intended to be overridden by subclasses. The default implementation returns the value of
+     * {@link NodeInfo#cost()} of the {@link NodeInfo} annotation declared at the subclass. If no
+     * {@link NodeInfo} annotation is declared the method returns {@link NodeCost#MONOMORPHIC} as a
+     * default value.
+     */
+    public NodeCost getCost() {
         NodeInfo info = getClass().getAnnotation(NodeInfo.class);
         if (info != null) {
-            return info.kind();
+            return info.cost();
         }
-        return Kind.SPECIALIZED;
+        return NodeCost.MONOMORPHIC;
     }
 
     /**
@@ -179,7 +186,7 @@
      * @param reason a description of the reason for the replacement
      * @return the new node
      */
-    public final <T extends Node> T replace(T newNode, String reason) {
+    public final <T extends Node> T replace(T newNode, CharSequence reason) {
         CompilerDirectives.transferToInterpreterAndInvalidate();
         if (this.getParent() == null) {
             throw new IllegalStateException("This node cannot be replaced, because it does not yet have a parent.");
@@ -253,7 +260,7 @@
         return false;
     }
 
-    private void reportReplace(Node oldNode, Node newNode, String reason) {
+    private void reportReplace(Node oldNode, Node newNode, CharSequence reason) {
         RootNode rootNode = getRootNode();
         if (rootNode != null) {
             CallTarget target = rootNode.getCallTarget();
@@ -270,68 +277,61 @@
      * @param newNode the replacement node
      * @param reason the reason the replace supplied
      */
-    protected void onReplace(Node newNode, String reason) {
+    protected void onReplace(Node newNode, CharSequence reason) {
         if (TruffleOptions.TraceRewrites) {
             traceRewrite(newNode, reason);
         }
     }
 
-    private void traceRewrite(Node newNode, String reason) {
-        Class<? extends Node> from = getClass();
-        Class<? extends Node> to = newNode.getClass();
+    private void traceRewrite(Node newNode, CharSequence reason) {
 
-        if (TruffleOptions.TraceRewritesFilterFromKind != null) {
-            if (filterByKind(from, TruffleOptions.TraceRewritesFilterFromKind)) {
+        if (TruffleOptions.TraceRewritesFilterFromCost != null) {
+            if (filterByKind(this, TruffleOptions.TraceRewritesFilterFromCost)) {
                 return;
             }
         }
 
-        if (TruffleOptions.TraceRewritesFilterToKind != null) {
-            if (filterByKind(to, TruffleOptions.TraceRewritesFilterToKind)) {
+        if (TruffleOptions.TraceRewritesFilterToCost != null) {
+            if (filterByKind(newNode, TruffleOptions.TraceRewritesFilterToCost)) {
                 return;
             }
         }
 
         String filter = TruffleOptions.TraceRewritesFilterClass;
+        Class<? extends Node> from = getClass();
+        Class<? extends Node> to = newNode.getClass();
         if (filter != null && (filterByContainsClassName(from, filter) || filterByContainsClassName(to, filter))) {
             return;
         }
 
         PrintStream out = System.out;
-        out.printf("[truffle]   rewrite %-50s |From %-40s |To %-40s |Reason %s.%n", this.toString(), formatNodeInfo(from), formatNodeInfo(to), reason);
+        out.printf("[truffle]   rewrite %-50s |From %-40s |To %-40s |Reason %s.%n", this.toString(), formatNodeInfo(this), formatNodeInfo(newNode), reason);
     }
 
-    private static String formatNodeInfo(Class<? extends Node> clazz) {
-        NodeInfo nodeInfo = clazz.getAnnotation(NodeInfo.class);
-        String kind = "?";
-        if (nodeInfo != null) {
-            switch (nodeInfo.kind()) {
-                case GENERIC:
-                    kind = "G";
-                    break;
-                case SPECIALIZED:
-                    kind = "S";
-                    break;
-                case UNINITIALIZED:
-                    kind = "U";
-                    break;
-                case POLYMORPHIC:
-                    kind = "P";
-                    break;
-                default:
-                    kind = "?";
-                    break;
-            }
+    private static String formatNodeInfo(Node node) {
+        String cost = "?";
+        switch (node.getCost()) {
+            case NONE:
+                cost = "G";
+                break;
+            case MONOMORPHIC:
+                cost = "M";
+                break;
+            case POLYMORPHIC:
+                cost = "P";
+                break;
+            case MEGAMORPHIC:
+                cost = "G";
+                break;
+            default:
+                cost = "?";
+                break;
         }
-        return kind + " " + clazz.getSimpleName();
+        return cost + " " + node.getClass().getSimpleName();
     }
 
-    private static boolean filterByKind(Class<?> clazz, Kind kind) {
-        NodeInfo info = clazz.getAnnotation(NodeInfo.class);
-        if (info != null) {
-            return info.kind() != kind;
-        }
-        return true;
+    private static boolean filterByKind(Node node, NodeCost cost) {
+        return node.getCost() == cost;
     }
 
     private static boolean filterByContainsClassName(Class<? extends Node> from, String filter) {
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/NodeCost.java	Tue Mar 18 11:51:37 2014 -0700
@@ -0,0 +1,69 @@
+/*
+ * Copyright (c) 2012, 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.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * 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.truffle.api.nodes;
+
+import com.oracle.truffle.api.*;
+
+/**
+ * Represents a rough estimate for the cost of a {@link Node}. This estimate can be used by runtime
+ * systems or guest languages to implement heuristics based on Truffle ASTs.
+ * 
+ * @see Node#getCost()
+ */
+public enum NodeCost {
+
+    /**
+     * This node has literally no costs and should be ignored for heuristics. This is particularly
+     * useful for wrapper and profiling nodes which should not influence the heuristics.
+     */
+    NONE,
+
+    /**
+     * This node has a {@link CompilerDirectives#transferToInterpreter()} or
+     * {@link CompilerDirectives#transferToInterpreterAndInvalidate()} as its first unconditional
+     * statement.
+     */
+    UNINITIALIZED,
+
+    /**
+     * This node represents a specialized monomorphic version of an operation.
+     */
+    MONOMORPHIC,
+
+    /**
+     * This node represents a polymorphic version of an operation. For multiple chained polymorphic
+     * nodes the first may return {@link #MONOMORPHIC} and all addtional nodes should return
+     * {@link #POLYMORPHIC}.
+     */
+    POLYMORPHIC,
+
+    /**
+     * This node represents a megamorphic version of an operation. This value should only be used if
+     * the operation implementation supports monomorphism and polymorphism otherwise
+     * {@link #MONOMORPHIC} should be used instead.
+     */
+    MEGAMORPHIC;
+
+}
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/NodeInfo.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/NodeInfo.java	Tue Mar 18 11:51:37 2014 -0700
@@ -40,10 +40,13 @@
      */
     String shortName() default "";
 
-    Kind kind() default Kind.SPECIALIZED;
-
-    public enum Kind {
-        UNINITIALIZED, SPECIALIZED, POLYMORPHIC, GENERIC
-    }
+    /**
+     * Provides a rough estimate for the cost of the annotated {@link Node}. This estimate can be
+     * used by runtime systems or guest languages to implement heuristics based on Truffle ASTs.
+     * 
+     * @see Node#getCost()
+     * @see NodeCost
+     */
+    NodeCost cost() default NodeCost.MONOMORPHIC;
 
 }
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/NodeUtil.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/NodeUtil.java	Tue Mar 18 11:51:37 2014 -0700
@@ -34,7 +34,6 @@
 import com.oracle.truffle.api.*;
 import com.oracle.truffle.api.nodes.Node.Child;
 import com.oracle.truffle.api.nodes.Node.Children;
-import com.oracle.truffle.api.nodes.NodeInfo.Kind;
 
 /**
  * Utility class that manages the special access methods for node instances.
@@ -452,48 +451,6 @@
         return null;
     }
 
-    /**
-     * @deprecated will be removed, exposed Truffle runtime specific functionality.
-     */
-    @Deprecated
-    public static List<CallTarget> findOutermostCallTargets(Node node) {
-        RootNode root = node.getRootNode();
-        if (root == null) {
-            return Collections.emptyList();
-        }
-        List<CallTarget> roots = new ArrayList<>();
-        roots.add(root.getCallTarget());
-        for (CallNode callNode : root.getCachedCallNodes()) {
-            if (callNode.isInlined()) {
-                roots.addAll(findOutermostCallTargets(callNode));
-            }
-        }
-        return roots;
-    }
-
-    /**
-     * @deprecated will be removed, exposed Truffle runtime specific functionality.
-     */
-    @Deprecated
-    public static RootNode findOutermostRootNode(Node node) {
-        Node parent = node;
-        while (parent != null) {
-            if (parent instanceof RootNode) {
-                RootNode root = (RootNode) parent;
-                @SuppressWarnings("deprecation")
-                Node next = root.getParentInlinedCall();
-                if (next != null) {
-                    parent = next;
-                } else {
-                    return root;
-                }
-            } else {
-                parent = parent.getParent();
-            }
-        }
-        return null;
-    }
-
     public static <T> T findParent(Node start, Class<T> clazz) {
         Node parent = start.getParent();
         if (parent == null) {
@@ -614,39 +571,43 @@
     }
 
     public static int countNodes(Node root) {
-        return countNodes(root, null, null, false);
+        return countNodes(root, null, false);
     }
 
-    public static int countNodes(Node root, Class<?> clazz, Kind nodeKind, boolean countInlinedCallNodes) {
-        NodeCountVisitor nodeCount = new NodeCountVisitor(clazz, nodeKind, countInlinedCallNodes);
+    public static int countNodes(Node root, NodeCountFilter filter) {
+        return countNodes(root, filter, false);
+    }
+
+    public static int countNodes(Node root, NodeCountFilter filter, boolean visitInlinedCallNodes) {
+        NodeCountVisitor nodeCount = new NodeCountVisitor(filter, visitInlinedCallNodes);
         root.accept(nodeCount);
         return nodeCount.nodeCount;
     }
 
-    public static int countNodes(Node root, Class<?> clazz, boolean countInlinedCallNodes) {
-        return countNodes(root, clazz, null, countInlinedCallNodes);
+    public interface NodeCountFilter {
+
+        boolean isCounted(Node node);
+
     }
 
     private static final class NodeCountVisitor implements NodeVisitor {
 
-        private final boolean inspectInlinedCalls;
+        private final boolean visitInlinedCallNodes;
         int nodeCount;
-        private final Kind kind;
-        private final Class<?> clazz;
+        private final NodeCountFilter filter;
 
-        private NodeCountVisitor(Class<?> clazz, Kind kind, boolean inspectInlinedCalls) {
-            this.clazz = clazz;
-            this.kind = kind;
-            this.inspectInlinedCalls = inspectInlinedCalls;
+        private NodeCountVisitor(NodeCountFilter filter, boolean visitInlinedCallNodes) {
+            this.filter = filter;
+            this.visitInlinedCallNodes = visitInlinedCallNodes;
         }
 
         @Override
         public boolean visit(Node node) {
-            if ((clazz == null || clazz.isInstance(node)) && (kind == null || isKind(node))) {
+            if (filter == null || filter.isCounted(node)) {
                 nodeCount++;
             }
 
-            if (inspectInlinedCalls && node instanceof CallNode) {
+            if (visitInlinedCallNodes && node instanceof CallNode) {
                 CallNode call = (CallNode) node;
                 if (call.isInlined()) {
                     Node target = ((RootCallTarget) call.getCurrentCallTarget()).getRootNode();
@@ -659,9 +620,6 @@
             return true;
         }
 
-        private boolean isKind(Node n) {
-            return kind == n.getKind();
-        }
     }
 
     public static void printInliningTree(final PrintStream stream, RootNode root) {
--- a/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/RootNode.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.api/src/com/oracle/truffle/api/nodes/RootNode.java	Tue Mar 18 11:51:37 2014 -0700
@@ -36,7 +36,7 @@
  */
 public abstract class RootNode extends Node {
 
-    private CallTarget callTarget;
+    private RootCallTarget callTarget;
     private final FrameDescriptor frameDescriptor;
 
     /*
@@ -62,36 +62,24 @@
     }
 
     /**
-     * @deprecated Not required anymore. Do not use.
+     * Creates a split {@link RootNode} based on the current {@link RootNode}. This method should
+     * return an AST that was never executed and must not be shared with other {@link RootNode} or
+     * {@link CallTarget} instances. This method is intended to be overridden by a subclass.
+     * 
+     * @return the split {@link RootNode}
      */
-    @Deprecated
-    public RootNode inline() {
-        if (!isInlinable()) {
-            throw new UnsupportedOperationException("Inlining is not enabled.");
-        }
-        return split();
+    public RootNode split() {
+        throw new UnsupportedOperationException();
     }
 
     /**
-     * @deprecated Not required anymore. Do not use.
-     */
-    @Deprecated
-    public int getInlineNodeCount() {
-        return 0;
-    }
-
-    /**
-     * @deprecated Not required anymore. Do not use.
+     * Returns <code>true</code> if this {@link RootNode} can be split. A {@link RootNode} can be
+     * split inside of a {@link CallTarget} that is invoked using a {@link CallNode}. If this method
+     * returns <code>true</code> a proper implementation of {@link #split()} must also be provided.
+     * This method is intended to be overridden by a subclass.
+     * 
+     * @return <code>true</code> if splittable else <code>false</code>.
      */
-    @Deprecated
-    public boolean isInlinable() {
-        return true;
-    }
-
-    public RootNode split() {
-        return NodeUtil.cloneNode(this);
-    }
-
     public boolean isSplittable() {
         return false;
     }
@@ -100,7 +88,7 @@
      * Reports the execution count of a loop that is a child of this node. The optimization
      * heuristics can use the loop count to guide compilation and inlining.
      */
-    public void reportLoopCount(int count) {
+    public final void reportLoopCount(int count) {
         if (getCallTarget() instanceof LoopCountReceiver) {
             ((LoopCountReceiver) getCallTarget()).reportLoopCount(count);
         }
@@ -114,7 +102,7 @@
      */
     public abstract Object execute(VirtualFrame frame);
 
-    public CallTarget getCallTarget() {
+    public final RootCallTarget getCallTarget() {
         return callTarget;
     }
 
@@ -122,17 +110,17 @@
         return frameDescriptor;
     }
 
-    public final void setCallTarget(CallTarget callTarget) {
+    public final void setCallTarget(RootCallTarget callTarget) {
         this.callTarget = callTarget;
     }
 
     /* Internal API. Do not use. */
-    void addCachedCallNode(CallNode callSite) {
+    final void addCachedCallNode(CallNode callSite) {
         this.cachedCallNodes.add(callSite);
     }
 
     /* Internal API. Do not use. */
-    void removeCachedCallNode(CallNode callSite) {
+    final void removeCachedCallNode(CallNode callSite) {
         this.cachedCallNodes.remove(callSite);
     }
 
@@ -148,11 +136,4 @@
         return Collections.unmodifiableSet(cachedCallNodes);
     }
 
-    /**
-     * @deprecated use {@link #getCachedCallNodes()} instead.
-     */
-    @Deprecated
-    public final CallNode getParentInlinedCall() {
-        return cachedCallNodes.isEmpty() ? null : cachedCallNodes.iterator().next();
-    }
 }
--- a/graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/TruffleTypes.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/TruffleTypes.java	Tue Mar 18 11:51:37 2014 -0700
@@ -52,7 +52,7 @@
     private final DeclaredType childAnnotation;
     private final DeclaredType childrenAnnotation;
     private final DeclaredType nodeInfoAnnotation;
-    private final DeclaredType nodeInfoKind;
+    private final DeclaredType nodeCost;
     private final TypeMirror compilerDirectives;
     private final TypeMirror compilerAsserts;
     private final DeclaredType slowPath;
@@ -75,7 +75,7 @@
         assumption = getRequired(context, Assumption.class);
         invalidAssumption = getRequired(context, InvalidAssumptionException.class);
         nodeInfoAnnotation = getRequired(context, NodeInfo.class);
-        nodeInfoKind = getRequired(context, NodeInfo.Kind.class);
+        nodeCost = getRequired(context, NodeCost.class);
         slowPath = getRequired(context, SlowPath.class);
         sourceSection = getRequired(context, SourceSection.class);
         truffleOptions = getRequired(context, TruffleOptions.class);
@@ -107,8 +107,8 @@
         return false;
     }
 
-    public DeclaredType getNodeInfoKind() {
-        return nodeInfoKind;
+    public DeclaredType getNodeCost() {
+        return nodeCost;
     }
 
     private DeclaredType getRequired(ProcessorContext context, Class clazz) {
--- a/graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/codewriter/AbstractCodeWriter.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/codewriter/AbstractCodeWriter.java	Tue Mar 18 11:51:37 2014 -0700
@@ -267,11 +267,9 @@
         if (parent.getKind() == ElementKind.ENUM && f.getModifiers().contains(Modifier.STATIC)) {
             write(f.getSimpleName());
             if (init != null) {
-                if (init != null) {
-                    write("(");
-                    init.acceptCodeElementScanner(this, p);
-                    write(")");
-                }
+                write("(");
+                init.acceptCodeElementScanner(this, p);
+                write(")");
             }
         } else {
             Element enclosing = f.getEnclosingElement();
--- a/graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/node/NodeCodeGenerator.java	Tue Mar 18 11:07:47 2014 -0700
+++ b/graal/com.oracle.truffle.dsl.processor/src/com/oracle/truffle/dsl/processor/node/NodeCodeGenerator.java	Tue Mar 18 11:51:37 2014 -0700
@@ -32,7 +32,6 @@
 import javax.lang.model.util.*;
 
 import com.oracle.truffle.api.dsl.*;
-import com.oracle.truffle.api.nodes.NodeInfo.Kind;
 import com.oracle.truffle.api.nodes.*;
 import com.oracle.truffle.dsl.processor.*;
 import com.oracle.truffle.dsl.processor.ast.*;
@@ -223,7 +222,6 @@
                         }
                     }
                     ActualParameter sourceParameter = sourceMethod.findParameter(parameter.getLocalName());
-                    assert parameter != null;
 
                     if (castedValues && sourceParameter != null) {
                         builder.string(valueName(sourceParameter, parameter));
@@ -954,28 +952,28 @@
                 clazz.add(createGenericExecute(node, rootGroup));
             }
 
-            clazz.add(createGetKind(node, null, Kind.SPECIALIZED));
+            clazz.add(createGetCost(node, null, NodeCost.MONOMORPHIC));
         }
 
         protected boolean needsInvokeCopyConstructorMethod() {
             return getModel().getNode().isPolymorphic();
         }
 
-        protected CodeExecutableElement createGetKind(NodeData node, SpecializationData specialization, Kind kind) {
-            CodeExecutableElement method = new CodeExecutableElement(modifiers(PUBLIC), context.getTruffleTypes().getNodeInfoKind(), "getKind");
-
-            TypeMirror nodeInfoKind = context.getTruffleTypes().getNodeInfoKind();
+        protected CodeExecutableElement createGetCost(NodeData node, SpecializationData specialization, NodeCost cost) {
+            CodeExecutableElement method = new CodeExecutableElement(modifiers(PUBLIC), context.getTruffleTypes().getNodeCost(), "getCost");
+
+            TypeMirror nodeInfoKind = context.getTruffleTypes().getNodeCost();
 
             CodeTreeBuilder builder = method.createBuilder();
             if (node.isPolymorphic() && specialization == null) {
                 // assume next0 exists
-                builder.startIf().string("next0 != null && next0.getKind() == ").staticReference(nodeInfoKind, "SPECIALIZED").end();
+                builder.startIf().string("next0 != null && next0.getCost() == ").staticReference(nodeInfoKind, "MONOMORPHIC").end();
                 builder.startBlock();
                 builder.startReturn().staticReference(nodeInfoKind, "POLYMORPHIC").end();
                 builder.end();
             }
 
-            builder.startReturn().staticReference(nodeInfoKind, kind.name()).end();
+            builder.startReturn().staticReference(nodeInfoKind, cost.name()).end();
             return method;
         }
 
@@ -2476,7 +2474,7 @@
             }
             CodeTypeElement clazz = createClass(node, modifiers(PRIVATE, STATIC, FINAL), nodePolymorphicClassName(node), baseType, false);
 
-            clazz.getAnnotationMirrors().add(createNodeInfo(node, Kind.POLYMORPHIC));
+            clazz.getAnnotationMirrors().add(createNodeInfo(node, NodeCost.NONE));
 
             for (ActualParameter polymorphParameter : polymorph.getSignatureParameters()) {
                 if (!polymorphParameter.getTypeSystemType().isGeneric()) {
@@ -2523,7 +2521,7 @@
             }
 
             createCachedExecuteMethods(specialization);
-            clazz.add(createGetKind(specialization.getNode(), specialization, Kind.SPECIALIZED));
+            clazz.add(createGetCost(specialization.getNode(), specialization, NodeCost.NONE));
         }
 
         private ExecutableElement createUpdateType(ActualParameter parameter) {
@@ -2563,34 +2561,34 @@
             }
             CodeTypeElement clazz = createClass(node, modifiers(PRIVATE, STATIC, FINAL), nodeSpecializationClassName(specialization), baseType, false);
 
-            Kind kind;
+            NodeCost cost;
             if (specialization.isGeneric()) {
-                kind = Kind.GENERIC;
+                cost = NodeCost.MEGAMORPHIC;
             } else if (specialization.isUninitialized()) {
-                kind = Kind.UNINITIALIZED;
+                cost = NodeCost.UNINITIALIZED;
             } else if (specialization.isPolymorphic()) {
-                kind = Kind.POLYMORPHIC;
+                cost = NodeCost.NONE;
             } else if (specialization.isSpecialized()) {
-                kind = Kind.SPECIALIZED;
+                cost = NodeCost.MONOMORPHIC;
             } else {
                 throw new AssertionError();
             }
-            clazz.getAnnotationMirrors().add(createNodeInfo(node, kind));
+            clazz.getAnnotationMirrors().add(createNodeInfo(node, cost));
 
             return clazz;
         }
 
-        protected CodeAnnotationMirror createNodeInfo(NodeData node, Kind kind) {
+        protected CodeAnnotationMirror createNodeInfo(NodeData node, NodeCost cost) {
             String shortName = node.getShortName();
             CodeAnnotationMirror nodeInfoMirror = new CodeAnnotationMirror(getContext().getTruffleTypes().getNodeInfoAnnotation());
             if (shortName != null) {
                 nodeInfoMirror.setElementValue(nodeInfoMirror.findExecutableElement("shortName"), new CodeAnnotationValue(shortName));
             }
 
-            DeclaredType nodeinfoKind = getContext().getTruffleTypes().getNodeInfoKind();
-            VariableElement varKind = Utils.findVariableElement(nodeinfoKind, kind.name());
-
-            nodeInfoMirror.setElementValue(nodeInfoMirror.findExecutableElement("kind"), new CodeAnnotationValue(varKind));
+            DeclaredType nodeinfoCost = getContext().getTruffleTypes().getNodeCost();
+            VariableElement varKind = Utils.findVariableElement(nodeinfoCost, cost.name());
+
+            nodeInfoMirror.setElementValue(nodeInfoMirror.findExecutableElement("cost"), new CodeAnnotationValue(varKind));
             return nodeInfoMirror;
         }
 
@@ -2609,9 +2607,9 @@
             }
 
             if (specialization.isGeneric()) {
-                clazz.add(createGetKind(specialization.getNode(), specialization, Kind.GENERIC));
+                clazz.add(createGetCost(specialization.getNode(), specialization, NodeCost.MEGAMORPHIC));
             } else if (specialization.isUninitialized()) {
-                clazz.add(createGetKind(specialization.getNode(), specialization, Kind.UNINITIALIZED));
+                clazz.add(createGetCost(specialization.getNode(), specialization, NodeCost.UNINITIALIZED));
             }
         }
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/findbugsExcludeFilter.xml	Tue Mar 18 11:51:37 2014 -0700
@@ -0,0 +1,41 @@
+<FindBugsFilter>
+
+  <Match>
+    <Class name="com.oracle.graal.hotspot.CompilationTask" />
+    <Method name="run" />
+    <Bug pattern="NN_NAKED_NOTIFY" />
+  </Match>
+
+  <!-- justification = "concurrent abstraction calls are in synchronized block" -->
+  <Match>
+    <Class name="com.oracle.graal.hotspot.debug.BenchmarkCounters" />
+    <Method name="getIndex" />
+    <Bug pattern="AT_OPERATION_SEQUENCE_ON_CONCURRENT_ABSTRACTION" />
+  </Match>
+
+  <!-- justification = "counters are only used for statistics" -->
+  <Match>
+    <Class name="com.oracle.graal.hotspot.meta.HotSpotGraphCache" />
+    <Or>
+      <Method name="get" />
+      <Method name="put" />
+      <Method name="removeGraphs" />
+    </Or>
+    <Bug pattern="VO_VOLATILE_INCREMENT" />
+  </Match>
+
+  <!-- justification = "reference equality on the receiver is what we want" -->
+  <Match>
+    <Class name="com.oracle.graal.replacements.StringSubstitutions" />
+    <Method name="equals" />
+    <Bug pattern="ES_COMPARING_PARAMETER_STRING_WITH_EQ" />
+  </Match>
+
+  <!-- justification = "reference equality to test whether string is interned" -->
+  <Match>
+    <Class name="com.oracle.graal.hotspot.phases.AheadOfTimeVerificationPhase" />
+    <Method name="isInternedString" />
+    <Bug pattern="ES_COMPARING_STRINGS_WITH_EQ" />
+  </Match>
+
+</FindBugsFilter>
--- a/make/Makefile	Tue Mar 18 11:07:47 2014 -0700
+++ b/make/Makefile	Tue Mar 18 11:51:37 2014 -0700
@@ -307,7 +307,7 @@
 
 # Builds code that can be shared among different build flavors
 buildshared:
-#	python2.7 -u $(GAMMADIR)/mxtool/mx.py build --no-native --export-dir $(SHARED_DIR)
+	python2.7 -u $(GAMMADIR)/mxtool/mx.py build --no-native --export-dir $(SHARED_DIR)
 
 # Export file rule
 generic_export: $(EXPORT_LIST)
@@ -315,11 +315,11 @@
 export_product:
 	$(MAKE) BUILD_FLAVOR=$(@:export_%=%) generic_export
 export_fastdebug:
-	$(MAKE) BUILD_FLAVOR=$(@:export_%=%) generic_export
+	$(MAKE) BUILD_FLAVOR=$(@:export_%=%) EXPORT_SUBDIR=/$(@:export_%=%) generic_export
 export_debug:
-	$(MAKE) BUILD_FLAVOR=$(@:export_%=%) generic_export
+	$(MAKE) BUILD_FLAVOR=$(@:export_%=%) EXPORT_SUBDIR=/$(@:export_%=%) generic_export
 export_optimized:
-	$(MAKE) BUILD_FLAVOR=$(@:export_%=%) generic_export
+	$(MAKE) BUILD_FLAVOR=$(@:export_%=%) EXPORT_SUBDIR=/$(@:export_%=%) generic_export
 
 export_product_jdk::
 	$(MAKE) BUILD_FLAVOR=$(@:export_%_jdk=%) ALT_EXPORT_PATH=$(JDK_IMAGE_DIR) generic_export
--- a/mx/mx_graal.py	Tue Mar 18 11:07:47 2014 -0700
+++ b/mx/mx_graal.py	Tue Mar 18 11:51:37 2014 -0700
@@ -1638,6 +1638,38 @@
     valueMap = parser.parse(output.getvalue())
     return valueMap
 
+def findbugs(args):
+    '''run FindBugs against non-test Java projects'''
+    findBugsHome = mx.get_env('FINDBUGS_HOME', None)
+    if findBugsHome:
+        findbugsJar = join(findBugsHome, 'lib', 'findbugs.jar')
+    else:
+        findbugsLib = join(_graal_home, 'lib', 'findbugs-3.0.0')
+        if not exists(findbugsLib):
+            tmp = tempfile.mkdtemp(prefix='findbugs-download-tmp', dir=_graal_home)
+            try:
+                findbugsDist = join(tmp, 'findbugs.zip')
+                mx.download(findbugsDist, ['http://sourceforge.net/projects/findbugs/files/findbugs/3.0.0/findbugs-3.0.0-dev-20131204-e3cbbd5.zip'])
+                with zipfile.ZipFile(findbugsDist) as zf:
+                    candidates = [e for e in zf.namelist() if e.endswith('/lib/findbugs.jar')]
+                    assert len(candidates) == 1, candidates
+                    libDirInZip = os.path.dirname(candidates[0])
+                    zf.extractall(tmp)
+                shutil.copytree(join(tmp, libDirInZip), findbugsLib)
+            finally:
+                shutil.rmtree(tmp)
+        findbugsJar = join(findbugsLib, 'findbugs.jar')
+    assert exists(findbugsJar)
+    nonTestProjects = [p for p in mx.projects() if not p.name.endswith('.test') and not p.name.endswith('.jtt')]
+    outputDirs = [p.output_dir() for p in nonTestProjects]
+    findbugsResults = join(_graal_home, 'findbugs.results')
+    exitcode = mx.run_java(['-jar', findbugsJar, '-textui', '-low', '-maxRank', '15', '-exclude', join(_graal_home, 'graal', 'findbugsExcludeFilter.xml'),
+                 '-auxclasspath', mx.classpath([p.name for p in nonTestProjects]), '-output', findbugsResults, '-progress', '-exitcode'] + args + outputDirs, nonZeroIsFatal=False)
+    if exitcode != 0:
+        with open(findbugsResults) as fp:
+            mx.log(fp.read())
+    os.unlink(findbugsResults)
+    return exitcode
 
 def mx_init(suite):
     commands = {
@@ -1646,6 +1678,7 @@
         'buildvms': [buildvms, '[-options]'],
         'c1visualizer' : [c1visualizer, ''],
         'clean': [clean, ''],
+        'findbugs': [findbugs, ''],
         'generateZshCompletion' : [generateZshCompletion, ''],
         'hsdis': [hsdis, '[att]'],
         'hcfdis': [hcfdis, ''],
--- a/mx/projects	Tue Mar 18 11:07:47 2014 -0700
+++ b/mx/projects	Tue Mar 18 11:51:37 2014 -0700
@@ -13,9 +13,6 @@
 library@CHECKSTYLE@path=lib/checkstyle-5.5-all.jar
 library@CHECKSTYLE@urls=jar:http://sourceforge.net/projects/checkstyle/files/checkstyle/5.5/checkstyle-5.5-bin.zip/download!/checkstyle-5.5/checkstyle-5.5-all.jar
 
-library@FINDBUGS@path=lib/findbugs-3.0.0-dev-20131204-e3cbbd5.jar
-library@FINDBUGS@urls=jar:http://sourceforge.net/projects/findbugs/files/findbugs/3.0.0/findbugs-3.0.0-dev-20131204-e3cbbd5.zip/download!/findbugs-3.0.0-dev-20131204-e3cbbd5/lib/findbugs.jar
-
 library@DACAPO@path=lib/dacapo-9.12-bach.jar
 library@DACAPO@urls=http://softlayer.dl.sourceforge.net/project/dacapobench/9.12-bach/dacapo-9.12-bach.jar
 
@@ -498,7 +495,7 @@
 # graal.java.decompiler.test
 project@com.oracle.graal.java.decompiler.test@subDir=graal
 project@com.oracle.graal.java.decompiler.test@sourceDirs=src
-project@com.oracle.graal.java.decompiler.test@dependencies=com.oracle.graal.printer,com.oracle.graal.runtime
+project@com.oracle.graal.java.decompiler.test@dependencies=JUNIT,com.oracle.graal.printer,com.oracle.graal.runtime
 project@com.oracle.graal.java.decompiler.test@checkstyle=com.oracle.graal.graph
 project@com.oracle.graal.java.decompiler.test@javaCompliance=1.7
 project@com.oracle.graal.java.decompiler.test@workingSets=Graal,Test
--- a/mxtool/mx.py	Tue Mar 18 11:07:47 2014 -0700
+++ b/mxtool/mx.py	Tue Mar 18 11:51:37 2014 -0700
@@ -1099,6 +1099,8 @@
     return run(java().format_cmd(args, addDefaultArgs), nonZeroIsFatal=nonZeroIsFatal, out=out, err=err, cwd=cwd)
 
 def _kill_process_group(pid, sig):
+    if not sig:
+        sig = signal.SIGKILL
     pgid = os.getpgid(pid)
     try:
         os.killpg(pgid, sig)
@@ -1892,10 +1894,13 @@
         abort('Could not find Eclipse executable. Use -e option or ensure ECLIPSE_EXE environment variable is set.')
 
     # Maybe an Eclipse installation dir was specified - look for the executable in it
-    if join(args.eclipse_exe, exe_suffix('eclipse')):
+    if isdir(args.eclipse_exe):
         args.eclipse_exe = join(args.eclipse_exe, exe_suffix('eclipse'))
-
-    if not os.path.isfile(args.eclipse_exe) or not os.access(args.eclipse_exe, os.X_OK):
+        warn("The eclipse-exe was a directory, now using " + args.eclipse_exe)
+
+    if not os.path.isfile(args.eclipse_exe):
+        abort('File does not exist: ' + args.eclipse_exe)
+    if not os.access(args.eclipse_exe, os.X_OK):
         abort('Not an executable file: ' + args.eclipse_exe)
 
     eclipseinit([], buildProcessorJars=False)
--- a/src/cpu/sparc/vm/graalCodeInstaller_sparc.hpp	Tue Mar 18 11:07:47 2014 -0700
+++ b/src/cpu/sparc/vm/graalCodeInstaller_sparc.hpp	Tue Mar 18 11:51:37 2014 -0700
@@ -41,55 +41,32 @@
   }
 }
 
-inline void CodeInstaller::pd_site_DataPatch(int pc_offset, oop site) {
-  oop inlineData = CompilationResult_DataPatch::inlineData(site);
-  address pc = _instructions->start() + pc_offset;
+inline void CodeInstaller::pd_patch_OopData(int pc_offset, oop data) {
+  if (OopData::compressed(obj)) {
+    fatal("unimplemented: narrow oop relocation");
+  } else {
+    address pc = _instructions->start() + pc_offset;
+    Handle obj = OopData::object(data);
+    jobject value = JNIHandles::make_local(obj());
 
-  if (inlineData != NULL) {
-    oop kind = Constant::kind(inlineData);
-    char typeChar = Kind::typeChar(kind);
+    NativeMovConstReg* move = nativeMovConstReg_at(pc);
+    move->set_data((intptr_t) value);
 
-    switch (typeChar) {
-      case 'z':
-      case 'b':
-      case 's':
-      case 'c':
-      case 'i':
-        fatal("int-sized values not expected in DataPatch");
-        break;
-      case 'f':
-      case 'j':
-      case 'd': {
-        NativeMovConstReg* move = nativeMovConstReg_at(pc);
-        uint64_t value = Constant::primitive(inlineData);
-        move->set_data(value);
-        break;
-      }
-      case 'a': {
-        NativeMovConstReg* move = nativeMovConstReg_at(pc);
-        Handle obj = Constant::object(inlineData);
-        jobject value = JNIHandles::make_local(obj());
-        move->set_data((intptr_t) value);
+    // We need two relocations:  one on the sethi and one on the add.
+    int oop_index = _oop_recorder->find_index(value);
+    RelocationHolder rspec = oop_Relocation::spec(oop_index);
+    _instructions->relocate(pc + NativeMovConstReg::sethi_offset, rspec);
+    _instructions->relocate(pc + NativeMovConstReg::add_offset, rspec);
+  }
+}
 
-        // We need two relocations:  one on the sethi and one on the add.
-        int oop_index = _oop_recorder->find_index(value);
-        RelocationHolder rspec = oop_Relocation::spec(oop_index);
-        _instructions->relocate(pc + NativeMovConstReg::sethi_offset, rspec);
-        _instructions->relocate(pc + NativeMovConstReg::add_offset, rspec);
-        break;
-      }
-      default:
-        fatal(err_msg("unexpected Kind (%d) in DataPatch", typeChar));
-        break;
-    }
-  } else {
-    oop dataRef = CompilationResult_DataPatch::externalData(site);
-    jint offset = HotSpotCompiledCode_HotSpotData::offset(dataRef);
+inline void CodeInstaller::pd_patch_DataSectionReference(int pc_offset, oop data) {
+  address pc = _instructions->start() + pc_offset;
+  jint offset = DataSectionReference::offset(data);
 
-    NativeMovRegMem* load = nativeMovRegMem_at(pc);
-    int disp = _constants_size + pc_offset - offset - BytesPerInstWord;
-    load->set_offset(-disp);
-  }
+  NativeMovRegMem* load = nativeMovRegMem_at(pc);
+  int disp = _constants_size + pc_offset - offset - BytesPerInstWord;
+  load->set_offset(-disp);
 }
 
 inline void CodeInstaller::pd_relocate_CodeBlob(CodeBlob* cb, NativeInstruction* inst) {
@@ -121,24 +98,24 @@
   }
 #endif
   switch (_next_call_type) {
-    case MARK_INLINE_INVOKE:
+    case INLINE_INVOKE:
       break;
-    case MARK_INVOKEVIRTUAL:
-    case MARK_INVOKEINTERFACE: {
+    case INVOKEVIRTUAL:
+    case INVOKEINTERFACE: {
       assert(method == NULL || !method->is_static(), "cannot call static method with invokeinterface");
       NativeCall* call = nativeCall_at(_instructions->start() + pc_offset);
       call->set_destination(SharedRuntime::get_resolve_virtual_call_stub());
       _instructions->relocate(call->instruction_address(), virtual_call_Relocation::spec(_invoke_mark_pc));
       break;
     }
-    case MARK_INVOKESTATIC: {
+    case INVOKESTATIC: {
       assert(method == NULL || method->is_static(), "cannot call non-static method with invokestatic");
       NativeCall* call = nativeCall_at(_instructions->start() + pc_offset);
       call->set_destination(SharedRuntime::get_resolve_static_call_stub());
       _instructions->relocate(call->instruction_address(), relocInfo::static_call_type);
       break;
     }
-    case MARK_INVOKESPECIAL: {
+    case INVOKESPECIAL: {
       assert(method == NULL || !method->is_static(), "cannot call static method with invokespecial");
       NativeCall* call = nativeCall_at(_instructions->start() + pc_offset);
       call->set_destination(SharedRuntime::get_resolve_opt_virtual_call_stub());
@@ -153,16 +130,16 @@
 
 inline void CodeInstaller::pd_relocate_poll(address pc, jint mark) {
   switch (mark) {
-    case MARK_POLL_NEAR: {
+    case POLL_NEAR: {
       fatal("unimplemented");
     }
-    case MARK_POLL_FAR:
+    case POLL_FAR:
       _instructions->relocate(pc, relocInfo::poll_type);
       break;
-    case MARK_POLL_RETURN_NEAR: {
+    case POLL_RETURN_NEAR: {
       fatal("unimplemented");
     }
-    case MARK_POLL_RETURN_FAR:
+    case POLL_RETURN_FAR:
       _instructions->relocate(pc, relocInfo::poll_return_type);
       break;
     default:
--- a/src/cpu/x86/vm/graalCodeInstaller_x86.hpp	Tue Mar 18 11:07:47 2014 -0700
+++ b/src/cpu/x86/vm/graalCodeInstaller_x86.hpp	Tue Mar 18 11:51:37 2014 -0700
@@ -59,68 +59,49 @@
   }
 }
 
-inline void CodeInstaller::pd_site_DataPatch(int pc_offset, oop site) {
-  oop inlineData = CompilationResult_DataPatch::inlineData(site);
+inline bool check_metaspace_data(address pc, oop data) {
+  jlong value = MetaspaceData::value(data);
+  address operand = Assembler::locate_operand(pc, Assembler::imm_operand);
+  if (MetaspaceData::compressed(data)) {
+    assert(*((jint*) operand) == value, err_msg("wrong compressed metaspace pointer: %p != %p", *((jint*) operand), value));
+  } else {
+    assert(*((jlong*) operand) == value, err_msg("wrong metaspace pointer: %p != %p", *((jlong*) operand), value));
+  }
+  return true;
+}
+
+inline void CodeInstaller::pd_patch_OopData(int pc_offset, oop data) {
   address pc = _instructions->start() + pc_offset;
 
-  if (inlineData != NULL) {
-    oop kind = Constant::kind(inlineData);
-    char typeChar = Kind::typeChar(kind);
-
-    switch (typeChar) {
-      case 'z':
-      case 'b':
-      case 's':
-      case 'c':
-      case 'i':
-        fatal("int-sized values not expected in DataPatch");
-        break;
-      case 'n': {
-        address operand = Assembler::locate_operand(pc, Assembler::narrow_oop_operand);
-        Handle obj = Constant::object(inlineData);
+  Handle obj = OopData::object(data);
+  jobject value = JNIHandles::make_local(obj());
+  if (OopData::compressed(data)) {
+    address operand = Assembler::locate_operand(pc, Assembler::narrow_oop_operand);
+    int oop_index = _oop_recorder->find_index(value);
+    _instructions->relocate(pc, oop_Relocation::spec(oop_index), Assembler::narrow_oop_operand);
+    TRACE_graal_3("relocating (narrow oop constant) at %p/%p", pc, operand);
+  } else {
+    address operand = Assembler::locate_operand(pc, Assembler::imm_operand);
+    *((jobject*) operand) = value;
+    _instructions->relocate(pc, oop_Relocation::spec_for_immediate(), Assembler::imm_operand);
+    TRACE_graal_3("relocating (oop constant) at %p/%p", pc, operand);
+  }
+}
 
-        jobject value = JNIHandles::make_local(obj());
-        int oop_index = _oop_recorder->find_index(value);
-        _instructions->relocate(pc, oop_Relocation::spec(oop_index), Assembler::narrow_oop_operand);
-        TRACE_graal_3("relocating (narrow oop constant) at %p/%p", pc, operand);
-        break;
-      }
-      case 'f':
-      case 'j':
-      case 'd':
-      case '*': {
-        address operand = Assembler::locate_operand(pc, Assembler::imm_operand);
-        *((jlong*) operand) = Constant::primitive(inlineData);
-        break;
-      }
-      case 'a': {
-        address operand = Assembler::locate_operand(pc, Assembler::imm_operand);
-        Handle obj = Constant::object(inlineData);
+inline void CodeInstaller::pd_patch_DataSectionReference(int pc_offset, oop data) {
+  address pc = _instructions->start() + pc_offset;
+  jint offset = DataSectionReference::offset(data);
 
-        jobject value = JNIHandles::make_local(obj());
-        *((jobject*) operand) = value;
-        _instructions->relocate(pc, oop_Relocation::spec_for_immediate(), Assembler::imm_operand);
-        TRACE_graal_3("relocating (oop constant) at %p/%p", pc, operand);
-        break;
-      }
-      default:
-        fatal(err_msg("unexpected Kind (%d) in DataPatch", typeChar));
-        break;
-    }
-  } else {
-    oop dataRef = CompilationResult_DataPatch::externalData(site);
-    jint offset = HotSpotCompiledCode_HotSpotData::offset(dataRef);
-    address operand = Assembler::locate_operand(pc, Assembler::disp32_operand);
-    address next_instruction = Assembler::locate_next_instruction(pc);
-    address dest = _constants->start() + offset;
+  address operand = Assembler::locate_operand(pc, Assembler::disp32_operand);
+  address next_instruction = Assembler::locate_next_instruction(pc);
+  address dest = _constants->start() + offset;
 
-    long disp = dest - next_instruction;
-    assert(disp == (jint) disp, "disp doesn't fit in 32 bits");
-    *((jint*) operand) = (jint) disp;
+  long disp = dest - next_instruction;
+  assert(disp == (jint) disp, "disp doesn't fit in 32 bits");
+  *((jint*) operand) = (jint) disp;
 
-    _instructions->relocate(pc, section_word_Relocation::spec((address) dest, CodeBuffer::SECT_CONSTS), Assembler::disp32_operand);
-    TRACE_graal_3("relocating at %p/%p with destination at %p (%d)", pc, operand, dest, offset);
-  }
+  _instructions->relocate(pc, section_word_Relocation::spec((address) dest, CodeBuffer::SECT_CONSTS), Assembler::disp32_operand);
+  TRACE_graal_3("relocating at %p/%p with destination at %p (%d)", pc, operand, dest, offset);
 }
 
 inline void CodeInstaller::pd_relocate_CodeBlob(CodeBlob* cb, NativeInstruction* inst) {
@@ -170,10 +151,10 @@
   }
 #endif
   switch (_next_call_type) {
-    case MARK_INLINE_INVOKE:
+    case INLINE_INVOKE:
       break;
-    case MARK_INVOKEVIRTUAL:
-    case MARK_INVOKEINTERFACE: {
+    case INVOKEVIRTUAL:
+    case INVOKEINTERFACE: {
       assert(method == NULL || !method->is_static(), "cannot call static method with invokeinterface");
 
       NativeCall* call = nativeCall_at(_instructions->start() + pc_offset);
@@ -183,7 +164,7 @@
                                              Assembler::call32_operand);
       break;
     }
-    case MARK_INVOKESTATIC: {
+    case INVOKESTATIC: {
       assert(method == NULL || method->is_static(), "cannot call non-static method with invokestatic");
 
       NativeCall* call = nativeCall_at(_instructions->start() + pc_offset);
@@ -192,7 +173,7 @@
                                              relocInfo::static_call_type, Assembler::call32_operand);
       break;
     }
-    case MARK_INVOKESPECIAL: {
+    case INVOKESPECIAL: {
       assert(method == NULL || !method->is_static(), "cannot call static method with invokespecial");
       NativeCall* call = nativeCall_at(_instructions->start() + pc_offset);
       call->set_destination(SharedRuntime::get_resolve_opt_virtual_call_stub());
@@ -216,24 +197,24 @@
 
 inline void CodeInstaller::pd_relocate_poll(address pc, jint mark) {
   switch (mark) {
-    case MARK_POLL_NEAR: {
+    case POLL_NEAR: {
       relocate_poll_near(pc);
       _instructions->relocate(pc, relocInfo::poll_type, Assembler::disp32_operand);
       break;
     }
-    case MARK_POLL_FAR:
+    case POLL_FAR:
       // This is a load from a register so there is no relocatable operand.
       // We just have to ensure that the format is not disp32_operand
       // so that poll_Relocation::fix_relocation_after_move does the right
       // thing (i.e. ignores this relocation record)
       _instructions->relocate(pc, relocInfo::poll_type, Assembler::imm_operand);
       break;
-    case MARK_POLL_RETURN_NEAR: {
+    case POLL_RETURN_NEAR: {
       relocate_poll_near(pc);
       _instructions->relocate(pc, relocInfo::poll_return_type, Assembler::disp32_operand);
       break;
     }
-    case MARK_POLL_RETURN_FAR:
+    case POLL_RETURN_FAR:
       // see comment above for MARK_POLL_FAR
       _instructions->relocate(pc, relocInfo::poll_return_type, Assembler::imm_operand);
       break;
--- a/src/share/vm/classfile/systemDictionary.hpp	Tue Mar 18 11:07:47 2014 -0700
+++ b/src/share/vm/classfile/systemDictionary.hpp	Tue Mar 18 11:51:37 2014 -0700
@@ -187,12 +187,15 @@
   do_klass(BitSet_klass,                          java_util_BitSet,                                             Opt) \
   /* graal.hotspot */                                                                                                \
   do_klass(HotSpotCompiledCode_klass,             com_oracle_graal_hotspot_HotSpotCompiledCode,                 Opt) \
-  do_klass(HotSpotCompiledCode_HotSpotData_klass, com_oracle_graal_hotspot_HotSpotCompiledCode_HotSpotData,     Opt) \
-  do_klass(HotSpotCompiledCode_DataSection_klass, com_oracle_graal_hotspot_HotSpotCompiledCode_DataSection,     Opt) \
   do_klass(HotSpotCompiledCode_Comment_klass,     com_oracle_graal_hotspot_HotSpotCompiledCode_Comment,         Opt) \
   do_klass(HotSpotCompiledNmethod_klass,          com_oracle_graal_hotspot_HotSpotCompiledNmethod,              Opt) \
   do_klass(HotSpotCompiledRuntimeStub_klass,      com_oracle_graal_hotspot_HotSpotCompiledRuntimeStub,          Opt) \
   do_klass(HotSpotForeignCallLinkage_klass,       com_oracle_graal_hotspot_HotSpotForeignCallLinkage,           Opt) \
+  do_klass(HotSpotReferenceMap_klass,             com_oracle_graal_hotspot_HotSpotReferenceMap,                 Opt) \
+  do_klass(DataSection_klass,                     com_oracle_graal_hotspot_data_DataSection,                    Opt) \
+  do_klass(DataSectionReference_klass,            com_oracle_graal_hotspot_data_DataSectionReference,           Opt) \
+  do_klass(MetaspaceData_klass,                   com_oracle_graal_hotspot_data_MetaspaceData,                  Opt) \
+  do_klass(OopData_klass,                         com_oracle_graal_hotspot_data_OopData,                        Opt) \
   do_klass(HotSpotCodeInfo_klass,                 com_oracle_graal_hotspot_meta_HotSpotCodeInfo,                Opt) \
   do_klass(HotSpotInstalledCode_klass,            com_oracle_graal_hotspot_meta_HotSpotInstalledCode,           Opt) \
   do_klass(HotSpotNmethod_klass,                  com_oracle_graal_hotspot_meta_HotSpotNmethod,                 Opt) \
@@ -210,7 +213,6 @@
   do_klass(Assumptions_CallSiteTargetValue_klass, com_oracle_graal_api_code_Assumptions_CallSiteTargetValue,    Opt) \
   do_klass(BytecodePosition_klass,                com_oracle_graal_api_code_BytecodePosition,                   Opt) \
   do_klass(DebugInfo_klass,                       com_oracle_graal_api_code_DebugInfo,                          Opt) \
-  do_klass(ReferenceMap_klass,                    com_oracle_graal_api_code_ReferenceMap,                       Opt) \
   do_klass(RegisterSaveLayout_klass,              com_oracle_graal_api_code_RegisterSaveLayout,                 Opt) \
   do_klass(BytecodeFrame_klass,                   com_oracle_graal_api_code_BytecodeFrame,                      Opt) \
   do_klass(CompilationResult_klass,               com_oracle_graal_api_code_CompilationResult,                  Opt) \
--- a/src/share/vm/classfile/vmSymbols.hpp	Tue Mar 18 11:07:47 2014 -0700
+++ b/src/share/vm/classfile/vmSymbols.hpp	Tue Mar 18 11:51:37 2014 -0700
@@ -296,14 +296,17 @@
   template(com_oracle_graal_hotspot_HotSpotKlassOop,                 "com/oracle/graal/hotspot/HotSpotKlassOop")                      \
   template(com_oracle_graal_hotspot_HotSpotOptions,                  "com/oracle/graal/hotspot/HotSpotOptions")                       \
   template(com_oracle_graal_hotspot_HotSpotCompiledCode,             "com/oracle/graal/hotspot/HotSpotCompiledCode")                  \
-  template(com_oracle_graal_hotspot_HotSpotCompiledCode_HotSpotData, "com/oracle/graal/hotspot/HotSpotCompiledCode$HotSpotData")      \
-  template(com_oracle_graal_hotspot_HotSpotCompiledCode_DataSection, "com/oracle/graal/hotspot/HotSpotCompiledCode$DataSection")      \
   template(com_oracle_graal_hotspot_HotSpotCompiledCode_Comment,     "com/oracle/graal/hotspot/HotSpotCompiledCode$Comment")          \
   template(com_oracle_graal_hotspot_HotSpotCompiledNmethod,          "com/oracle/graal/hotspot/HotSpotCompiledNmethod")               \
   template(com_oracle_graal_hotspot_HotSpotCompiledRuntimeStub,      "com/oracle/graal/hotspot/HotSpotCompiledRuntimeStub")           \
   template(com_oracle_graal_hotspot_HotSpotForeignCallLinkage,       "com/oracle/graal/hotspot/HotSpotForeignCallLinkage")            \
+  template(com_oracle_graal_hotspot_HotSpotReferenceMap,             "com/oracle/graal/hotspot/HotSpotReferenceMap")                  \
   template(com_oracle_graal_hotspot_bridge_VMToCompiler,             "com/oracle/graal/hotspot/bridge/VMToCompiler")                  \
   template(com_oracle_graal_hotspot_bridge_CompilerToVMImpl,         "com/oracle/graal/hotspot/bridge/CompilerToVMImpl")              \
+  template(com_oracle_graal_hotspot_data_DataSection,                "com/oracle/graal/hotspot/data/DataSection")                     \
+  template(com_oracle_graal_hotspot_data_DataSectionReference,       "com/oracle/graal/hotspot/data/DataSectionReference")            \
+  template(com_oracle_graal_hotspot_data_MetaspaceData,              "com/oracle/graal/hotspot/data/MetaspaceData")                   \
+  template(com_oracle_graal_hotspot_data_OopData,                    "com/oracle/graal/hotspot/data/OopData")                         \
   template(com_oracle_graal_hotspot_meta_HotSpotCodeInfo,            "com/oracle/graal/hotspot/meta/HotSpotCodeInfo")                 \
   template(com_oracle_graal_hotspot_meta_HotSpotInstalledCode,       "com/oracle/graal/hotspot/meta/HotSpotInstalledCode")            \
   template(com_oracle_graal_hotspot_meta_HotSpotNmethod,             "com/oracle/graal/hotspot/meta/HotSpotNmethod")                  \
@@ -340,7 +343,6 @@
   template(com_oracle_graal_api_code_BytecodeFrame,                  "com/oracle/graal/api/code/BytecodeFrame")                       \
   template(com_oracle_graal_api_code_BytecodePosition,               "com/oracle/graal/api/code/BytecodePosition")                    \
   template(com_oracle_graal_api_code_DebugInfo,                      "com/oracle/graal/api/code/DebugInfo")                           \
-  template(com_oracle_graal_api_code_ReferenceMap,                   "com/oracle/graal/api/code/ReferenceMap")                        \
   template(com_oracle_graal_api_code_Register,                       "com/oracle/graal/api/code/Register")                            \
   template(com_oracle_graal_api_code_RegisterValue,                  "com/oracle/graal/api/code/RegisterValue")                       \
   template(com_oracle_graal_api_code_StackSlot,                      "com/oracle/graal/api/code/StackSlot")                           \
--- a/src/share/vm/code/nmethod.cpp	Tue Mar 18 11:07:47 2014 -0700
+++ b/src/share/vm/code/nmethod.cpp	Tue Mar 18 11:51:37 2014 -0700
@@ -1025,6 +1025,7 @@
 void nmethod::print_on(outputStream* st, const char* msg) const {
   if (st != NULL) {
     ttyLocker ttyl;
+    if (CIPrintCompilerName) st->print("%s:", compiler()->name());
     if (WizardMode) {
       CompileTask::print_compilation(st, this, msg, /*short_form:*/ true);
       st->print_cr(" (" INTPTR_FORMAT ")", this);
--- a/src/share/vm/graal/graalCodeInstaller.cpp	Tue Mar 18 11:07:47 2014 -0700
+++ b/src/share/vm/graal/graalCodeInstaller.cpp	Tue Mar 18 11:51:37 2014 -0700
@@ -91,8 +91,8 @@
 static OopMap* create_oop_map(jint total_frame_size, jint parameter_count, oop debug_info) {
   OopMap* map = new OopMap(total_frame_size, parameter_count);
   oop reference_map = DebugInfo::referenceMap(debug_info);
-  oop register_map = ReferenceMap::registerRefMap(reference_map);
-  oop frame_map = ReferenceMap::frameRefMap(reference_map);
+  oop register_map = HotSpotReferenceMap::registerRefMap(reference_map);
+  oop frame_map = HotSpotReferenceMap::frameRefMap(reference_map);
   oop callee_save_info = (oop) DebugInfo::calleeSaveInfo(debug_info);
 
   if (register_map != NULL) {
@@ -157,6 +157,27 @@
   return map;
 }
 
+static void record_metadata_reference(oop obj, jlong prim, bool compressed, OopRecorder* oop_recorder) {
+  if (obj->is_a(HotSpotResolvedObjectType::klass())) {
+    Klass* klass = java_lang_Class::as_Klass(HotSpotResolvedObjectType::javaClass(obj));
+    if (compressed) {
+      assert(Klass::decode_klass((narrowKlass) prim) == klass, err_msg("%s @ %p != %p", klass->name()->as_C_string(), klass, prim));
+    } else {
+      assert((Klass*) prim == klass, err_msg("%s @ %p != %p", klass->name()->as_C_string(), klass, prim));
+    }
+    int index = oop_recorder->find_index(klass);
+    TRACE_graal_3("metadata[%d of %d] = %s", index, oop_recorder->metadata_count(), klass->name()->as_C_string());
+  } else if (obj->is_a(HotSpotResolvedJavaMethod::klass())) {
+    Method* method = (Method*) (address) HotSpotResolvedJavaMethod::metaspaceMethod(obj);
+    assert(!compressed, err_msg("unexpected compressed method pointer %s @ %p = %p", method->name()->as_C_string(), method, prim));
+    int index = oop_recorder->find_index(method);
+    TRACE_graal_3("metadata[%d of %d] = %s", index, oop_recorder->metadata_count(), method->name()->as_C_string());
+  } else {
+    assert(java_lang_String::is_instance(obj),
+        err_msg("unexpected metadata reference (%s) for constant %ld (%p)", obj->klass()->name()->as_C_string(), prim, prim));
+  }
+}
+
 // Records any Metadata values embedded in a Constant (e.g., the value returned by HotSpotResolvedObjectType.klass()).
 static void record_metadata_in_constant(oop constant, OopRecorder* oop_recorder) {
   char kind = Kind::typeChar(Constant::kind(constant));
@@ -165,23 +186,15 @@
     oop obj = Constant::object(constant);
     jlong prim = Constant::primitive(constant);
     if (obj != NULL) {
-      if (obj->is_a(HotSpotResolvedObjectType::klass())) {
-        Klass* klass = java_lang_Class::as_Klass(HotSpotResolvedObjectType::javaClass(obj));
-        assert((Klass*) prim == klass, err_msg("%s @ %p != %p", klass->name()->as_C_string(), klass, prim));
-        int index = oop_recorder->find_index(klass);
-        TRACE_graal_3("metadata[%d of %d] = %s", index, oop_recorder->metadata_count(), klass->name()->as_C_string());
-      } else if (obj->is_a(HotSpotResolvedJavaMethod::klass())) {
-        Method* method = (Method*) (address) HotSpotResolvedJavaMethod::metaspaceMethod(obj);
-        int index = oop_recorder->find_index(method);
-        TRACE_graal_3("metadata[%d of %d] = %s", index, oop_recorder->metadata_count(), method->name()->as_C_string());
-      } else {
-        assert(java_lang_String::is_instance(obj),
-            err_msg("unexpected annotation type (%s) for constant %ld (%p) of kind %c", obj->klass()->name()->as_C_string(), prim, prim, kind));
-      }
+      record_metadata_reference(obj, prim, false, oop_recorder);
     }
   }
 }
 
+static void record_metadata_in_patch(oop data, OopRecorder* oop_recorder) {
+  record_metadata_reference(MetaspaceData::annotation(data), MetaspaceData::value(data), MetaspaceData::compressed(data) != 0, oop_recorder);
+}
+
 ScopeValue* CodeInstaller::get_scope_value(oop value, int total_frame_size, GrowableArray<ScopeValue*>* objects, ScopeValue* &second, OopRecorder* oop_recorder) {
   second = NULL;
   if (value == Value::ILLEGAL()) {
@@ -445,8 +458,8 @@
 
   // Pre-calculate the constants section size.  This is required for PC-relative addressing.
   _dataSection = HotSpotCompiledCode::dataSection(compiled_code);
-  guarantee(HotSpotCompiledCode_DataSection::sectionAlignment(_dataSection) <= _constants->alignment(), "Alignment inside constants section is restricted by alignment of section begin");
-  arrayOop data = (arrayOop) HotSpotCompiledCode_DataSection::data(_dataSection);
+  guarantee(DataSection::sectionAlignment(_dataSection) <= _constants->alignment(), "Alignment inside constants section is restricted by alignment of section begin");
+  arrayOop data = (arrayOop) DataSection::data(_dataSection);
   _constants_size = data->length();
   if (_constants_size > 0) {
     _constants_size = align_size_up(_constants_size, _constants->alignment());
@@ -456,7 +469,7 @@
   _comments = (arrayOop) HotSpotCompiledCode::comments(compiled_code);
 #endif
 
-  _next_call_type = MARK_INVOKE_INVALID;
+  _next_call_type = INVOKE_INVALID;
 }
 
 // perform data and call relocation on the CodeBuffer
@@ -482,30 +495,24 @@
 
   // copy the constant data into the newly created CodeBuffer
   address end_data = _constants->start() + _constants_size;
-  arrayOop data = (arrayOop) HotSpotCompiledCode_DataSection::data(_dataSection);
+  arrayOop data = (arrayOop) DataSection::data(_dataSection);
   memcpy(_constants->start(), data->base(T_BYTE), data->length());
   _constants->set_end(end_data);
 
-  objArrayOop patches = (objArrayOop) HotSpotCompiledCode_DataSection::patches(_dataSection);
+  objArrayOop patches = (objArrayOop) DataSection::patches(_dataSection);
   for (int i = 0; i < patches->length(); i++) {
     oop patch = patches->obj_at(i);
-    oop constant = HotSpotCompiledCode_HotSpotData::constant(patch);
-    oop kind = Constant::kind(constant);
-    char typeChar = Kind::typeChar(kind);
-    switch (typeChar) {
-      case 'f':
-      case 'j':
-      case 'd':
-        record_metadata_in_constant(constant, _oop_recorder);
-        break;
-      case 'a':
-        Handle obj = Constant::object(constant);
-        jobject value = JNIHandles::make_local(obj());
-        int oop_index = _oop_recorder->find_index(value);
+    oop data = CompilationResult_DataPatch::data(patch);
+    if (data->is_a(MetaspaceData::klass())) {
+      record_metadata_in_patch(data, _oop_recorder);
+    } else if (data->is_a(OopData::klass())) {
+      Handle obj = OopData::object(data);
+      jobject value = JNIHandles::make_local(obj());
+      int oop_index = _oop_recorder->find_index(value);
 
-        address dest = _constants->start() + HotSpotCompiledCode_HotSpotData::offset(patch);
-        _constants->relocate(dest, oop_Relocation::spec(oop_index));
-        break;
+      address dest = _constants->start() + CompilationResult_Site::pcOffset(patch);
+      assert(!OopData::compressed(data), err_msg("unexpected compressed oop in data section"));
+      _constants->relocate(dest, oop_Relocation::spec(oop_index));
     }
   }
 
@@ -769,7 +776,7 @@
     CodeInstaller::pd_relocate_JavaMethod(hotspot_method, pc_offset);
   }
 
-  _next_call_type = MARK_INVOKE_INVALID;
+  _next_call_type = INVOKE_INVALID;
 
   if (debug_info != NULL) {
     _debug_recorder->end_safepoint(next_pc_offset);
@@ -777,19 +784,16 @@
 }
 
 void CodeInstaller::site_DataPatch(CodeBuffer& buffer, jint pc_offset, oop site) {
-  oop inlineData = CompilationResult_DataPatch::inlineData(site);
-  if (inlineData != NULL) {
-    oop kind = Constant::kind(inlineData);
-    char typeChar = Kind::typeChar(kind);
-    switch (typeChar) {
-      case 'f':
-      case 'j':
-      case 'd':
-        record_metadata_in_constant(inlineData, _oop_recorder);
-        break;
-    }
+  oop data = CompilationResult_DataPatch::data(site);
+  if (data->is_a(MetaspaceData::klass())) {
+    record_metadata_in_patch(data, _oop_recorder);
+  } else if (data->is_a(OopData::klass())) {
+    pd_patch_OopData(pc_offset, data);
+  } else if (data->is_a(DataSectionReference::klass())) {
+    pd_patch_DataSectionReference(pc_offset, data);
+  } else {
+    fatal("unknown data patch type");
   }
-  CodeInstaller::pd_site_DataPatch(pc_offset, site);
 }
 
 void CodeInstaller::site_Mark(CodeBuffer& buffer, jint pc_offset, oop site) {
@@ -802,33 +806,33 @@
     address pc = _instructions->start() + pc_offset;
 
     switch (id) {
-      case MARK_UNVERIFIED_ENTRY:
+      case UNVERIFIED_ENTRY:
         _offsets.set_value(CodeOffsets::Entry, pc_offset);
         break;
-      case MARK_VERIFIED_ENTRY:
+      case VERIFIED_ENTRY:
         _offsets.set_value(CodeOffsets::Verified_Entry, pc_offset);
         break;
-      case MARK_OSR_ENTRY:
+      case OSR_ENTRY:
         _offsets.set_value(CodeOffsets::OSR_Entry, pc_offset);
         break;
-      case MARK_EXCEPTION_HANDLER_ENTRY:
+      case EXCEPTION_HANDLER_ENTRY:
         _offsets.set_value(CodeOffsets::Exceptions, pc_offset);
         break;
-      case MARK_DEOPT_HANDLER_ENTRY:
+      case DEOPT_HANDLER_ENTRY:
         _offsets.set_value(CodeOffsets::Deopt, pc_offset);
         break;
-      case MARK_INVOKEVIRTUAL:
-      case MARK_INVOKEINTERFACE:
-      case MARK_INLINE_INVOKE:
-      case MARK_INVOKESTATIC:
-      case MARK_INVOKESPECIAL:
+      case INVOKEVIRTUAL:
+      case INVOKEINTERFACE:
+      case INLINE_INVOKE:
+      case INVOKESTATIC:
+      case INVOKESPECIAL:
         _next_call_type = (MarkId) id;
         _invoke_mark_pc = pc;
         break;
-      case MARK_POLL_NEAR:
-      case MARK_POLL_FAR:
-      case MARK_POLL_RETURN_NEAR:
-      case MARK_POLL_RETURN_FAR:
+      case POLL_NEAR:
+      case POLL_FAR:
+      case POLL_RETURN_NEAR:
+      case POLL_RETURN_FAR:
         pd_relocate_poll(pc, id);
         break;
       default:
--- a/src/share/vm/graal/graalCodeInstaller.hpp	Tue Mar 18 11:07:47 2014 -0700
+++ b/src/share/vm/graal/graalCodeInstaller.hpp	Tue Mar 18 11:51:37 2014 -0700
@@ -24,28 +24,30 @@
 #ifndef SHARE_VM_GRAAL_GRAAL_CODE_INSTALLER_HPP
 #define SHARE_VM_GRAAL_GRAAL_CODE_INSTALLER_HPP
 
+#include "graal/graalEnv.hpp"
+
 /*
  * This class handles the conversion from a InstalledCode to a CodeBlob or an nmethod.
  */
 class CodeInstaller {
+  friend class VMStructs;
 private:
-  // these need to correspond to Marks.java
   enum MarkId {
-    MARK_VERIFIED_ENTRY             = 1,
-    MARK_UNVERIFIED_ENTRY           = 2,
-    MARK_OSR_ENTRY                  = 3,
-    MARK_EXCEPTION_HANDLER_ENTRY    = 4,
-    MARK_DEOPT_HANDLER_ENTRY        = 5,
-    MARK_INVOKEINTERFACE            = 6,
-    MARK_INVOKEVIRTUAL              = 7,
-    MARK_INVOKESTATIC               = 8,
-    MARK_INVOKESPECIAL              = 9,
-    MARK_INLINE_INVOKE              = 10,
-    MARK_POLL_NEAR                  = 11,
-    MARK_POLL_RETURN_NEAR           = 12,
-    MARK_POLL_FAR                   = 13,
-    MARK_POLL_RETURN_FAR            = 14,
-    MARK_INVOKE_INVALID             = -1
+    VERIFIED_ENTRY             = 1,
+    UNVERIFIED_ENTRY           = 2,
+    OSR_ENTRY                  = 3,
+    EXCEPTION_HANDLER_ENTRY    = 4,
+    DEOPT_HANDLER_ENTRY        = 5,
+    INVOKEINTERFACE            = 6,
+    INVOKEVIRTUAL              = 7,
+    INVOKESTATIC               = 8,
+    INVOKESPECIAL              = 9,
+    INLINE_INVOKE              = 10,
+    POLL_NEAR                  = 11,
+    POLL_RETURN_NEAR           = 12,
+    POLL_FAR                   = 13,
+    POLL_RETURN_FAR            = 14,
+    INVOKE_INVALID             = -1
   };
 
   Arena         _arena;
@@ -77,7 +79,8 @@
   ExceptionHandlerTable     _exception_handler_table;
 
   jint pd_next_offset(NativeInstruction* inst, jint pc_offset, oop method);
-  void pd_site_DataPatch(int pc_offset, oop site);
+  void pd_patch_OopData(int pc_offset, oop data);
+  void pd_patch_DataSectionReference(int pc_offset, oop data);
   void pd_relocate_CodeBlob(CodeBlob* cb, NativeInstruction* inst);
   void pd_relocate_ForeignCall(NativeInstruction* inst, jlong foreign_call_destination);
   void pd_relocate_JavaMethod(oop method, jint pc_offset);
--- a/src/share/vm/graal/graalCompilerToVM.cpp	Tue Mar 18 11:07:47 2014 -0700
+++ b/src/share/vm/graal/graalCompilerToVM.cpp	Tue Mar 18 11:51:37 2014 -0700
@@ -348,11 +348,6 @@
   return CompilerOracle::should_inline(method) || method->force_inline();
 C2V_END
 
-C2V_ENTRY(jint, getCompiledCodeSize, (JNIEnv *env, jobject, jlong metaspace_method))
-  nmethod* code = (asMethod(metaspace_method))->code();
-  return code == NULL ? 0 : code->insts_size();
-C2V_END
-
 C2V_VMENTRY(jlong, lookupType, (JNIEnv *env, jobject, jstring jname, jclass accessing_class, jboolean resolve))
   ResourceMark rm;
   Handle name = JNIHandles::resolve(jname);
@@ -378,23 +373,15 @@
   return (jlong) (address) resolved_klass;
 C2V_END
 
-C2V_VMENTRY(jobject, lookupConstantInPool, (JNIEnv *env, jobject, jlong metaspace_constant_pool, jint index))
+C2V_VMENTRY(jobject, resolveConstantInPool, (JNIEnv *env, jobject, jlong metaspace_constant_pool, jint index))
   ConstantPool* cp = (ConstantPool*) metaspace_constant_pool;
-  oop result = NULL;
-  constantTag tag = cp->tag_at(index);
-  switch (tag.value()) {
-  case JVM_CONSTANT_String:
-      result = cp->resolve_possibly_cached_constant_at(index, CHECK_NULL);
-      break;
-  case JVM_CONSTANT_MethodHandle:
-  case JVM_CONSTANT_MethodHandleInError:
-  case JVM_CONSTANT_MethodType:
-  case JVM_CONSTANT_MethodTypeInError:
-      result = cp->resolve_constant_at(index, CHECK_NULL);
-      break;
-  default:
-    fatal(err_msg_res("unknown constant pool tag %s at cpi %d in %s", tag.internal_name(), index, cp->pool_holder()->name()->as_C_string()));
-  }
+  oop result = cp->resolve_constant_at(index, CHECK_NULL);
+  return JNIHandles::make_local(THREAD, result);
+C2V_END
+
+C2V_VMENTRY(jobject, resolvePossiblyCachedConstantInPool, (JNIEnv *env, jobject, jlong metaspace_constant_pool, jint index))
+  ConstantPool* cp = (ConstantPool*) metaspace_constant_pool;
+  oop result = cp->resolve_possibly_cached_constant_at(index, CHECK_NULL);
   return JNIHandles::make_local(THREAD, result);
 C2V_END
 
@@ -418,6 +405,11 @@
   return cp->klass_ref_index_at(index);
 C2V_END
 
+C2V_VMENTRY(jlong, constantPoolKlassAt, (JNIEnv *env, jobject, jlong metaspace_constant_pool, jint index))
+  ConstantPool* cp = (ConstantPool*) metaspace_constant_pool;
+  return (jlong) (address) cp->klass_at(index, THREAD);
+C2V_END
+
 C2V_VMENTRY(jlong, lookupKlassInPool, (JNIEnv *env, jobject, jlong metaspace_constant_pool, jint index, jbyte opcode))
   constantPoolHandle cp = (ConstantPool*) metaspace_constant_pool;
   KlassHandle loading_klass(cp->pool_holder());
@@ -456,26 +448,9 @@
   return (jlong) (address) method();
 C2V_END
 
-C2V_VMENTRY(void, loadReferencedTypeInPool, (JNIEnv *env, jobject, jlong metaspace_constant_pool, jint index, jbyte op))
+C2V_VMENTRY(jint, constantPoolRemapInstructionOperandFromCache, (JNIEnv *env, jobject, jlong metaspace_constant_pool, jint index))
   ConstantPool* cp = (ConstantPool*) metaspace_constant_pool;
-  Bytecodes::Code bc = (Bytecodes::Code) (((int) op) & 0xFF);
-  if (bc != Bytecodes::_checkcast && bc != Bytecodes::_instanceof && bc != Bytecodes::_new && bc != Bytecodes::_anewarray
-      && bc != Bytecodes::_multianewarray && bc != Bytecodes::_ldc && bc != Bytecodes::_ldc_w && bc != Bytecodes::_ldc2_w)
-  {
-    index = cp->remap_instruction_operand_from_cache(index);
-  }
-  constantTag tag = cp->tag_at(index);
-  if (tag.is_field_or_method()) {
-    index = cp->uncached_klass_ref_index_at(index);
-    tag = cp->tag_at(index);
-  }
-
-  if (tag.is_unresolved_klass() || tag.is_klass()) {
-    Klass* klass = cp->klass_at(index, CHECK);
-    if (klass->oop_is_instance()) {
-      InstanceKlass::cast(klass)->initialize(CHECK);
-    }
-  }
+  return cp->remap_instruction_operand_from_cache(index);
 C2V_END
 
 C2V_VMENTRY(jlong, resolveField, (JNIEnv *env, jobject, jlong metaspace_constant_pool, jint index, jbyte opcode, jlongArray info_handle))
@@ -823,53 +798,54 @@
 #define METASPACE_SYMBOL      "J"
 
 JNINativeMethod CompilerToVM_methods[] = {
-  {CC"initializeBytecode",              CC"("METASPACE_METHOD"[B)[B",                                     FN_PTR(initializeBytecode)},
-  {CC"exceptionTableStart",             CC"("METASPACE_METHOD")J",                                        FN_PTR(exceptionTableStart)},
-  {CC"exceptionTableLength",            CC"("METASPACE_METHOD")I",                                        FN_PTR(exceptionTableLength)},
-  {CC"hasBalancedMonitors",             CC"("METASPACE_METHOD")Z",                                        FN_PTR(hasBalancedMonitors)},
-  {CC"findUniqueConcreteMethod",        CC"("METASPACE_METHOD")"METASPACE_METHOD,                         FN_PTR(findUniqueConcreteMethod)},
-  {CC"getKlassImplementor",             CC"("METASPACE_KLASS")"METASPACE_KLASS,                           FN_PTR(getKlassImplementor)},
-  {CC"getStackTraceElement",            CC"("METASPACE_METHOD"I)"STACK_TRACE_ELEMENT,                     FN_PTR(getStackTraceElement)},
-  {CC"initializeMethod",                CC"("METASPACE_METHOD HS_RESOLVED_METHOD")V",                     FN_PTR(initializeMethod)},
-  {CC"doNotInlineOrCompile",            CC"("METASPACE_METHOD")V",                                        FN_PTR(doNotInlineOrCompile)},
-  {CC"canInlineMethod",                 CC"("METASPACE_METHOD")Z",                                        FN_PTR(canInlineMethod)},
-  {CC"shouldInlineMethod",              CC"("METASPACE_METHOD")Z",                                        FN_PTR(shouldInlineMethod)},
-  {CC"getCompiledCodeSize",             CC"("METASPACE_METHOD")I",                                        FN_PTR(getCompiledCodeSize)},
-  {CC"lookupType",                      CC"("STRING CLASS"Z)"METASPACE_KLASS,                             FN_PTR(lookupType)},
-  {CC"lookupConstantInPool",            CC"("METASPACE_CONSTANT_POOL"I)"OBJECT,                           FN_PTR(lookupConstantInPool)},
-  {CC"lookupNameRefInPool",             CC"("METASPACE_CONSTANT_POOL"I)"METASPACE_SYMBOL,                 FN_PTR(lookupNameRefInPool)},
-  {CC"lookupNameAndTypeRefIndexInPool", CC"("METASPACE_CONSTANT_POOL"I)I",                                FN_PTR(lookupNameAndTypeRefIndexInPool)},
-  {CC"lookupSignatureRefInPool",        CC"("METASPACE_CONSTANT_POOL"I)"METASPACE_SYMBOL,                 FN_PTR(lookupSignatureRefInPool)},
-  {CC"lookupKlassRefIndexInPool",       CC"("METASPACE_CONSTANT_POOL"I)I",                                FN_PTR(lookupKlassRefIndexInPool)},
-  {CC"lookupKlassInPool",               CC"("METASPACE_CONSTANT_POOL"I)"METASPACE_KLASS,                  FN_PTR(lookupKlassInPool)},
-  {CC"lookupAppendixInPool",            CC"("METASPACE_CONSTANT_POOL"I)"OBJECT,                           FN_PTR(lookupAppendixInPool)},
-  {CC"lookupMethodInPool",              CC"("METASPACE_CONSTANT_POOL"IB)"METASPACE_METHOD,                FN_PTR(lookupMethodInPool)},
-  {CC"loadReferencedTypeInPool",        CC"("METASPACE_CONSTANT_POOL"IB)V",                               FN_PTR(loadReferencedTypeInPool)},
-  {CC"resolveField",                    CC"("METASPACE_CONSTANT_POOL"IB[J)"METASPACE_KLASS,               FN_PTR(resolveField)},
-  {CC"resolveMethod",                   CC"("METASPACE_KLASS STRING STRING")"METASPACE_METHOD,            FN_PTR(resolveMethod)},
-  {CC"getClassInitializer",             CC"("METASPACE_KLASS")"METASPACE_METHOD,                          FN_PTR(getClassInitializer)},
-  {CC"hasFinalizableSubclass",          CC"("METASPACE_KLASS")Z",                                         FN_PTR(hasFinalizableSubclass)},
-  {CC"getMaxCallTargetOffset",          CC"(J)J",                                                         FN_PTR(getMaxCallTargetOffset)},
-  {CC"getMetaspaceMethod",              CC"("CLASS"I)"METASPACE_METHOD,                                   FN_PTR(getMetaspaceMethod)},
-  {CC"initializeConfiguration",         CC"("HS_CONFIG")V",                                               FN_PTR(initializeConfiguration)},
-  {CC"installCode0",                    CC"("HS_COMPILED_CODE HS_INSTALLED_CODE SPECULATION_LOG")I",      FN_PTR(installCode0)},
-  {CC"notifyCompilationStatistics",     CC"(I"HS_RESOLVED_METHOD"ZIJJ"HS_INSTALLED_CODE")V",              FN_PTR(notifyCompilationStatistics)},
-  {CC"printCompilationStatistics",      CC"(ZZ)V",                                                        FN_PTR(printCompilationStatistics)},
-  {CC"resetCompilationStatistics",      CC"()V",                                                          FN_PTR(resetCompilationStatistics)},
-  {CC"disassembleCodeBlob",             CC"(J)"STRING,                                                    FN_PTR(disassembleCodeBlob)},
-  {CC"executeCompiledMethodVarargs",    CC"(["OBJECT HS_INSTALLED_CODE")"OBJECT,                          FN_PTR(executeCompiledMethodVarargs)},
-  {CC"getLineNumberTable",              CC"("METASPACE_METHOD")[J",                                       FN_PTR(getLineNumberTable)},
-  {CC"getLocalVariableTableStart",      CC"("METASPACE_METHOD")J",                                        FN_PTR(getLocalVariableTableStart)},
-  {CC"getLocalVariableTableLength",     CC"("METASPACE_METHOD")I",                                        FN_PTR(getLocalVariableTableLength)},
-  {CC"reprofile",                       CC"("METASPACE_METHOD")V",                                        FN_PTR(reprofile)},
-  {CC"invalidateInstalledCode",         CC"("HS_INSTALLED_CODE")V",                                       FN_PTR(invalidateInstalledCode)},
-  {CC"readUnsafeUncompressedPointer",   CC"("OBJECT"J)"OBJECT,                                            FN_PTR(readUnsafeUncompressedPointer)},
-  {CC"readUnsafeKlassPointer",          CC"("OBJECT")J",                                                  FN_PTR(readUnsafeKlassPointer)},
-  {CC"collectCounters",                 CC"()[J",                                                         FN_PTR(collectCounters)},
-  {CC"getGPUs",                         CC"()"STRING,                                                     FN_PTR(getGPUs)},
-  {CC"allocateCompileId",               CC"("METASPACE_METHOD"I)I",                                       FN_PTR(allocateCompileId)},
-  {CC"isMature",                        CC"("METASPACE_METHOD_DATA")Z",                                   FN_PTR(isMature)},
-  {CC"hasCompiledCodeForOSR",         CC"("METASPACE_METHOD"II)Z",                                      FN_PTR(hasCompiledCodeForOSR)},
+  {CC"initializeBytecode",                           CC"("METASPACE_METHOD"[B)[B",                                     FN_PTR(initializeBytecode)},
+  {CC"exceptionTableStart",                          CC"("METASPACE_METHOD")J",                                        FN_PTR(exceptionTableStart)},
+  {CC"exceptionTableLength",                         CC"("METASPACE_METHOD")I",                                        FN_PTR(exceptionTableLength)},
+  {CC"hasBalancedMonitors",                          CC"("METASPACE_METHOD")Z",                                        FN_PTR(hasBalancedMonitors)},
+  {CC"findUniqueConcreteMethod",                     CC"("METASPACE_METHOD")"METASPACE_METHOD,                         FN_PTR(findUniqueConcreteMethod)},
+  {CC"getKlassImplementor",                          CC"("METASPACE_KLASS")"METASPACE_KLASS,                           FN_PTR(getKlassImplementor)},
+  {CC"getStackTraceElement",                         CC"("METASPACE_METHOD"I)"STACK_TRACE_ELEMENT,                     FN_PTR(getStackTraceElement)},
+  {CC"initializeMethod",                             CC"("METASPACE_METHOD HS_RESOLVED_METHOD")V",                     FN_PTR(initializeMethod)},
+  {CC"doNotInlineOrCompile",                         CC"("METASPACE_METHOD")V",                                        FN_PTR(doNotInlineOrCompile)},
+  {CC"canInlineMethod",                              CC"("METASPACE_METHOD")Z",                                        FN_PTR(canInlineMethod)},
+  {CC"shouldInlineMethod",                           CC"("METASPACE_METHOD")Z",                                        FN_PTR(shouldInlineMethod)},
+  {CC"lookupType",                                   CC"("STRING CLASS"Z)"METASPACE_KLASS,                             FN_PTR(lookupType)},
+  {CC"resolveConstantInPool",                        CC"("METASPACE_CONSTANT_POOL"I)"OBJECT,                           FN_PTR(resolveConstantInPool)},
+  {CC"resolvePossiblyCachedConstantInPool",          CC"("METASPACE_CONSTANT_POOL"I)"OBJECT,                           FN_PTR(resolvePossiblyCachedConstantInPool)},
+  {CC"lookupNameRefInPool",                          CC"("METASPACE_CONSTANT_POOL"I)"METASPACE_SYMBOL,                 FN_PTR(lookupNameRefInPool)},
+  {CC"lookupNameAndTypeRefIndexInPool",              CC"("METASPACE_CONSTANT_POOL"I)I",                                FN_PTR(lookupNameAndTypeRefIndexInPool)},
+  {CC"lookupSignatureRefInPool",                     CC"("METASPACE_CONSTANT_POOL"I)"METASPACE_SYMBOL,                 FN_PTR(lookupSignatureRefInPool)},
+  {CC"lookupKlassRefIndexInPool",                    CC"("METASPACE_CONSTANT_POOL"I)I",                                FN_PTR(lookupKlassRefIndexInPool)},
+  {CC"constantPoolKlassAt",                          CC"("METASPACE_CONSTANT_POOL"I)"METASPACE_KLASS,                  FN_PTR(constantPoolKlassAt)},
+  {CC"lookupKlassInPool",                            CC"("METASPACE_CONSTANT_POOL"I)"METASPACE_KLASS,                  FN_PTR(lookupKlassInPool)},
+  {CC"lookupAppendixInPool",                         CC"("METASPACE_CONSTANT_POOL"I)"OBJECT,                           FN_PTR(lookupAppendixInPool)},
+  {CC"lookupMethodInPool",                           CC"("METASPACE_CONSTANT_POOL"IB)"METASPACE_METHOD,                FN_PTR(lookupMethodInPool)},
+  {CC"constantPoolRemapInstructionOperandFromCache", CC"("METASPACE_CONSTANT_POOL"I)I",                                FN_PTR(constantPoolRemapInstructionOperandFromCache)},
+  {CC"resolveField",                                 CC"("METASPACE_CONSTANT_POOL"IB[J)"METASPACE_KLASS,               FN_PTR(resolveField)},
+  {CC"resolveMethod",                                CC"("METASPACE_KLASS STRING STRING")"METASPACE_METHOD,            FN_PTR(resolveMethod)},
+  {CC"getClassInitializer",                          CC"("METASPACE_KLASS")"METASPACE_METHOD,                          FN_PTR(getClassInitializer)},
+  {CC"hasFinalizableSubclass",                       CC"("METASPACE_KLASS")Z",                                         FN_PTR(hasFinalizableSubclass)},
+  {CC"getMaxCallTargetOffset",                       CC"(J)J",                                                         FN_PTR(getMaxCallTargetOffset)},
+  {CC"getMetaspaceMethod",                           CC"("CLASS"I)"METASPACE_METHOD,                                   FN_PTR(getMetaspaceMethod)},
+  {CC"initializeConfiguration",                      CC"("HS_CONFIG")V",                                               FN_PTR(initializeConfiguration)},
+  {CC"installCode0",                                 CC"("HS_COMPILED_CODE HS_INSTALLED_CODE SPECULATION_LOG")I",      FN_PTR(installCode0)},
+  {CC"notifyCompilationStatistics",                  CC"(I"HS_RESOLVED_METHOD"ZIJJ"HS_INSTALLED_CODE")V",              FN_PTR(notifyCompilationStatistics)},
+  {CC"printCompilationStatistics",                   CC"(ZZ)V",                                                        FN_PTR(printCompilationStatistics)},
+  {CC"resetCompilationStatistics",                   CC"()V",                                                          FN_PTR(resetCompilationStatistics)},
+  {CC"disassembleCodeBlob",                          CC"(J)"STRING,                                                    FN_PTR(disassembleCodeBlob)},
+  {CC"executeCompiledMethodVarargs",                 CC"(["OBJECT HS_INSTALLED_CODE")"OBJECT,                          FN_PTR(executeCompiledMethodVarargs)},
+  {CC"getLineNumberTable",                           CC"("METASPACE_METHOD")[J",                                       FN_PTR(getLineNumberTable)},
+  {CC"getLocalVariableTableStart",                   CC"("METASPACE_METHOD")J",                                        FN_PTR(getLocalVariableTableStart)},
+  {CC"getLocalVariableTableLength",                  CC"("METASPACE_METHOD")I",                                        FN_PTR(getLocalVariableTableLength)},
+  {CC"reprofile",                                    CC"("METASPACE_METHOD")V",                                        FN_PTR(reprofile)},
+  {CC"invalidateInstalledCode",                      CC"("HS_INSTALLED_CODE")V",                                       FN_PTR(invalidateInstalledCode)},
+  {CC"readUnsafeUncompressedPointer",                CC"("OBJECT"J)"OBJECT,                                            FN_PTR(readUnsafeUncompressedPointer)},
+  {CC"readUnsafeKlassPointer",                       CC"("OBJECT")J",                                                  FN_PTR(readUnsafeKlassPointer)},
+  {CC"collectCounters",                              CC"()[J",                                                         FN_PTR(collectCounters)},
+  {CC"getGPUs",                                      CC"()"STRING,                                                     FN_PTR(getGPUs)},
+  {CC"allocateCompileId",                            CC"("METASPACE_METHOD"I)I",                                       FN_PTR(allocateCompileId)},
+  {CC"isMature",                                     CC"("METASPACE_METHOD_DATA")Z",                                   FN_PTR(isMature)},
+  {CC"hasCompiledCodeForOSR",                        CC"("METASPACE_METHOD"II)Z",                                      FN_PTR(hasCompiledCodeForOSR)},
 };
 
 int CompilerToVM_methods_count() {
--- a/src/share/vm/graal/graalJavaAccess.hpp	Tue Mar 18 11:07:47 2014 -0700
+++ b/src/share/vm/graal/graalJavaAccess.hpp	Tue Mar 18 11:51:37 2014 -0700
@@ -79,16 +79,7 @@
     oop_field(HotSpotCompiledCode, sites, "[Lcom/oracle/graal/api/code/CompilationResult$Site;")                                                               \
     oop_field(HotSpotCompiledCode, exceptionHandlers, "[Lcom/oracle/graal/api/code/CompilationResult$ExceptionHandler;")                                       \
     oop_field(HotSpotCompiledCode, comments, "[Lcom/oracle/graal/hotspot/HotSpotCompiledCode$Comment;")                                                        \
-    oop_field(HotSpotCompiledCode, dataSection, "Lcom/oracle/graal/hotspot/HotSpotCompiledCode$DataSection;")                                                  \
-  end_class                                                                                                                                                    \
-  start_class(HotSpotCompiledCode_HotSpotData)                                                                                                                 \
-    int_field(HotSpotCompiledCode_HotSpotData, offset)                                                                                                         \
-    oop_field(HotSpotCompiledCode_HotSpotData, constant, "Lcom/oracle/graal/api/meta/Constant;")                                                               \
-  end_class                                                                                                                                                    \
-  start_class(HotSpotCompiledCode_DataSection)                                                                                                                 \
-    int_field(HotSpotCompiledCode_DataSection, sectionAlignment)                                                                                               \
-    oop_field(HotSpotCompiledCode_DataSection, data, "[B")                                                                                                     \
-    oop_field(HotSpotCompiledCode_DataSection, patches, "[Lcom/oracle/graal/hotspot/HotSpotCompiledCode$HotSpotData;")                                         \
+    oop_field(HotSpotCompiledCode, dataSection, "Lcom/oracle/graal/hotspot/data/DataSection;")                                                                 \
   end_class                                                                                                                                                    \
   start_class(HotSpotCompiledCode_Comment)                                                                                                                     \
     oop_field(HotSpotCompiledCode_Comment, text, "Ljava/lang/String;")                                                                                         \
@@ -97,7 +88,7 @@
   start_class(HotSpotCompiledNmethod)                                                                                                                          \
     oop_field(HotSpotCompiledNmethod, method, "Lcom/oracle/graal/hotspot/meta/HotSpotResolvedJavaMethod;")                                                     \
     int_field(HotSpotCompiledNmethod, entryBCI)                                                                                                                \
-    int_field(HotSpotCompiledNmethod, id)                                                                                                                \
+    int_field(HotSpotCompiledNmethod, id)                                                                                                                      \
   end_class                                                                                                                                                    \
   start_class(HotSpotCompiledRuntimeStub)                                                                                                                      \
     oop_field(HotSpotCompiledRuntimeStub, stubName, "Ljava/lang/String;")                                                                                      \
@@ -105,6 +96,23 @@
   start_class(HotSpotForeignCallLinkage)                                                                                                                       \
     long_field(HotSpotForeignCallLinkage, address)                                                                                                             \
   end_class                                                                                                                                                    \
+  start_class(DataSection)                                                                                                                                     \
+    int_field(DataSection, sectionAlignment)                                                                                                                   \
+    oop_field(DataSection, data, "[B")                                                                                                                         \
+    oop_field(DataSection, patches, "[Lcom/oracle/graal/api/code/CompilationResult$DataPatch;")                                                                \
+  end_class                                                                                                                                                    \
+  start_class(DataSectionReference)                                                                                                                            \
+    int_field(DataSectionReference, offset)                                                                                                                    \
+  end_class                                                                                                                                                    \
+  start_class(MetaspaceData)                                                                                                                                   \
+    long_field(MetaspaceData, value)                                                                                                                           \
+    oop_field(MetaspaceData, annotation, "Ljava/lang/Object;")                                                                                                 \
+    boolean_field(MetaspaceData, compressed)                                                                                                                   \
+  end_class                                                                                                                                                    \
+  start_class(OopData)                                                                                                                                         \
+    oop_field(OopData, object, "Ljava/lang/Object;")                                                                                                           \
+    boolean_field(OopData, compressed)                                                                                                                         \
+  end_class                                                                                                                                                    \
   start_class(ExternalCompilationResult)                                                                                                                       \
     long_field(ExternalCompilationResult, entryPoint)                                                                                                          \
   end_class                                                                                                                                                    \
@@ -145,8 +153,7 @@
     oop_field(CompilationResult_Call, debugInfo, "Lcom/oracle/graal/api/code/DebugInfo;")                                                                      \
   end_class                                                                                                                                                    \
   start_class(CompilationResult_DataPatch)                                                                                                                     \
-    oop_field(CompilationResult_DataPatch, externalData, "Lcom/oracle/graal/api/code/CompilationResult$Data;")                                                 \
-    oop_field(CompilationResult_DataPatch, inlineData, "Lcom/oracle/graal/api/meta/Constant;")                                                                 \
+    oop_field(CompilationResult_DataPatch, data, "Lcom/oracle/graal/api/code/CompilationResult$Data;")                                                         \
   end_class                                                                                                                                                    \
   start_class(InfopointReason)                                                                                                                                 \
     static_oop_field(InfopointReason, UNKNOWN, "Lcom/oracle/graal/api/code/InfopointReason;")                                                                  \
@@ -172,9 +179,9 @@
     oop_field(DebugInfo, referenceMap, "Lcom/oracle/graal/api/code/ReferenceMap;")                                                                             \
     oop_field(DebugInfo, calleeSaveInfo, "Lcom/oracle/graal/api/code/RegisterSaveLayout;")                                                                     \
   end_class                                                                                                                                                    \
-  start_class(ReferenceMap)                                                                                                                                    \
-    oop_field(ReferenceMap, registerRefMap, "Ljava/util/BitSet;")                                                                                              \
-    oop_field(ReferenceMap, frameRefMap, "Ljava/util/BitSet;")                                                                                                 \
+  start_class(HotSpotReferenceMap)                                                                                                                             \
+    oop_field(HotSpotReferenceMap, registerRefMap, "Ljava/util/BitSet;")                                                                                       \
+    oop_field(HotSpotReferenceMap, frameRefMap, "Ljava/util/BitSet;")                                                                                          \
   end_class                                                                                                                                                    \
   start_class(RegisterSaveLayout)                                                                                                                              \
     oop_field(RegisterSaveLayout, registers, "[Lcom/oracle/graal/api/code/Register;")                                                                          \
--- a/src/share/vm/graal/vmStructs_graal.hpp	Tue Mar 18 11:07:47 2014 -0700
+++ b/src/share/vm/graal/vmStructs_graal.hpp	Tue Mar 18 11:51:37 2014 -0700
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2013, 2014, 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
@@ -26,12 +26,14 @@
 #define SHARE_VM_GRAAL_VMSTRUCTS_GRAAL_HPP
 
 #include "compiler/abstractCompiler.hpp"
+#include "graal/graalCodeInstaller.hpp"
 #include "graal/graalCompilerToVM.hpp"
 #include "graal/graalEnv.hpp"
 
 #define VM_STRUCTS_GRAAL(nonstatic_field, static_field)                       \
   nonstatic_field(ThreadShadow, _pending_deoptimization, int)                 \
   nonstatic_field(ThreadShadow, _pending_failed_speculation, oop)             \
+  nonstatic_field(MethodData,   _graal_node_count, int)                       \
 
 #define VM_TYPES_GRAAL(declare_type, declare_toplevel_type)                   \
 
@@ -47,5 +49,21 @@
                                                                                                   \
   declare_constant(CompilerToVM::KLASS_TAG)                                                       \
   declare_constant(CompilerToVM::SYMBOL_TAG)                                                      \
+                                                                                                  \
+  declare_constant(CodeInstaller::VERIFIED_ENTRY)                                                 \
+  declare_constant(CodeInstaller::UNVERIFIED_ENTRY)                                               \
+  declare_constant(CodeInstaller::OSR_ENTRY)                                                      \
+  declare_constant(CodeInstaller::EXCEPTION_HANDLER_ENTRY)                                        \
+  declare_constant(CodeInstaller::DEOPT_HANDLER_ENTRY)                                            \
+  declare_constant(CodeInstaller::INVOKEINTERFACE)                                                \
+  declare_constant(CodeInstaller::INVOKEVIRTUAL)                                                  \
+  declare_constant(CodeInstaller::INVOKESTATIC)                                                   \
+  declare_constant(CodeInstaller::INVOKESPECIAL)                                                  \
+  declare_constant(CodeInstaller::INLINE_INVOKE)                                                  \
+  declare_constant(CodeInstaller::POLL_NEAR)                                                      \
+  declare_constant(CodeInstaller::POLL_RETURN_NEAR)                                               \
+  declare_constant(CodeInstaller::POLL_FAR)                                                       \
+  declare_constant(CodeInstaller::POLL_RETURN_FAR)                                                \
+  declare_constant(CodeInstaller::INVOKE_INVALID)                                                 \
 
 #endif // SHARE_VM_GRAAL_VMSTRUCTS_GRAAL_HPP
--- a/src/share/vm/oops/methodData.cpp	Tue Mar 18 11:07:47 2014 -0700
+++ b/src/share/vm/oops/methodData.cpp	Tue Mar 18 11:51:37 2014 -0700
@@ -1216,6 +1216,9 @@
   _highest_comp_level = 0;
   _highest_osr_comp_level = 0;
   _would_profile = true;
+#ifdef GRAAL
+  _graal_node_count = 0;
+#endif
 
   // Initialize flags and trap history.
   _nof_decompiles = 0;
--- a/src/share/vm/oops/methodData.hpp	Tue Mar 18 11:07:47 2014 -0700
+++ b/src/share/vm/oops/methodData.hpp	Tue Mar 18 11:51:37 2014 -0700
@@ -2203,6 +2203,11 @@
   // Does this method contain anything worth profiling?
   bool              _would_profile;
 
+#ifdef GRAAL
+  // Support for HotSpotMethodData.setCompiledGraphSize(int)
+  int               _graal_node_count;
+#endif
+
   // Size of _data array in bytes.  (Excludes header and extra_data fields.)
   int _data_size;
 
--- a/src/share/vm/utilities/globalDefinitions.hpp	Tue Mar 18 11:07:47 2014 -0700
+++ b/src/share/vm/utilities/globalDefinitions.hpp	Tue Mar 18 11:51:37 2014 -0700
@@ -834,7 +834,7 @@
   CompLevel_full_profile      = 3,         // C1, invocation & backedge counters + mdo
   CompLevel_full_optimization = 4,         // C2, Shark or Graal
 
-#if defined(COMPILER2) || defined(SHARK) || defined(GRAAL)
+#if defined(COMPILER2) || defined(SHARK) || defined(COMPILERGRAAL)
   CompLevel_highest_tier      = CompLevel_full_optimization,  // pure C2 and tiered or Graal and tiered
 #elif defined(COMPILER1)
   CompLevel_highest_tier      = CompLevel_simple,             // pure C1 or Graal
@@ -844,7 +844,7 @@
 
 #if defined(TIERED)
   CompLevel_initial_compile   = CompLevel_full_profile        // tiered
-#elif defined(COMPILER1) || defined(GRAAL)
+#elif defined(COMPILER1) || defined(COMPILERGRAAL)
   CompLevel_initial_compile   = CompLevel_simple              // pure C1 or Graal
 #elif defined(COMPILER2) || defined(SHARK)
   CompLevel_initial_compile   = CompLevel_full_optimization   // pure C2