clarify licensing
[nestedvm.git] / src / org / ibex / nestedvm / ClassFileCompiler.java
index ccf7657..70ff235 100644 (file)
@@ -1,3 +1,7 @@
+// Copyright 2000-2005 the Contributors, as shown in the revision logs.
+// Licensed under the Apache License 2.0 ("the License").
+// You may not use this file except in compliance with the License.
+
 package org.ibex.nestedvm;
 
 import java.io.*;
@@ -40,9 +44,9 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
     private File outDir;
     private PrintStream warn = System.err;
 
-    private final Type.Object me;
+    private final Type.Class me;
     
-    private ClassGen cg;
+    private ClassFile cg;
     private MethodGen clinit, init;
     
     public ClassFileCompiler(String path, String className, OutputStream os) throws IOException { this(new Seekable.File(path),className,os); }
@@ -58,7 +62,7 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
     }
     private ClassFileCompiler(Seekable binary, String className) throws IOException {
         super(binary,className);
-        me = new Type.Object(fullClassName);
+        me = Type.Class.instance(fullClassName);
     }
     
     public void setWarnWriter(PrintStream warn) { this.warn = warn; }
@@ -66,7 +70,7 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
     protected void _go() throws Exn, IOException {
         try {
             __go();
-        } catch(ClassGen.Exn e) {
+        } catch(ClassFile.Exn e) {
             e.printStackTrace(warn);
             throw new Exn("Class generation exception: " + e.toString());
         }
@@ -76,47 +80,69 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
         if(!pruneCases) throw new Exn("-o prunecases MUST be enabled for ClassFileCompiler");
 
         // Class
-        Type.Object superClass = new Type.Object(runtimeClass);
-        cg = new ClassGen(me,superClass,ACC_PUBLIC|ACC_FINAL|ACC_SUPER);
+        Type.Class superClass = Type.Class.instance(runtimeClass);
+        cg = new ClassFile(me,superClass,PUBLIC|FINAL|SUPER);
         if(source != null) cg.setSourceFile(source);
         
         // Fields
-        cg.addField("pc",Type.INT,ACC_PRIVATE);
-        cg.addField("hi",Type.INT,ACC_PRIVATE);
-        cg.addField("lo",Type.INT,ACC_PRIVATE);
-        cg.addField("fcsr",Type.INT,ACC_PRIVATE);
-        for(int i=1;i<32;i++) cg.addField("r" + i,Type.INT,ACC_PRIVATE);
-        for(int i=0;i<32;i++) cg.addField("f" + i,singleFloat ? Type.FLOAT : Type.INT,ACC_PRIVATE);
+        cg.addField("pc",Type.INT,PRIVATE);
+        cg.addField("hi",Type.INT,PRIVATE);
+        cg.addField("lo",Type.INT,PRIVATE);
+        cg.addField("fcsr",Type.INT,PRIVATE);
+        for(int i=1;i<32;i++) cg.addField("r" + i,Type.INT,PRIVATE);
+        for(int i=0;i<32;i++) cg.addField("f" + i,singleFloat ? Type.FLOAT : Type.INT,PRIVATE);
 
         // <clinit>
-        clinit = cg.addMethod("<clinit>",Type.VOID,Type.NO_ARGS,ACC_PRIVATE|ACC_STATIC);
-        
+        clinit = cg.addMethod("<clinit>",Type.VOID,Type.NO_ARGS,PRIVATE|STATIC);
+
+        // GCCLASS_HINT: org.ibex.nestedvm.RuntimeCompiler.compile org.ibex.nestedvm.UnixRuntime.<init>
+
         // <init>
-        init = cg.addMethod("<init>",Type.VOID,Type.NO_ARGS,ACC_PUBLIC);        
+        init = cg.addMethod("<init>",Type.VOID,Type.NO_ARGS,PUBLIC);        
         init.add(ALOAD_0);
         init.add(LDC,pageSize);
         init.add(LDC,totalPages);
-        init.add(INVOKESPECIAL,new MethodRef(me,"<init>",Type.VOID,new Type[]{Type.INT,Type.INT}));
+        init.add(INVOKESPECIAL,me.method("<init>",Type.VOID,new Type[]{Type.INT,Type.INT}));
         init.add(RETURN);
 
-        init = cg.addMethod("<init>",Type.VOID,new Type[]{Type.INT,Type.INT},ACC_PUBLIC);
+        // <init>(Z)
+        init = cg.addMethod("<init>",Type.VOID,new Type[]{Type.BOOLEAN},PUBLIC);        
+        init.add(ALOAD_0);
+        init.add(LDC,pageSize);
+        init.add(LDC,totalPages);
+        init.add(ILOAD_1);
+        init.add(INVOKESPECIAL,me.method("<init>",Type.VOID,new Type[]{Type.INT,Type.INT,Type.BOOLEAN}));
+        init.add(RETURN);
+        
+        // <init>(II)
+        init = cg.addMethod("<init>",Type.VOID,new Type[]{Type.INT,Type.INT},PUBLIC);
+        init.add(ALOAD_0);
+        init.add(ILOAD_1);
+        init.add(ILOAD_2);
+        init.add(ICONST_0);
+        init.add(INVOKESPECIAL,me.method("<init>",Type.VOID,new Type[]{Type.INT,Type.INT,Type.BOOLEAN}));
+        init.add(RETURN);
+        
+        // <init>(IIZ)
+        init = cg.addMethod("<init>",Type.VOID,new Type[]{Type.INT,Type.INT,Type.BOOLEAN},PUBLIC);
         init.add(ALOAD_0);
         init.add(ILOAD_1);
         init.add(ILOAD_2);
-        init.add(INVOKESPECIAL,new MethodRef(superClass,"<init>",Type.VOID,new Type[]{Type.INT,Type.INT}));
+        init.add(ILOAD_3);
+        init.add(INVOKESPECIAL,superClass.method("<init>",Type.VOID,new Type[]{Type.INT,Type.INT,Type.BOOLEAN}));
         
         if(onePage) {
-            cg.addField("page",Type.arrayType(Type.INT),ACC_PRIVATE|ACC_FINAL);
+            cg.addField("page",Type.INT.makeArray(),PRIVATE|FINAL);
             init.add(ALOAD_0);
             init.add(DUP);
-            init.add(GETFIELD,new FieldRef(me,"readPages",Type.arrayType(Type.INT,2)));
+            init.add(GETFIELD,me.field("readPages",Type.INT.makeArray(2)));
             init.add(LDC,0);
             init.add(AALOAD);
-            init.add(PUTFIELD,new FieldRef(me,"page",Type.arrayType(Type.INT)));
+            init.add(PUTFIELD,me.field("page",Type.INT.makeArray()));
         }
         
         if(supportCall)
-            cg.addField("symbols",new Type.Object(hashClass),ACC_PRIVATE|ACC_STATIC|ACC_FINAL);
+            cg.addField("symbols",Type.Class.instance(hashClass),PRIVATE|STATIC|FINAL);
         
         int highestAddr = 0;
         
@@ -143,12 +169,12 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
         
         // Finish clinit
         if(supportCall) {
-            Type.Object hash = new Type.Object(hashClass);
+            Type.Class hash = Type.Class.instance(hashClass);
             clinit.add(NEW,hash);
             clinit.add(DUP);
             clinit.add(DUP);
-            clinit.add(INVOKESPECIAL,new MethodRef(hash,"<init>",Type.VOID,Type.NO_ARGS));
-            clinit.add(PUTSTATIC,new FieldRef(me,"symbols",hash));
+            clinit.add(INVOKESPECIAL,hash.method("<init>",Type.VOID,Type.NO_ARGS));
+            clinit.add(PUTSTATIC,me.field("symbols",hash));
             ELF.Symbol[] symbols = elf.getSymtab().symbols;
             for(int i=0;i<symbols.length;i++) {
                 ELF.Symbol s = symbols[i];
@@ -158,8 +184,8 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
                     clinit.add(NEW,Type.INTEGER_OBJECT);
                     clinit.add(DUP);
                     clinit.add(LDC,s.addr);
-                    clinit.add(INVOKESPECIAL,new MethodRef(Type.INTEGER_OBJECT,"<init>",Type.VOID,new Type[]{Type.INT}));
-                    clinit.add(INVOKEVIRTUAL,new MethodRef(hash,"put",Type.OBJECT,new Type[]{Type.OBJECT,Type.OBJECT}));
+                    clinit.add(INVOKESPECIAL,Type.INTEGER_OBJECT.method("<init>",Type.VOID,new Type[]{Type.INT}));
+                    clinit.add(INVOKEVIRTUAL,hash.method("put",Type.OBJECT,new Type[]{Type.OBJECT,Type.OBJECT}));
                     clinit.add(POP);
                 }
             }
@@ -171,62 +197,53 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
         ELF.SHeader text = elf.sectionWithName(".text");
         
         // Trampoline
-        MethodGen tramp = cg.addMethod("trampoline",Type.VOID,Type.NO_ARGS,ACC_PRIVATE);
+        MethodGen tramp = cg.addMethod("trampoline",Type.VOID,Type.NO_ARGS,PRIVATE);
         
         int start = tramp.size();
         tramp.add(ALOAD_0);
-        tramp.add(GETFIELD,new FieldRef(me,"state",Type.INT));
+        tramp.add(GETFIELD,me.field("state",Type.INT));
         tramp.add(IFEQ,tramp.size()+2);
         tramp.add(RETURN);
         
         tramp.add(ALOAD_0);
         tramp.add(ALOAD_0);
-        tramp.add(GETFIELD,new FieldRef(me,"pc",Type.INT));
+        tramp.add(GETFIELD,me.field("pc",Type.INT));
         tramp.add(LDC,methodShift);
         tramp.add(IUSHR);
         
         int beg = text.addr >>> methodShift;
         int end = ((text.addr + text.size + maxBytesPerMethod - 1) >>> methodShift);
 
-        MethodGen.TSI tsi = new MethodGen.TSI(beg,end-1);
+        MethodGen.Switch.Table tsi = new MethodGen.Switch.Table(beg,end-1);
         tramp.add(TABLESWITCH,tsi);
         for(int n=beg;n<end;n++) {
             tsi.setTargetForVal(n,tramp.size());
-            tramp.add(INVOKESPECIAL,new MethodRef(me,"run_"+toHex(n<<methodShift),Type.VOID,Type.NO_ARGS));
+            tramp.add(INVOKESPECIAL,me.method("run_"+toHex(n<<methodShift),Type.VOID,Type.NO_ARGS));
             tramp.add(GOTO,start);
         }
         tsi.setDefaultTarget(tramp.size());
         
         tramp.add(POP);
-        tramp.add(NEW,new Type.Object("org.ibex.nestedvm.Runtime$ExecutionException"));
+        tramp.add(NEW,Type.Class.instance("org.ibex.nestedvm.Runtime$ExecutionException"));
         tramp.add(DUP);
         tramp.add(NEW, Type.STRINGBUFFER);
         tramp.add(DUP);
         tramp.add(LDC,"Jumped to invalid address in trampoline (r2: ");
-        tramp.add(INVOKESPECIAL,new MethodRef(Type.STRINGBUFFER,"<init>",Type.VOID,new Type[]{Type.STRING}));
+        tramp.add(INVOKESPECIAL,Type.STRINGBUFFER.method("<init>",Type.VOID,new Type[]{Type.STRING}));
         tramp.add(ALOAD_0);
-        tramp.add(GETFIELD, new FieldRef(me,"r2",Type.INT));
-        tramp.add(INVOKEVIRTUAL,new MethodRef(Type.STRINGBUFFER,"append",Type.STRINGBUFFER,new Type[]{Type.INT}));
+        tramp.add(GETFIELD, me.field("r2",Type.INT));
+        tramp.add(INVOKEVIRTUAL,Type.STRINGBUFFER.method("append",Type.STRINGBUFFER,new Type[]{Type.INT}));
         tramp.add(LDC," pc: ");
-        tramp.add(INVOKEVIRTUAL,new MethodRef(Type.STRINGBUFFER,"append",Type.STRINGBUFFER,new Type[]{Type.STRING}));
+        tramp.add(INVOKEVIRTUAL,Type.STRINGBUFFER.method("append",Type.STRINGBUFFER,new Type[]{Type.STRING}));
         tramp.add(ALOAD_0);
-        tramp.add(GETFIELD, new FieldRef(me,"pc",Type.INT));        
-        tramp.add(INVOKEVIRTUAL,new MethodRef(Type.STRINGBUFFER,"append",Type.STRINGBUFFER,new Type[]{Type.INT}));
+        tramp.add(GETFIELD, me.field("pc",Type.INT));        
+        tramp.add(INVOKEVIRTUAL,Type.STRINGBUFFER.method("append",Type.STRINGBUFFER,new Type[]{Type.INT}));
         tramp.add(LDC,")");
-        tramp.add(INVOKEVIRTUAL,new MethodRef(Type.STRINGBUFFER,"append",Type.STRINGBUFFER,new Type[]{Type.STRING}));
-        tramp.add(INVOKEVIRTUAL,new MethodRef(Type.STRINGBUFFER,"toString",Type.STRING,Type.NO_ARGS));
-        tramp.add(INVOKESPECIAL,new MethodRef(new Type.Object("org.ibex.nestedvm.Runtime$ExecutionException"),"<init>",Type.VOID,new Type[]{Type.STRING}));
+        tramp.add(INVOKEVIRTUAL,Type.STRINGBUFFER.method("append",Type.STRINGBUFFER,new Type[]{Type.STRING}));
+        tramp.add(INVOKEVIRTUAL,Type.STRINGBUFFER.method("toString",Type.STRING,Type.NO_ARGS));
+        // GCCLASS_HINT: org.ibex.nestedvm.RuntimeCompiler.compile org.ibex.nestedvm.Runtime$ExecutionException.<init>
+        tramp.add(INVOKESPECIAL,Type.Class.instance("org.ibex.nestedvm.Runtime$ExecutionException").method("<init>",Type.VOID,new Type[]{Type.STRING}));
         tramp.add(ATHROW);
-                
-        
-        if(false) {
-        try {
-            tramp.finish();
-        } catch(ClassGen.Exn e) {
-            e.printStackTrace(warn);
-            throw new Exn("Generation of the trampoline method failed. Try increasing maxInsnPerMethod");
-        }
-        }
         
         addConstReturnMethod("gp",gp.addr);
         addConstReturnMethod("entryPoint",elf.header.entry);
@@ -238,15 +255,15 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
         }
         
         if(supportCall) {
-            Type.Object hashClassType = new Type.Object(hashClass);
-            MethodGen ls = cg.addMethod("lookupSymbol",Type.INT,new Type[]{Type.STRING},ACC_PROTECTED);
-            ls.add(GETSTATIC,new FieldRef(me,"symbols",hashClassType));
+            Type.Class hashClassType = Type.Class.instance(hashClass);
+            MethodGen ls = cg.addMethod("lookupSymbol",Type.INT,new Type[]{Type.STRING},PROTECTED);
+            ls.add(GETSTATIC,me.field("symbols",hashClassType));
             ls.add(ALOAD_1);
-            ls.add(INVOKEVIRTUAL,new MethodRef(hashClassType,"get",Type.OBJECT,new Type[]{Type.OBJECT}));
+            ls.add(INVOKEVIRTUAL,hashClassType.method("get",Type.OBJECT,new Type[]{Type.OBJECT}));
             ls.add(DUP);
             int b = ls.add(IFNULL);
             ls.add(CHECKCAST,Type.INTEGER_OBJECT);
-            ls.add(INVOKEVIRTUAL,new MethodRef(Type.INTEGER_OBJECT,"intValue",Type.INT,Type.NO_ARGS));
+            ls.add(INVOKEVIRTUAL,Type.INTEGER_OBJECT.method("intValue",Type.INT,Type.NO_ARGS));
             ls.add(IRETURN);
             ls.setArg(b,ls.size());
             ls.add(POP);
@@ -254,14 +271,16 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
             ls.add(IRETURN);
         }
         
-        Type.Object cpuStateType = new Type.Object("org.ibex.nestedvm.Runtime$CPUState");
-        MethodGen setCPUState = cg.addMethod("setCPUState",Type.VOID,new Type[]{cpuStateType},ACC_PROTECTED);
-        MethodGen getCPUState = cg.addMethod("getCPUState",Type.VOID,new Type[]{cpuStateType},ACC_PROTECTED);
+        // Kind of a hack, referencing dup() gets us all the fields for free
+        // GCCLASS_HINT: org.ibex.nestedvm.RuntimeCompiler.compile org.ibex.nestedvm.Runtime$CPUState.dup
+        Type.Class cpuStateType = Type.Class.instance("org.ibex.nestedvm.Runtime$CPUState");
+        MethodGen setCPUState = cg.addMethod("setCPUState",Type.VOID,new Type[]{cpuStateType},PROTECTED);
+        MethodGen getCPUState = cg.addMethod("getCPUState",Type.VOID,new Type[]{cpuStateType},PROTECTED);
         
         setCPUState.add(ALOAD_1);
         getCPUState.add(ALOAD_1);
-        setCPUState.add(GETFIELD,new FieldRef(cpuStateType,"r",Type.arrayType(Type.INT)));
-        getCPUState.add(GETFIELD,new FieldRef(cpuStateType,"r",Type.arrayType(Type.INT)));
+        setCPUState.add(GETFIELD,cpuStateType.field("r",Type.INT.makeArray()));
+        getCPUState.add(GETFIELD,cpuStateType.field("r",Type.INT.makeArray()));
         setCPUState.add(ASTORE_2);
         getCPUState.add(ASTORE_2);
         
@@ -270,19 +289,19 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
             setCPUState.add(ALOAD_2);
             setCPUState.add(LDC,i);
             setCPUState.add(IALOAD);
-            setCPUState.add(PUTFIELD,new FieldRef(me,"r"+i,Type.INT));
+            setCPUState.add(PUTFIELD,me.field("r"+i,Type.INT));
             
             getCPUState.add(ALOAD_2);
             getCPUState.add(LDC,i);
             getCPUState.add(ALOAD_0);
-            getCPUState.add(GETFIELD,new FieldRef(me,"r"+i,Type.INT));
+            getCPUState.add(GETFIELD,me.field("r"+i,Type.INT));
             getCPUState.add(IASTORE);
         }
         
         setCPUState.add(ALOAD_1);
         getCPUState.add(ALOAD_1);
-        setCPUState.add(GETFIELD,new FieldRef(cpuStateType,"f",Type.arrayType(Type.INT)));
-        getCPUState.add(GETFIELD,new FieldRef(cpuStateType,"f",Type.arrayType(Type.INT)));
+        setCPUState.add(GETFIELD,cpuStateType.field("f",Type.INT.makeArray()));
+        getCPUState.add(GETFIELD,cpuStateType.field("f",Type.INT.makeArray()));
         setCPUState.add(ASTORE_2);
         getCPUState.add(ASTORE_2);
         
@@ -291,14 +310,14 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
             setCPUState.add(ALOAD_2);
             setCPUState.add(LDC,i);
             setCPUState.add(IALOAD);
-            if(singleFloat) setCPUState.add(INVOKESTATIC,new MethodRef(Type.FLOAT_OBJECT,"intBitsToFloat",Type.FLOAT,new Type[]{Type.INT}));
-            setCPUState.add(PUTFIELD,new FieldRef(me,"f"+i,singleFloat ? Type.FLOAT : Type.INT));
+            if(singleFloat) setCPUState.add(INVOKESTATIC,Type.FLOAT_OBJECT.method("intBitsToFloat",Type.FLOAT,new Type[]{Type.INT}));
+            setCPUState.add(PUTFIELD,me.field("f"+i,singleFloat ? Type.FLOAT : Type.INT));
             
             getCPUState.add(ALOAD_2);
             getCPUState.add(LDC,i);
             getCPUState.add(ALOAD_0);
-            getCPUState.add(GETFIELD,new FieldRef(me,"f"+i,singleFloat ? Type.FLOAT: Type.INT));
-            if(singleFloat) getCPUState.add(INVOKESTATIC,new MethodRef(Type.FLOAT_OBJECT,"floatToIntBits",Type.INT,new Type[]{Type.FLOAT}));
+            getCPUState.add(GETFIELD,me.field("f"+i,singleFloat ? Type.FLOAT: Type.INT));
+            if(singleFloat) getCPUState.add(INVOKESTATIC,Type.FLOAT_OBJECT.method("floatToIntBits",Type.INT,new Type[]{Type.FLOAT}));
             getCPUState.add(IASTORE);            
         }
         
@@ -306,49 +325,52 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
         for(int i=0;i<each.length;i++) {
             setCPUState.add(ALOAD_0);
             setCPUState.add(ALOAD_1);
-            setCPUState.add(GETFIELD,new FieldRef(cpuStateType,each[i],Type.INT));
-            setCPUState.add(PUTFIELD,new FieldRef(me,each[i],Type.INT));
+            setCPUState.add(GETFIELD,cpuStateType.field(each[i],Type.INT));
+            setCPUState.add(PUTFIELD,me.field(each[i],Type.INT));
 
             getCPUState.add(ALOAD_1);
             getCPUState.add(ALOAD_0);
-            getCPUState.add(GETFIELD,new FieldRef(me,each[i],Type.INT));
-            getCPUState.add(PUTFIELD,new FieldRef(cpuStateType,each[i],Type.INT));
+            getCPUState.add(GETFIELD,me.field(each[i],Type.INT));
+            getCPUState.add(PUTFIELD,cpuStateType.field(each[i],Type.INT));
         }
         setCPUState.add(RETURN);
         getCPUState.add(RETURN);
         
 
-        MethodGen execute = cg.addMethod("_execute",Type.VOID,Type.NO_ARGS,ACC_PROTECTED);
+        MethodGen execute = cg.addMethod("_execute",Type.VOID,Type.NO_ARGS,PROTECTED);
         int tryStart = execute.size();
         execute.add(ALOAD_0);
-        execute.add(INVOKESPECIAL,new MethodRef(me,"trampoline",Type.VOID,Type.NO_ARGS));
+        execute.add(INVOKESPECIAL,me.method("trampoline",Type.VOID,Type.NO_ARGS));
         int tryEnd = execute.size();
         execute.add(RETURN);
         
         int catchInsn = execute.size();
         execute.add(ASTORE_1);
-        execute.add(NEW, new Type.Object("org.ibex.nestedvm.Runtime$FaultException"));
+        execute.add(NEW, Type.Class.instance("org.ibex.nestedvm.Runtime$FaultException"));
         execute.add(DUP);
         execute.add(ALOAD_1);
-        execute.add(INVOKESPECIAL,new MethodRef("org.ibex.nestedvm.Runtime$FaultException","<init>",Type.VOID,new Type[]{new Type.Object("java.lang.RuntimeException")}));
+        // GCCLASS_HINT: org.ibex.nestedvm.RuntimeCompiler.compile org.ibex.nestedvm.Runtime$FaultException.<init>
+        execute.add(INVOKESPECIAL,Type.Class.instance("org.ibex.nestedvm.Runtime$FaultException").method("<init>",Type.VOID,new Type[]{Type.Class.instance("java.lang.RuntimeException")}));
         execute.add(ATHROW);
         
-        execute.addExceptionHandler(tryStart,tryEnd,catchInsn,new Type.Object("java.lang.RuntimeException"));
-        execute.addThrow(new Type.Object("org.ibex.nestedvm.Runtime$ExecutionException"));
+        execute.addExceptionHandler(tryStart,tryEnd,catchInsn,Type.Class.instance("java.lang.RuntimeException"));
+        execute.addThrow(Type.Class.instance("org.ibex.nestedvm.Runtime$ExecutionException"));
 
-        MethodGen main = cg.addMethod("main",Type.VOID,new Type[]{Type.arrayType(Type.STRING)},ACC_STATIC|ACC_PUBLIC);
+        MethodGen main = cg.addMethod("main",Type.VOID,new Type[]{Type.STRING.makeArray()},STATIC|PUBLIC);
         main.add(NEW,me);
         main.add(DUP);
-        main.add(INVOKESPECIAL,new MethodRef(me,"<init>",Type.VOID,Type.NO_ARGS));
+        main.add(INVOKESPECIAL,me.method("<init>",Type.VOID,Type.NO_ARGS));
         main.add(LDC,fullClassName);
         main.add(ALOAD_0);
         if(unixRuntime) {
-            Type.Object ur = new Type.Object("org.ibex.nestedvm.UnixRuntime");
-            main.add(INVOKESTATIC,new MethodRef(ur,"runAndExec",Type.INT,new Type[]{ur,Type.STRING,Type.arrayType(Type.STRING)}));
+            Type.Class ur = Type.Class.instance("org.ibex.nestedvm.UnixRuntime");
+            // GCCLASS_HINT: org.ibex.nestedvm.RuntimeCompiler.compile org.ibex.nestedvm.Runtime.runAndExec
+            main.add(INVOKESTATIC,ur.method("runAndExec",Type.INT,new Type[]{ur,Type.STRING,Type.STRING.makeArray()}));
         } else {
-            main.add(INVOKEVIRTUAL,new MethodRef(me,"run",Type.INT,new Type[]{Type.STRING,Type.arrayType(Type.STRING)}));
+            // GCCLASS_HINT: org.ibex.nestedvm.RuntimeCompiler.compile org.ibex.nestedvm.Runtime.run
+            main.add(INVOKEVIRTUAL,me.method("run",Type.INT,new Type[]{Type.STRING,Type.STRING.makeArray()}));
         }
-        main.add(INVOKESTATIC,new MethodRef(new Type.Object("java.lang.System"),"exit",Type.VOID,new Type[]{Type.INT}));
+        main.add(INVOKESTATIC,Type.Class.instance("java.lang.System").method("exit",Type.VOID,new Type[]{Type.INT}));
         main.add(RETURN);
         
         if(outDir != null) {
@@ -360,7 +382,7 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
     }
     
     private void addConstReturnMethod(String name, int val) {
-        MethodGen  m = cg.addMethod(name,Type.INT,Type.NO_ARGS,ACC_PROTECTED);
+        MethodGen  m = cg.addMethod(name,Type.INT,Type.NO_ARGS,PROTECTED);
         m.add(LDC,val);
         m.add(IRETURN);
     }
@@ -383,18 +405,19 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
                     sb.append((char) ((l>>>(7*(7-j)))&0x7f));
             }
             String fieldname =  "_data" + (++initDataCount);
-            cg.addField(fieldname,Type.arrayType(Type.INT),ACC_PRIVATE|ACC_STATIC|ACC_FINAL);
+            cg.addField(fieldname,Type.INT.makeArray(),PRIVATE|STATIC|FINAL);
             
             clinit.add(LDC,sb.toString());
             clinit.add(LDC,segSize/4);
-            clinit.add(INVOKESTATIC,new MethodRef(new Type.Object("org.ibex.nestedvm.Runtime"),"decodeData",Type.arrayType(Type.INT),new Type[]{Type.STRING,Type.INT}));
-            clinit.add(PUTSTATIC,new FieldRef(me,fieldname,Type.arrayType(Type.INT)));
-
+            // GCCLASS_HINT: org.ibex.nestedvm.RuntimeCompiler.compile org.ibex.nestedvm.Runtime.decodeData
+            clinit.add(INVOKESTATIC,Type.Class.instance("org.ibex.nestedvm.Runtime").method("decodeData",Type.INT.makeArray(),new Type[]{Type.STRING,Type.INT}));
+            clinit.add(PUTSTATIC,me.field(fieldname,Type.INT.makeArray()));
             init.add(ALOAD_0);
-            init.add(GETSTATIC,new FieldRef(me,fieldname,Type.arrayType(Type.INT)));
+            init.add(GETSTATIC,me.field(fieldname,Type.INT.makeArray()));
             init.add(LDC,addr);
             init.add(LDC,readOnly ? 1 : 0);
-            init.add(INVOKEVIRTUAL,new MethodRef(me,"initPages",Type.VOID,new Type[]{Type.arrayType(Type.INT),Type.INT,Type.BOOLEAN}));
+            // GCCLASS_HINT: org.ibex.nestedvm.RuntimeCompiler.compile org.ibex.nestedvm.Runtime.initPages
+            init.add(INVOKEVIRTUAL,me.method("initPages",Type.VOID,new Type[]{Type.INT.makeArray(),Type.INT,Type.BOOLEAN}));
             
             addr += segSize;
             size -= segSize;
@@ -410,7 +433,8 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
         init.add(ALOAD_0);
         init.add(LDC,addr);
         init.add(LDC,count);
-        init.add(INVOKEVIRTUAL,new MethodRef(me,"clearPages",Type.VOID,new Type[]{Type.INT,Type.INT}));
+        // GCCLASS_HINT: org.ibex.nestedvm.RuntimeCompiler.compile org.ibex.nestedvm.Runtime.clearPages
+        init.add(INVOKEVIRTUAL,me.method("clearPages",Type.VOID,new Type[]{Type.INT,Type.INT}));
     }
     
     // Method state info
@@ -471,17 +495,17 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
         startOfMethod = first & methodMask;
         endOfMethod = startOfMethod + maxBytesPerMethod;
         
-        mg = cg.addMethod("run_" + toHex(startOfMethod),Type.VOID,Type.NO_ARGS,ACC_PRIVATE|ACC_FINAL);
+        mg = cg.addMethod("run_" + toHex(startOfMethod),Type.VOID,Type.NO_ARGS,PRIVATE|FINAL);
         if(onePage) {
             mg.add(ALOAD_0);
-            mg.add(GETFIELD,new FieldRef(me,"page",Type.arrayType(Type.INT)));
+            mg.add(GETFIELD,me.field("page",Type.INT.makeArray()));
             mg.add(ASTORE_2);
         } else {
             mg.add(ALOAD_0);
-            mg.add(GETFIELD,new FieldRef(me,"readPages",Type.arrayType(Type.INT,2)));
+            mg.add(GETFIELD,me.field("readPages",Type.INT.makeArray(2)));
             mg.add(ASTORE_2);
             mg.add(ALOAD_0);
-            mg.add(GETFIELD,new FieldRef(me,"writePages",Type.arrayType(Type.INT,2)));
+            mg.add(GETFIELD,me.field("writePages",Type.INT.makeArray(2)));
             mg.add(ASTORE_3);
         }
         
@@ -499,7 +523,7 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
             }
         }
 
-        MethodGen.LSI lsi = new MethodGen.LSI(n);
+        MethodGen.Switch.Lookup lsi = new MethodGen.Switch.Lookup(n);
         System.arraycopy(buf,0,lsi.vals,0,n);
         System.arraycopy(targetBuf,0,lsi.targets,0,n);
         lsi.setDefaultTarget(defaultTarget = new MethodGen.PhantomTarget());
@@ -507,7 +531,7 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
         fixupRegsStart();
         
         mg.add(ALOAD_0);
-        mg.add(GETFIELD,new FieldRef(me,"pc",Type.INT));
+        mg.add(GETFIELD,me.field("pc",Type.INT));
         mg.add(LOOKUPSWITCH,lsi);
     }
     
@@ -531,23 +555,23 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
         defaultTarget.setTarget(mg.size());
         
         if(debugCompiler) {
-            mg.add(NEW,new Type.Object("org.ibex.nestedvm.Runtime$ExecutionException"));
+            mg.add(NEW,Type.Class.instance("org.ibex.nestedvm.Runtime$ExecutionException"));
             mg.add(DUP);
             mg.add(NEW,Type.STRINGBUFFER);
             mg.add(DUP);
             mg.add(LDC,"Jumped to invalid address: ");
-            mg.add(INVOKESPECIAL,new MethodRef(Type.STRINGBUFFER,"<init>",Type.VOID,new Type[]{Type.STRING}));
+            mg.add(INVOKESPECIAL,Type.STRINGBUFFER.method("<init>",Type.VOID,new Type[]{Type.STRING}));
             mg.add(ALOAD_0);
-            mg.add(GETFIELD,new FieldRef(me,"pc",Type.INT));
-            mg.add(INVOKEVIRTUAL,new MethodRef(Type.STRINGBUFFER,"append",Type.STRINGBUFFER,new Type[]{Type.INT}));
-            mg.add(INVOKEVIRTUAL,new MethodRef(Type.STRINGBUFFER,"toString",Type.STRING,Type.NO_ARGS));
-            mg.add(INVOKESPECIAL,new MethodRef(new Type.Object("org.ibex.nestedvm.Runtime$ExecutionException"),"<init>",Type.VOID,new Type[]{Type.STRING}));
+            mg.add(GETFIELD,me.field("pc",Type.INT));
+            mg.add(INVOKEVIRTUAL,Type.STRINGBUFFER.method("append",Type.STRINGBUFFER,new Type[]{Type.INT}));
+            mg.add(INVOKEVIRTUAL,Type.STRINGBUFFER.method("toString",Type.STRING,Type.NO_ARGS));
+            mg.add(INVOKESPECIAL,Type.Class.instance("org.ibex.nestedvm.Runtime$ExecutionException").method("<init>",Type.VOID,new Type[]{Type.STRING}));
             mg.add(ATHROW);
         } else {
-            mg.add(NEW,new Type.Object("org.ibex.nestedvm.Runtime$ExecutionException"));
+            mg.add(NEW,Type.Class.instance("org.ibex.nestedvm.Runtime$ExecutionException"));
             mg.add(DUP);
             mg.add(LDC,"Jumped to invalid address");
-            mg.add(INVOKESPECIAL,new MethodRef(new Type.Object("org.ibex.nestedvm.Runtime$ExecutionException"),"<init>",Type.VOID,new Type[]{Type.STRING}));
+            mg.add(INVOKESPECIAL,Type.Class.instance("org.ibex.nestedvm.Runtime$ExecutionException").method("<init>",Type.VOID,new Type[]{Type.STRING}));
             mg.add(ATHROW);
         }
         
@@ -731,11 +755,12 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
                 pushRegZ(R+A3);
                 pushRegZ(R+T0);
                 pushRegZ(R+T1);
-                mg.add(INVOKEVIRTUAL,new MethodRef(me,"syscall",Type.INT,new Type[]{Type.INT,Type.INT,Type.INT,Type.INT,Type.INT,Type.INT,Type.INT}));
+                // GCCLASS_HINT: org.ibex.nestedvm.RuntimeCompiler.compile org.ibex.nestedvm.Runtime.syscall
+                mg.add(INVOKEVIRTUAL,me.method("syscall",Type.INT,new Type[]{Type.INT,Type.INT,Type.INT,Type.INT,Type.INT,Type.INT,Type.INT}));
                 setReg();
                 
                 mg.add(ALOAD_0);
