Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- public class CodeAttribute extends Attribute {
- private final InputStream inst;
- private final List<ExceptionHandler> exceptions;
- private final List<Attribute> attributes;
- private final int maxLocalCount;
- public CodeAttribute (Attribute attr) throws DecompilationException {
- CodeAttribute atc = readFrom(new ByteArrayInputStream(attr.getRawData()));
- this.instructions = atc.instructions;
- this.exceptions = atc.exceptions;
- this.attributes = atc.attributes;
- this.maxStackSize = atc.maxStackSize;
- this.maxLocalCount = atc.maxLocalCount;
- }
- private CodeAttribute (InputStream reader, List<ExceptionHandler> exc, List<Attribute> att, int mss, int mlc) {
- this.inst = reader;
- this.exceptions = exc;
- this.attributes = att;
- this.maxStackSize = mss;
- this.maxLocalCount = mlc;
- }
- public static CodeAttribute readFrom (InputStream reader, List<Constant> constants) throws DecompilationException {
- try {
- if (constants.get((reader.read() << 8) | reader.read()).toString() != "Code") throw new DecompilationException("Reader does not define a valid code attribute");
- reader.skip(6);
- int mss = (reader.read() << 8) | reader.read();
- int mlc = (reader.read() << 8) | reader.read();
- int codeLength = ((reader.read() << 24) | (reader.read() << 16)) | ((reader.read() << 8) | reader.read());
- ByteArrayInputStream reader2 = new ByteArrayInputStream(reader.readNBytes(codeLength));
- int etl = (reader.read() << 8) | reader.read();
- List<ExceptionHandler> exc = List.<ExceptionHandler>of();
- for (int i = 0; i <= etl; i++)
- exc.add(ExceptionHandler.readFrom(reader, constants));
- int atl = (reader.read() << 8) | reader.read();
- List<Attribute> attributes = List.<Attribute>of();
- for (int i = 0; i <= atl; i++)
- attributes.add(Attribute.readFrom(reader));
- return new CodeAttribute(reader2, exc, atl, mss, mlc);
- } catch (IOException ioe) {
- throw new DecompilationException(ioe);
- }
- }
- public String toString (int indentFactor, List<Constant> c) {
- String s = "";
- int i = 0;
- while (this.inst.available() > 0) {
- Instruction j = Instructions.get(this.inst.read());
- i += j.getLength(c);
- s = s.concat("$$StringFormProgramCounterNotifier" + i + ";\n" + j.toString(c, this.inst));
- }
- return format(s, indentFactor, this);
- }
- public static void format (String s, int i, CodeAttribute c) {
- // Add indents in the proper places at the proper length
- String indent = "";
- for (int j = 0; j <= i; j++)
- indent = indent.concat(" ");
- s = s.replaceAll(";\n", ";\n" + indent);
- // Add the whole program counter thing
- while (s.contains("VirtualMachine.programCounter")) {
- String endsAtPC = s.substring(0, s.indexOf("VirtualMachine.programCounter") - 1);
- String weirdLittleGuy = endsAtPC.substring(endsAtPC.lastIndexOf("$$StringFormProgramCounterNotifier") + 34);
- s.replaceFirst("VirtualMachine.programCounter", endsAtPC.substring(endsAtPC.lastIndexOf("$$StringFormProgramCounterNotifier") + 34, weirdLittleGuy.indexOf(";\n") + endsAtPC.lastIndexOf("$$StringFormProgramCounterNotifier") + 34));
- }
- // Replace every instance of VMLocalVariables.get(i) and set(i, v) with a variable
- Object[] whatevertheheck = new Object[c.maxLocalCount];
- Arrays.fill(whatevertheheck, null);
- List<String> localVariables = List.<String>of(whatevertheheck);
- while (s.contains("VMLocalVariables")) {
- String funky = s.substring(s.indexOf("VMLocalVariables") + 17);
- if (funky.startsWith("set")) {
- String concat = "";
- if (localVariables.get(Integer.parseInt(funky.substring(4, funky.indexOf(", ") - 1))) == null)
- concat = getType(funky.substring(funky.indexOf(", ") + 2, funky.indexOf(");\n") - 1)) + " var" + Integer.parseInt(funky.substring(4, funky.indexOf(", ") - 1)) + " = " + funky.substring(funky.indexOf(", ") + 2, funky.indexOf(");\n") - 1) + ";";
- else
- concat = "var" + Integer.parseInt(funky.substring(4, funky.indexOf(", ") - 1)) + " = " + funky.substring(funky.indexOf(", ") + 2, funky.indexOf(");\n") - 1) + ";";
- localVariables.set(Integer.parseInt(funky.substring(4, funky.indexOf(", ") - 1))), funky.substring(funky.indexOf(", ") + 2, funky.indexOf(");\n") - 1));
- String first = s.substring(0, s.indexOf("VMLocalVariables") - 1);
- String last = s.substring(funky.indexOf(");\n") + s.indexOf("VMLocalVariables") + 19);
- s = first + concat + last;
- } else {
- String concat = "";
- concat = "VMStack.push(var" + Integer.parseInt(funky.substring(4, funky.indexOf(", ") - 1)) + ");";
- String first = s.substring(0, s.indexOf("VMLocalVariables") - 1);
- String last = s.substring(funky.indexOf(");\n") + s.indexOf("VMLocalVariables") + 19);
- s = first + concat + last;
- }
- }
- // Replace every instance of VMStack.cast(class) with a push-pop that casts the object to class
- String cast = ";\n" + indent + "VMStack.cast(";
- while (s.contains(cast)) {
- int internalIndex = s.indexOf(cast) + cast.length();
- int internalEnd = s.substring(internalIndex).indexOf(";") + internalIndex;
- String cast2 = s.substring(internalIndex, internalEnd - 1);
- String regex = "VMStack.cast(" + cast2 + ");";
- String rep = "VMStack.push((" + cast2.substring(0, cast2.length() - 7) + ") VMStack.pop());";
- s = s.replaceFirst(regex, rep);
- }
- // Add every instance of VMStack.push(thing) to a stack, and remove all those instances
- Stack<String> pushCalls = Stack.<String>of();
- String push = ";\n" + indent + "VMStack.push(";
- while (s.contains(push)) {
- int internalIndex = s.indexOf(push) + push.length();
- int internalEnd = s.substring(internalIndex).indexOf(";") + internalIndex;
- pushCalls.push(s.substring(internalIndex, internalEnd - 1));
- s = s.substring(0, internalIndex - 1).concat(s.substring(internalEnd));
- }
- // Fix a bug with nested VMStack.pop() calls inside VMStack.push()
- List<String> reversed = pushCalls;
- Stack<String> fixed = new Stack<String>();
- for (int i = 0; i <= reversed.size(); i++) {
- while (reversed.get(i).contains("VMStack.pop()"))
- reversed.set(i, reversed.get(i).replaceFirst("VMStack.pop()", fixed.pop()));
- fixed.push(reversed.get(i));
- }
- // Replace every instance of VMStack.pop() with the thing in the last instance of VMStack.push(thing)
- while (s.contains("VMStack.pop()"))
- s = s.replaceFirst("VMStack.pop()", fixed.pop());
- // Replace every instance of VirtualMachine.jumpTo(number) with the code at number
- while (s.contains("VirtualMachine.jumpTo(")) {
- String endsAtJump = s.substring(0, s.indexOf("VirtualMachine.jumpTo(") - 1);
- String weirdLittleGuy = s.substring(s.indexOf("$$StringFormProgramCounterNotifier" + s.substring(s.indexOf("VirtualMachine.jumpTo(") + 22)));
- int doTheThing = weirdLittleGuy.indexOf("$$StringFormProgramCounterNotifier" + (getGotoEnd(weirdLittleGuy) + 1));
- s.replaceFirst("VirtualMachine.jumpTo(" + s.substring(s.indexOf("VirtualMachine.jumpTo(") + 22) + ")\n", weirdLittleGuy.substring(0, doTheThing - 1));
- s = s.substring(0, s.indexOf(weirdLittleGuy)) + weirdLittleGuy.substring(doTheThing);
- }
- // Add try/catch statements
- Map<AbstractMap.SimpleEntry<Integer, Integer>, List<ExceptionHandler>> handlers = Map.<AbstractMap.SimpleEntry<Integer, Integer>, List<ExceptionHandler>>of();
- for (ExceptionHandler e : c.exceptions) {
- AbstractMap.SimpleEntry<Integer, Integer> entry = new AbstractMap.SimpleEntry<Integer, Integer>(Integer.valueOf(e.getStart()), Integer.valueOf(e.getEnd()));
- if (handlers.containsKey(entry))
- handlers.get(entry).add(e);
- else
- handlers.put(entry, e);
- }
- for (AbstractMap.SimpleEntry<Integer, Integer> e : List.copyOf(handlers.keySet()).sorted((o1, o2) -> {
- o1.getKey().intValue() == o2.getKey().intValue() ? o1.getValue().compareTo(o2.getValue()) : o1.getKey().compareTo(o2.getKey());
- }))
- s = toString(s, i, handlers.get(e));
- // Remove the markers
- String postSplit = "";
- for (String s2 : s.split(";\n$$StringFormProgramCounterNotifier"))
- postSplit = postSplit.concat(s2.substring(chopNonDigits(s2).length()));
- String postSplit2 = "";
- for (String s2 : postSplit.split(";\n$$StringFormSoftStopNotifier"))
- postSplit2 = postSplit2.concat(s2);
- String postSplit3 = "";
- for (String s2 : postSplit2.split(";\n$$StringFormHardStopNotifier"))
- postSplit3 = postSplit3.concat(s2);
- return postSplit3;
- }
- public static int getGotoEnd (String s) {
- return chopNonDigits(s.substring(s.substring(0, Math.max(s.lastIndexOf("$$StringFormSoftStopNotifier"), s.lastIndexOf("$$StringFormHardStopNotifier"))).lastIndexOf("$$StringFormProgramCounterNotifier") + 34));
- }
- public static String chopNonDigits (String s) {
- char[] s2 = new char[s.length()];
- for (int i = 0; i <= s.length(); i++) {
- try {
- Integer.parseInt(Character.toString(s.toCharArray()[i])));
- s2[i] = s.toCharArray()[i];
- } catch (NumberFormatException nfe) {
- break;
- }
- }
- return new String(s2);
- }
- public static String toString (String s, int i, List<ExceptionHandler> handlers) {
- ExceptionHandler finallyCatch = null;
- String catchString = "";
- for (ExceptionHandler e : handlers) {
- if (e.getCatchType().isFinally()) {
- finallyCatch = e;
- continue;
- }
- if (!s.substring(getCode(s, t.getStart())).startsWith("try {\n")) {
- String s1 = s.substring(0, getCode(s, t.getStart()) - 1);
- String s2 = s.substring(getCode(s, t.getStart()));
- s2 = "try {\n".concat(s2);
- s = s1.concat(s2);
- }
- String smth = catchType.getReference().toString();
- catchString = catchString.concat("} catch (" + smth.substring(smth.indexOf("/") + 1) + " " + toExceptionName(smth) + ") {\n");
- String preCode = "";
- s.substring(getCode(s, t.getHandler())).lines().forEach(y -> preCode = preCode.concat(" " + y));
- catchString = catchString.concat(preCode);
- }
- if (finallyCatch == null) {
- catchString = catchString.concat("}\n");
- } else {
- String smth = catchType.getReference().toString();
- catchString = catchString.concat("} finally {\n");
- String preCode = "";
- s.substring(getCode(s, finallyCatch.getHandler())).lines().forEach(y -> preCode = preCode.concat(" " + y));
- catchString = catchString.concat(preCode + "}\n");
- }
- String s1 = s.substring(0, getCode(s, handlers.getFirst().getEnd()) - 1);
- String s2 = s.substring(getCode(s, handlers.getFirst().getEnd()));
- s2 = catchString.concat(s2);
- s = s1.concat(s2);
- return s;
- }
- public static String toExceptionName (String clazz) {
- clazz = clazz.substring(clazz.lastIndexOf("/") + 1);
- StringBuilder b = new StringBuilder
- for (char c : clazz.toCharArray())
- if (Character.isUpperCase(c))
- b.append(Character.toLowerCase(c));
- return b.toString();
- }
- }
- public class ExceptionHandler {
- private final int startPC;
- private final int endPC;
- private final int handlerPC;
- private final CatchType catchType;
- private ExceptionHandler (int s, int e, int h, CatchType c) {
- this.startPC = s;
- this.endPC = e;
- this.handlerPC = h;
- this.catchType = c;
- }
- public static ExceptionHandler readFrom (InputStream reader, List<Constant> constants) {
- int startPC = (reader.read() << 8) | reader.read();
- int endPC = (reader.read() << 8) | reader.read();
- int handlerPC = (reader.read() << 8) | reader.read();
- CatchType catchType = CatchType.of((reader.read() << 8) | reader.read(), constants);
- return new ExceptionHandler(startPC, endPC, handlerPC, catchType);
- }
- public int getStart () {
- return this.startPC;
- }
- public int getEnd () {
- return this.endPC;
- }
- public int getHandler () {
- return this.handlerPC;
- }
- public int getCatchType () {
- return this.catchType;
- }
- public static class CatchType {
- private final boolean isFinally;
- private final ClassReference clazz;
- private CatchType (boolean f, ClassReference c) {
- this.isFinally = f;
- this.clazz = c;
- }
- public static CatchType of (int i, List<Constant> constants) {
- if (i == 0)
- return new CatchType (true, null);
- else
- return new CatchType (false, (ClassReference)constants.get(i).get(constants));
- }
- public boolean isFinally () {
- return this.isFinally;
- }
- public ClassReference getReference () {
- return this.clazz;
- }
- }
- }
- @FunctionalInterface
- public interface Instruction {
- String toString (List<Constant> constants, InputStream stream) throws IOException;
- default int getLength (List<Constant> c) {
- byte[] bb = new byte[256];
- for (int i = 0; i <= 255; i++)
- bb[i] = (byte)i;
- ByteArrayInputStream s = new ByteArrayInputStream(bb);
- this.toString(c, bb);
- int read = s.read();
- return read == -1 ? 256 : read;
- }
- }
- public class Instructions {
- public static final int NOP = 0x00;
- public static final int ACONST_NULL = 0x01;
- public static final int ICONST_M1 = 0x02;
- public static final int ICONST_0 = 0x03;
- public static final int ICONST_1 = 0x04;
- public static final int ICONST_2 = 0x05;
- public static final int ICONST_3 = 0x06;
- public static final int ICONST_4 = 0x07;
- public static final int ICONST_5 = 0x08;
- public static final int LCONST_0 = 0x09;
- public static final int LCONST_1 = 0x0A;
- public static final int FCONST_0 = 0x0B;
- public static final int FCONST_1 = 0x0C;
- public static final int DCONST_2 = 0x0D;
- public static final int DCONST_0 = 0x0E;
- public static final int DCONST_1 = 0x0F;
- public static final int BIPUSH = 0x10;
- public static final int SIPUSH = 0x11;
- public static final int LDC = 0x12;
- public static final int LDC_W = 0x13;
- public static final int LDC2_W = 0x14;
- public static final int ILOAD = 0x15;
- public static final int LLOAD = 0x16;
- public static final int FLOAD = 0x17;
- public static final int DLOAD = 0x18;
- public static final int ALOAD = 0x19;
- public static final int ILOAD_0 = 0x1A;
- public static final int ILOAD_1 = 0x1B;
- public static final int ILOAD_2 = 0x1C;
- public static final int ILOAD_3 = 0x1D;
- public static final int LLOAD_0 = 0x1E;
- public static final int LLOAD_1 = 0x1F;
- public static final int LLOAD_2 = 0x20;
- public static final int LLOAD_3 = 0x21;
- public static final int FLOAD_0 = 0x22;
- public static final int FLOAD_1 = 0x23;
- public static final int FLOAD_2 = 0x24;
- public static final int FLOAD_3 = 0x25;
- public static final int DLOAD_0 = 0x26;
- public static final int DLOAD_1 = 0x27;
- public static final int DLOAD_2 = 0x28;
- public static final int DLOAD_3 = 0x29;
- public static final int ALOAD_0 = 0x2A;
- public static final int ALOAD_1 = 0x2B;
- public static final int ALOAD_2 = 0x2C;
- public static final int ALOAD_3 = 0x2D;
- public static final int IALOAD = 0x2E;
- public static final int LALOAD = 0x2F;
- public static final int FALOAD = 0x30;
- public static final int DALOAD = 0x31;
- public static final int AALOAD = 0x32;
- public static final int BALOAD = 0x33;
- public static final int CALOAD = 0x34;
- public static final int SALOAD = 0x35;
- public static final int ISTORE = 0x36;
- public static final int LSTORE = 0x37;
- public static final int FSTORE = 0x38;
- public static final int DSTORE = 0x39;
- public static final int ASTORE = 0x3A;
- public static final int ISTORE_0 = 0x3B;
- public static final int ISTORE_1 = 0x3C;
- public static final int ISTORE_2 = 0x3D;
- public static final int ISTORE_3 = 0x3E;
- public static final int LSTORE_0 = 0x3F;
- public static final int LSTORE_1 = 0x40;
- public static final int LSTORE_2 = 0x41;
- public static final int LSTORE_3 = 0x42;
- public static final int FSTORE_0 = 0x43;
- public static final int FSTORE_1 = 0x44;
- public static final int FSTORE_2 = 0x45;
- public static final int FSTORE_3 = 0x46;
- public static final int DSTORE_0 = 0x47;
- public static final int DSTORE_1 = 0x48;
- public static final int DSTORE_2 = 0x49;
- public static final int DSTORE_3 = 0x4A;
- public static final int ASTORE_0 = 0x4B;
- public static final int ASTORE_1 = 0x4C;
- public static final int ASTORE_2 = 0x4D;
- public static final int ASTORE_3 = 0x4E;
- public static final int IASTORE = 0x4F;
- public static final int LASTORE = 0x50;
- public static final int FASTORE = 0x51;
- public static final int DASTORE = 0x52;
- public static final int AASTORE = 0x53;
- public static final int BASTORE = 0x54;
- public static final int CASTORE = 0x55;
- public static final int SASTORE = 0x56;
- public static final int POP = 0x57;
- public static final int POP2 = 0x58;
- public static final int DUP = 0x59;
- public static final int DUP_X1 = 0x5A;
- public static final int DUP_X2 = 0x5B;
- public static final int DUP2 = 0x5C;
- public static final int DUP2_X1 = 0x5D;
- public static final int DUP2_X2 = 0x5E;
- public static final int SWAP = 0x5F;
- public static final int IADD = 0x60;
- public static final int LADD = 0x61;
- public static final int FADD = 0x62;
- public static final int DADD = 0x63;
- public static final int ISUB = 0x64;
- public static final int LSUB = 0x65;
- public static final int FSUB = 0x66;
- public static final int DSUB = 0x67;
- public static final int IMUL = 0x68;
- public static final int LMUL = 0x69;
- public static final int FMUL = 0x6A;
- public static final int DMUL = 0x6B;
- public static final int IDIV = 0x6C;
- public static final int LDIV = 0x6D;
- public static final int FDIV = 0x6E;
- public static final int DDIV = 0x6F;
- public static final int IREM = 0x70;
- public static final int LREM = 0x71;
- public static final int FREM = 0x72;
- public static final int DREM = 0x73;
- public static final int INEG = 0x74;
- public static final int LNEG = 0x75;
- public static final int FNEG = 0x76;
- public static final int DNEG = 0x77;
- public static final int ISHL = 0x78;
- public static final int LSHL = 0x79;
- public static final int ISHR = 0x7A;
- public static final int LSHR = 0x7B;
- public static final int IUSHR = 0x7C;
- public static final int LUSHR = 0x7D;
- public static final int IAND = 0x7E;
- public static final int LAND = 0x7F;
- public static final int IOR = 0x80;
- public static final int LOR = 0x81;
- public static final int IXOR = 0x82;
- public static final int LXOR = 0x83;
- public static final int IINC = 0x84;
- public static final int I2L = 0x85;
- public static final int I2F = 0x86;
- public static final int I2L = 0x87;
- public static final int L2I = 0x88;
- public static final int L2F = 0x89;
- public static final int L2D = 0x8A;
- public static final int F2I = 0x8B;
- public static final int F2L = 0x8C;
- public static final int F2D = 0x8D;
- public static final int D2I = 0x8E;
- public static final int D2L = 0x8F;
- public static final int D2F = 0x90;
- public static final int I2B = 0x91;
- public static final int I2C = 0x92;
- public static final int I2S = 0x93;
- public static final int LCMP = 0x94;
- public static final int FCMPL = 0x95;
- public static final int FCMPG = 0x96;
- public static final int DCMPL = 0x97;
- public static final int DCMPG = 0x98;
- public static final int IFEQ = 0x99;
- public static final int IFNE = 0x9A;
- public static final int IFLT = 0x9B;
- public static final int IFGE = 0x9C;
- public static final int IFGT = 0x9D;
- public static final int IFLE = 0x9E;
- public static final int IF_ICMPEQ = 0x9F;
- public static final int IF_ICMPNE = 0xA0;
- public static final int IF_ICMPLT = 0xA1;
- public static final int IF_ICMPGE = 0xA2;
- public static final int IF_ICMPGT = 0xA3;
- public static final int IF_ICMPLE = 0xA4;
- public static final int IF_ACMPEQ = 0xA5;
- public static final int IF_ACMPNE = 0xA6;
- public static final int GOTO = 0xA7;
- public static final int JSR = 0xA8;
- public static final int RET = 0xA9;
- public static final int TABLESWITCH = 0xAA;
- public static final int LOOKUPSWITCH = 0xAB;
- public static final int IRETURN = 0xAC;
- public static final int LRETURN = 0xAD;
- public static final int FRETURN = 0xAE;
- public static final int DRETURN = 0xAF;
- public static final int ARETURN = 0xB0;
- public static final int RETURN = 0xB1;
- public static final int GETSTATIC = 0xB2;
- public static final int PUTSTATIC = 0xB3;
- public static final int GETFIELD = 0xB4;
- public static final int PUTFIELD = 0xB5;
- public static final int INVOKEVIRTUAL = 0xB6;
- public static final int INVOKESPECIAL = 0xB7;
- public static final int INVOKESTATIC = 0xB8;
- public static final int INVOKEINTERFACE = 0xB9;
- public static final int INVOKEDYNAMIC = 0xBA;
- public static final int NEW = 0xBB;
- public static final int NEWARRAY = 0xBC;
- public static final int ANEWARRAY = 0xBD;
- public static final int ARRAYLENGTH = 0xBE;
- public static final int ATHROW = 0xBF;
- public static final int CHECKCAST = 0xC0;
- public static final int INSTANCEOF = 0xC1;
- public static final int MONITORENTER = 0xC2;
- public static final int MONITOREXIT = 0xC3;
- public static final int WIDE = 0xC4;
- public static final int MULTIANEWARRAY = 0xC5;
- public static final int IFNULL = 0xC6;
- public static final int IFNONNULL = 0xC7;
- public static final int GOTO_W = 0xC8;
- public static final int JSR_W = 0xC9;
- public static final int BREAKPOINT = 0xCA;
- public static final int IMPDEP1 = 0xFE;
- public static final int IMPDEP2 = 0xFF;
- public static Instruction get (int opcode) {
- switch (opcode) {
- case NOP:
- return (c, r) -> "";
- case ACONST_NULL:
- return (c, r) -> "VMStack.push(null);\n";
- case ICONST_M1:
- return (c, r) -> "VMStack.push(-1);\n";
- case ICONST_0:
- return (c, r) -> "VMStack.push(0);\n";
- case ICONST_1:
- return (c, r) -> "VMStack.push(1);\n";
- case ICONST_2:
- return (c, r) -> "VMStack.push(2);\n";
- case ICONST_3:
- return (c, r) -> "VMStack.push(3);\n";
- case ICONST_4:
- return (c, r) -> "VMStack.push(4);\n";
- case ICONST_5:
- return (c, r) -> "VMStack.push(5);\n";
- case LCONST_0:
- return (c, r) -> "VMStack.push(0L);\n";
- case LCONST_1:
- return (c, r) -> "VMStack.push(1L);\n";
- case FCONST_0:
- return (c, r) -> "VMStack.push(0F);\n";
- case FCONST_1:
- return (c, r) -> "VMStack.push(1F);\n";
- case FCONST_2:
- return (c, r) -> "VMStack.push(2F);\n";
- case DCONST_0:
- return (c, r) -> "VMStack.push(0D);\n";
- case DCONST_1:
- return (c, r) -> "VMStack.push(1D);\n";
- case BIPUSH:
- return (c, r) -> "VMStack.push((byte) " + r.read() + ");\n";
- case SIPUSH:
- return (c, r) -> "VMStack.push((short) " + (r.read() << 8) | r.read() + ");\n";
- case LDC:
- return (c, r) -> "VMStack.push(" + constants.get(r.read()).toString() + ");\n";
- case LDC_W:
- return (c, r) -> "VMStack.push(" + constants.get((r.read() << 8) | r.read()).toString() + ");\n";
- case LDC2_W:
- return (c, r) -> "VMStack.push(" + constants.get((r.read() << 8) | r.read()).toString() + ");\n";
- case ILOAD:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(" + r.read() + "));\n";
- case LLOAD:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(" + r.read() + "));\n";
- case FLOAD:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(" + r.read() + "));\n";
- case DLOAD:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(" + r.read() + "));\n";
- case ALOAD:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(" + r.read() + "));\n";
- case ILOAD_0:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(0));\n";
- case ILOAD_1:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(1));\n";
- case ILOAD_2:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(2));\n";
- case ILOAD_3:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(3));\n";
- case LLOAD_0:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(0));\n";
- case LLOAD_1:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(1));\n";
- case LLOAD_2:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(2));\n";
- case LLOAD_3:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(3));\n";
- case FLOAD_0:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(0));\n";
- case FLOAD_1:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(1));\n";
- case FLOAD_2:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(2));\n";
- case FLOAD_3:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(3));\n";
- case DLOAD_0:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(0));\n";
- case DLOAD_1:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(1));\n";
- case DLOAD_2:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(2));\n";
- case DLOAD_3:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(3));\n";
- case ALOAD_0:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(0));\n";
- case ALOAD_1:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(1));\n";
- case ALOAD_2:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(2));\n";
- case ALOAD_3:
- return (c, r) -> "VMStack.push(VMLocalVariables.get(3));\n";
- case IALOAD:
- return (c, r) -> "VMStack.push(VMStack.pop()[VMStack.pop()]);\n";
- case LALOAD:
- return (c, r) -> "VMStack.push(VMStack.pop()[VMStack.pop()]);\n";
- case FALOAD:
- return (c, r) -> "VMStack.push(VMStack.pop()[VMStack.pop()]);\n";
- case DALOAD:
- return (c, r) -> "VMStack.push(VMStack.pop()[VMStack.pop()]);\n";
- case AALOAD:
- return (c, r) -> "VMStack.push(VMStack.pop()[VMStack.pop()]);\n";
- case BALOAD:
- return (c, r) -> "VMStack.push(VMStack.pop()[VMStack.pop()]);\n";
- case CALOAD:
- return (c, r) -> "VMStack.push(VMStack.pop()[VMStack.pop()]);\n";
- case SALOAD:
- return (c, r) -> "VMStack.push(VMStack.pop()[VMStack.pop()]);\n";
- case ISTORE:
- return (c, r) -> "VMLocalVariables.set(" + r.read() + ", VMStack.pop());\n";
- case LSTORE:
- return (c, r) -> "VMLocalVariables.set(" + r.read() + ", VMStack.pop());\n";
- case FSTORE:
- return (c, r) -> "VMLocalVariables.set(" + r.read() + ", VMStack.pop());\n";
- case DSTORE:
- return (c, r) -> "VMLocalVariables.set(" + r.read() + ", VMStack.pop());\n";
- case ASTORE:
- return (c, r) -> "VMLocalVariables.set(" + r.read() + ", VMStack.pop());\n";
- case ISTORE_0:
- return (c, r) -> "VMLocalVariables.set(0, VMStack.pop());\n";
- case ISTORE_1:
- return (c, r) -> "VMLocalVariables.set(1, VMStack.pop());\n";
- case ISTORE_2:
- return (c, r) -> "VMLocalVariables.set(2, VMStack.pop());\n";
- case ISTORE_3:
- return (c, r) -> "VMLocalVariables.set(3, VMStack.pop());\n";
- case LSTORE_0:
- return (c, r) -> "VMLocalVariables.set(0, VMStack.pop());\n";
- case LSTORE_1:
- return (c, r) -> "VMLocalVariables.set(1, VMStack.pop());\n";
- case LSTORE_2:
- return (c, r) -> "VMLocalVariables.set(2, VMStack.pop());\n";
- case LSTORE_3:
- return (c, r) -> "VMLocalVariables.set(3, VMStack.pop());\n";
- case FSTORE_0:
- return (c, r) -> "VMLocalVariables.set(0, VMStack.pop());\n";
- case FSTORE_1:
- return (c, r) -> "VMLocalVariables.set(1, VMStack.pop());\n";
- case FSTORE_2:
- return (c, r) -> "VMLocalVariables.set(2, VMStack.pop());\n";
- case FSTORE_3:
- return (c, r) -> "VMLocalVariables.set(3, VMStack.pop());\n";
- case DSTORE_0:
- return (c, r) -> "VMLocalVariables.set(0, VMStack.pop());\n";
- case DSTORE_1:
- return (c, r) -> "VMLocalVariables.set(1, VMStack.pop());\n";
- case DSTORE_2:
- return (c, r) -> "VMLocalVariables.set(2, VMStack.pop());\n";
- case DSTORE_3:
- return (c, r) -> "VMLocalVariables.set(3, VMStack.pop());\n";
- case ASTORE_0:
- return (c, r) -> "VMLocalVariables.set(0, VMStack.pop());\n";
- case ASTORE_1:
- return (c, r) -> "VMLocalVariables.set(1, VMStack.pop());\n";
- case ASTORE_2:
- return (c, r) -> "VMLocalVariables.set(2, VMStack.pop());\n";
- case ASTORE_3:
- return (c, r) -> "VMLocalVariables.set(3, VMStack.pop());\n";
- case IASTORE:
- return (c, r) -> "VMStack.pop()[VMStack.pop()] = VMStack.pop();\n";
- case LASTORE:
- return (c, r) -> "VMStack.pop()[VMStack.pop()] = VMStack.pop();\n";
- case FASTORE:
- return (c, r) -> "VMStack.pop()[VMStack.pop()] = VMStack.pop();\n";
- case DASTORE:
- return (c, r) -> "VMStack.pop()[VMStack.pop()] = VMStack.pop();\n";
- case AASTORE:
- return (c, r) -> "VMStack.pop()[VMStack.pop()] = VMStack.pop();\n";
- case BASTORE:
- return (c, r) -> "VMStack.pop()[VMStack.pop()] = VMStack.pop();\n";
- case CASTORE:
- return (c, r) -> "VMStack.pop()[VMStack.pop()] = VMStack.pop();\n";
- case SASTORE:
- return (c, r) -> "VMStack.pop()[VMStack.pop()] = VMStack.pop();\n";
- case POP:
- return (c, r) -> "VMStack.pop();\n";
- case POP2:
- return (c, r) -> "VMStack.pop();\nVMStack.pop();\n";
- case DUP:
- return (c, r) -> "VMStack.Value val = VMStack.pop();\nVMStack.push(val);\nVMStack.push(val);\n";
- case DUP_X1:
- return (c, r) -> "VMStack.Value top = VMStack.pop();\nVMStack.Value next = VMStack.pop();\nVMStack.push(top);\nVMStack.push(next);\nVMStack.push(top);\n";
- case DUP_X2:
- return (c, r) -> "VMStack.Value top = VMStack.pop();\nVMStack.Value next = VMStack.pop();\nVMStack.Value next2 = VMStack.pop();\nVMStack.push(top);\nVMStack.push(next2);\nVMStack.push(next);\nVMStack.push(top);\n";
- case DUP2:
- return (c, r) -> "VMStack.Value top = VMStack.pop();\nVMStack.Value next = VMStack.pop();\nVMStack.push(next);\nVMStack.push(top);\nVMStack.push(next);\nVMStack.push(top);\n";
- case DUP2_X1:
- return (c, r) -> "VMStack.Value top = VMStack.pop();\nVMStack.Value next = VMStack.pop();\nVMStack.Value next2 = VMStack.pop();\nVMStack.push(next);\nVMStack.push(top);\nVMStack.push(next2);\nVMStack.push(next);\nVMStack.push(top);\n";
- case DUP2_X2:
- return (c, r) -> "VMStack.Value top = VMStack.pop();\nVMStack.Value next = VMStack.pop();\nVMStack.Value next2 = VMStack.pop();\nVMStack.Value next3 = VMStack.pop();\nVMStack.push(next);\nVMStack.push(top);\nVMStack.push(next3);\nVMStack.push(next2);\nVMStack.push(next);\nVMStack.push(top);\n";
- case SWAP:
- return (c, r) -> "VMStack.Value top = VMStack.pop();\nVMStack.Value next = VMStack.pop();\nVMStack.push(top);\nVMStack.push(next);\n";
- case IADD:
- return (c, r) -> "VMStack.push(VMStack.pop() + VMStack.pop());\n";
- case LADD:
- return (c, r) -> "VMStack.push(VMStack.pop() + VMStack.pop());\n";
- case FADD:
- return (c, r) -> "VMStack.push(VMStack.pop() + VMStack.pop());\n";
- case DADD:
- return (c, r) -> "VMStack.push(VMStack.pop() + VMStack.pop());\n";
- case ISUB:
- return (c, r) -> "VMStack.push(VMStack.pop() - VMStack.pop());\n";
- case LSUB:
- return (c, r) -> "VMStack.push(VMStack.pop() - VMStack.pop());\n";
- case FSUB:
- return (c, r) -> "VMStack.push(VMStack.pop() - VMStack.pop());\n";
- case DSUB:
- return (c, r) -> "VMStack.push(VMStack.pop() - VMStack.pop());\n";
- case IMUL:
- return (c, r) -> "VMStack.push(VMStack.pop() * VMStack.pop());\n";
- case LMUL:
- return (c, r) -> "VMStack.push(VMStack.pop() * VMStack.pop());\n";
- case FMUL:
- return (c, r) -> "VMStack.push(VMStack.pop() * VMStack.pop());\n";
- case DMUL:
- return (c, r) -> "VMStack.push(VMStack.pop() * VMStack.pop());\n";
- case IDIV:
- return (c, r) -> "VMStack.push(VMStack.pop() / VMStack.pop());\n";
- case LDIV:
- return (c, r) -> "VMStack.push(VMStack.pop() / VMStack.pop());\n";
- case FDIV:
- return (c, r) -> "VMStack.push(VMStack.pop() / VMStack.pop());\n";
- case DDIV:
- return (c, r) -> "VMStack.push(VMStack.pop() / VMStack.pop());\n";
- case IREM:
- return (c, r) -> "VMStack.push(VMStack.pop() % VMStack.pop());\n";
- case LREM:
- return (c, r) -> "VMStack.push(VMStack.pop() % VMStack.pop());\n";
- case FREM:
- return (c, r) -> "VMStack.push(VMStack.pop() % VMStack.pop());\n";
- case DREM:
- return (c, r) -> "VMStack.push(VMStack.pop() % VMStack.pop());\n";
- case INEG:
- return (c, r) -> "VMStack.push(-VMStack.pop());\n";
- case LNEG:
- return (c, r) -> "VMStack.push(-VMStack.pop());\n";
- case FNEG:
- return (c, r) -> "VMStack.push(-VMStack.pop());\n";
- case DNEG:
- return (c, r) -> "VMStack.push(-VMStack.pop());\n";
- case ISHL:
- return (c, r) -> "VMStack.push(VMStack.pop() << VMStack.pop());\n";
- case LSHL:
- return (c, r) -> "VMStack.push(VMStack.pop() << VMStack.pop());\n";
- case ISHR:
- return (c, r) -> "VMStack.push(VMStack.pop() >> VMStack.pop());\n";
- case LSHR:
- return (c, r) -> "VMStack.push(VMStack.pop() >> VMStack.pop());\n";
- case IUSHR:
- return (c, r) -> "VMStack.push(VMStack.pop() >>> VMStack.pop());\n";
- case LUSHR:
- return (c, r) -> "VMStack.push(VMStack.pop() >>> VMStack.pop());\n";
- case IAND:
- return (c, r) -> "VMStack.push(VMStack.pop() & VMStack.pop());\n";
- case LAND:
- return (c, r) -> "VMStack.push(VMStack.pop() & VMStack.pop());\n";
- case IOR:
- return (c, r) -> "VMStack.push(VMStack.pop() | VMStack.pop());\n";
- case LOR:
- return (c, r) -> "VMStack.push(VMStack.pop() | VMStack.pop());\n";
- case IXOR:
- return (c, r) -> "VMStack.push(VMStack.pop() ^ VMStack.pop());\n";
- case LXOR:
- return (c, r) -> "VMStack.push(VMStack.pop() ^ VMStack.pop());\n";
- case IINC:
- return (c, r) -> "VMLocalVariables.set(" + r.read() + ", VMLocalVariables.get(" + r.read() + ") + 1);\n";
- case I2L:
- return (c, r) -> "VMStack.cast(long.class);\n";
- case I2F:
- return (c, r) -> "VMStack.cast(float.class);\n";
- case I2D:
- return (c, r) -> "VMStack.cast(double.class);\n";
- case L2I:
- return (c, r) -> "VMStack.cast(long.class);\n";
- case L2F:
- return (c, r) -> "VMStack.cast(float.class);\n";
- case L2D:
- return (c, r) -> "VMStack.cast(double.class);\n";
- case F2I:
- return (c, r) -> "VMStack.cast(long.class);\n";
- case F2L:
- return (c, r) -> "VMStack.cast(float.class);\n";
- case F2D:
- return (c, r) -> "VMStack.cast(double.class);\n";
- case D2I:
- return (c, r) -> "VMStack.cast(long.class);\n";
- case D2L:
- return (c, r) -> "VMStack.cast(float.class);\n";
- case D2F:
- return (c, r) -> "VMStack.cast(double.class);\n";
- case I2B:
- return (c, r) -> "VMStack.cast(byte.class);\n";
- case I2C:
- return (c, r) -> "VMStack.cast(char.class);\n";
- case I2S:
- return (c, r) -> "VMStack.cast(short.class);\n";
- case LCMP:
- return (c, r) -> "VMStack.push(Long.compare(VMStack.pop(), VMStack.pop()));\n";
- case FCMPL:
- return (c, r) -> "float f1 = VMStack.pop();\nfloat f2 = VMStack.pop();\nVMStack.push(Float.compare(f1 == Float.NAN ? -1F : f1, f2 == Float.NAN ? -1F : f2));\n";
- case FCMPG:
- return (c, r) -> "float f1 = VMStack.pop();\nfloat f2 = VMStack.pop();\nVMStack.push(Float.compare(f1 == Float.NAN ? 1F : f1, f2 == Float.NAN ? 1F : f2));\n";
- case DCMPL:
- return (c, r) -> "double d1 = VMStack.pop();\ndouble d2 = VMStack.pop();\nVMStack.push(Double.compare(d1 == Double.NAN ? -1D : d1, d2 == Double.NAN ? -1D : d2));\n";
- case DCMPG:
- return (c, r) -> "double d1 = VMStack.pop();\ndouble d2 = VMStack.pop();\nVMStack.push(Double.compare(d1 == Double.NAN ? 1D : d1, d2 == Double.NAN ? 1D : d2));\n";
- case IFEQ:
- return (c, r) -> "if (VMStack.pop() == 0) {\nVirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n}\n";
- case IFNE:
- return (c, r) -> "if (VMStack.pop() != 0) {\nVirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n}\n";
- case IFLT:
- return (c, r) -> "if (VMStack.pop() < 0) {\nVirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n}\n";
- case IFGE:
- return (c, r) -> "if (VMStack.pop() >= 0) {\nVirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n}\n";
- case IFGT:
- return (c, r) -> "if (VMStack.pop() > 0) {\nVirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n}\n";
- case IFLE:
- return (c, r) -> "if (VMStack.pop() <= 0) {\nVirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n}\n";
- case IF_ICMPEQ:
- return (c, r) -> "if (VMStack.pop() == 0) {\nVirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n}\n";
- case IF_ICMPNE:
- return (c, r) -> return "if (VMStack.pop() != 0) {\nVirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n}\n";
- case IF_ICMPLT:
- return (c, r) -> "if (VMStack.pop() < 0) {\nVirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n}\n";
- case IF_ICMPGE:
- return (c, r) -> "if (VMStack.pop() >= 0) {\nVirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n}\n";
- case IF_ICMPGT:
- return (c, r) -> "if (VMStack.pop() > 0) {\nVirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n}\n";
- case IF_ICMPLE:
- return (c, r) -> "if (VMStack.pop() <= 0) {\nVirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n}\n";
- case IF_ACMPEQ:
- return (c, r) -> "if (VMStack.pop() == VMStack.pop()) {\nVirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n}\n";
- case IF_ACMPNE:
- return (c, r) -> "if (VMStack.pop() != VMStack.pop()) {\nVirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n}\n";
- case GOTO:
- return (c, r) -> return "VirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n";
- case JSR:
- return (c, r) -> "VMStack.push(VirtualMachine.programCounter);\nVirtualMachine.jumpTo(" + (r.read() << 8) | r.read() + ");\n$$StringFormSoftStopNotifier;\n";
- case RTS:
- return (c, r) -> "VirtualMachine.jumpTo(VMLocalVariables.get(" + r.read() + "));\n$$StringFormSoftStopNotifier;\n";
- case TABLESWITCH:
- return (c, r) -> {
- byte[] data = new byte[12];
- int read;
- while ((read = r.read()) == 0) {}
- data[0] = (byte)read;
- for (int i = 0; i <= 10; i++)
- data[i + 1] = (byte)r.read();
- int defaultValue = ((data[0] << 24) | (data[1] << 16)) | ((data[2] << 8) | data[3]);
- int lowLength = ((data[4] << 24) | (data[5] << 16)) | ((data[6] << 8) | data[7]);
- int highLength = ((data[8] << 24) | (data[9] << 16)) | ((data[10] << 8) | data[11]);
- int jumpLength = highLength - lowLength + 1;
- int[] jumpTable = new int[jumpLength];
- for (int i = 0; i <= jumpLength; i++)
- jumpTable[i] = ((r.read() << 24) | (r.read() << 16)) | ((r.read() << 8) | r.read());
- return "int[] jumpTable = " + Arrays.toString(jumpTable).replaceAll("[", "{").replaceAll("]", "}") + ";\nVirtualMachine.jumpTo(jumpTable[VMStack.pop()]);\n$$StringFormSoftStopNotifier;\n";
- }
- case LOOKUPSWITCH:
- return (c, r) -> {
- byte[] data = new byte[12];
- int read;
- while ((read = r.read()) == 0) {}
- data[0] = (byte)read;
- for (int i = 0; i <= 10; i++)
- data[i + 1] = (byte)r.read();
- int pairLength = ((data[4] << 24) | (data[5] << 16)) | ((data[6] << 8) | data[7]);
- int[] keys = new int[pairLength];
- Arrays.fill(keys, 0);
- int[] values = new int[pairLength];
- for (int i = 0; i <= pairLength; i++) {
- keys[((r.read() << 24) | (r.read() << 16)) | ((r.read() << 8) | r.read())] = i;
- values[i] = ((r.read() << 24) | (r.read() << 16)) | ((r.read() << 8) | r.read());
- }
- return "int[] keys = " + Arrays.toString(keys).replaceAll("[", "{").replaceAll("]", "}") + ";\nint[] values = " + Arrays.toString(values).replaceAll("[", "{").replaceAll("]", "}") + ";\nVirtualMachine.jumpTo(values[keys[VMStack.pop()]]);\n$$StringFormSoftStopNotifier;\n";
- }
- case IRETURN:
- return (c, r) -> "return VMStack.pop();\n$$StringFormHardStopNotifier;\n";
- case LRETURN:
- return (c, r) -> "return VMStack.pop();\n$$StringFormHardStopNotifier;\n";
- case FRETURN:
- return (c, r) -> "return VMStack.pop();\n$$StringFormHardStopNotifier;\n";
- case DRETURN:
- return (c, r) -> "return VMStack.pop();\n$$StringFormHardStopNotifier;\n";
- case ARETURN:
- return (c, r) -> "return VMStack.pop();\n$$StringFormHardStopNotifier;\n";
- case RETURN:
- return (c, r) -> "return;\n$$StringFormHardStopNotifier;\n";
- case GETSTATIC:
- return (c, r) -> {
- FieldReference ref = ((FieldReference)c.get((r.read() << 8) | r.read()).get(c));
- return "VMStack.push(" + ref.getClass().toString() + "." + ref.getNameAndType().getName() + ");\n";
- }
- case PUTSTATIC:
- return (c, r) -> {
- FieldReference ref = ((FieldReference)constants.get((r.read() << 8) | r.read()).get(c));
- return ref.getClass().toString() + "." + ref.getNameAndType().getName() + " = VMStack.pop();\n";
- }
- case GETFIELD:
- return (c, r) -> {
- FieldReference ref = ((FieldReference)c.get((r.read() << 8) | r.read()).get(c));
- return "VMStack.push(VMStack.pop()." + ref.getNameAndType().getName() + ");\n";
- }
- case PUTFIELD:
- return (c, r) -> {
- FieldReference ref = ((FieldReference)c.get((r.read() << 8) | r.read()).get(c));
- return "VMStack.pop()." + ref.getNameAndType().getName() + " = VMStack.pop();\n";
- }
- case INVOKEVIRTUAL:
- return (c, r) -> {
- MethodReference ref = ((MethodReference)c.get((r.read() << 8) | r.read()).get(c));
- return "VMStack.push(VMStack.pop()." + ref.getNameAndType().getName() + "());\n";
- }
- case INVOKESPECIAL:
- return (c, r) -> {
- MethodReference ref = ((MethodReference)c.get((r.read() << 8) | r.read()).get(c));
- return "VMStack.push(new " + ref.getClass().toString() + "());\n";
- }
- case INVOKESTATIC:
- return (c, r) -> {
- MethodReference ref = ((MethodReference)c.get((r.read() << 8) | r.read()).get(c));
- return "VMStack.push(" + ref.getClass().toString() + "." + ref.getNameAndType().getName() + "());\n";
- }
- case INVOKEINTERFACE:
- return (c, r) -> {
- AbstractMethodReference ref = ((AbstractMethodReference)c.get((r.read() << 8) | r.read()));
- return "VMStack.push(VMStack.pop()." + ref.getNameAndType().getName() + "());\n";
- }
- case INVOKEDYNAMIC:
- return (c, r) -> {
- MethodReference ref = ((MethodReference)constants.get((r.read() << 8) | r.read()));
- return "VMStack.push(VMStack.pop()." + ref.getNameAndType().getName() + "());\n";
- }
- case NEW:
- return (c, r) -> {
- r.skip(2);
- return "";
- }
- case NEWARRAY:
- return (c, r) -> {
- String type;
- switch (r.read()) {
- case 4:
- type = "boolean";
- break;
- case 5:
- type = "char";
- break;
- case 6:
- type = "float";
- break;
- case 7:
- type = "double";
- break;
- case 8:
- type = "byte";
- break;
- case 9:
- type = "short";
- break;
- case 10:
- type = "int";
- break;
- case 11:
- type = "long";
- break;
- }
- return "VMStack.push(new " + type + "[VMStack.pop()]);\n";
- }
- case ANEWARRAY:
- return (c, r) -> {
- return "VMStack.push(new " + ((ClassReference)constants.get((r.read() << 8) | r.read())).toString() + "[VMStack.pop()]);\n";
- }
- case ARRAYLENGTH:
- return (c, r) -> "VMStack.push(VMStack.pop().length);\n";
- case ATHROW:
- return (c, r) -> "throw VMStack.pop();\n$$StringFormHardStopNotifier;\n";
- case CHECKCAST:
- return (c, r) -> "VMStack.cast(" + ((ClassReference)constants.get((r.read() << 8) | r.read())).toString() + ".class);\n";
- case INSTANCEOF:
- return (c, r) -> "VMStack.push(VMStack.pop() instanceof " + ((ClassReference)constants.get((r.read() << 8) | r.read())).toString() + ");\n";
- case MONITORENTER:
- return (c, r) -> "";
- case MONITOREXIT:
- return (c, r) -> "";
- case WIDE:
- return (c, r) -> return get(r.read()).toString(i, c, a, r);
- case MULTIANEWARRAY:
- return (c, r) -> {
- String s = "VMStack.push(new " + ((ClassReference)constants.get((r.read() << 8) | r.read())).toString();
- for (int i = 0; i <= r.read(); i++)
- s = s.concat("[VMStack.pop()]");
- return s.concat(");\n");
- }
- case IFNULL:
- return (c, r) -> "if (VMStack.pop() == null) {\nVirtualMachine.jumpTo(" + ((r.read() << 24) | (r.read() << 16)) | (r.read() << 8) | r.read())) + ");\n$$StringFormSoftStopNotifier;\n}\n";
- case IFNONNULL:
- return (c, r) -> "if (VMStack.pop() != null) {\nVirtualMachine.jumpTo(" + ((r.read() << 24) | (r.read() << 16)) | ((r.read() << 8) | r.read())) + ";\n$$StringFormSoftStopNotifier;\n}\n";
- case GOTO_W:
- return (c, r) -> "VirtualMachine.jumpTo(" + ((r.read() << 24) | (r.read() << 16)) | (r.read() << 8) | r.read())) + ";\n$$StringFormSoftStopNotifier;\n";
- case JSR_W:
- return (c, r) -> {
- r.skip(4);
- return "";
- }
- case BREAKPOINT:
- return (c, r) -> "";
- case IMPDEP1:
- return (c, r) -> "";
- case IMPDEP2:
- return (c, r) -> "";
- default:
- return (c, r) -> "";
- }
- }
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement