changeset 10688:87d2df0a7624

Merge.
author Thomas Wuerthinger <thomas.wuerthinger@oracle.com>
date Wed, 10 Jul 2013 05:27:45 +0200
parents d2055a110396 (current diff) 73122b5edf6a (diff)
children 3ae117e62905
files
diffstat 28 files changed, 1248 insertions(+), 531 deletions(-) [+]
line wrap: on
line diff
--- a/graal/com.oracle.graal.asm.sparc/src/com/oracle/graal/asm/sparc/SPARCAddress.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.asm.sparc/src/com/oracle/graal/asm/sparc/SPARCAddress.java	Wed Jul 10 05:27:45 2013 +0200
@@ -22,11 +22,17 @@
  */
 package com.oracle.graal.asm.sparc;
 
-import com.oracle.graal.api.code.AbstractAddress;
-import com.oracle.graal.api.code.Register;
+import static com.oracle.graal.sparc.SPARC.*;
+
+import com.oracle.graal.api.code.*;
 
 public class SPARCAddress extends AbstractAddress {
 
+    /**
+     * Stack bias for stack and frame pointer loads.
+     */
+    private static final int STACK_BIAS = 0x7ff;
+
     private final Register base;
     private final int displacement; // need Register offset / displacement CompositeValue?
 
@@ -66,6 +72,10 @@
      * @return Optional additive displacement.
      */
     public int getDisplacement() {
+        // TODO Should we also hide the register save area size here?
+        if (getBase() == sp || getBase() == fp) {
+            return displacement + STACK_BIAS;
+        }
         return displacement;
     }
 }
--- a/graal/com.oracle.graal.asm.sparc/src/com/oracle/graal/asm/sparc/SPARCAssembler.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.asm.sparc/src/com/oracle/graal/asm/sparc/SPARCAssembler.java	Wed Jul 10 05:27:45 2013 +0200
@@ -36,7 +36,7 @@
 public abstract class SPARCAssembler extends AbstractAssembler {
 
     /**
-     * Constructs an assembler for the AMD64 architecture.
+     * Constructs an assembler for the SPARC architecture.
      * 
      * @param registerConfig the register configuration used to bind {@link Register#Frame} and
      *            {@link Register#CallerFrame} to physical registers. This value can be null if this
@@ -47,6 +47,14 @@
         super(target);
     }
 
+    // @formatter:off
+    /**
+     * Instruction format for sethi.
+     * 
+     * | 00  |  rd    | op2 |               imm22                     |
+     * |31 30|29    25|24 22|21                                      0|
+     */
+    // @formatter:on
     public static class Fmt00a {
 
         private int rd;
@@ -74,9 +82,9 @@
      * |31 30|29|28  25|24 22|21                                      0|
      */
     // @formatter:on
-    public static class Fmt2b {
-
-        public Fmt2b(SPARCAssembler masm, int op, int a, int cond, int op2, int disp22) {
+    public static class Fmt00b {
+
+        public Fmt00b(SPARCAssembler masm, int op, int a, int cond, int op2, int disp22) {
             assert op == 0;
             assert op == 0;
             assert cond < 0x10;
@@ -211,7 +219,7 @@
             final int op2 = (inst & OP2_MASK) >> OP2_SHIFT;
             final int cc = (inst & CC_MASK) >> CC_SHIFT;
             final int p = (inst & P_MASK) >> P_SHIFT;
-            final int disp19 = (inst & DISP19_MASK) >> DISP19_SHIFT;
+            final int disp19 = (inst & DISP19_MASK) >> DISP19_SHIFT << 2;
 
             Fmt00c fmt = new Fmt00c(a, cond, op2, cc, p, disp19);
             fmt.verify();
@@ -240,9 +248,9 @@
         }
     }
 
-    public static class Fmt2d {
-
-        public Fmt2d(SPARCAssembler masm, int op, int a, int rcond, int op2, int d16hi, int predict, int rs1, int d16lo) {
+    public static class Fmt00d {
+
+        public Fmt00d(SPARCAssembler masm, int op, int a, int rcond, int op2, int d16hi, int predict, int rs1, int d16lo) {
             assert predict == 0 || predict == 1;
             assert rcond >= 0 && rcond < 0x8;
             assert op == 0;
@@ -253,9 +261,9 @@
         }
     }
 
-    public static class Fmt2e {
-
-        public Fmt2e(SPARCAssembler asm, int op, int c4lo, int cc2, int rs1, int d10lo, int regOrImmediate) {
+    public static class Fmt00e {
+
+        public Fmt00e(SPARCAssembler asm, int op, int c4lo, int cc2, int rs1, int d10lo, int regOrImmediate) {
             assert op == 0;
             assert (cc2 & 0xFFFFFFFE) == 0;
             assert c4lo >= 0 && rs1 < 0x10;
@@ -268,110 +276,75 @@
         }
     }
 
+    // @formatter:off
+    /**
+     * Instruction format for calls.
+     * 
+     * | 01  |                      disp30                             |
+     * |31 30|29                                                      0|
+     */
+    // @formatter:on
     public static class Fmt01 {
 
+        private static final int OP_SHIFT = 30;
+        private static final int DISP30_SHIFT = 0;
+
+        // @formatter:off
+        private static final int OP_MASK     = 0b11000000000000000000000000000000;
+        private static final int DISP30_MASK = 0b00111111111111111111111111111111;
+        // @formatter:on
+
         private int disp30;
 
         public Fmt01(int disp30) {
-            this.disp30 = disp30;
-        }
-
-        public void emit(SPARCAssembler masm) {
-            assert ((disp30 & 0xc0000000) == 0);
-            masm.emitInt(Ops.CallOp.getValue() << 30 | disp30);
-        }
-    }
-
-    public static class Fmt3a {
-
-        public Fmt3a(SPARCAssembler masm, int op, int rd, int op3, int rs1, int rs2) {
-            assert op == 2 || op == 3;
-            assert op3 >= 0 && op3 < 0x40;
-            assert rs1 >= 0 && rs1 < 0x20;
-            assert rs2 >= 0 && rs2 < 0x20;
-            assert rd >= 0 && rd < 0x20;
-
-            masm.emitInt(op << 30 | rd << 25 | op3 << 19 | rs1 << 14 | rs2);
-        }
-    }
-
-    public static class Fmt3b {
-
-        private boolean isImm;
-        private int op;
-        private int op3;
-        private int rs1;
-        private int rs2;
-        private int simm13;
-        private int rd;
-
-        public Fmt3b(Ops op, Op3s op3, Register rs1, Register rs2, Register rd) {
-            this.op = op.getValue();
-            this.op3 = op3.getValue();
-            this.rs1 = rs1.encoding();
-            this.rs2 = rs2.encoding();
-            this.rd = rd.encoding();
-        }
-
-        public Fmt3b(Ops op, Op3s op3, Register rs1, int simm13, Register rd) {
-            isImm = true;
-            this.op = op.getValue();
-            this.op3 = op3.getValue();
-            this.rs1 = rs1.encoding();
-            this.simm13 = simm13;
-            this.rd = rd.encoding();
+            setDisp30(disp30);
+        }
+
+        /**
+         * Return the displacement in bytes.
+         */
+        public int getDisp30() {
+            return disp30 << 2;
+        }
+
+        /**
+         * The instructions requires displacements to be word-sized.
+         */
+        public void setDisp30(int disp30) {
+            this.disp30 = disp30 >> 2;
+        }
+
+        private int getInstructionBits() {
+            return Ops.CallOp.getValue() << OP_SHIFT | (disp30 & DISP30_MASK) << DISP30_SHIFT;
+        }
+
+        public static Fmt01 read(SPARCAssembler masm, int pos) {
+            final int inst = masm.codeBuffer.getInt(pos);
+
+            // Make sure it's the right instruction:
+            final int op = (inst & OP_MASK) >> OP_SHIFT;
+            assert op == Ops.CallOp.getValue();
+
+            // Get the instruction fields:
+            final int disp30 = (inst & DISP30_MASK) >> DISP30_SHIFT << 2;
+
+            Fmt01 fmt = new Fmt01(disp30);
+            fmt.verify();
+            return fmt;
+        }
+
+        public void write(SPARCAssembler masm, int pos) {
+            verify();
+            masm.codeBuffer.emitInt(getInstructionBits(), pos);
         }
 
         public void emit(SPARCAssembler masm) {
-            assert op == 2 || op == 3;
-            assert op3 >= 0 && op3 < 0x40;
-            assert rs1 >= 0 && rs1 < 0x20;
-            assert rd >= 0 && rd < 0x20;
-
-            if (isImm == false) {
-                assert rs2 >= 0 && rs2 < 0x20;
-                masm.emitInt(op << 30 | rd << 25 | op3 << 19 | rs1 << 14 | rs2);
-            } else {
-                assert isSimm13(simm13) : simm13;
-                masm.emitInt(op << 30 | rd << 25 | op3 << 19 | rs1 << 14 | ImmedTrue | (simm13 & 0x1fff));
-            }
-        }
-    }
-
-    public static class Fmt3c {
-
-        public Fmt3c(SPARCAssembler masm, int op, int op3, int rs1, int rs2) {
-            assert op == 2;
-            assert op3 >= 0 && op3 < 0x40;
-            assert rs1 >= 0 && rs1 < 0x20;
-            assert rs2 >= 0 && rs2 < 0x20;
-
-            masm.emitInt(op << 30 | op3 << 19 | rs1 << 14 | rs2);
-        }
-    }
-
-    public static class Fmt3d {
-
-        public Fmt3d(SPARCAssembler masm, int op, int op3, int rs1, int simm13) {
-            assert op == 2;
-            assert op3 >= 0 && op3 < 0x40;
-            assert rs1 >= 0 && rs1 < 0x20;
-
-            masm.emitInt(op << 30 | op3 << 19 | rs1 << 14 | ImmedTrue | simm13);
-        }
-    }
-
-    public static class Fmt3e {
-
-        public Fmt3e(SPARCAssembler masm, int op, int op3, int rcond, int rs1, int rs2, int rd) {
-            assert op == 2 || op == 3;
-            assert op3 >= 0 && op3 < 0x40;
-            assert rcond >= 0 && rcond < 0x8;
-            assert rs1 >= 0 && rs1 < 0x20;
-            assert rs2 >= 0 && rs2 < 0x20;
-            assert rd >= 0 && rd < 0x20;
-
-            masm.emitInt(op << 30 | rd << 25 | op3 << 19 | rs1 << 14 | rcond << 10 | rs2);
+            verify();
+            masm.emitInt(getInstructionBits());
+        }
+
+        public void verify() {
+            assert (disp30 & DISP30_MASK) == 0;
         }
     }
 
@@ -430,26 +403,227 @@
         }
     }
 
-    public static class Fmt3q {
-
-        public Fmt3q(SPARCAssembler masm, int op, int op3, int rs1, int rd) {
-            assert op == 2 || op == 3;
-            assert op3 >= 0 && op3 < 0x40;
-            assert rs1 >= 0 && rs1 < 0x20;
-            assert rd >= 0 && rd < 0x20;
-
-            masm.emitInt(op << 30 | rd << 25 | op3 << 19 | rs1 << 14);
+    // @formatter:off
+    /**
+     * Instruction format for Arithmetic, Logical, Moves, Tcc, Prefetch, and Misc.
+     * 
+     * | 10  |   rd   |   op3   |   rs1   | i|   imm_asi   |   rs2   |
+     * | 10  |   rd   |   op3   |   rs1   | i|        simm13         |
+     * |31 30|29    25|24     19|18     14|13|12          5|4       0|
+     */
+    // @formatter:on
+    public static class Fmt10 {
+
+        private static final int OP_SHIFT = 30;
+        private static final int RD_SHIFT = 25;
+        private static final int OP3_SHIFT = 19;
+        private static final int RS1_SHIFT = 14;
+        private static final int I_SHIFT = 13;
+        private static final int IMM_ASI_SHIFT = 5;
+        private static final int RS2_SHIFT = 0;
+        private static final int SIMM13_SHIFT = 0;
+
+        // @formatter:off
+        private static final int OP_MASK      = 0b11000000000000000000000000000000;
+        private static final int RD_MASK      = 0b00111110000000000000000000000000;
+        private static final int OP3_MASK     = 0b00000001111110000000000000000000;
+        private static final int RS1_MASK     = 0b00000000000001111100000000000000;
+        private static final int I_MASK       = 0b00000000000000000010000000000000;
+        private static final int IMM_ASI_MASK = 0b00000000000000000001111111100000;
+        private static final int RS2_MASK     = 0b00000000000000000000000000011111;
+        private static final int SIMM13_MASK  = 0b00000000000000000001111111111111;
+        // @formatter:on
+
+        private int rd;
+        private int op3;
+        private int rs1;
+        private int i;
+        private int immAsi;
+        private int rs2;
+        private int simm13;
+
+        private Fmt10(int rd, int op3, int rs1, int i, int immAsi, int rs2, int simm13) {
+            this.rd = rd;
+            this.op3 = op3;
+            this.rs1 = rs1;
+            this.i = i;
+            this.immAsi = immAsi;
+            this.rs2 = rs2;
+            this.simm13 = simm13;
+            verify();
+        }
+
+        public Fmt10(Op3s op3, Register rs1, Register rs2, Register rd) {
+            this(rd.encoding(), op3.getValue(), rs1.encoding(), 0, 0, rs2.encoding(), 0);
+        }
+
+        public Fmt10(Op3s op3, Register rs1, int simm13, Register rd) {
+            this(rd.encoding(), op3.getValue(), rs1.encoding(), 1, 0, 0, simm13);
+        }
+
+        public Fmt10(Op3s op3) {
+            this(0, op3.getValue(), 0, 0, 0, 0, 0);
+        }
+
+        public Fmt10(Op3s op3, Register rs1, Register rd) {
+            this(rd.encoding(), op3.getValue(), rs1.encoding(), 0, 0, 0, 0);
+        }
+
+        private int getInstructionBits() {
+            if (i == 0) {
+                return Ops.ArithOp.getValue() << OP_SHIFT | rd << RD_SHIFT | op3 << OP3_SHIFT | rs1 << RS1_SHIFT | i << I_SHIFT | immAsi << IMM_ASI_SHIFT | rs2 << RS2_SHIFT;
+            } else {
+                return Ops.ArithOp.getValue() << OP_SHIFT | rd << RD_SHIFT | op3 << OP3_SHIFT | rs1 << RS1_SHIFT | i << I_SHIFT | ((simm13 << SIMM13_SHIFT) & SIMM13_MASK);
+            }
+        }
+
+        public static Fmt10 read(SPARCAssembler masm, int pos) {
+            final int inst = masm.codeBuffer.getInt(pos);
+
+            // Make sure it's the right instruction:
+            final int op = (inst & OP_MASK) >> OP_SHIFT;
+            assert op == Ops.ArithOp.getValue();
+
+            // Get the instruction fields:
+            final int rd = (inst & RD_MASK) >> RD_SHIFT;
+            final int op3 = (inst & OP3_MASK) >> OP3_SHIFT;
+            final int rs1 = (inst & RS1_MASK) >> RS1_SHIFT;
+            final int i = (inst & I_MASK) >> I_SHIFT;
+            final int immAsi = (inst & IMM_ASI_MASK) >> IMM_ASI_SHIFT;
+            final int rs2 = (inst & RS2_MASK) >> RS2_SHIFT;
+            final int simm13 = (inst & SIMM13_MASK) >> SIMM13_SHIFT;
+
+            return new Fmt10(rd, op3, rs1, i, immAsi, rs2, simm13);
+        }
+
+        public void write(SPARCAssembler masm, int pos) {
+            verify();
+            masm.codeBuffer.emitInt(getInstructionBits(), pos);
+        }
+
+        public void emit(SPARCAssembler masm) {
+            verify();
+            masm.emitInt(getInstructionBits());
+        }
+
+        public void verify() {
+            assert ((rd << RD_SHIFT) & RD_MASK) == (rd << RD_SHIFT);
+            assert ((op3 << OP3_SHIFT) & OP3_MASK) == (op3 << OP3_SHIFT);
+            assert ((rs1 << RS1_SHIFT) & RS1_MASK) == (rs1 << RS1_SHIFT);
+            assert ((i << I_SHIFT) & I_MASK) == (i << I_SHIFT);
+            assert ((immAsi << IMM_ASI_SHIFT) & IMM_ASI_MASK) == (immAsi << IMM_ASI_SHIFT);
+            assert ((rs2 << RS2_SHIFT) & RS2_MASK) == (rs2 << RS2_SHIFT);
+            assert isSimm13(simm13);
         }
     }
 
-    public static class Fmt3r {
-
-        public Fmt3r(SPARCAssembler masm, int op, int fcn, int op3) {
-            assert op == 23;
-            assert op3 >= 0 && op3 < 0x40;
-            assert fcn >= 0 && fcn < 0x40;
-
-            masm.emitInt(op << 30 | fcn << 25 | op3 << 19);
+    // @formatter:off
+    /**
+     * Instruction format for Loads, Stores and Misc.
+     * 
+     * | 11  |   rd   |   op3   |   rs1   | i|   imm_asi   |   rs2   |
+     * | 11  |   rd   |   op3   |   rs1   | i|        simm13         |
+     * |31 30|29    25|24     19|18     14|13|12          5|4       0|
+     */
+    // @formatter:on
+    public static class Fmt11 {
+
+        private static final int OP_SHIFT = 30;
+        private static final int RD_SHIFT = 25;
+        private static final int OP3_SHIFT = 19;
+        private static final int RS1_SHIFT = 14;
+        private static final int I_SHIFT = 13;
+        private static final int IMM_ASI_SHIFT = 5;
+        private static final int RS2_SHIFT = 0;
+        private static final int SIMM13_SHIFT = 0;
+
+        // @formatter:off
+        private static final int OP_MASK      = 0b11000000000000000000000000000000;
+        private static final int RD_MASK      = 0b00111110000000000000000000000000;
+        private static final int OP3_MASK     = 0b00000001111110000000000000000000;
+        private static final int RS1_MASK     = 0b00000000000001111100000000000000;
+        private static final int I_MASK       = 0b00000000000000000010000000000000;
+        private static final int IMM_ASI_MASK = 0b00000000000000000001111111100000;
+        private static final int RS2_MASK     = 0b00000000000000000000000000011111;
+        private static final int SIMM13_MASK  = 0b00000000000000000001111111111111;
+        // @formatter:on
+
+        private int rd;
+        private int op3;
+        private int rs1;
+        private int i;
+        private int immAsi;
+        private int rs2;
+        private int simm13;
+
+        private Fmt11(int rd, int op3, int rs1, int i, int immAsi, int rs2, int simm13) {
+            this.rd = rd;
+            this.op3 = op3;
+            this.rs1 = rs1;
+            this.i = i;
+            this.immAsi = immAsi;
+            this.rs2 = rs2;
+            this.simm13 = simm13;
+            verify();
+        }
+
+        public Fmt11(Op3s op3, Register rs1, Register rs2, Register rd) {
+            this(rd.encoding(), op3.getValue(), rs1.encoding(), 0, 0, rs2.encoding(), 0);
+        }
+
+        public Fmt11(Op3s op3, Register rs1, int simm13, Register rd) {
+            this(rd.encoding(), op3.getValue(), rs1.encoding(), 1, 0, 0, simm13);
+        }
+
+        public Fmt11(Op3s op3, Register rs1, Register rd) {
+            this(rd.encoding(), op3.getValue(), rs1.encoding(), 0, 0, 0, 0);
+        }
+
+        private int getInstructionBits() {
+            if (i == 0) {
+                return Ops.LdstOp.getValue() << OP_SHIFT | rd << RD_SHIFT | op3 << OP3_SHIFT | rs1 << RS1_SHIFT | i << I_SHIFT | immAsi << IMM_ASI_SHIFT | rs2 << RS2_SHIFT;
+            } else {
+                return Ops.LdstOp.getValue() << OP_SHIFT | rd << RD_SHIFT | op3 << OP3_SHIFT | rs1 << RS1_SHIFT | i << I_SHIFT | ((simm13 << SIMM13_SHIFT) & SIMM13_MASK);
+            }
+        }
+
+        public static Fmt11 read(SPARCAssembler masm, int pos) {
+            final int inst = masm.codeBuffer.getInt(pos);
+
+            // Make sure it's the right instruction:
+            final int op = (inst & OP_MASK) >> OP_SHIFT;
+            assert op == Ops.LdstOp.getValue();
+
+            // Get the instruction fields:
+            final int rd = (inst & RD_MASK) >> RD_SHIFT;
+            final int op3 = (inst & OP3_MASK) >> OP3_SHIFT;
+            final int rs1 = (inst & RS1_MASK) >> RS1_SHIFT;
+            final int i = (inst & I_MASK) >> I_SHIFT;
+            final int immAsi = (inst & IMM_ASI_MASK) >> IMM_ASI_SHIFT;
+            final int rs2 = (inst & RS2_MASK) >> RS2_SHIFT;
+            final int simm13 = (inst & SIMM13_MASK) >> SIMM13_SHIFT;
+
+            return new Fmt11(rd, op3, rs1, i, immAsi, rs2, simm13);
+        }
+
+        public void write(SPARCAssembler masm, int pos) {
+            verify();
+            masm.codeBuffer.emitInt(getInstructionBits(), pos);
+        }
+
+        public void emit(SPARCAssembler masm) {
+            verify();
+            masm.emitInt(getInstructionBits());
+        }
+
+        public void verify() {
+            assert ((rd << RD_SHIFT) & RD_MASK) == (rd << RD_SHIFT);
+            assert ((op3 << OP3_SHIFT) & OP3_MASK) == (op3 << OP3_SHIFT);
+            assert ((rs1 << RS1_SHIFT) & RS1_MASK) == (rs1 << RS1_SHIFT);
+            assert ((i << I_SHIFT) & I_MASK) == (i << I_SHIFT);
+            assert ((immAsi << IMM_ASI_SHIFT) & IMM_ASI_MASK) == (immAsi << IMM_ASI_SHIFT);
+            assert ((rs2 << RS2_SHIFT) & RS2_MASK) == (rs2 << RS2_SHIFT);
+            assert isSimm13(simm13);
         }
     }
 
@@ -1060,47 +1234,47 @@
         return x & ((1 << 10) - 1);
     }
 
-    public static class Add extends Fmt3b {
+    public static class Add extends Fmt10 {
 
         public Add(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Add, src1, simm13, dst);
+            super(Op3s.Add, src1, simm13, dst);
         }
 
         public Add(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Add, src1, src2, dst);
+            super(Op3s.Add, src1, src2, dst);
         }
     }
 
-    public static class Addc extends Fmt3b {
+    public static class Addc extends Fmt10 {
 
         public Addc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Addc, src1, simm13, dst);
+            super(Op3s.Addc, src1, simm13, dst);
         }
 
         public Addc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Addc, src1, src2, dst);
+            super(Op3s.Addc, src1, src2, dst);
         }
     }
 
-    public static class Addcc extends Fmt3b {
+    public static class Addcc extends Fmt10 {
 
         public Addcc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Addcc, src1, simm13, dst);
+            super(Op3s.Addcc, src1, simm13, dst);
         }
 
         public Addcc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Addcc, src1, src2, dst);
+            super(Op3s.Addcc, src1, src2, dst);
         }
     }
 
-    public static class Addccc extends Fmt3b {
+    public static class Addccc extends Fmt10 {
 
         public Addccc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Addccc, src1, simm13, dst);
+            super(Op3s.Addccc, src1, simm13, dst);
         }
 
         public Addccc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Addccc, src1, src2, dst);
+            super(Op3s.Addccc, src1, src2, dst);
         }
     }
 
@@ -1136,47 +1310,47 @@
         }
     }
 
-    public static class And extends Fmt3b {
+    public static class And extends Fmt10 {
 
         public And(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.And, src1, simm13, dst);
+            super(Op3s.And, src1, simm13, dst);
         }
 
         public And(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.And, src1, src2, dst);
+            super(Op3s.And, src1, src2, dst);
         }
     }
 
-    public static class Andcc extends Fmt3b {
+    public static class Andcc extends Fmt10 {
 
         public Andcc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Andcc, src1, simm13, dst);
+            super(Op3s.Andcc, src1, simm13, dst);
         }
 
         public Andcc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Andcc, src1, src2, dst);
+            super(Op3s.Andcc, src1, src2, dst);
         }
     }
 
-    public static class Andn extends Fmt3b {
+    public static class Andn extends Fmt10 {
 
         public Andn(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Andn, src1, simm13, dst);
+            super(Op3s.Andn, src1, simm13, dst);
         }
 
         public Andn(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Andn, src1, src2, dst);
+            super(Op3s.Andn, src1, src2, dst);
         }
     }
 
-    public static class Andncc extends Fmt3b {
+    public static class Andncc extends Fmt10 {
 
         public Andncc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Andncc, src1, simm13, dst);
+            super(Op3s.Andncc, src1, simm13, dst);
         }
 
         public Andncc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Andncc, src1, src2, dst);
+            super(Op3s.Andncc, src1, src2, dst);
         }
     }
 
@@ -1396,6 +1570,13 @@
         }
     }
 
+    public static class Call extends Fmt01 {
+
+        public Call(int disp30) {
+            super(disp30);
+        }
+    }
+
     public static class CammelliaFl extends Fmt3p {
 
         public CammelliaFl(Register src1, Register src2, Register dst) {
@@ -1446,7 +1627,7 @@
         }
     }
 
-    public static class Cwbcc extends Fmt2e {
+    public static class Cwbcc extends Fmt00e {
 
         public Cwbcc(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.CarryClear.getValue(), 0, src1.encoding(), simm10, src2.encoding());
@@ -1457,7 +1638,7 @@
         }
     }
 
-    public static class Cwbcs extends Fmt2e {
+    public static class Cwbcs extends Fmt00e {
 
         public Cwbcs(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.CarrySet.getValue(), 0, src1.encoding(), simm10, src2.encoding());
@@ -1468,7 +1649,7 @@
         }
     }
 
-    public static class Cwbe extends Fmt2e {
+    public static class Cwbe extends Fmt00e {
 
         public Cwbe(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.CarryClear.getValue(), 0, src1.encoding(), simm10, src2.encoding());
@@ -1479,7 +1660,7 @@
         }
     }
 
-    public static class Cwbg extends Fmt2e {
+    public static class Cwbg extends Fmt00e {
 
         public Cwbg(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.Greater.getValue(), 0, src1.encoding(), simm10, src2.encoding());
@@ -1490,7 +1671,7 @@
         }
     }
 
-    public static class Cwbge extends Fmt2e {
+    public static class Cwbge extends Fmt00e {
 
         public Cwbge(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.GreaterEqual.getValue(), 0, src1.encoding(), simm10, src2.encoding());
@@ -1501,7 +1682,7 @@
         }
     }
 
-    public static class Cwbgu extends Fmt2e {
+    public static class Cwbgu extends Fmt00e {
 
         public Cwbgu(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.GreaterUnsigned.getValue(), 0, src1.encoding(), simm10, src2.encoding());
@@ -1512,7 +1693,7 @@
         }
     }
 
-    public static class Cwbl extends Fmt2e {
+    public static class Cwbl extends Fmt00e {
 
         public Cwbl(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.Less.getValue(), 0, src1.encoding(), simm10, src2.encoding());
@@ -1523,7 +1704,7 @@
         }
     }
 
-    public static class Cwble extends Fmt2e {
+    public static class Cwble extends Fmt00e {
 
         public Cwble(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.LessEqual.getValue(), 0, src1.encoding(), simm10, src2.encoding());
@@ -1534,7 +1715,7 @@
         }
     }
 
-    public static class Cwbleu extends Fmt2e {
+    public static class Cwbleu extends Fmt00e {
 
         public Cwbleu(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.LessEqualUnsigned.getValue(), 0, src1.encoding(), simm10, src2.encoding());
@@ -1545,7 +1726,7 @@
         }
     }
 
-    public static class Cwbne extends Fmt2e {
+    public static class Cwbne extends Fmt00e {
 
         public Cwbne(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.NotEqual.getValue(), 0, src1.encoding(), simm10, src2.encoding());
@@ -1556,7 +1737,7 @@
         }
     }
 
-    public static class Cwbneg extends Fmt2e {
+    public static class Cwbneg extends Fmt00e {
 
         public Cwbneg(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.Negative.getValue(), 0, src1.encoding(), simm10, src2.encoding());
@@ -1567,7 +1748,7 @@
         }
     }
 
-    public static class Cwbpos extends Fmt2e {
+    public static class Cwbpos extends Fmt00e {
 
         public Cwbpos(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.Positive.getValue(), 0, src1.encoding(), simm10, src2.encoding());
@@ -1578,7 +1759,7 @@
         }
     }
 
-    public static class Cwbvc extends Fmt2e {
+    public static class Cwbvc extends Fmt00e {
 
         public Cwbvc(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.OverflowClear.getValue(), 0, src1.encoding(), simm10, src2.encoding());
@@ -1589,7 +1770,7 @@
         }
     }
 
-    public static class Cwbvs extends Fmt2e {
+    public static class Cwbvs extends Fmt00e {
 
         public Cwbvs(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.OverflowSet.getValue(), 0, src1.encoding(), simm10, src2.encoding());
@@ -1600,7 +1781,7 @@
         }
     }
 
-    public static class Cxbcc extends Fmt2e {
+    public static class Cxbcc extends Fmt00e {
 
         public Cxbcc(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.CarryClear.getValue(), 1, src1.encoding(), simm10, src2.encoding());
@@ -1611,7 +1792,7 @@
         }
     }
 
-    public static class Cxbcs extends Fmt2e {
+    public static class Cxbcs extends Fmt00e {
 
         public Cxbcs(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.CarrySet.getValue(), 1, src1.encoding(), simm10, src2.encoding());
@@ -1622,7 +1803,7 @@
         }
     }
 
-    public static class Cxbe extends Fmt2e {
+    public static class Cxbe extends Fmt00e {
 
         public Cxbe(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.CarryClear.getValue(), 1, src1.encoding(), simm10, src2.encoding());
@@ -1633,7 +1814,7 @@
         }
     }
 
-    public static class Cxbg extends Fmt2e {
+    public static class Cxbg extends Fmt00e {
 
         public Cxbg(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.Greater.getValue(), 1, src1.encoding(), simm10, src2.encoding());
@@ -1644,7 +1825,7 @@
         }
     }
 
-    public static class Cxbge extends Fmt2e {
+    public static class Cxbge extends Fmt00e {
 
         public Cxbge(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.GreaterEqual.getValue(), 1, src1.encoding(), simm10, src2.encoding());
@@ -1655,7 +1836,7 @@
         }
     }
 
-    public static class Cxbgu extends Fmt2e {
+    public static class Cxbgu extends Fmt00e {
 
         public Cxbgu(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.GreaterUnsigned.getValue(), 1, src1.encoding(), simm10, src2.encoding());
@@ -1666,7 +1847,7 @@
         }
     }
 
-    public static class Cxbl extends Fmt2e {
+    public static class Cxbl extends Fmt00e {
 
         public Cxbl(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.Less.getValue(), 1, src1.encoding(), simm10, src2.encoding());
@@ -1677,7 +1858,7 @@
         }
     }
 
-    public static class Cxble extends Fmt2e {
+    public static class Cxble extends Fmt00e {
 
         public Cxble(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.LessEqual.getValue(), 1, src1.encoding(), simm10, src2.encoding());
@@ -1688,7 +1869,7 @@
         }
     }
 
-    public static class Cxbleu extends Fmt2e {
+    public static class Cxbleu extends Fmt00e {
 
         public Cxbleu(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.LessEqualUnsigned.getValue(), 1, src1.encoding(), simm10, src2.encoding());
@@ -1699,7 +1880,7 @@
         }
     }
 
-    public static class Cxbne extends Fmt2e {
+    public static class Cxbne extends Fmt00e {
 
         public Cxbne(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.NotEqual.getValue(), 1, src1.encoding(), simm10, src2.encoding());
@@ -1710,7 +1891,7 @@
         }
     }
 
-    public static class Cxbneg extends Fmt2e {
+    public static class Cxbneg extends Fmt00e {
 
         public Cxbneg(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.Negative.getValue(), 1, src1.encoding(), simm10, src2.encoding());
@@ -1721,7 +1902,7 @@
         }
     }
 
-    public static class Cxbpos extends Fmt2e {
+    public static class Cxbpos extends Fmt00e {
 
         public Cxbpos(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.Positive.getValue(), 1, src1.encoding(), simm10, src2.encoding());
@@ -1732,7 +1913,7 @@
         }
     }
 
-    public static class Cxbvc extends Fmt2e {
+    public static class Cxbvc extends Fmt00e {
 
         public Cxbvc(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.OverflowClear.getValue(), 1, src1.encoding(), simm10, src2.encoding());
@@ -1743,7 +1924,7 @@
         }
     }
 
-    public static class Cxbvs extends Fmt2e {
+    public static class Cxbvs extends Fmt00e {
 
         public Cxbvs(SPARCAssembler asm, Register src1, Register src2, int simm10) {
             super(asm, Ops.BranchOp.getValue(), ConditionFlag.OverflowSet.getValue(), 1, src1.encoding(), simm10, src2.encoding());
@@ -2098,10 +2279,10 @@
         }
     }
 
-    public static class Flushw extends Fmt3r {
-
-        public Flushw(SPARCAssembler masm) {
-            super(masm, Ops.ArithOp.getValue(), 0, Op3s.Flushw.getValue());
+    public static class Flushw extends Fmt10 {
+
+        public Flushw() {
+            super(Op3s.Flushw);
         }
     }
 
@@ -2296,67 +2477,67 @@
         }
     }
 
-    public static class Jmpl extends Fmt3b {
+    public static class Jmpl extends Fmt10 {
 
         public Jmpl(Register src, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Jmpl, src, simm13, dst);
+            super(Op3s.Jmpl, src, simm13, dst);
         }
     }
 
-    public static class Lddf extends Fmt3b {
+    public static class Lddf extends Fmt11 {
 
         // TODO remove address
         public Lddf(SPARCAddress src, Register dst) {
-            super(Ops.LdstOp, Op3s.Lddf, src.getBase(), src.getDisplacement(), dst);
+            super(Op3s.Lddf, src.getBase(), src.getDisplacement(), dst);
         }
     }
 
-    public static class Ldf extends Fmt3b {
+    public static class Ldf extends Fmt11 {
 
         public Ldf(SPARCAddress src, Register dst) {
-            super(Ops.LdstOp, Op3s.Ldf, src.getBase(), src.getDisplacement(), dst);
+            super(Op3s.Ldf, src.getBase(), src.getDisplacement(), dst);
         }
     }
 
-    public static class Ldsb extends Fmt3b {
+    public static class Ldsb extends Fmt11 {
 
         public Ldsb(SPARCAddress src, Register dst) {
-            super(Ops.LdstOp, Op3s.Ldsb, src.getBase(), src.getDisplacement(), dst);
+            super(Op3s.Ldsb, src.getBase(), src.getDisplacement(), dst);
         }
     }
 
-    public static class Ldsh extends Fmt3b {
+    public static class Ldsh extends Fmt11 {
 
         public Ldsh(SPARCAddress src, Register dst) {
-            super(Ops.LdstOp, Op3s.Ldsh, src.getBase(), src.getDisplacement(), dst);
+            super(Op3s.Ldsh, src.getBase(), src.getDisplacement(), dst);
         }
     }
 
-    public static class Ldsw extends Fmt3b {
+    public static class Ldsw extends Fmt11 {
 
         public Ldsw(SPARCAddress src, Register dst) {
-            super(Ops.LdstOp, Op3s.Ldsw, src.getBase(), src.getDisplacement(), dst);
+            super(Op3s.Ldsw, src.getBase(), src.getDisplacement(), dst);
         }
     }
 
-    public static class Lduw extends Fmt3b {
+    public static class Lduw extends Fmt11 {
 
         public Lduw(SPARCAddress src, Register dst) {
-            super(Ops.LdstOp, Op3s.Lduw, src.getBase(), src.getDisplacement(), dst);
+            super(Op3s.Lduw, src.getBase(), src.getDisplacement(), dst);
         }
     }
 
-    public static class Ldx extends Fmt3b {
+    public static class Ldx extends Fmt11 {
 
         public Ldx(SPARCAddress src, Register dst) {
-            super(Ops.LdstOp, Op3s.Ldx, src.getBase(), src.getDisplacement(), dst);
+            super(Op3s.Ldx, src.getBase(), src.getDisplacement(), dst);
         }
     }
 
-    public static class Membar extends Fmt3b {
+    public static class Membar extends Fmt10 {
 
         public Membar(int barriers) {
-            super(Ops.ArithOp, Op3s.Membar, r15, ImmedTrue | barriers, r0);
+            super(Op3s.Membar, r15, barriers, r0);
         }
     }
 
@@ -2383,209 +2564,209 @@
     }
 
     @Deprecated
-    public static class Mulscc extends Fmt3b {
+    public static class Mulscc extends Fmt10 {
 
         @Deprecated
         public Mulscc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Mulscc, src1, simm13, dst);
+            super(Op3s.Mulscc, src1, simm13, dst);
         }
 
         @Deprecated
         public Mulscc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Mulscc, src1, src2, dst);
+            super(Op3s.Mulscc, src1, src2, dst);
         }
     }
 
-    public static class Mulx extends Fmt3b {
+    public static class Mulx extends Fmt10 {
 
         public Mulx(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Mulx, src1, simm13, dst);
+            super(Op3s.Mulx, src1, simm13, dst);
         }
 
         public Mulx(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Mulx, src1, src2, dst);
+            super(Op3s.Mulx, src1, src2, dst);
         }
     }
 
-    public static class Or extends Fmt3b {
+    public static class Or extends Fmt10 {
 
         public Or(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Or, src1, simm13, dst);
+            super(Op3s.Or, src1, simm13, dst);
         }
 
         public Or(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Or, src1, src2, dst);
+            super(Op3s.Or, src1, src2, dst);
         }
     }
 
-    public static class Orcc extends Fmt3b {
+    public static class Orcc extends Fmt10 {
 
         public Orcc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Orcc, src1, simm13, dst);
+            super(Op3s.Orcc, src1, simm13, dst);
         }
 
         public Orcc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Orcc, src1, src2, dst);
+            super(Op3s.Orcc, src1, src2, dst);
         }
     }
 
-    public static class Orn extends Fmt3b {
+    public static class Orn extends Fmt10 {
 
         public Orn(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Orn, src1, simm13, dst);
+            super(Op3s.Orn, src1, simm13, dst);
         }
 
         public Orn(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Orn, src1, src2, dst);
+            super(Op3s.Orn, src1, src2, dst);
         }
     }
 
-    public static class Orncc extends Fmt3b {
+    public static class Orncc extends Fmt10 {
 
         public Orncc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Orncc, src1, simm13, dst);
+            super(Op3s.Orncc, src1, simm13, dst);
         }
 
         public Orncc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Orncc, src1, src2, dst);
+            super(Op3s.Orncc, src1, src2, dst);
         }
     }
 
-    public static class Popc extends Fmt3b {
+    public static class Popc extends Fmt10 {
 
         public Popc(int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Popc, r0, simm13, dst);
+            super(Op3s.Popc, r0, simm13, dst);
         }
 
         public Popc(Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Popc, r0, src2, dst);
+            super(Op3s.Popc, r0, src2, dst);
         }
     }
 
     // A.44 Read State Register
 
     @Deprecated
-    public static class Rdy extends Fmt3q {
-
-        public Rdy(SPARCAssembler masm, Register dst) {
-            super(masm, Ops.ArithOp.getValue(), Op3s.Rdreg.getValue(), 0, dst.encoding());
+    public static class Rdy extends Fmt10 {
+
+        public Rdy(Register dst) {
+            super(Op3s.Rdreg, r0, dst);
         }
     }
 
-    public static class Rdccr extends Fmt3q {
-
-        public Rdccr(SPARCAssembler masm, Register dst) {
-            super(masm, Ops.ArithOp.getValue(), Op3s.Rdreg.getValue(), 2, dst.encoding());
+    public static class Rdccr extends Fmt10 {
+
+        public Rdccr(Register dst) {
+            super(Op3s.Rdreg, r2, dst);
         }
     }
 
-    public static class Rdasi extends Fmt3q {
-
-        public Rdasi(SPARCAssembler masm, Register dst) {
-            super(masm, Ops.ArithOp.getValue(), Op3s.Rdreg.getValue(), 3, dst.encoding());
+    public static class Rdasi extends Fmt10 {
+
+        public Rdasi(Register dst) {
+            super(Op3s.Rdreg, r3, dst);
         }
     }
 
-    public static class Rdtick extends Fmt3q {
-
-        public Rdtick(SPARCAssembler masm, Register dst) {
-            super(masm, Ops.ArithOp.getValue(), Op3s.Rdreg.getValue(), 4, dst.encoding());
+    public static class Rdtick extends Fmt10 {
+
+        public Rdtick(Register dst) {
+            super(Op3s.Rdreg, r4, dst);
         }
     }
 
-    public static class Rdpc extends Fmt3q {
-
-        public Rdpc(SPARCAssembler masm, Register dst) {
-            super(masm, Ops.ArithOp.getValue(), Op3s.Rdreg.getValue(), 5, dst.encoding());
+    public static class Rdpc extends Fmt10 {
+
+        public Rdpc(Register dst) {
+            super(Op3s.Rdreg, r5, dst);
         }
     }
 
-    public static class Rdfprs extends Fmt3q {
-
-        public Rdfprs(SPARCAssembler masm, Register dst) {
-            super(masm, Ops.ArithOp.getValue(), Op3s.Rdreg.getValue(), 6, dst.encoding());
+    public static class Rdfprs extends Fmt10 {
+
+        public Rdfprs(Register dst) {
+            super(Op3s.Rdreg, r6, dst);
         }
     }
 
-    public static class Restore extends Fmt3b {
+    public static class Restore extends Fmt10 {
 
         public Restore(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Restore, src1, src2, dst);
+            super(Op3s.Restore, src1, src2, dst);
         }
     }
 
-    public static class Restored extends Fmt3r {
-
-        public Restored(SPARCAssembler asm) {
-            super(asm, Ops.ArithOp.getValue(), 1, Op3s.Saved.getValue());
+    public static class Restored extends Fmt10 {
+
+        public Restored() {
+            super(Op3s.Saved, r0, r0, r1);
         }
     }
 
-    public static class Return extends Fmt3d {
-
-        public Return(SPARCAssembler masm, Register src1, int simm13) {
-            super(masm, Ops.ArithOp.getValue(), Op3s.Rett.getValue(), src1.encoding(), simm13);
-        }
-
-        public Return(SPARCAssembler masm, Register src1, Register src2) {
-            super(masm, Ops.ArithOp.getValue(), Op3s.Rett.getValue(), src1.encoding(), src2.encoding());
+    public static class Return extends Fmt10 {
+
+        public Return(Register src1, int simm13) {
+            super(Op3s.Rett, src1, simm13, r0);
+        }
+
+        public Return(Register src1, Register src2) {
+            super(Op3s.Rett, src1, src2, r0);
         }
     }
 
-    public static class Save extends Fmt3b {
+    public static class Save extends Fmt10 {
 
         public Save(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Save, src1, src2, dst);
+            super(Op3s.Save, src1, src2, dst);
         }
 
         public Save(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Save, src1, simm13, dst);
+            super(Op3s.Save, src1, simm13, dst);
         }
     }
 
-    public static class Saved extends Fmt3r {
-
-        public Saved(SPARCAssembler asm) {
-            super(asm, Ops.ArithOp.getValue(), 0, Op3s.Saved.getValue());
+    public static class Saved extends Fmt10 {
+
+        public Saved() {
+            super(Op3s.Saved, r0, r0, r0);
         }
     }
 
     @Deprecated
-    public static class Sdiv extends Fmt3b {
+    public static class Sdiv extends Fmt10 {
 
         @Deprecated
         public Sdiv(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Sdiv, src1, simm13, dst);
+            super(Op3s.Sdiv, src1, simm13, dst);
         }
 
         @Deprecated
         public Sdiv(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Sdiv, src1, src2, dst);
+            super(Op3s.Sdiv, src1, src2, dst);
         }
     }
 
     @Deprecated
-    public static class Sdivcc extends Fmt3b {
+    public static class Sdivcc extends Fmt10 {
 
         @Deprecated
         public Sdivcc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Sdivcc, src1, simm13, dst);
+            super(Op3s.Sdivcc, src1, simm13, dst);
         }
 
         @Deprecated
         public Sdivcc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Sdivcc, src1, src2, dst);
+            super(Op3s.Sdivcc, src1, src2, dst);
         }
     }
 
-    public static class Sdivx extends Fmt3b {
+    public static class Sdivx extends Fmt10 {
 
         public Sdivx(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Sdivx, src1, simm13, dst);
+            super(Op3s.Sdivx, src1, simm13, dst);
         }
 
         public Sdivx(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Sdivx, src1, src2, dst);
+            super(Op3s.Sdivx, src1, src2, dst);
         }
     }
 
@@ -2596,148 +2777,148 @@
         }
     }
 
-    public static class Sir extends Fmt3b {
+    public static class Sir extends Fmt10 {
 
         public Sir(int simm13) {
-            super(Ops.ArithOp, Op3s.Sir, r0, simm13, r15);
+            super(Op3s.Sir, r0, simm13, r15);
         }
     }
 
-    public static class Sll extends Fmt3b {
+    public static class Sll extends Fmt10 {
 
         public Sll(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Sll, src1, simm13, dst);
+            super(Op3s.Sll, src1, simm13, dst);
         }
 
         public Sll(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Sll, src1, src2, dst);
+            super(Op3s.Sll, src1, src2, dst);
         }
     }
 
-    public static class Sllx extends Fmt3b {
+    public static class Sllx extends Fmt10 {
 
         public Sllx(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Sllx, src1, simm13, dst);
+            super(Op3s.Sllx, src1, simm13, dst);
         }
 
         public Sllx(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Sllx, src1, src2, dst);
+            super(Op3s.Sllx, src1, src2, dst);
         }
     }
 
-    public static class Sra extends Fmt3b {
+    public static class Sra extends Fmt10 {
 
         public Sra(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Sra, src1, simm13, dst);
+            super(Op3s.Sra, src1, simm13, dst);
         }
 
         public Sra(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Sra, src1, src2, dst);
+            super(Op3s.Sra, src1, src2, dst);
         }
     }
 
-    public static class Srax extends Fmt3b {
+    public static class Srax extends Fmt10 {
 
         public Srax(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Srax, src1, simm13, dst);
+            super(Op3s.Srax, src1, simm13, dst);
         }
 
         public Srax(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Srax, src1, src2, dst);
+            super(Op3s.Srax, src1, src2, dst);
         }
     }
 
-    public static class Srl extends Fmt3b {
+    public static class Srl extends Fmt10 {
 
         public Srl(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Srl, src1, simm13, dst);
+            super(Op3s.Srl, src1, simm13, dst);
         }
 
         public Srl(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Srl, src1, src2, dst);
+            super(Op3s.Srl, src1, src2, dst);
         }
     }
 
-    public static class Srlx extends Fmt3b {
+    public static class Srlx extends Fmt10 {
 
         public Srlx(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Srlx, src1, simm13, dst);
+            super(Op3s.Srlx, src1, simm13, dst);
         }
 
         public Srlx(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Srlx, src1, src2, dst);
+            super(Op3s.Srlx, src1, src2, dst);
         }
     }
 
-    public static class Stb extends Fmt3b {
+    public static class Stb extends Fmt11 {
 
         public Stb(Register dst, SPARCAddress addr) {
-            super(Ops.LdstOp, Op3s.Stb, addr.getBase(), addr.getDisplacement(), dst);
+            super(Op3s.Stb, addr.getBase(), addr.getDisplacement(), dst);
         }
     }
 
-    public static class Sth extends Fmt3b {
+    public static class Sth extends Fmt11 {
 
         public Sth(Register dst, SPARCAddress addr) {
-            super(Ops.LdstOp, Op3s.Sth, addr.getBase(), addr.getDisplacement(), dst);
+            super(Op3s.Sth, addr.getBase(), addr.getDisplacement(), dst);
         }
     }
 
-    public static class Stw extends Fmt3b {
+    public static class Stw extends Fmt11 {
 
         public Stw(Register dst, SPARCAddress addr) {
-            super(Ops.LdstOp, Op3s.Stw, addr.getBase(), addr.getDisplacement(), dst);
+            super(Op3s.Stw, addr.getBase(), addr.getDisplacement(), dst);
         }
     }
 
-    public static class Stx extends Fmt3b {
+    public static class Stx extends Fmt11 {
 
         public Stx(Register dst, SPARCAddress addr) {
-            super(Ops.LdstOp, Op3s.Stx, addr.getBase(), addr.getDisplacement(), dst);
+            super(Op3s.Stx, addr.getBase(), addr.getDisplacement(), dst);
         }
     }
 
-    public static class Sub extends Fmt3b {
+    public static class Sub extends Fmt10 {
 
         public Sub(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Sub, src1, simm13, dst);
+            super(Op3s.Sub, src1, simm13, dst);
         }
 
         public Sub(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Sub, src1, src2, dst);
+            super(Op3s.Sub, src1, src2, dst);
         }
     }
 
-    public static class Subc extends Fmt3b {
+    public static class Subc extends Fmt10 {
 
         public Subc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Subc, src1, simm13, dst);
+            super(Op3s.Subc, src1, simm13, dst);
         }
 
         public Subc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Subc, src1, src2, dst);
+            super(Op3s.Subc, src1, src2, dst);
         }
     }
 
-    public static class Subcc extends Fmt3b {
+    public static class Subcc extends Fmt10 {
 
         public Subcc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Subcc, src1, simm13, dst);
+            super(Op3s.Subcc, src1, simm13, dst);
         }
 
         public Subcc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Subcc, src1, src2, dst);
+            super(Op3s.Subcc, src1, src2, dst);
         }
     }
 
-    public static class Subccc extends Fmt3b {
+    public static class Subccc extends Fmt10 {
 
         public Subccc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Subccc, src1, simm13, dst);
+            super(Op3s.Subccc, src1, simm13, dst);
         }
 
         public Subccc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Subccc, src1, src2, dst);
+            super(Op3s.Subccc, src1, src2, dst);
         }
     }
 
@@ -2752,14 +2933,14 @@
         }
     }
 
-    public static class Taddcc extends Fmt3b {
+    public static class Taddcc extends Fmt10 {
 
         public Taddcc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Taddcc, src1, simm13, dst);
+            super(Op3s.Taddcc, src1, simm13, dst);
         }
 
         public Taddcc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Taddcc, src1, src2, dst);
+            super(Op3s.Taddcc, src1, src2, dst);
         }
     }
 
@@ -2884,14 +3065,14 @@
         }
     }
 
-    public static class Tsubcc extends Fmt3b {
+    public static class Tsubcc extends Fmt10 {
 
         public Tsubcc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Tsubcc, src1, simm13, dst);
+            super(Op3s.Tsubcc, src1, simm13, dst);
         }
 
         public Tsubcc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Tsubcc, src1, src2, dst);
+            super(Op3s.Tsubcc, src1, src2, dst);
         }
     }
 
@@ -2917,105 +3098,105 @@
         }
     }
 
-    public static class Udivx extends Fmt3b {
+    public static class Udivx extends Fmt10 {
 
         public Udivx(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Udivx, src1, simm13, dst);
+            super(Op3s.Udivx, src1, simm13, dst);
         }
 
         public Udivx(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Udivx, src1, src2, dst);
+            super(Op3s.Udivx, src1, src2, dst);
         }
     }
 
     @Deprecated
-    public static class Wry extends Fmt3b {
+    public static class Wry extends Fmt10 {
 
         @Deprecated
         public Wry(Register src1, int simm13) {
-            super(Ops.ArithOp, Op3s.Wrreg, src1, simm13, r0);
+            super(Op3s.Wrreg, src1, simm13, r0);
         }
 
         @Deprecated
         public Wry(Register src1, Register src2) {
-            super(Ops.ArithOp, Op3s.Wrreg, src1, src2, r0);
+            super(Op3s.Wrreg, src1, src2, r0);
         }
     }
 
-    public static class Wrccr extends Fmt3b {
+    public static class Wrccr extends Fmt10 {
 
         public Wrccr(Register src1, int simm13) {
-            super(Ops.ArithOp, Op3s.Wrreg, src1, simm13, r2);
+            super(Op3s.Wrreg, src1, simm13, r2);
         }
 
         public Wrccr(Register src1, Register src2) {
-            super(Ops.ArithOp, Op3s.Wrreg, src1, src2, r2);
+            super(Op3s.Wrreg, src1, src2, r2);
         }
     }
 
-    public static class Wrasi extends Fmt3b {
+    public static class Wrasi extends Fmt10 {
 
         public Wrasi(Register src1, int simm13) {
-            super(Ops.ArithOp, Op3s.Wrreg, src1, simm13, r3);
+            super(Op3s.Wrreg, src1, simm13, r3);
         }
 
         public Wrasi(Register src1, Register src2) {
-            super(Ops.ArithOp, Op3s.Wrreg, src1, src2, r3);
+            super(Op3s.Wrreg, src1, src2, r3);
         }
     }
 
-    public static class Wrfprs extends Fmt3b {
+    public static class Wrfprs extends Fmt10 {
 
         public Wrfprs(Register src1, int simm13) {
-            super(Ops.ArithOp, Op3s.Wrreg, src1, simm13, r6);
+            super(Op3s.Wrreg, src1, simm13, r6);
         }
 
         public Wrfprs(Register src1, Register src2) {
-            super(Ops.ArithOp, Op3s.Wrreg, src1, src2, r6);
+            super(Op3s.Wrreg, src1, src2, r6);
         }
     }
 
-    public static class Xor extends Fmt3b {
+    public static class Xor extends Fmt10 {
 
         public Xor(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Xor, src1, simm13, dst);
+            super(Op3s.Xor, src1, simm13, dst);
         }
 
         public Xor(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Xor, src1, src2, dst);
+            super(Op3s.Xor, src1, src2, dst);
         }
     }
 
-    public static class Xorcc extends Fmt3b {
+    public static class Xorcc extends Fmt10 {
 
         public Xorcc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Xorcc, src1, simm13, dst);
+            super(Op3s.Xorcc, src1, simm13, dst);
         }
 
         public Xorcc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Xorcc, src1, src2, dst);
+            super(Op3s.Xorcc, src1, src2, dst);
         }
     }
 
-    public static class Xnor extends Fmt3b {
+    public static class Xnor extends Fmt10 {
 
         public Xnor(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Xnor, src1, simm13, dst);
+            super(Op3s.Xnor, src1, simm13, dst);
         }
 
         public Xnor(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Xnor, src1, src2, dst);
+            super(Op3s.Xnor, src1, src2, dst);
         }
     }
 
-    public static class Xnorcc extends Fmt3b {
+    public static class Xnorcc extends Fmt10 {
 
         public Xnorcc(Register src1, int simm13, Register dst) {
-            super(Ops.ArithOp, Op3s.Xnorcc, src1, simm13, dst);
+            super(Op3s.Xnorcc, src1, simm13, dst);
         }
 
         public Xnorcc(Register src1, Register src2, Register dst) {
-            super(Ops.ArithOp, Op3s.Xnorcc, src1, src2, dst);
+            super(Op3s.Xnorcc, src1, src2, dst);
         }
     }
 }
--- a/graal/com.oracle.graal.asm.sparc/src/com/oracle/graal/asm/sparc/SPARCMacroAssembler.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.asm.sparc/src/com/oracle/graal/asm/sparc/SPARCMacroAssembler.java	Wed Jul 10 05:27:45 2013 +0200
@@ -22,14 +22,20 @@
  */
 package com.oracle.graal.asm.sparc;
 
+import static com.oracle.graal.asm.sparc.SPARCAssembler.CC.*;
 import static com.oracle.graal.sparc.SPARC.*;
-import static com.oracle.graal.asm.sparc.SPARCAssembler.CC.*;
 
 import com.oracle.graal.api.code.*;
 import com.oracle.graal.asm.*;
 
 public class SPARCMacroAssembler extends SPARCAssembler {
 
+    /**
+     * A sentinel value used as a place holder in an instruction stream for an address that will be
+     * patched.
+     */
+    private static final SPARCAddress Placeholder = new SPARCAddress(g0, 0);
+
     public SPARCMacroAssembler(TargetDescription target, RegisterConfig registerConfig) {
         super(target, registerConfig);
     }
@@ -60,12 +66,12 @@
 
     @Override
     public AbstractAddress makeAddress(Register base, int displacement) {
-        throw new InternalError("NYI");
+        return new SPARCAddress(base, displacement);
     }
 
     @Override
     public AbstractAddress getPlaceholder() {
-        throw new InternalError("NYI");
+        return Placeholder;
     }
 
     public static class Bclr extends Andn {
--- a/graal/com.oracle.graal.compiler.sparc/src/com/oracle/graal/compiler/sparc/SPARCLIRGenerator.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.compiler.sparc/src/com/oracle/graal/compiler/sparc/SPARCLIRGenerator.java	Wed Jul 10 05:27:45 2013 +0200
@@ -25,35 +25,27 @@
 
 import static com.oracle.graal.api.code.ValueUtil.*;
 import static com.oracle.graal.lir.LIRValueUtil.*;
+import static com.oracle.graal.lir.sparc.SPARCArithmetic.*;
 import static com.oracle.graal.lir.sparc.SPARCBitManipulationOp.IntrinsicOpcode.*;
+import static com.oracle.graal.lir.sparc.SPARCCompare.*;
 import static com.oracle.graal.lir.sparc.SPARCMathIntrinsicOp.IntrinsicOpcode.*;
-import static com.oracle.graal.lir.sparc.SPARCArithmetic.*;
-import static com.oracle.graal.lir.sparc.SPARCCompare.*;
 
-import com.oracle.graal.api.code.CallingConvention;
-import com.oracle.graal.api.code.CodeCacheProvider;
-import com.oracle.graal.api.code.DeoptimizationAction;
-import com.oracle.graal.api.code.ForeignCallLinkage;
-import com.oracle.graal.api.code.StackSlot;
-import com.oracle.graal.api.code.TargetDescription;
+import com.oracle.graal.api.code.*;
 import com.oracle.graal.api.meta.*;
 import com.oracle.graal.asm.sparc.*;
-import com.oracle.graal.compiler.gen.LIRGenerator;
-import com.oracle.graal.compiler.target.LIRGenLowerable;
-import com.oracle.graal.graph.GraalInternalError;
+import com.oracle.graal.compiler.gen.*;
+import com.oracle.graal.compiler.target.*;
+import com.oracle.graal.graph.*;
 import com.oracle.graal.lir.*;
-import com.oracle.graal.lir.StandardOp.*;
-import com.oracle.graal.lir.sparc.SPARCAddressValue;
+import com.oracle.graal.lir.StandardOp.JumpOp;
+import com.oracle.graal.lir.sparc.*;
 import com.oracle.graal.lir.sparc.SPARCArithmetic.BinaryRegConst;
 import com.oracle.graal.lir.sparc.SPARCArithmetic.Op1Stack;
+import com.oracle.graal.lir.sparc.SPARCArithmetic.Op2Reg;
 import com.oracle.graal.lir.sparc.SPARCArithmetic.Op2Stack;
-import com.oracle.graal.lir.sparc.SPARCArithmetic.Op2Reg;
 import com.oracle.graal.lir.sparc.SPARCArithmetic.ShiftOp;
 import com.oracle.graal.lir.sparc.SPARCArithmetic.Unary1Op;
 import com.oracle.graal.lir.sparc.SPARCArithmetic.Unary2Op;
-import com.oracle.graal.lir.sparc.SPARCBitManipulationOp;
-import com.oracle.graal.lir.sparc.SPARCBreakpointOp;
-import com.oracle.graal.lir.sparc.SPARCByteSwapOp;
 import com.oracle.graal.lir.sparc.SPARCCompare.CompareOp;
 import com.oracle.graal.lir.sparc.SPARCControlFlow.BranchOp;
 import com.oracle.graal.lir.sparc.SPARCControlFlow.CondMoveOp;
@@ -62,7 +54,6 @@
 import com.oracle.graal.lir.sparc.SPARCControlFlow.SequentialSwitchOp;
 import com.oracle.graal.lir.sparc.SPARCControlFlow.SwitchRangesOp;
 import com.oracle.graal.lir.sparc.SPARCControlFlow.TableSwitchOp;
-import com.oracle.graal.lir.sparc.SPARCMathIntrinsicOp;
 import com.oracle.graal.lir.sparc.SPARCMove.LoadOp;
 import com.oracle.graal.lir.sparc.SPARCMove.MembarOp;
 import com.oracle.graal.lir.sparc.SPARCMove.MoveFromRegOp;
@@ -70,29 +61,21 @@
 import com.oracle.graal.lir.sparc.SPARCMove.NullCheckOp;
 import com.oracle.graal.lir.sparc.SPARCMove.StackLoadAddressOp;
 import com.oracle.graal.lir.sparc.SPARCMove.StoreOp;
-import com.oracle.graal.lir.sparc.SPARCTestOp;
-import com.oracle.graal.nodes.BreakpointNode;
-import com.oracle.graal.nodes.DeoptimizingNode;
-import com.oracle.graal.nodes.DirectCallTargetNode;
-import com.oracle.graal.nodes.IndirectCallTargetNode;
-import com.oracle.graal.nodes.InfopointNode;
-import com.oracle.graal.nodes.SafepointNode;
-import com.oracle.graal.nodes.StructuredGraph;
-import com.oracle.graal.nodes.ValueNode;
+import com.oracle.graal.nodes.*;
 import com.oracle.graal.nodes.calc.*;
 import com.oracle.graal.nodes.calc.ConvertNode.Op;
-import com.oracle.graal.nodes.java.CompareAndSwapNode;
+import com.oracle.graal.nodes.java.*;
 
 /**
  * This class implements the SPARC specific portion of the LIR generator.
  */
-public class SPARCLIRGenerator extends LIRGenerator {
+public abstract class SPARCLIRGenerator extends LIRGenerator {
 
-    public static class SPARCSpillMoveFactory implements LIR.SpillMoveFactory {
+    private class SPARCSpillMoveFactory implements LIR.SpillMoveFactory {
 
         @Override
         public LIRInstruction createMove(AllocatableValue result, Value input) {
-            throw new InternalError("NYI");
+            return SPARCLIRGenerator.this.createMove(result, input);
         }
     }
 
@@ -117,20 +100,20 @@
         return result;
     }
 
+    protected SPARCLIRInstruction createMove(AllocatableValue dst, Value src) {
+        if (src instanceof SPARCAddressValue) {
+            // return new LeaOp(dst, (AMD64AddressValue) src);
+            throw new InternalError("NYI");
+        } else if (isRegister(src) || isStackSlot(dst)) {
+            return new MoveFromRegOp(dst, src);
+        } else {
+            return new MoveToRegOp(dst, src);
+        }
+    }
+
     @Override
     public void emitMove(AllocatableValue dst, Value src) {
-        // XXX SPARCAddress loads
-        /*
-         * if (src instanceof SPARCAddressValue) { public LoadOp(Kind kind, AllocatableValue result,
-         * SPARCAddressValue address, LIRFrameState state) {
-         * 
-         * return new LoadOp(result.getKind(), result, (SPARCAddressValue) src); }
-         */
-        if (isRegister(src) || isStackSlot(dst)) {
-            append(new MoveFromRegOp(dst, src));
-        } else {
-            append(new MoveToRegOp(dst, src));
-        }
+        append(createMove(dst, src));
     }
 
     @Override
@@ -300,16 +283,6 @@
     }
 
     @Override
-    protected void emitDirectCall(DirectCallTargetNode callTarget, Value result, Value[] parameters, Value[] temps, LIRFrameState callState) {
-        throw new InternalError("NYI");
-    }
-
-    @Override
-    protected void emitIndirectCall(IndirectCallTargetNode callTarget, Value result, Value[] parameters, Value[] temps, LIRFrameState callState) {
-        throw new InternalError("NYI");
-    }
-
-    @Override
     protected void emitForeignCall(ForeignCallLinkage linkage, Value result, Value[] arguments, Value[] temps, LIRFrameState info) {
         throw new InternalError("NYI");
     }
--- a/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotBackend.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotBackend.java	Wed Jul 10 05:27:45 2013 +0200
@@ -97,13 +97,15 @@
 
         @Override
         public void enter(TargetMethodAssembler tasm) {
-            final int frameSize = tasm.frameMap.frameSize();
+            final int alignment = target.wordSize * 2;
+            final int frameSize = (tasm.frameMap.frameSize() + (alignment - 1)) & ~(alignment - 1);
+            assert frameSize % alignment == 0 : "must preserve 2*wordSize alignment";
 
             SPARCMacroAssembler masm = (SPARCMacroAssembler) tasm.asm;
             if (!isStub) {
                 emitStackOverflowCheck(tasm, false);
             }
-            new Save(sp, frameSize, sp).emit(masm);
+            new Save(sp, -frameSize, sp).emit(masm);
 
             if (ZapStackOnMethodEntry.getValue()) {
                 final int slotSize = 8;
--- a/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotLIRGenerator.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotLIRGenerator.java	Wed Jul 10 05:27:45 2013 +0200
@@ -22,29 +22,24 @@
  */
 package com.oracle.graal.hotspot.sparc;
 
-import com.oracle.graal.api.code.CallingConvention;
-import com.oracle.graal.api.code.CodeCacheProvider;
-import com.oracle.graal.api.code.DeoptimizationAction;
-import com.oracle.graal.api.code.StackSlot;
-import com.oracle.graal.api.code.TargetDescription;
-import com.oracle.graal.api.meta.DeoptimizationReason;
-import com.oracle.graal.api.meta.Value;
-import com.oracle.graal.compiler.sparc.SPARCLIRGenerator;
-import com.oracle.graal.hotspot.HotSpotLIRGenerator;
-import com.oracle.graal.hotspot.nodes.DirectCompareAndSwapNode;
-import com.oracle.graal.hotspot.stubs.Stub;
-import com.oracle.graal.lir.FrameMap;
-import com.oracle.graal.lir.LIR;
-import com.oracle.graal.nodes.StructuredGraph;
-import com.oracle.graal.nodes.ValueNode;
+import java.lang.reflect.*;
 
-public class SPARCHotSpotLIRGenerator  extends SPARCLIRGenerator implements HotSpotLIRGenerator {
+import com.oracle.graal.api.code.*;
+import com.oracle.graal.api.meta.*;
+import com.oracle.graal.compiler.sparc.*;
+import com.oracle.graal.hotspot.*;
+import com.oracle.graal.hotspot.meta.*;
+import com.oracle.graal.hotspot.nodes.*;
+import com.oracle.graal.hotspot.stubs.*;
+import com.oracle.graal.lir.*;
+import com.oracle.graal.nodes.*;
+import com.oracle.graal.nodes.java.MethodCallTargetNode.InvokeKind;
+
+public class SPARCHotSpotLIRGenerator extends SPARCLIRGenerator implements HotSpotLIRGenerator {
 
     public StackSlot deoptimizationRescueSlot;
 
-    public SPARCHotSpotLIRGenerator(StructuredGraph graph,
-            CodeCacheProvider runtime, TargetDescription target,
-            FrameMap frameMap, CallingConvention cc, LIR lir) {
+    public SPARCHotSpotLIRGenerator(StructuredGraph graph, CodeCacheProvider runtime, TargetDescription target, FrameMap frameMap, CallingConvention cc, LIR lir) {
         super(graph, runtime, target, frameMap, cc, lir);
         // TODO Auto-generated constructor stub
     }
@@ -55,8 +50,35 @@
     }
 
     @Override
-    public void emitDeoptimizeCaller(DeoptimizationAction action,
-            DeoptimizationReason reason) {
+    protected void emitDirectCall(DirectCallTargetNode callTarget, Value result, Value[] parameters, Value[] temps, LIRFrameState callState) {
+        InvokeKind invokeKind = ((HotSpotDirectCallTargetNode) callTarget).invokeKind();
+        if (invokeKind == InvokeKind.Interface || invokeKind == InvokeKind.Virtual) {
+// append(new SPARCHotspotDirectVirtualCallOp(callTarget.target(), result, parameters, temps,
+// callState, invokeKind));
+            throw new InternalError("NYI");
+        } else {
+            assert invokeKind == InvokeKind.Static || invokeKind == InvokeKind.Special;
+            HotSpotResolvedJavaMethod resolvedMethod = (HotSpotResolvedJavaMethod) callTarget.target();
+            assert !Modifier.isAbstract(resolvedMethod.getModifiers()) : "Cannot make direct call to abstract method.";
+            Constant metaspaceMethod = resolvedMethod.getMetaspaceMethodConstant();
+            append(new SPARCHotspotDirectStaticCallOp(callTarget.target(), result, parameters, temps, callState, invokeKind, metaspaceMethod));
+        }
+    }
+
+    @Override
+    protected void emitIndirectCall(IndirectCallTargetNode callTarget, Value result, Value[] parameters, Value[] temps, LIRFrameState callState) {
+// AllocatableValue metaspaceMethod = AMD64.rbx.asValue();
+// emitMove(metaspaceMethod, operand(((HotSpotIndirectCallTargetNode)
+// callTarget).metaspaceMethod()));
+// AllocatableValue targetAddress = AMD64.rax.asValue();
+// emitMove(targetAddress, operand(callTarget.computedAddress()));
+// append(new AMD64IndirectCallOp(callTarget.target(), result, parameters, temps, metaspaceMethod,
+// targetAddress, callState));
+        throw new InternalError("NYI");
+    }
+
+    @Override
+    public void emitDeoptimizeCaller(DeoptimizationAction action, DeoptimizationReason reason) {
         // TODO Auto-generated method stub
     }
 
@@ -66,8 +88,7 @@
     }
 
     @Override
-    public void emitJumpToExceptionHandlerInCaller(ValueNode handlerInCallerPc,
-            ValueNode exception, ValueNode exceptionPc) {
+    public void emitJumpToExceptionHandlerInCaller(ValueNode handlerInCallerPc, ValueNode exception, ValueNode exceptionPc) {
         // TODO Auto-generated method stub
     }
 
--- a/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotRegisterConfig.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotSpotRegisterConfig.java	Wed Jul 10 05:27:45 2013 +0200
@@ -75,6 +75,9 @@
     private final Register[] nativeGeneralParameterRegisters;
     private final Register[] fpuParameterRegisters = {f0, f1, f2, f3, f4, f5, f6, f7};
 
+    private final Register[] callerSaveRegisters = {g1, g3, g4, g5, o0, o1, o2, o3, o4, o5, o7};
+    private final Register[] calleeSaveRegisters = {l0, l1, l2, l3, l4, l5, l6, l7, i0, i1, i2, i3, i4, i5, i6, i7};
+
     private final CalleeSaveLayout csl;
 
     private static Register findRegister(String name, Register[] all) {
@@ -124,14 +127,14 @@
         javaGeneralParameterRegisters = new Register[]{i0, i1, i2, i3, i4, i5};
         nativeGeneralParameterRegisters = new Register[]{i0, i1, i2, i3, i4, i5};
 
-        csl = null;
+        csl = new CalleeSaveLayout(architecture, -1, -1, architecture.getWordSize(), calleeSaveRegisters);
         allocatable = initAllocatable(config.useCompressedOops);
         attributesMap = RegisterAttributes.createMap(this, SPARC.allRegisters);
     }
 
     @Override
     public Register[] getCallerSaveRegisters() {
-        return getAllocatableRegisters();
+        return callerSaveRegisters;
     }
 
     @Override
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.hotspot.sparc/src/com/oracle/graal/hotspot/sparc/SPARCHotspotDirectStaticCallOp.java	Wed Jul 10 05:27:45 2013 +0200
@@ -0,0 +1,78 @@
+/*
+ * 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.hotspot.sparc;
+
+import static com.oracle.graal.sparc.SPARC.*;
+import static com.oracle.graal.asm.sparc.SPARCMacroAssembler.*;
+
+import com.oracle.graal.api.meta.*;
+import com.oracle.graal.asm.sparc.*;
+import com.oracle.graal.hotspot.bridge.*;
+import com.oracle.graal.lir.*;
+import com.oracle.graal.lir.asm.*;
+import com.oracle.graal.lir.sparc.SPARCCall.DirectCallOp;
+import com.oracle.graal.lir.sparc.*;
+import com.oracle.graal.nodes.java.MethodCallTargetNode.InvokeKind;
+
+/**
+ * A direct call that complies with the conventions for such calls in HotSpot. In particular, for
+ * calls using an inline cache, a MOVE instruction is emitted just prior to the aligned direct call.
+ * This instruction (which moves 0L in G3) is patched by the C++ Graal code to replace the 0L
+ * constant with Universe::non_oop_word(), a special sentinel used for the initial value of the
+ * Klass in an inline cache. It puts the called method into G5 before calling.
+ */
+@Opcode("CALL_DIRECT")
+final class SPARCHotspotDirectStaticCallOp extends DirectCallOp {
+
+    private final Constant metaspaceMethod;
+    private final InvokeKind invokeKind;
+
+    SPARCHotspotDirectStaticCallOp(ResolvedJavaMethod target, Value result, Value[] parameters, Value[] temps, LIRFrameState state, InvokeKind invokeKind, Constant metaspaceMethod) {
+        super(target, result, parameters, temps, state);
+        assert invokeKind == InvokeKind.Static || invokeKind == InvokeKind.Special;
+        this.metaspaceMethod = metaspaceMethod;
+        this.invokeKind = invokeKind;
+    }
+
+    @Override
+    public void emitCode(TargetMethodAssembler tasm, 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 so that the C++ code can find it
+        // and replace the inline 0L value with Universe::non_oop_word()
+// SPARCMove.move(tasm, masm, g5.asValue(Kind.Long), tasm.asLongConstRef(metaspaceMethod));
+
+        new Rdpc(g5).emit(masm);
+        tasm.asLongConstRef(metaspaceMethod);
+        new Ldx(new SPARCAddress(g5, 0), g5).emit(masm);
+        tasm.recordMark(invokeKind == InvokeKind.Static ? Marks.MARK_INVOKESTATIC : Marks.MARK_INVOKESPECIAL);
+        // XXX move must be patchable!
+        SPARCMove.move(tasm, masm, g3.asValue(Kind.Long), Constant.LONG_0);
+        new Nop().emit(masm);
+        new Nop().emit(masm);
+        new Nop().emit(masm);
+        new Nop().emit(masm);
+        new Nop().emit(masm);
+        new Nop().emit(masm);
+        super.emitCode(tasm, masm);
+    }
+}
--- a/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCArithmetic.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCArithmetic.java	Wed Jul 10 05:27:45 2013 +0200
@@ -27,10 +27,35 @@
 import static com.oracle.graal.lir.LIRInstruction.OperandFlag.*;
 
 import com.oracle.graal.api.meta.*;
-import com.oracle.graal.asm.sparc.SPARCAssembler;
-import com.oracle.graal.graph.GraalInternalError;
+import com.oracle.graal.asm.sparc.*;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Add;
+import com.oracle.graal.asm.sparc.SPARCAssembler.And;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Faddd;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Fadds;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Fdivd;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Fdivs;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Fdtoi;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Fmuld;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Fmuls;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Fnegd;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Fnegs;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Fstoi;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Fsubd;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Fsubs;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Mulx;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Or;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Sdivx;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Sll;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Sllx;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Sra;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Srax;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Srl;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Srlx;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Sub;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Xor;
+import com.oracle.graal.graph.*;
 import com.oracle.graal.lir.*;
-import com.oracle.graal.lir.asm.TargetMethodAssembler;
+import com.oracle.graal.lir.asm.*;
 
 public enum SPARCArithmetic {
     // @formatter:off
@@ -64,7 +89,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             SPARCMove.move(tasm, masm, result, x);
             emit(tasm, masm, opcode, result, y, null);
         }
@@ -92,7 +117,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             SPARCMove.move(tasm, masm, result, x);
             emit(tasm, masm, opcode, result, x, null);
         }
@@ -114,7 +139,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             emit(masm, opcode, result);
         }
     }
@@ -132,7 +157,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             emit(tasm, masm, opcode, result, x, null);
         }
     }
@@ -152,7 +177,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             emit(tasm, masm, opcode, result, x, y, null);
         }
 
@@ -178,7 +203,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             emit(tasm, masm, opcode, result, x, y, null);
         }
 
@@ -204,7 +229,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             emit(tasm, masm, opcode, result, x, y, null);
         }
 
--- a/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCBitManipulationOp.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCBitManipulationOp.java	Wed Jul 10 05:27:45 2013 +0200
@@ -51,7 +51,7 @@
     }
 
     @Override
-    public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+    public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
         Register dst = ValueUtil.asIntReg(result);
         Register tmp = null;  // ??
         if (ValueUtil.isRegister(input)) {
--- a/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCBreakpointOp.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCBreakpointOp.java	Wed Jul 10 05:27:45 2013 +0200
@@ -52,7 +52,7 @@
 
     @Override
     @SuppressWarnings("unused")
-    public void emitCode(TargetMethodAssembler tasm, SPARCAssembler asm) {
-        new Trap(asm, ST_RESERVED_FOR_USER_0);
+    public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
+        new Trap(masm, ST_RESERVED_FOR_USER_0);
     }
 }
--- a/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCByteSwapOp.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCByteSwapOp.java	Wed Jul 10 05:27:45 2013 +0200
@@ -39,7 +39,7 @@
     }
 
     @Override
-    public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+    public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
         SPARCMove.move(tasm, masm, result, input);
         switch (input.getKind()) {
         // case Int:
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCCall.java	Wed Jul 10 05:27:45 2013 +0200
@@ -0,0 +1,190 @@
+/*
+ * 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.lir.sparc;
+
+import static com.oracle.graal.api.code.ValueUtil.*;
+import static com.oracle.graal.lir.LIRInstruction.OperandFlag.*;
+import static com.oracle.graal.asm.sparc.SPARCMacroAssembler.*;
+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.lir.*;
+import com.oracle.graal.lir.asm.*;
+import com.oracle.graal.nodes.spi.*;
+
+public class SPARCCall {
+
+    public abstract static class CallOp extends SPARCLIRInstruction {
+
+        @Def({REG, ILLEGAL}) protected Value result;
+        @Use({REG, STACK}) protected Value[] parameters;
+        @Temp protected Value[] temps;
+        @State protected LIRFrameState state;
+
+        public CallOp(Value result, Value[] parameters, Value[] temps, LIRFrameState state) {
+            this.result = result;
+            this.parameters = parameters;
+            this.state = state;
+            this.temps = temps;
+            assert temps != null;
+        }
+
+        @Override
+        public boolean destroysCallerSavedRegisters() {
+            return true;
+        }
+    }
+
+    public abstract static class MethodCallOp extends CallOp {
+
+        protected final ResolvedJavaMethod callTarget;
+
+        public MethodCallOp(ResolvedJavaMethod callTarget, Value result, Value[] parameters, Value[] temps, LIRFrameState state) {
+            super(result, parameters, temps, state);
+            this.callTarget = callTarget;
+        }
+
+    }
+
+    @Opcode("CALL_DIRECT")
+    public static class DirectCallOp extends MethodCallOp {
+
+        public DirectCallOp(ResolvedJavaMethod callTarget, Value result, Value[] parameters, Value[] temps, LIRFrameState state) {
+            super(callTarget, result, parameters, temps, state);
+        }
+
+        @Override
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
+            directCall(tasm, masm, callTarget, null, true, state);
+        }
+    }
+
+    @Opcode("CALL_INDIRECT")
+    public static class IndirectCallOp extends MethodCallOp {
+
+        @Use({REG}) protected Value targetAddress;
+
+        public IndirectCallOp(ResolvedJavaMethod callTarget, Value result, Value[] parameters, Value[] temps, Value targetAddress, LIRFrameState state) {
+            super(callTarget, result, parameters, temps, state);
+            this.targetAddress = targetAddress;
+        }
+
+        @Override
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
+            indirectCall(tasm, masm, asRegister(targetAddress), callTarget, state);
+        }
+
+        @Override
+        protected void verify() {
+            super.verify();
+            assert isRegister(targetAddress) : "The current register allocator cannot handle variables to be used at call sites, it must be in a fixed register for now";
+        }
+    }
+
+    public abstract static class ForeignCallOp extends CallOp {
+
+        protected final ForeignCallLinkage callTarget;
+
+        public ForeignCallOp(ForeignCallLinkage callTarget, Value result, Value[] parameters, Value[] temps, LIRFrameState state) {
+            super(result, parameters, temps, state);
+            this.callTarget = callTarget;
+        }
+
+        @Override
+        public boolean destroysCallerSavedRegisters() {
+            return callTarget.destroysRegisters();
+        }
+    }
+
+    @Opcode("NEAR_FOREIGN_CALL")
+    public static class DirectNearForeignCallOp extends ForeignCallOp {
+
+        public DirectNearForeignCallOp(ForeignCallLinkage linkage, Value result, Value[] parameters, Value[] temps, LIRFrameState state) {
+            super(linkage, result, parameters, temps, state);
+        }
+
+        @Override
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
+            directCall(tasm, masm, callTarget, null, false, state);
+        }
+    }
+
+    @Opcode("FAR_FOREIGN_CALL")
+    public static class DirectFarForeignCallOp extends ForeignCallOp {
+
+        @Temp({REG}) protected AllocatableValue callTemp;
+
+        public DirectFarForeignCallOp(LIRGeneratorTool gen, ForeignCallLinkage callTarget, Value result, Value[] parameters, Value[] temps, LIRFrameState state) {
+            super(callTarget, result, parameters, temps, state);
+            callTemp = gen.newVariable(Kind.Long);
+        }
+
+        @Override
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
+            directCall(tasm, masm, callTarget, ((RegisterValue) callTemp).getRegister(), false, state);
+        }
+    }
+
+    public static void directCall(TargetMethodAssembler tasm, SPARCMacroAssembler masm, InvokeTarget callTarget, Register scratch, boolean align, LIRFrameState info) {
+        if (align) {
+            // We don't need alignment on SPARC.
+        }
+        int before = masm.codeBuffer.position();
+        if (scratch != null) {
+// // offset might not fit a 32-bit immediate, generate an
+// // indirect call with a 64-bit immediate
+// masm.movq(scratch, 0L);
+// masm.call(scratch);
+// } else {
+// masm.call();
+        }
+        new Call(0).emit(masm);
+        int after = masm.codeBuffer.position();
+        tasm.recordDirectCall(before, after, callTarget, info);
+        tasm.recordExceptionHandlers(after, info);
+// masm.ensureUniquePC();
+        new Nop().emit(masm);  // delay slot
+    }
+
+    public static void directJmp(TargetMethodAssembler tasm, SPARCMacroAssembler masm, InvokeTarget target) {
+        int before = masm.codeBuffer.position();
+// masm.jmp(0, true);
+        int after = masm.codeBuffer.position();
+        tasm.recordDirectCall(before, after, target, null);
+// masm.ensureUniquePC();
+        new Nop().emit(masm);  // delay slot
+        throw new InternalError("NYI");
+    }
+
+    public static void indirectCall(TargetMethodAssembler tasm, SPARCMacroAssembler masm, Register dst, InvokeTarget callTarget, LIRFrameState info) {
+        int before = masm.codeBuffer.position();
+        new Jmpl(dst, 0, r15).emit(masm);
+        int after = masm.codeBuffer.position();
+        tasm.recordIndirectCall(before, after, callTarget, info);
+        tasm.recordExceptionHandlers(after, info);
+// masm.ensureUniquePC();
+        new Nop().emit(masm);  // delay slot
+    }
+}
--- a/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCCompare.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCCompare.java	Wed Jul 10 05:27:45 2013 +0200
@@ -49,7 +49,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             emit(tasm, masm, opcode, x, y);
         }
 
@@ -62,7 +62,7 @@
         }
     }
 
-    public static void emit(TargetMethodAssembler tasm, SPARCAssembler masm, SPARCCompare opcode, Value x, Value y) {
+    public static void emit(TargetMethodAssembler tasm, SPARCMacroAssembler masm, SPARCCompare opcode, Value x, Value y) {
         if (isRegister(y)) {
             switch (opcode) {
                 case ICMP:
--- a/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCControlFlow.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCControlFlow.java	Wed Jul 10 05:27:45 2013 +0200
@@ -52,7 +52,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             switch (condition) {
                 case GT:
                     // FIXME xcc is wrong! It depends on the compare.
@@ -93,7 +93,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             cmove(tasm, masm, result, false, condition, false, trueValue, falseValue);
         }
     }
@@ -116,12 +116,12 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             cmove(tasm, masm, result, true, condition, unorderedIsTrue, trueValue, falseValue);
         }
     }
 
-    private static void cmove(TargetMethodAssembler tasm, SPARCAssembler masm, Value result, boolean isFloat, ConditionFlag condition, boolean unorderedIsTrue, Value trueValue, Value falseValue) {
+    private static void cmove(TargetMethodAssembler tasm, SPARCMacroAssembler masm, Value result, boolean isFloat, ConditionFlag condition, boolean unorderedIsTrue, Value trueValue, Value falseValue) {
         // check that we don't overwrite an input operand before it is used.
         assert !result.equals(trueValue);
 
@@ -137,7 +137,7 @@
         }
     }
 
-    private static void cmove(TargetMethodAssembler tasm, SPARCAssembler masm, Value result, ConditionFlag cond, Value other) {
+    private static void cmove(TargetMethodAssembler tasm, SPARCMacroAssembler masm, Value result, ConditionFlag cond, Value other) {
         if (!isRegister(other)) {
             SPARCMove.move(tasm, masm, result, other);
             throw new InternalError("result should be scratch");
@@ -213,7 +213,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             new Ret().emit(masm);
             // On SPARC we always leave the frame.
             tasm.frameContext.leave(tasm);
@@ -239,7 +239,7 @@
 
         @Override
         @SuppressWarnings("unused")
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             if (key.getKind() == Kind.Int) {
                 Register intKey = asIntReg(key);
                 for (int i = 0; i < keyConstants.length; i++) {
@@ -309,7 +309,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             assert isSorted(lowKeys) && isSorted(highKeys);
 
             Label actualDefaultTarget = defaultTarget == null ? new Label() : defaultTarget.label();
@@ -387,7 +387,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             tableswitch(tasm, masm, lowKey, defaultTarget, targets, asIntReg(index), asLongReg(scratch));
         }
     }
--- a/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCLIRInstruction.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCLIRInstruction.java	Wed Jul 10 05:27:45 2013 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2011, 2012, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011, 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
@@ -27,14 +27,14 @@
 import com.oracle.graal.lir.asm.*;
 
 /**
- * Convenience class to provide SPARCAssembler for the {@link #emitCode} method.
+ * Convenience class to provide SPARCMacroAssembler for the {@link #emitCode} method.
  */
 public abstract class SPARCLIRInstruction extends LIRInstruction {
 
     @Override
     public final void emitCode(TargetMethodAssembler tasm) {
-        emitCode(tasm, (SPARCAssembler) tasm.asm);
+        emitCode(tasm, (SPARCMacroAssembler) tasm.asm);
     }
 
-    public abstract void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm);
+    public abstract void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm);
 }
--- a/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCMathIntrinsicOp.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCMathIntrinsicOp.java	Wed Jul 10 05:27:45 2013 +0200
@@ -25,8 +25,8 @@
 import static com.oracle.graal.api.code.ValueUtil.*;
 
 import com.oracle.graal.api.meta.*;
-import com.oracle.graal.asm.sparc.SPARCAssembler;
 import com.oracle.graal.asm.sparc.SPARCAssembler.Fsqrtd;