-                mg.add(GETFIELD,new FieldRef(me,"state",Type.INT));
+                mg.add(GETFIELD,me.field("state",Type.INT));
                 b1 = mg.add(IFEQ);
                 preSetPC();
                 mg.add(LDC,pc+4);
@@ -744,10 +769,10 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
                 mg.setArg(b1,mg.size());
                 break;
             case 13: // BREAK
-                mg.add(NEW,new Type.Object("org.ibex.nestedvm.Runtime$ExecutionException"));
+                mg.add(NEW,Type.Class.instance("org.ibex.nestedvm.Runtime$ExecutionException"));
                 mg.add(DUP);
                 mg.add(LDC,"BREAK Code " + toHex(breakCode));
-                mg.add(INVOKESPECIAL,new MethodRef(new Type.Object("org.ibex.nestedvm.Runtime$ExecutionException"),"<init>",Type.VOID,new Type[]{Type.STRING}));
+                mg.add(INVOKESPECIAL,Type.Class.instance("org.ibex.nestedvm.Runtime$ExecutionException").method("<init>",Type.VOID,new Type[]{Type.STRING}));
                 mg.add(ATHROW);
                 ret |= UNREACHABLE;
                 break;
@@ -1262,7 +1287,7 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
                     setDouble();
                     break;
                 case 36: { // CVT.W.D
-                    MethodGen.TSI tsi = new MethodGen.TSI(0,3);
+                    MethodGen.Switch.Table tsi = new MethodGen.Switch.Table(0,3);
                     preSetReg(F+fd);
                     pushDouble(F+fs,d);
                     pushReg(FCSR);
@@ -1273,7 +1298,7 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
                     // Round towards plus infinity
                     tsi.setTarget(2,mg.size());
                     if(!d) mg.add(F2D); // Ugh.. java.lang.Math doesn't have a float ceil/floor
-                    mg.add(INVOKESTATIC,new MethodRef("java.lang.Math","ceil",Type.DOUBLE,new Type[]{Type.DOUBLE}));
+                    mg.add(INVOKESTATIC,Type.Class.instance("java.lang.Math").method("ceil",Type.DOUBLE,new Type[]{Type.DOUBLE}));
                     if(!d) mg.add(D2F);
                     b1 = mg.add(GOTO);
                     
@@ -1286,7 +1311,7 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
                     // Round towards minus infinity
                     tsi.setTarget(3,mg.size());
                     if(!d) mg.add(F2D);
-                    mg.add(INVOKESTATIC,new MethodRef("java.lang.Math","floor",Type.DOUBLE,new Type[]{Type.DOUBLE}));
+                    mg.add(INVOKESTATIC,Type.Class.instance("java.lang.Math").method("floor",Type.DOUBLE,new Type[]{Type.DOUBLE}));
                     if(!d) mg.add(D2F);
                     
                     tsi.setTarget(1,mg.size());
@@ -1752,13 +1777,13 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
         for(int i=0;i<REG_COUNT;i++) {
             if(regLocalMapping[i] == 0) continue;
             mg.set(p++,ALOAD_0);
-            mg.set(p++,GETFIELD,new FieldRef(me,regField[i],Type.INT));
+            mg.set(p++,GETFIELD,me.field(regField[i],Type.INT));
             mg.set(p++,ISTORE,regLocalMapping[i]);
             
             if(regLocalWritten[i]) {
                 mg.add(ALOAD_0);
                 mg.add(ILOAD,regLocalMapping[i]);
-                mg.add(PUTFIELD,new FieldRef(me,regField[i],Type.INT));
+                mg.add(PUTFIELD,me.field(regField[i],Type.INT));
             }
         }
     }
@@ -1768,7 +1793,7 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
             if(regLocalWritten[i]) {
                 mg.add(ALOAD_0);
                 mg.add(ILOAD,regLocalMapping[i]);
-                mg.add(PUTFIELD,new FieldRef(me,regField[i],Type.INT));
+                mg.add(PUTFIELD,me.field(regField[i],Type.INT));
             }
         }
     }
@@ -1793,11 +1818,11 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
             mg.add(ILOAD,getLocalForReg(reg));
         } else if(reg >= F+0 && reg <= F+31 && singleFloat) {
             mg.add(ALOAD_0);
-            mg.add(GETFIELD,new FieldRef(me,regField[reg],Type.FLOAT));
-            mg.add(INVOKESTATIC,new MethodRef(Type.FLOAT_OBJECT,"floatToIntBits",Type.INT,new Type[]{Type.FLOAT}));
+            mg.add(GETFIELD,me.field(regField[reg],Type.FLOAT));
+            mg.add(INVOKESTATIC,Type.FLOAT_OBJECT.method("floatToIntBits",Type.INT,new Type[]{Type.FLOAT}));
         } else {
             mg.add(ALOAD_0);
-            mg.add(GETFIELD,new FieldRef(me,regField[reg],Type.INT));
+            mg.add(GETFIELD,me.field(regField[reg],Type.INT));
         }
         return h;
     }
