List of usage examples for org.objectweb.asm.tree InsnList InsnList
InsnList
From source file:org.apache.commons.javaflow.providers.asm3.ContinuableMethodNode.java
License:Apache License
void moveNew() throws AnalyzerException { final SourceInterpreter i = new SourceInterpreter(); final Analyzer a = new Analyzer(i); a.analyze(className, this); final HashMap<AbstractInsnNode, MethodInsnNode> movable = new HashMap<AbstractInsnNode, MethodInsnNode>(); final Frame[] frames = a.getFrames(); for (int j = 0; j < methods.size(); j++) { final MethodInsnNode mnode = (MethodInsnNode) methods.get(j); // require to move NEW instruction int n = instructions.indexOf(mnode); Frame f = frames[n];// ww w . j a v a2s. c o m Type[] args = Type.getArgumentTypes(mnode.desc); SourceValue v = (SourceValue) f.getStack(f.getStackSize() - args.length - 1); @SuppressWarnings("unchecked") Set<AbstractInsnNode> insns = v.insns; for (final AbstractInsnNode ins : insns) { if (ins.getOpcode() == NEW) { movable.put(ins, mnode); } else { // other known patterns int n1 = instructions.indexOf(ins); if (ins.getOpcode() == DUP) { // <init> with params AbstractInsnNode ins1 = instructions.get(n1 - 1); if (ins1.getOpcode() == NEW) { movable.put(ins1, mnode); } } else if (ins.getOpcode() == SWAP) { // in exception handler AbstractInsnNode ins1 = instructions.get(n1 - 1); AbstractInsnNode ins2 = instructions.get(n1 - 2); if (ins1.getOpcode() == DUP_X1 && ins2.getOpcode() == NEW) { movable.put(ins2, mnode); } } } } } int updateMaxStack = 0; for (final Map.Entry<AbstractInsnNode, MethodInsnNode> e : movable.entrySet()) { AbstractInsnNode node1 = e.getKey(); int n1 = instructions.indexOf(node1); AbstractInsnNode node2 = instructions.get(n1 + 1); AbstractInsnNode node3 = instructions.get(n1 + 2); int producer = node2.getOpcode(); instructions.remove(node1); // NEW boolean requireDup = false; if (producer == DUP) { instructions.remove(node2); // DUP requireDup = true; } else if (producer == DUP_X1) { instructions.remove(node2); // DUP_X1 instructions.remove(node3); // SWAP requireDup = true; } MethodInsnNode mnode = (MethodInsnNode) e.getValue(); AbstractInsnNode nm = mnode; int varOffset = stackRecorderVar + 1; Type[] args = Type.getArgumentTypes(mnode.desc); // optimizations for some common cases if (args.length == 0) { final InsnList doNew = new InsnList(); doNew.add(node1); // NEW if (requireDup) doNew.add(new InsnNode(DUP)); instructions.insertBefore(nm, doNew); nm = doNew.getLast(); continue; } if (args.length == 1 && args[0].getSize() == 1) { final InsnList doNew = new InsnList(); doNew.add(node1); // NEW if (requireDup) { doNew.add(new InsnNode(DUP)); doNew.add(new InsnNode(DUP2_X1)); doNew.add(new InsnNode(POP2)); updateMaxStack = updateMaxStack < 2 ? 2 : updateMaxStack; // a two extra slots for temp values } else doNew.add(new InsnNode(SWAP)); instructions.insertBefore(nm, doNew); nm = doNew.getLast(); continue; } // TODO this one untested! if ((args.length == 1 && args[0].getSize() == 2) || (args.length == 2 && args[0].getSize() == 1 && args[1].getSize() == 1)) { final InsnList doNew = new InsnList(); doNew.add(node1); // NEW if (requireDup) { doNew.add(new InsnNode(DUP)); doNew.add(new InsnNode(DUP2_X2)); doNew.add(new InsnNode(POP2)); updateMaxStack = updateMaxStack < 2 ? 2 : updateMaxStack; // a two extra slots for temp values } else { doNew.add(new InsnNode(DUP_X2)); doNew.add(new InsnNode(POP)); updateMaxStack = updateMaxStack < 1 ? 1 : updateMaxStack; // an extra slot for temp value } instructions.insertBefore(nm, doNew); nm = doNew.getLast(); continue; } final InsnList doNew = new InsnList(); // generic code using temporary locals // save stack for (int j = args.length - 1; j >= 0; j--) { Type type = args[j]; doNew.add(new VarInsnNode(type.getOpcode(ISTORE), varOffset)); varOffset += type.getSize(); } if (varOffset > maxLocals) { maxLocals = varOffset; } doNew.add(node1); // NEW if (requireDup) doNew.add(new InsnNode(DUP)); // restore stack for (int j = 0; j < args.length; j++) { Type type = args[j]; varOffset -= type.getSize(); doNew.add(new VarInsnNode(type.getOpcode(ILOAD), varOffset)); // clean up store to avoid memory leak? if (type.getSort() == Type.OBJECT || type.getSort() == Type.ARRAY) { updateMaxStack = updateMaxStack < 1 ? 1 : updateMaxStack; // an extra slot for ACONST_NULL doNew.add(new InsnNode(ACONST_NULL)); doNew.add(new VarInsnNode(type.getOpcode(ISTORE), varOffset)); } } instructions.insertBefore(nm, doNew); nm = doNew.getLast(); } maxStack += updateMaxStack; }
From source file:org.blockartistry.DynSurround.asm.Transformer.java
License:MIT License
private byte[] transformEntityRenderer(final byte[] classBytes) { final String names[] = { "func_78484_h", "addRainParticles" }; final String targetName = "addRainParticles"; final ClassReader cr = new ClassReader(classBytes); final ClassNode cn = new ClassNode(ASM5); cr.accept(cn, 0);/*from ww w . j ava 2 s. c om*/ for (final MethodNode m : cn.methods) { if (isOneOf(m.name, names)) { logger.debug("Hooking " + m.name); final InsnList list = new InsnList(); list.add(new VarInsnNode(ALOAD, 0)); final String sig = "(Lnet/minecraft/client/renderer/EntityRenderer;)V"; list.add(new MethodInsnNode(INVOKESTATIC, "org/blockartistry/DynSurround/client/weather/RenderWeather", targetName, sig, false)); list.add(new InsnNode(RETURN)); m.instructions.insertBefore(m.instructions.getFirst(), list); } } final ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS); cn.accept(cw); return cw.toByteArray(); }
From source file:org.blockartistry.DynSurround.asm.Transformer.java
License:MIT License
private byte[] transformWorldServer(final byte[] classBytes) { final String names[] = { "func_73051_P", "resetRainAndThunder" }; final String targetName = "resetRainAndThunder"; final ClassReader cr = new ClassReader(classBytes); final ClassNode cn = new ClassNode(ASM5); cr.accept(cn, 0);/*from w w w . j a va 2s . c o m*/ for (final MethodNode m : cn.methods) { if (isOneOf(m.name, names)) { logger.debug("Hooking " + m.name); InsnList list = new InsnList(); list.add(new VarInsnNode(ALOAD, 0)); final String sig = "(Lnet/minecraft/world/WorldServer;)V"; list.add(new MethodInsnNode(INVOKESTATIC, "org/blockartistry/DynSurround/server/PlayerSleepHandler", targetName, sig, false)); list.add(new InsnNode(RETURN)); m.instructions.insertBefore(m.instructions.getFirst(), list); break; } } final ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS); cn.accept(cw); return cw.toByteArray(); }
From source file:org.blockartistry.mod.DynSurround.asm.Transformer.java
License:MIT License
private byte[] transformEntityRenderer(final byte[] classBytes) { final String names[]; if (TransformLoader.runtimeDeobEnabled) names = new String[] { "func_78474_d", "func_78484_h" }; else//from w w w .j a v a 2 s. co m names = new String[] { "renderRainSnow", "addRainParticles" }; final String targetName[] = new String[] { "renderRainSnow", "addRainParticles" }; final ClassReader cr = new ClassReader(classBytes); final ClassNode cn = new ClassNode(ASM5); cr.accept(cn, 0); for (final MethodNode m : cn.methods) { if (m.name.equals(names[0])) { logger.debug("Hooking " + names[0]); final InsnList list = new InsnList(); list.add(new VarInsnNode(ALOAD, 0)); list.add(new VarInsnNode(FLOAD, 1)); final String sig = "(Lnet/minecraft/client/renderer/EntityRenderer;F)V"; list.add(new MethodInsnNode(INVOKESTATIC, "org/blockartistry/mod/DynSurround/client/RenderWeather", targetName[0], sig, false)); list.add(new InsnNode(RETURN)); m.instructions.insertBefore(m.instructions.getFirst(), list); } else if (m.name.equals(names[1])) { logger.debug("Hooking " + names[1]); final InsnList list = new InsnList(); list.add(new VarInsnNode(ALOAD, 0)); final String sig = "(Lnet/minecraft/client/renderer/EntityRenderer;)V"; list.add(new MethodInsnNode(INVOKESTATIC, "org/blockartistry/mod/DynSurround/client/RenderWeather", targetName[1], sig, false)); list.add(new InsnNode(RETURN)); m.instructions.insertBefore(m.instructions.getFirst(), list); } } final ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS); cn.accept(cw); return cw.toByteArray(); }
From source file:org.blockartistry.mod.DynSurround.asm.Transformer.java
License:MIT License
private byte[] transformWorldServer(final byte[] classBytes) { final String names[]; if (TransformLoader.runtimeDeobEnabled) names = new String[] { "func_73051_P" }; else// www. j av a 2s . co m names = new String[] { "resetRainAndThunder" }; final String targetName[] = new String[] { "resetRainAndThunder" }; final ClassReader cr = new ClassReader(classBytes); final ClassNode cn = new ClassNode(ASM5); cr.accept(cn, 0); for (final MethodNode m : cn.methods) { if (m.name.equals(names[0])) { logger.debug("Hooking " + names[0]); InsnList list = new InsnList(); list.add(new VarInsnNode(ALOAD, 0)); final String sig = "(Lnet/minecraft/world/WorldServer;)V"; list.add(new MethodInsnNode(INVOKESTATIC, "org/blockartistry/mod/DynSurround/server/PlayerSleepHandler", targetName[0], sig, false)); list.add(new InsnNode(RETURN)); m.instructions.insertBefore(m.instructions.getFirst(), list); break; } } final ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS); cn.accept(cw); return cw.toByteArray(); }
From source file:org.blockartistry.mod.DynSurround.asm.Transformer.java
License:MIT License
private byte[] transformWorld(final byte[] classBytes) { final String names[]; if (TransformLoader.runtimeDeobEnabled) names = new String[] { "updateWeatherBody", "func_72896_J", "func_72911_I" }; else/*from www.j ava 2 s .c om*/ names = new String[] { "updateWeatherBody", "isRaining", "isThundering" }; final String targetName[] = new String[] { "updateWeatherBody", "isRaining", "isThundering" }; final ClassReader cr = new ClassReader(classBytes); final ClassNode cn = new ClassNode(ASM5); cr.accept(cn, 0); for (final MethodNode m : cn.methods) { int idx = -1; if (m.name.equals(names[0])) idx = 0; else if (m.name.equals(names[1])) idx = 1; else if (m.name.equals(names[2])) idx = 2; else continue; logger.debug("Hooking " + names[idx]); InsnList list = new InsnList(); list.add(new VarInsnNode(ALOAD, 0)); final String sig; if (idx == 0) sig = "(Lnet/minecraft/world/World;)V"; else sig = "(Lnet/minecraft/world/World;)Z"; list.add(new MethodInsnNode(INVOKESTATIC, "org/blockartistry/mod/DynSurround/server/WorldHandler", targetName[idx], sig, false)); if (idx == 0) list.add(new InsnNode(RETURN)); else list.add(new InsnNode(IRETURN)); m.instructions.insertBefore(m.instructions.getFirst(), list); } final ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS); cn.accept(cw); return cw.toByteArray(); }
From source file:org.blockartistry.mod.DynSurround.asm.Transformer.java
License:MIT License
private byte[] transformSoundManager(final byte[] classBytes) { final String names[]; if (TransformLoader.runtimeDeobEnabled) names = new String[] { "func_188770_e" }; else//from ww w. ja v a2 s .co m names = new String[] { "getClampedVolume" }; final String targetName[] = new String[] { "getClampedVolume" }; final ClassReader cr = new ClassReader(classBytes); final ClassNode cn = new ClassNode(ASM5); cr.accept(cn, 0); for (final MethodNode m : cn.methods) { if (m.name.equals(names[0])) { logger.debug("Hooking " + names[0]); final InsnList list = new InsnList(); list.add(new VarInsnNode(ALOAD, 1)); final String sig = "(Lnet/minecraft/client/audio/ISound;)F"; list.add(new MethodInsnNode(INVOKESTATIC, "org/blockartistry/mod/DynSurround/client/sound/SoundManager", targetName[0], sig, false)); list.add(new InsnNode(FRETURN)); m.instructions.insertBefore(m.instructions.getFirst(), list); break; } } final ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS); cn.accept(cw); return cw.toByteArray(); }
From source file:org.brutusin.instrumentation.Instrumentator.java
License:Apache License
private void addTraceStart() { InsnList il = new InsnList(); int methodParametersIndex = addMethodParametersVariable(il); addGetMethodInvocation(il);//from www .j a v a2s .co m addStoreMethod(il); addGetCallback(il); il.add(new VarInsnNode(Opcodes.ALOAD, this.methodVarIndex)); il.add(new VarInsnNode(Opcodes.ALOAD, methodParametersIndex)); il.add(new MethodInsnNode(Opcodes.INVOKEVIRTUAL, "org/brutusin/instrumentation/Callback", "onStart", "(Ljava/lang/Object;[Ljava/lang/Object;)Ljava/lang/String;", false)); this.executionIdIndex = getFistAvailablePosition(); il.add(new VarInsnNode(Opcodes.ASTORE, this.executionIdIndex)); this.mn.maxLocals++; this.startNode = new LabelNode(); this.mn.instructions.insert(startNode); this.mn.instructions.insert(il); }
From source file:org.brutusin.instrumentation.Instrumentator.java
License:Apache License
private void addCatchBlock(LabelNode startNode, LabelNode endNode) { InsnList il = new InsnList(); LabelNode handlerNode = new LabelNode(); il.add(handlerNode);// w w w.j av a2 s.c om int exceptionVariablePosition = getFistAvailablePosition(); il.add(new VarInsnNode(Opcodes.ASTORE, exceptionVariablePosition)); this.methodOffset++; // Actualizamos el offset addGetCallback(il); il.add(new VarInsnNode(Opcodes.ALOAD, this.methodVarIndex)); il.add(new VarInsnNode(Opcodes.ALOAD, exceptionVariablePosition)); il.add(new VarInsnNode(Opcodes.ALOAD, this.executionIdIndex)); il.add(new MethodInsnNode(Opcodes.INVOKEVIRTUAL, "org/brutusin/instrumentation/Callback", "onThrowableUncatched", "(Ljava/lang/Object;Ljava/lang/Throwable;Ljava/lang/String;)V", false)); il.add(new VarInsnNode(Opcodes.ALOAD, exceptionVariablePosition)); il.add(new InsnNode(Opcodes.ATHROW)); TryCatchBlockNode blockNode = new TryCatchBlockNode(startNode, endNode, handlerNode, null); this.mn.tryCatchBlocks.add(blockNode); this.mn.instructions.add(il); }
From source file:org.brutusin.instrumentation.Instrumentator.java
License:Apache License
private InsnList getVoidReturnTraceInstructions() { InsnList il = new InsnList(); addGetCallback(il);/*from www. j a v a 2 s . c o m*/ il.add(new VarInsnNode(Opcodes.ALOAD, this.methodVarIndex)); il.add(new VarInsnNode(Opcodes.ALOAD, this.executionIdIndex)); il.add(new MethodInsnNode(Opcodes.INVOKEVIRTUAL, "org/brutusin/instrumentation/Callback", "onVoidFinish", "(Ljava/lang/Object;Ljava/lang/String;)V", false)); return il; }