+import com.oracle.graal.asm.sparc.*;
 import com.oracle.graal.graph.*;
 import com.oracle.graal.lir.*;
 import com.oracle.graal.lir.asm.*;
@@ -48,10 +48,10 @@
     }
 
     @Override
-    public void emitCode(TargetMethodAssembler tasm, SPARCAssembler asm) {
+    public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
         switch (opcode) {
             case SQRT:
-                new Fsqrtd(asDoubleReg(result), asDoubleReg(input)).emit(asm);
+                new Fsqrtd(asDoubleReg(result), asDoubleReg(input)).emit(masm);
                 break;
             case LOG:
             case LOG10:
--- a/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCMove.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCMove.java	Wed Jul 10 05:27:45 2013 +0200
@@ -24,19 +24,31 @@
 
 import static com.oracle.graal.api.code.ValueUtil.*;
 import static com.oracle.graal.lir.LIRInstruction.OperandFlag.*;
+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.asm.sparc.SPARCAssembler.*;
-import com.oracle.graal.asm.sparc.SPARCMacroAssembler.*;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Lddf;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Ldf;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Ldsb;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Ldsh;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Ldsw;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Lduw;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Ldx;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Membar;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Stb;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Sth;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Stw;
+import com.oracle.graal.asm.sparc.SPARCAssembler.Stx;
+import com.oracle.graal.asm.sparc.SPARCMacroAssembler.Mov;
+import com.oracle.graal.asm.sparc.SPARCMacroAssembler.Setuw;
+import com.oracle.graal.asm.sparc.SPARCMacroAssembler.Setx;
 import com.oracle.graal.graph.*;
 import com.oracle.graal.lir.*;
 import com.oracle.graal.lir.StandardOp.MoveOp;
 import com.oracle.graal.lir.asm.*;
 
-import static com.oracle.graal.sparc.SPARC.*;
-
 public class SPARCMove {
 
     public static class LoadOp extends SPARCLIRInstruction {
@@ -54,7 +66,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             SPARCAddress addr = address.toAddress();
             switch (kind) {
                 case Byte:
@@ -96,8 +108,8 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler asm) {
-            new Membar(barriers).emit(asm);
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
+            new Membar(barriers).emit(masm);
         }
     }
 
@@ -113,7 +125,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             move(tasm, masm, getResult(), getInput());
         }
 
@@ -140,7 +152,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             move(tasm, masm, getResult(), getInput());
         }
 
@@ -167,7 +179,7 @@
 
         @Override
         @SuppressWarnings("unused")
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             tasm.recordImplicitException(masm.codeBuffer.position(), state);
             new Ldx(new SPARCAddress(asRegister(input), 0), r0);
         }
@@ -184,8 +196,8 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler asm) {
-            new Ldx((SPARCAddress) tasm.asAddress(slot), asLongReg(result)).emit(asm);
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
+            new Ldx((SPARCAddress) tasm.asAddress(slot), asLongReg(result)).emit(masm);
         }
     }
 
@@ -204,7 +216,7 @@
         }
 
         @Override
-        public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+        public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
             assert isRegister(input);
             SPARCAddress addr = address.toAddress();
             switch (kind) {
@@ -231,10 +243,18 @@
         }
     }
 
-    public static void move(TargetMethodAssembler tasm, SPARCAssembler masm, Value result, Value input) {
+    public static void move(TargetMethodAssembler tasm, SPARCMacroAssembler masm, Value result, Value input) {
         if (isRegister(input)) {
             if (isRegister(result)) {
                 reg2reg(masm, result, input);
+            } else if (isStackSlot(result)) {
+                reg2stack(tasm, masm, result, input);
+            } else {
+                throw GraalInternalError.shouldNotReachHere();
+            }
+        } else if (isStackSlot(input)) {
+            if (isRegister(result)) {
+                stack2reg(tasm, masm, result, input);
             } else {
                 throw GraalInternalError.shouldNotReachHere();
             }
@@ -268,8 +288,38 @@
         }
     }
 
+    private static void reg2stack(TargetMethodAssembler tasm, SPARCMacroAssembler masm, Value result, Value input) {
+        SPARCAddress dest = (SPARCAddress) tasm.asAddress(result);
+        switch (input.getKind()) {
+            case Int:
+                new Stw(asRegister(input), dest).emit(masm);
+                break;
+            case Long:
+            case Float:
+            case Double:
+            case Object:
+            default:
+                throw GraalInternalError.shouldNotReachHere();
+        }
+    }
+
+    private static void stack2reg(TargetMethodAssembler tasm, SPARCMacroAssembler masm, Value result, Value input) {
+        SPARCAddress src = (SPARCAddress) tasm.asAddress(input);
+        switch (input.getKind()) {
+            case Int:
+                new Ldsw(src, asRegister(result)).emit(masm);
+                break;
+            case Long:
+            case Float:
+            case Double:
+            case Object:
+            default:
+                throw GraalInternalError.shouldNotReachHere();
+        }
+    }
+
     @SuppressWarnings("unused")
-    private static void const2reg(TargetMethodAssembler tasm, SPARCAssembler masm, Value result, Constant input) {
+    private static void const2reg(TargetMethodAssembler tasm, SPARCMacroAssembler masm, Value result, Constant input) {
         switch (input.getKind().getStackKind()) {
             case Int:
                 if (tasm.runtime.needsDataPatch(input)) {
@@ -281,7 +331,7 @@
                 if (tasm.runtime.needsDataPatch(input)) {
                     tasm.recordDataReferenceInCode(input, 0, true);
                 }
-                new Setx(masm, input.asInt(), null, asRegister(result));
+                new Setx(masm, input.asLong(), null, asRegister(result));
                 break;
             case Object:
                 if (input.isNull()) {
--- a/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCTestOp.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.lir.sparc/src/com/oracle/graal/lir/sparc/SPARCTestOp.java	Wed Jul 10 05:27:45 2013 +0200
@@ -43,7 +43,7 @@
     }
 
     @Override
-    public void emitCode(TargetMethodAssembler tasm, SPARCAssembler masm) {
+    public void emitCode(TargetMethodAssembler tasm, SPARCMacroAssembler masm) {
         if (isRegister(y)) {
             switch (x.getKind()) {
                 case Int:
--- a/graal/com.oracle.graal.sparc/src/com/oracle/graal/sparc/SPARC.java	Wed Jul 10 05:26:50 2013 +0200
+++ b/graal/com.oracle.graal.sparc/src/com/oracle/graal/sparc/SPARC.java	Wed Jul 10 05:27:45 2013 +0200
@@ -113,9 +113,9 @@
     public static final Register fp = i6;
     public static final Register sp = o6;
 
-    public static final Register[] gprRegisters = {
+    public static final Register[] cpuRegisters = {
         r0,  r1,  r2,  r3,  r4,  r5,  r6,  r7,
-         r8,  r9, r10, r11, r12, r13, r14, r15,
+        r8,  r9,  r10, r11, r12, r13, r14, r15,
         r16, r17, r18, r19, r20, r21, r22, r23,
         r24, r25, r26, r27, r28, r29, r30, r31
     };
@@ -131,7 +131,7 @@
     public static final Register f7 = new Register(39, 7, "f7", FPU);
 
     public static final Register[] allRegisters = {
-        // GPR
+        // CPU
         r0,  r1,  r2,  r3,  r4,  r5,  r6,  r7,
         r8,  r9, r10, r11, r12, r13, r14, r15,
        r16, r17, r18, r19, r20, r21, r22, r23,
@@ -140,15 +140,12 @@
         f0,  f1,  f2,  f3,  f4,  f5,  f6,  f7,
     };
 
+    // @formatter:on
+
     public SPARC() {
-        super("SPARC",
-              8,
-              ByteOrder.BIG_ENDIAN,
-              allRegisters,
-              LOAD_STORE | STORE_STORE,
-              1,
-              r31.encoding + 1,
-              8);
+        // The return address doesn't have an extra slot in the frame so we pass 0 for the return
+        // address size.
+        super("SPARC", 8, ByteOrder.BIG_ENDIAN, allRegisters, LOAD_STORE | STORE_STORE, 1, r31.encoding + 1, 0);
     }
 
     @Override
@@ -176,12 +173,17 @@
                     return true;
             }
         }
-
         return false;
     }
 
     @Override
     public PlatformKind getLargestStorableKind(RegisterCategory category) {
-        throw new InternalError("NYI");
+        if (category == CPU) {
+            return Kind.Long;
+        } else if (category == FPU) {
+            return Kind.Double;
+        } else {
+            return Kind.Illegal;
+        }
     }
 }
--- a/src/cpu/sparc/vm/graalCodeInstaller_sparc.hpp	Wed Jul 10 05:26:50 2013 +0200
+++ b/src/cpu/sparc/vm/graalCodeInstaller_sparc.hpp	Wed Jul 10 05:27:45 2013 +0200
@@ -20,17 +20,82 @@
  * or visit www.oracle.com if you need additional information or have any
  * questions.
  */
+
 #ifndef CPU_SPARC_VM_CODEINSTALLER_SPARC_HPP
 #define CPU_SPARC_VM_CODEINSTALLER_SPARC_HPP
 
+#include "graal/graalCompiler.hpp"
+#include "graal/graalCompilerToVM.hpp"
+#include "graal/graalJavaAccess.hpp"
+
 inline jint CodeInstaller::pd_next_offset(NativeInstruction* inst, jint pc_offset, oop method) {
-  fatal("CodeInstaller::pd_next_offset - sparc unimp");
-  return 0;
+  assert(inst->is_call() || inst->is_jump(), "sanity");
+  return pc_offset + NativeCall::instruction_size;
 }
 
-inline void CodeInstaller::pd_site_DataPatch(oop constant, oop kind, bool inlined,
-                                             address instruction, int alignment, char typeChar) {
-  fatal("CodeInstaller::pd_site_DataPatch - sparc unimp");
+inline void CodeInstaller::pd_site_DataPatch(int pc_offset, oop site) {
+  oop constant = CompilationResult_DataPatch::constant(site);
+  int alignment = CompilationResult_DataPatch::alignment(site);
+  bool inlined = CompilationResult_DataPatch::inlined(site) == JNI_TRUE;
+
+  oop kind = Constant::kind(constant);
+  char typeChar = Kind::typeChar(kind);
+
+  address pc = _instructions->start() + pc_offset;
+
+  tty->print_cr("CodeInstaller::pd_site_DataPatch: typeChar=%c, inlined=%d", typeChar, inlined);
+
+  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': {
+      if (inlined) {
+        fatal(err_msg("inlined: type=%c, constant=%lx", inlined, Constant::primitive(constant)));
+      } else {
+        int size = _constants->size();
+        if (alignment > 0) {
+          guarantee(alignment <= _constants->alignment(), "Alignment inside constants section is restricted by alignment of section begin");
+          size = align_size_up(size, alignment);
+        }
+        // we don't care if this is a long/double/etc., the primitive field contains the right bits
+        address dest = _constants->start() + size;
+        _constants->set_end(dest);
+        uint64_t value = Constant::primitive(constant);
+        _constants->emit_int64(value);
+
+        NativeMovRegMem* load = nativeMovRegMem_at(pc);
+        int disp = _constants_size + pc_offset - size - BytesPerInstWord;
+        load->set_offset(-disp);
+
+//        assert(disp == (jint) disp, "disp doesn't fit in 32 bits");
+//        *((jint*) operand) = (jint) disp;
+
+//        _instructions->relocate(instruction, section_word_Relocation::spec((address) dest, CodeBuffer::SECT_CONSTS) /*, Assembler::disp32_operand*/);
+//        TRACE_graal_3("relocating (%c) at %p/%p with destination at %p (%d)", typeChar, instruction, operand, dest, size);
+      }
+      break;
+    }
+    case 'a': {
+//      address operand = Assembler::locate_operand(instruction, Assembler::imm_operand);
+//      Handle obj = Constant::object(constant);
+//
+//      jobject value = JNIHandles::make_local(obj());
+//      *((jobject*) operand) = value;
+//      _instructions->relocate(instruction, oop_Relocation::spec_for_immediate(), Assembler::imm_operand);
+//      TRACE_graal_3("relocating (oop constant) at %p/%p", instruction, operand);
+      break;
+    }
+    default:
+      fatal(err_msg("unexpected Kind (%d) in DataPatch", typeChar));
+      break;
+  }
 }
 
 inline void CodeInstaller::pd_relocate_CodeBlob(CodeBlob* cb, NativeInstruction* inst) {
@@ -41,8 +106,49 @@
   fatal("CodeInstaller::pd_relocate_ForeignCall - sparc unimp");
 }
 
-inline void CodeInstaller::pd_relocate_JavaMethod(oop method, jint pc_offset) {
-  fatal("CodeInstaller::pd_relocate_JavaMethod - sparc unimp");
+inline void CodeInstaller::pd_relocate_JavaMethod(oop hotspot_method, jint pc_offset) {
+#ifdef ASSERT
+  Method* method = NULL;
+  // we need to check, this might also be an unresolved method
+  if (hotspot_method->is_a(HotSpotResolvedJavaMethod::klass())) {
+    method = getMethodFromHotSpotMethod(hotspot_method);
+  }
+#endif
+  switch (_next_call_type) {
+    case MARK_INLINE_INVOKE:
+      break;
+    case MARK_INVOKEVIRTUAL:
+    case MARK_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),
+//                                             Assembler::call32_operand);
+      fatal("NYI");
+      break;
+    }
+    case MARK_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 /*, Assembler::call32_operand*/);
+      break;
+    }
+    case MARK_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());
+//      _instructions->relocate(call->instruction_address(),
+//                              relocInfo::opt_virtual_call_type, Assembler::call32_operand);
+      fatal("NYI");
+      break;
+    }
+    default:
+      fatal("invalid _next_call_type value");
+      break;
+  }
 }
 
 inline int32_t* CodeInstaller::pd_locate_operand(address instruction) {
--- a/src/cpu/sparc/vm/sharedRuntime_sparc.cpp	Wed Jul 10 05:26:50 2013 +0200
+++ b/src/cpu/sparc/vm/sharedRuntime_sparc.cpp	Wed Jul 10 05:27:45 2013 +0200
@@ -1826,6 +1826,31 @@
   verify_oop_args(masm, method, sig_bt, regs);
   vmIntrinsics::ID iid = method->intrinsic_id();
 
+#ifdef GRAAL
+  if (iid == vmIntrinsics::_CompilerToVMImpl_executeCompiledMethod) {
+    // We are called from compiled code here. The three object arguments
+    // are already in the correct registers (j_rarg0, jrarg1, jrarg2). The
+    // fourth argument (j_rarg3) is a pointer to the HotSpotInstalledCode object.
+
+    // Load the nmethod pointer from the HotSpotInstalledCode object
+//    __ movq(j_rarg3, Address(j_rarg3, sizeof(oopDesc)));
+
+    // Check whether the nmethod was invalidated
+//    __ testq(j_rarg3, j_rarg3);
+//    Label invalid_nmethod;
+//    __ jcc(Assembler::zero, invalid_nmethod);
+
+    // Perform a tail call to the verified entry point of the nmethod.
+//    __ jmp(Address(j_rarg3, nmethod::verified_entry_point_offset()));
+
+//    __ bind(invalid_nmethod);
+
+//    __ jump(RuntimeAddress(StubRoutines::throw_InvalidInstalledCodeException_entry()));
+    __ stop("_CompilerToVMImpl_executeCompiledMethod not implemented");
+    return;
+  }
+#endif
+
   // Now write the args into the outgoing interpreter space
   bool     has_receiver   = false;
   Register receiver_reg   = noreg;
--- a/src/cpu/x86/vm/graalCodeInstaller_x86.hpp	Wed Jul 10 05:26:50 2013 +0200
+++ b/src/cpu/x86/vm/graalCodeInstaller_x86.hpp	Wed Jul 10 05:27:45 2013 +0200
@@ -56,8 +56,16 @@
   }
 }
 