@@ -1826,17 +1851,17 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
             mg.add(ISTORE,getLocalForReg(reg));
             regLocalWritten[reg] = true;
         } else if(reg >= F+0 && reg <= F+31 && singleFloat) {
-            mg.add(INVOKESTATIC,new MethodRef(Type.FLOAT_OBJECT,"intBitsToFloat",Type.FLOAT,new Type[]{Type.INT}));
-            mg.add(PUTFIELD,new FieldRef(me,regField[reg],Type.FLOAT));            
+            mg.add(INVOKESTATIC,Type.FLOAT_OBJECT.method("intBitsToFloat",Type.FLOAT,new Type[]{Type.INT}));
+            mg.add(PUTFIELD,me.field(regField[reg],Type.FLOAT));            
         } else {
-            mg.add(PUTFIELD,new FieldRef(me,regField[reg],Type.INT));
+            mg.add(PUTFIELD,me.field(regField[reg],Type.INT));
         }
         return h;
     }
     
     private int preSetPC() { return mg.add(ALOAD_0); }
     private int setPC() {
-        return mg.add(PUTFIELD,new FieldRef(me,"pc",Type.INT));
+        return mg.add(PUTFIELD,me.field("pc",Type.INT));
     }
     
     //unused - private InstructionHandle pushDouble(int reg) throws CompilationException { return pushDouble(reg,true); }
@@ -1856,13 +1881,13 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
             mg.add(LDC,FFFFFFFF);
             mg.add(LAND);
             mg.add(LOR);
-            mg.add(INVOKESTATIC,new MethodRef(Type.DOUBLE_OBJECT,"longBitsToDouble",Type.DOUBLE,new Type[]{Type.LONG}));
+            mg.add(INVOKESTATIC,Type.DOUBLE_OBJECT.method("longBitsToDouble",Type.DOUBLE,new Type[]{Type.LONG}));
         } else if(singleFloat) {
             mg.add(ALOAD_0);
-            mg.add(GETFIELD,new FieldRef(me,regField[reg],Type.FLOAT));
+            mg.add(GETFIELD,me.field(regField[reg],Type.FLOAT));
         } else {
             pushReg(reg);
-            mg.add(INVOKESTATIC,new MethodRef("java.lang.Float","intBitsToFloat",Type.FLOAT,new Type[]{Type.INT}));
+            mg.add(INVOKESTATIC,Type.Class.instance("java.lang.Float").method("intBitsToFloat",Type.FLOAT,new Type[]{Type.INT}));
         }
         return h;
     }
@@ -1880,7 +1905,7 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
         if(d) {
             if(singleFloat) throw new Exn("Double operations not supported when singleFloat is enabled");
             if(reg == F+31) throw new Exn("Tried to use a double in f31");
-            mg.add(INVOKESTATIC,new MethodRef(Type.DOUBLE_OBJECT,"doubleToLongBits",Type.LONG,new Type[]{Type.DOUBLE}));
+            mg.add(INVOKESTATIC,Type.DOUBLE_OBJECT.method("doubleToLongBits",Type.LONG,new Type[]{Type.DOUBLE}));
             mg.add(DUP2);
             mg.add(LDC,32);
             mg.add(LUSHR);
@@ -1893,10 +1918,10 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
         } else if(singleFloat) {
             // HACK: Clean this up
             preSetRegStackPos--;
-            mg.add(PUTFIELD,new FieldRef(me,regField[reg],Type.FLOAT));
+            mg.add(PUTFIELD,me.field(regField[reg],Type.FLOAT));
         } else {
             //h = a(fac.createInvoke("java.lang.Float","floatToRawIntBits",Type.INT,new Type[]{Type.FLOAT},INVOKESTATIC));
-            mg.add(INVOKESTATIC,new MethodRef(Type.FLOAT_OBJECT,"floatToRawIntBits",Type.INT,new Type[]{Type.FLOAT}));
+            mg.add(INVOKESTATIC,Type.FLOAT_OBJECT.method("floatToRawIntBits",Type.INT,new Type[]{Type.FLOAT}));
             setReg();   
         }
         return h;
@@ -1942,7 +1967,8 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
             mg.add(DUP);
             mg.add(ALOAD_0);
             mg.add(SWAP);
-            mg.add(INVOKEVIRTUAL,new MethodRef(me,"nullPointerCheck",Type.VOID,new Type[]{Type.INT}));
+            // GCCLASS_HINT: org.ibex.nestedvm.RuntimeCompiler.compile org.ibex.nestedvm.Runtime.nullPointerCheck
+            mg.add(INVOKEVIRTUAL,me.method("nullPointerCheck",Type.VOID,new Type[]{Type.INT}));
         }
         
         if(onePage) {
@@ -1975,7 +2001,8 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
         } else if(fastMem) {
             mg.add(IASTORE);
         } else {
-            mg.add(INVOKEVIRTUAL,new MethodRef(me,"unsafeMemWrite",Type.VOID,new Type[]{Type.INT,Type.INT}));
+            // GCCLASS_HINT: org.ibex.nestedvm.RuntimeCompiler.compile org.ibex.nestedvm.Runtime.unsafeMemWrite
+            mg.add(INVOKEVIRTUAL,me.method("unsafeMemWrite",Type.VOID,new Type[]{Type.INT,Type.INT}));
         }
         
     }
@@ -2016,7 +2043,7 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
             mg.add(DUP);
             mg.add(ALOAD_0);
             mg.add(SWAP);
-            mg.add(INVOKEVIRTUAL,new MethodRef(me,"nullPointerCheck",Type.VOID,new Type[]{Type.INT}));
+            mg.add(INVOKEVIRTUAL,me.method("nullPointerCheck",Type.VOID,new Type[]{Type.INT}));
         }
         
         if(onePage) {
@@ -2046,7 +2073,8 @@ public class ClassFileCompiler extends Compiler implements CGConst  {
         } else {
             if(preMemReadDoPreWrite)
                 mg.add(DUP2);
-            mg.add(INVOKEVIRTUAL,new MethodRef(me,"unsafeMemRead",Type.INT,new Type[]{Type.INT}));
+            // GCCLASS_HINT: org.ibex.nestedvm.RuntimeCompiler.compile org.ibex.nestedvm.Runtime.unsafeMemRead
+            mg.add(INVOKEVIRTUAL,me.method("unsafeMemRead",Type.INT,new Type[]{Type.INT}));
         }
     }