-inline void CodeInstaller::pd_site_DataPatch(oop constant, oop kind, bool inlined,
-                                             address instruction, int alignment, char typeChar) {
+inline void CodeInstaller::pd_site_DataPatch(int pc_offset, oop site) {
+  oop constant = CompilationResult_DataPatch::constant(site);
+  int alignment = CompilationResult_DataPatch::alignment(site);
+  bool inlined = CompilationResult_DataPatch::inlined(site) == JNI_TRUE;
+
+  oop kind = Constant::kind(constant);
+  char typeChar = Kind::typeChar(kind);
+
+  address pc = _instructions->start() + pc_offset;
+
   switch (typeChar) {
     case 'z':
     case 'b':
@@ -70,11 +78,11 @@
     case 'j':
     case 'd': {
       if (inlined) {
-        address operand = Assembler::locate_operand(instruction, Assembler::imm_operand);
+        address operand = Assembler::locate_operand(pc, Assembler::imm_operand);
         *((jlong*) operand) = Constant::primitive(constant);
       } else {
-        address operand = Assembler::locate_operand(instruction, Assembler::disp32_operand);
-        address next_instruction = Assembler::locate_next_instruction(instruction);
+        address operand = Assembler::locate_operand(pc, Assembler::disp32_operand);
+        address next_instruction = Assembler::locate_next_instruction(pc);
         int size = _constants->size();
         if (alignment > 0) {
           guarantee(alignment <= _constants->alignment(), "Alignment inside constants section is restricted by alignment of section begin");
@@ -82,26 +90,27 @@
         }
         // we don't care if this is a long/double/etc., the primitive field contains the right bits
         address dest = _constants->start() + size;
-        _constants->set_end(dest + BytesPerLong);
-        *(jlong*) dest = Constant::primitive(constant);
+        _constants->set_end(dest);
+        uint64_t value = Constant::primitive(constant);
+        _constants->emit_int64(value);
 
         long disp = dest - next_instruction;
         assert(disp == (jint) disp, "disp doesn't fit in 32 bits");
         *((jint*) operand) = (jint) disp;
 
-        _instructions->relocate(instruction, section_word_Relocation::spec((address) dest, CodeBuffer::SECT_CONSTS), Assembler::disp32_operand);
-        TRACE_graal_3("relocating (%c) at %p/%p with destination at %p (%d)", typeChar, instruction, operand, dest, size);
+        _instructions->relocate(pc, section_word_Relocation::spec((address) dest, CodeBuffer::SECT_CONSTS), Assembler::disp32_operand);
+        TRACE_graal_3("relocating (%c) at %p/%p with destination at %p (%d)", typeChar, pc, operand, dest, size);
       }
       break;
     }
     case 'a': {
-      address operand = Assembler::locate_operand(instruction, Assembler::imm_operand);
+      address operand = Assembler::locate_operand(pc, Assembler::imm_operand);
       Handle obj = Constant::object(constant);
 
       jobject value = JNIHandles::make_local(obj());
       *((jobject*) operand) = value;
-      _instructions->relocate(instruction, oop_Relocation::spec_for_immediate(), Assembler::imm_operand);
-      TRACE_graal_3("relocating (oop constant) at %p/%p", instruction, operand);
+      _instructions->relocate(pc, oop_Relocation::spec_for_immediate(), Assembler::imm_operand);
+      TRACE_graal_3("relocating (oop constant) at %p/%p", pc, operand);
       break;
     }
     default:
--- a/src/share/vm/graal/graalCodeInstaller.cpp	Wed Jul 10 05:26:50 2013 +0200
+++ b/src/share/vm/graal/graalCodeInstaller.cpp	Wed Jul 10 05:27:45 2013 +0200
@@ -171,7 +171,7 @@
 
   if (value->is_a(RegisterValue::klass())) {
     jint number = code_Register::number(RegisterValue::reg(value));
-    if (number < 16) {
+    if (number < RegisterImpl::number_of_registers) {
       if (type == T_INT || type == T_FLOAT || type == T_SHORT || type == T_CHAR || type == T_BOOLEAN || type == T_BYTE || type == T_ADDRESS) {
         locationType = Location::int_in_long;
       } else if (type == T_LONG) {
@@ -366,6 +366,10 @@
   jobject compiled_code_obj = JNIHandles::make_local(compiled_code());
   initialize_assumptions(JNIHandles::resolve(compiled_code_obj));
 
+  // Get instructions and constants CodeSections early because we need it.
+  _instructions = buffer.insts();
+  _constants = buffer.consts();
+
   {
     No_Safepoint_Verifier no_safepoint;
     initialize_fields(JNIHandles::resolve(compiled_code_obj));
@@ -397,6 +401,11 @@
         GraalCompiler::instance(), _debug_recorder, _dependencies, NULL, -1, false, leaf_graph_ids, installed_code, triggered_deoptimizations);
     cb = nm;
   }
+
+  if (cb != NULL) {
+    // Make sure the pre-calculated constants section size was correct.
+    guarantee((cb->code_begin() - cb->content_begin()) == _constants_size, err_msg("%d != %d", cb->code_begin() - cb->content_begin(), _constants_size));
+  }
 }
 
 void CodeInstaller::initialize_fields(oop compiled_code) {
@@ -417,11 +426,12 @@
   _code = (arrayOop) CompilationResult::targetCode(comp_result);
   _code_size = CompilationResult::targetCodeSize(comp_result);
   // The frame size we get from the target method does not include the return address, so add one word for it here.
-  _total_frame_size = CompilationResult::frameSize(comp_result) + HeapWordSize;
+  _total_frame_size = CompilationResult::frameSize(comp_result) + HeapWordSize;  // FIXME this is an x86-ism
   _custom_stack_area_offset = CompilationResult::customStackAreaOffset(comp_result);
 
-  // (very) conservative estimate: each site needs a constant section entry
-  _constants_size = _sites->length() * (BytesPerLong*2);
+  // Pre-calculate the constants section size.  This is required for PC-relative addressing.
+  _constants_size = calculate_constants_size();
+
 #ifndef PRODUCT
   _comments = (arrayOop) HotSpotCompiledCode::comments(compiled_code);
 #endif
@@ -442,9 +452,6 @@
 
   buffer.initialize_oop_recorder(_oop_recorder);
 
-  _instructions = buffer.insts();
-  _constants = buffer.consts();
-
   // copy the code into the newly created CodeBuffer
   address end_pc = _instructions->start() + _code_size;
   if (!_instructions->allocates2(end_pc)) {
@@ -454,7 +461,7 @@
   _instructions->set_end(end_pc);
 
   for (int i = 0; i < _sites->length(); i++) {
-    oop site=((objArrayOop) (_sites))->obj_at(i);
+    oop site = ((objArrayOop) (_sites))->obj_at(i);
     jint pc_offset = CompilationResult_Site::pcOffset(site);
 
     if (site->is_a(CompilationResult_Call::klass())) {
@@ -485,7 +492,7 @@
 #ifndef PRODUCT
   if (_comments != NULL) {
     for (int i = 0; i < _comments->length(); i++) {
-      oop comment=((objArrayOop) (_comments))->obj_at(i);
+      oop comment = ((objArrayOop) (_comments))->obj_at(i);
       assert(comment->is_a(HotSpotCompiledCode_Comment::klass()), "cce");
       jint offset = HotSpotCompiledCode_Comment::pcOffset(comment);
       char* text = java_lang_String::as_utf8_string(HotSpotCompiledCode_Comment::text(comment));
@@ -496,6 +503,35 @@
   return true;
 }
 
+/**
+ * Calculate the constants section size by iterating over all DataPatches.
+ * Knowing the size of the constants section before patching instructions
+ * is necessary for PC-relative addressing.
+ */
+int CodeInstaller::calculate_constants_size() {
+  int size = 0;
+
+  for (int i = 0; i < _sites->length(); i++) {
+    oop site = ((objArrayOop) (_sites))->obj_at(i);
+    jint pc_offset = CompilationResult_Site::pcOffset(site);
+
+    if (site->is_a(CompilationResult_DataPatch::klass())) {
+      oop constant = CompilationResult_DataPatch::constant(site);
+      int alignment = CompilationResult_DataPatch::alignment(site);
+      bool inlined = CompilationResult_DataPatch::inlined(site) == JNI_TRUE;
+
+      if (!inlined) {
+        if (alignment > 0) {
+          guarantee(alignment <= _constants->alignment(), "Alignment inside constants section is restricted by alignment of section begin");
+          size = align_size_up(size, alignment);
+        }
+        size = size + sizeof(int64_t);
+      }
+    }
+  }
+  return size == 0 ? 0 : align_size_up(size, _constants->alignment());
+}
+
 void CodeInstaller::assumption_MethodContents(Handle assumption) {
   Handle method_handle = Assumptions_MethodContents::method(assumption());
   methodHandle method = getMethodFromHotSpotMethod(method_handle());
@@ -732,11 +768,7 @@
 
 void CodeInstaller::site_DataPatch(CodeBuffer& buffer, jint pc_offset, oop site) {
   oop constant = CompilationResult_DataPatch::constant(site);
-  int alignment = CompilationResult_DataPatch::alignment(site);
-  bool inlined = CompilationResult_DataPatch::inlined(site) == JNI_TRUE;
   oop kind = Constant::kind(constant);
-
-  address instruction = _instructions->start() + pc_offset;
   char typeChar = Kind::typeChar(kind);
   switch (typeChar) {
     case 'f':
@@ -745,7 +777,7 @@
       record_metadata_in_constant(constant, _oop_recorder);
       break;
   }
-  CodeInstaller::pd_site_DataPatch(constant, kind, inlined, instruction, alignment, typeChar);
+  CodeInstaller::pd_site_DataPatch(pc_offset, site);
 }
 
 void CodeInstaller::site_Mark(CodeBuffer& buffer, jint pc_offset, oop site) {
--- a/src/share/vm/graal/graalCodeInstaller.hpp	Wed Jul 10 05:26:50 2013 +0200
+++ b/src/share/vm/graal/graalCodeInstaller.hpp	Wed Jul 10 05:27:45 2013 +0200
@@ -76,7 +76,7 @@
   ExceptionHandlerTable     _exception_handler_table;
 
   jint pd_next_offset(NativeInstruction* inst, jint pc_offset, oop method);
-  void pd_site_DataPatch(oop constant, oop kind, bool inlined, address instruction, int alignment, char typeChar);
+  void pd_site_DataPatch(int pc_offset, oop site);
   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);
@@ -96,6 +96,8 @@
   // perform data and call relocation on the CodeBuffer
   bool initialize_buffer(CodeBuffer& buffer);
 
+  int calculate_constants_size();
+
   void assumption_MethodContents(Handle assumption);
   void assumption_NoFinalizableSubclass(Handle assumption);
   void assumption_ConcreteSubtype(Handle assumption);
--- a/src/share/vm/graal/graalCompilerToGPU.cpp	Wed Jul 10 05:26:50 2013 +0200
+++ b/src/share/vm/graal/graalCompilerToGPU.cpp	Wed Jul 10 05:27:45 2013 +0200
@@ -29,6 +29,7 @@
 #include "graal/graalEnv.hpp"
 #include "graal/graalJavaAccess.hpp"
 #include "runtime/gpu.hpp"
+#include "runtime/javaCalls.hpp"
 
 
 // Entry to native method implementation that transitions current thread to '_thread_in_vm'.
--- a/src/share/vm/graal/graalCompilerToVM.hpp	Wed Jul 10 05:26:50 2013 +0200
+++ b/src/share/vm/graal/graalCompilerToVM.hpp	Wed Jul 10 05:27:45 2013 +0200
@@ -1,5 +1,5 @@
 /*
- * Copyright (c) 2011, Oracle and/or its affiliates. All rights reserved.
+ * Copyright (c) 2011, 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
@@ -25,6 +25,7 @@
 #define SHARE_VM_GRAAL_GRAAL_COMPILER_TO_VM_HPP
 
 #include "prims/jni.h"
+#include "runtime/javaCalls.hpp"
 
 extern JNINativeMethod CompilerToVM_methods[];
 int CompilerToVM_methods_count();
--- a/src/share/vm/prims/methodHandles.cpp	Wed Jul 10 05:26:50 2013 +0200
+++ b/src/share/vm/prims/methodHandles.cpp	Wed Jul 10 05:27:45 2013 +0200
@@ -342,7 +342,7 @@
 
 
 Symbol* MethodHandles::signature_polymorphic_intrinsic_name(vmIntrinsics::ID iid) {
-  assert(is_signature_polymorphic_intrinsic(iid), err_msg("iid=%d", iid));
+  assert(is_signature_polymorphic_intrinsic(iid), err_msg("%d %s", iid, vmIntrinsics::name_at(iid)));
   switch (iid) {
   case vmIntrinsics::_invokeBasic:      return vmSymbols::invokeBasic_name();
   case vmIntrinsics::_linkToVirtual:    return vmSymbols::linkToVirtual_name();
@@ -350,7 +350,7 @@
   case vmIntrinsics::_linkToSpecial:    return vmSymbols::linkToSpecial_name();
   case vmIntrinsics::_linkToInterface:  return vmSymbols::linkToInterface_name();
   }
-  assert(false, "");
+  fatal(err_msg("unknown intrinsic id: %d %s", iid, vmIntrinsics::name_at(iid)));
   return 0;
 }
 
@@ -362,7 +362,7 @@
   case vmIntrinsics::_linkToSpecial:    return JVM_REF_invokeSpecial;
   case vmIntrinsics::_linkToInterface:  return JVM_REF_invokeInterface;
   }
-  assert(false, err_msg("iid=%d", iid));
+  fatal(err_msg("unknown intrinsic id: %d %s", iid, vmIntrinsics::name_at(iid)));
   return 0;
 }