List of usage examples for org.objectweb.asm.tree AbstractInsnNode getPrevious
public AbstractInsnNode getPrevious()
From source file:jaspex.speculation.newspec.FlowFrame.java
License:Open Source License
/** Obtm label antes da instruco. Se j existir uma, reutilizada, cc uma nova criada. **/ public static LabelNode labelBefore(InsnList il, AbstractInsnNode insn) { if (!(insn.getPrevious() instanceof LabelNode)) { il.insertBefore(insn, new LabelNode()); }// w w w.j a va 2s .c om return (LabelNode) insn.getPrevious(); }
From source file:jvstm.atomic.ProcessParNestAnnotations.java
License:Open Source License
protected static void processClassFile(File classFile) { alreadyProcessed = new ArrayList<String>(); callablesCreated = new HashMap<String, String>(); InputStream is = null;//from w ww. ja v a 2s.c om try { // get an input stream to read the bytecode of the class is = new FileInputStream(classFile); ClassNode cn = new ClassNode(ASM4); ClassReader cr = new ClassReader(is); cr.accept(cn, 0); List<MethodNode> parNestedMethods = new ArrayList<MethodNode>(); MethodNode combinerMethod = null; MethodNode execMethod = null; List<MethodNode> staticMethodsToAdd = new ArrayList<MethodNode>(); boolean parallelSpawn = extendsParallelSpawn(cn); boolean unsafeSpawn = extendsUnsafeSpawn(cn); if (parallelSpawn || unsafeSpawn) { Iterator<MethodNode> methodIter = cn.methods.iterator(); while (methodIter.hasNext()) { MethodNode mn = methodIter.next(); if (mn.name.equals("exec") && execMethod == null) { execMethod = mn; continue; } if (mn.invisibleAnnotations == null) { continue; } for (AnnotationNode an : mn.invisibleAnnotations) { if (an.desc.equals(PAR_NEST.getDescriptor())) { // Ensure the method can be called from outside mn.access = (mn.access & ~ACC_PRIVATE) | ACC_PUBLIC; parNestedMethods.add(mn); String uniqueMethodName = createUniqueMethodName(mn.name); String callableClass; if (parallelSpawn) { callableClass = cn.name + "$nested$work$unit$" + uniqueMethodName; } else { callableClass = cn.name + "$unsafe$work$unit$" + uniqueMethodName; } callablesCreated.put(mn.name, callableClass); boolean readOnlyCallable = (an.values == null) ? false : (Boolean) an.values.get(1); generateCallable(classFile, cn.name, callableClass, mn, readOnlyCallable, unsafeSpawn); staticMethodsToAdd.add(generateStaticCallableCreation(cn, cn.name, callableClass, mn)); break; } else if (an.desc.equals(COMBINER.getDescriptor())) { if (combinerMethod != null) { throw new RuntimeException("Class: " + cn.name + " contains two @Combiner methods: " + combinerMethod.name + " and " + mn.name); } combinerMethod = mn; } } } // TODO Verify the @Combiner method // The return should be of the same type of the parameterization // of the ParallelSpawn for (MethodNode methodToAdd : staticMethodsToAdd) { cn.methods.add(methodToAdd); } if (alreadyProcessed.size() == 0) { throw new RuntimeException( "Class: " + cn.name + " must have at least one method annotated with @ParNested"); } if (combinerMethod == null) { throw new RuntimeException( "Class: " + cn.name + " must have one method annotated with @Combiner"); } List<Integer> localVariablesIdx = new ArrayList<Integer>(); int numberLocalVariables = 0; int listIndex = execMethod.maxLocals; execMethod.maxLocals++; InsnList preamble = new InsnList(); preamble.add(new TypeInsnNode(NEW, ARRAY_LIST.getInternalName())); preamble.add(new InsnNode(DUP)); preamble.add(new MethodInsnNode(INVOKESPECIAL, ARRAY_LIST.getInternalName(), "<init>", "()V")); preamble.add(new VarInsnNode(ASTORE, listIndex)); Iterator<AbstractInsnNode> execInstIter = execMethod.instructions.iterator(); while (execInstIter.hasNext()) { AbstractInsnNode instr = execInstIter.next(); // Look out for calls to methods if (instr.getOpcode() == INVOKEVIRTUAL || instr.getOpcode() == INVOKESPECIAL) { MethodInsnNode methodInstr = (MethodInsnNode) instr; // Is method being called annotated with @ParNested for (MethodNode parNestedMethod : parNestedMethods) { if (parNestedMethod.name.equals(methodInstr.name)) { numberLocalVariables++; } } } } for (int i = 0; i < numberLocalVariables; i++) { localVariablesIdx.add(i, execMethod.maxLocals); execMethod.maxLocals++; } int callablesManipulated = 0; execInstIter = execMethod.instructions.iterator(); while (execInstIter.hasNext()) { AbstractInsnNode instr = execInstIter.next(); // Look out for calls to methods if (instr.getOpcode() != INVOKEVIRTUAL && instr.getOpcode() != INVOKESPECIAL) { continue; } MethodInsnNode methodInstr = (MethodInsnNode) instr; // Is method being called annotated with @ParNested boolean isParNestedMethod = false; for (MethodNode parNestedMethod : parNestedMethods) { if (parNestedMethod.name.equals(methodInstr.name)) { isParNestedMethod = true; break; } } if (!isParNestedMethod) { continue; } // Let's change this call // If it was a call to: @ParNested public int add(int i1, // int i2) // add(foo, bar) -> add$static$callable$creator(this, foo, // bar) // the 'this' will be already in the right place in the // stack // because the method being called now is static whereas // previously // it was not methodInstr.setOpcode(INVOKESTATIC); methodInstr.name = methodInstr.name + "$static$callable$creator"; for (MethodNode staticCreated : staticMethodsToAdd) { if (staticCreated.name.equals(methodInstr.name)) { methodInstr.desc = staticCreated.desc; break; } } InsnList midterm = new InsnList(); // Store the callable instantiated in local variable midterm.add(new VarInsnNode(ASTORE, localVariablesIdx.get(callablesManipulated))); // Load the list midterm.add(new VarInsnNode(ALOAD, listIndex)); // Load the callable midterm.add(new VarInsnNode(ALOAD, localVariablesIdx.get(callablesManipulated))); // Add it to the list midterm.add(new MethodInsnNode(INVOKEVIRTUAL, ARRAY_LIST.getInternalName(), "add", "(Ljava/lang/Object;)Z")); // Pop the boolean that results from the add(Object) // May reuse a POP if the previous call had a return if (methodInstr.getNext().getOpcode() != POP) { midterm.add(new InsnNode(POP)); } // Add this set of instructions after the call to the // constrution of the callable execMethod.instructions.insert(methodInstr, midterm); callablesManipulated++; } // Insert the preamble in the start execMethod.instructions.insert(preamble); InsnList finish = new InsnList(); // Push 'this' for the call to the combiner method finish.add(new VarInsnNode(ALOAD, 0)); // Call the static method current() of jvstm.Transaction finish.add(new MethodInsnNode(INVOKESTATIC, TRANSACTION.getInternalName(), "current", "()Ljvstm/Transaction;")); // Load the callables list finish.add(new VarInsnNode(ALOAD, listIndex)); // Call the manage parnested method finish.add(new MethodInsnNode(INVOKEVIRTUAL, TRANSACTION.getInternalName(), "manageNestedParallelTxs", "(Ljava/util/List;)Ljava/util/List;")); // Call the combiner method finish.add(new MethodInsnNode(INVOKEVIRTUAL, cn.name, combinerMethod.name, combinerMethod.desc)); // Return what the combiner returns finish.add(new InsnNode(ARETURN)); // Remove the "return null" that's supposed to be at the end of // the exec method execInstIter = execMethod.instructions.iterator(); while (execInstIter.hasNext()) { AbstractInsnNode curNode = execInstIter.next(); if (!execInstIter.hasNext()) { // Insert the finish in the end execMethod.instructions.insert(curNode.getPrevious().getPrevious(), finish); execMethod.instructions.remove(curNode.getPrevious()); execMethod.instructions.remove(curNode); break; } } } ClassWriter cw = new ClassWriter(ClassWriter.COMPUTE_MAXS); cn.accept(cw); writeClassFile(classFile, cw.toByteArray()); } catch (IOException e) { throw new Error("Error processing class file", e); } finally { if (is != null) { try { is.close(); } catch (IOException e) { } } } }
From source file:net.cazzar.corelib.asm.MethodTransformer.java
License:Open Source License
/** * Append the instructions to the method * * @param node the Class being worked on * @param access the Opcode access to the class * @param name the name of the function * @param desc the method description * @param insnList the instructions to append * @param tryCatchBlockNodes a/*from ww w . j a v a 2s . c o m*/ */ public final void appendToMethod(ClassNode node, int access, String name, String desc, InsnList insnList, TryCatchBlockNode... tryCatchBlockNodes) { InsnList insns = transformInsns(insnList); String srgName = getMapping(name); List<MethodDescription> methodNames = Lists.newArrayList(new MethodDescription(name, desc), new MethodDescription(srgName, desc), McpMappings.instance().getMethod(srgName)); MethodNode mtd = new MethodNode(access, srgName, desc, null, null); Collections.addAll(mtd.tryCatchBlocks, tryCatchBlockNodes); for (MethodNode methodNode : node.methods) { for (MethodDescription match : methodNames) { if (match == null) continue; if (methodNode.name.equals(match.getName()) && methodNode.desc.equals(match.getDesc())) { AbstractInsnNode lastInsn = methodNode.instructions.getLast(); while (lastInsn instanceof LabelNode || lastInsn instanceof LineNumberNode) lastInsn = lastInsn.getPrevious(); if (isReturn(lastInsn)) methodNode.instructions.insertBefore(lastInsn, insns); else methodNode.instructions.add(insns); } } } }
From source file:net.lyonlancer5.mcmp.karasu.asm.KarasuTransformer.java
License:Apache License
private static void transformEntityLivingBase(ClassNode classNode) { Constants.LOGGER.info("======== Project Karasu ~ Water Walking Enchantment Patch ========"); Constants.LOGGER.info("Patching net.minecraft.entity.EntityLivingBase"); for (MethodNode method : classNode.methods) { if (method.desc.equals("(FF)V")) { AbstractInsnNode movefNode = null; AbstractInsnNode motionxNode = null; AbstractInsnNode motionzNode = null; AbstractInsnNode motionyNode = null; AbstractInsnNode[] moveList = method.instructions.toArray(); int var11 = moveList.length; for (int var12 = 0; var12 < var11; ++var12) { AbstractInsnNode instruction = moveList[var12]; if (instruction.getOpcode() == Opcodes.ALOAD) { if (((VarInsnNode) instruction).var == 0 && instruction.getNext().getOpcode() == Opcodes.DUP && motionxNode == null) { motionxNode = instruction; } else if (((VarInsnNode) instruction).var == 0 && instruction.getNext().getOpcode() == Opcodes.DUP && motionyNode == null) { motionyNode = instruction; } else if (((VarInsnNode) instruction).var == 0 && instruction.getNext().getOpcode() == Opcodes.DUP && motionzNode == null) { motionzNode = instruction; } else if (movefNode == null && ((VarInsnNode) instruction).var == 0 && instruction.getNext().getOpcode() == Opcodes.FLOAD && ((VarInsnNode) instruction.getNext()).var == 1) { movefNode = instruction; }//ww w .j a v a2s .c om } } int var14; InsnList var15; if (method.name.equals("e")) { Constants.LOGGER.info("Found matching method: " + method.name + " " + method.desc + " - (Obf)"); if (motionxNode != null) { for (var14 = 0; var14 < 6; ++var14) { motionxNode = motionxNode.getNext(); method.instructions.remove(motionxNode.getPrevious()); } Constants.LOGGER.info("Patching sv.w"); var15 = new InsnList(); var15.add(new VarInsnNode(Opcodes.ALOAD, 0)); var15.add(new InsnNode(Opcodes.DUP)); var15.add(new FieldInsnNode(Opcodes.GETFIELD, "net/minecraft/entity/EntityLivingBase", "w", "D")); var15.add(new MethodInsnNode(Opcodes.INVOKESTATIC, "net/lyonlancer5/mcmp/karasu/asm/KarasuFeatherMetadata", "modifyHorizontalVel", "()D", false)); var15.add(new InsnNode(Opcodes.DMUL)); var15.add(new FieldInsnNode(Opcodes.PUTFIELD, "net/minecraft/entity/EntityLivingBase", "w", "D")); method.instructions.insertBefore(motionxNode, var15); Constants.LOGGER.info("Patched sv.w"); } if (motionzNode != null) { for (var14 = 0; var14 < 6; ++var14) { motionzNode = motionzNode.getNext(); method.instructions.remove(motionzNode.getPrevious()); } Constants.LOGGER.info("Patching sv.y"); var15 = new InsnList(); var15.add(new VarInsnNode(Opcodes.ALOAD, 0)); var15.add(new InsnNode(Opcodes.DUP)); var15.add(new FieldInsnNode(Opcodes.GETFIELD, "net/minecraft/entity/EntityLivingBase", "y", "D")); var15.add(new MethodInsnNode(Opcodes.INVOKESTATIC, "net/lyonlancer5/mcmp/karasu/asm/KarasuFeatherMetadata", "modifyHorizontalVel", "()D", false)); var15.add(new InsnNode(Opcodes.DMUL)); var15.add(new FieldInsnNode(Opcodes.PUTFIELD, "net/minecraft/entity/EntityLivingBase", "y", "D")); method.instructions.insertBefore(motionzNode, var15); Constants.LOGGER.info("Patched sv.y"); } if (movefNode != null) { for (var14 = 0; var14 < 14; ++var14) { movefNode = movefNode.getNext(); method.instructions.remove(movefNode.getPrevious()); } var15 = new InsnList(); var15.add(new VarInsnNode(Opcodes.ALOAD, 0)); var15.add(new VarInsnNode(Opcodes.FLOAD, 1)); var15.add(new VarInsnNode(Opcodes.FLOAD, 2)); var15.add(new MethodInsnNode(Opcodes.INVOKESTATIC, "net/lyonlancer5/mcmp/karasu/asm/KarasuFeatherMetadata", "modifyVerticalVel", "()F", false)); var15.add(new MethodInsnNode(Opcodes.INVOKEVIRTUAL, "net/minecraft/entity/EntityLivingBase", "a", "(FFF)V", false)); method.instructions.insertBefore(movefNode, var15); Constants.LOGGER.info("Patching method -- sv.a (FFF)V"); } Constants.LOGGER.info("Patch success!"); return; } else if (method.name.equals("moveEntityWithHeading")) { Constants.LOGGER .info("Found matching method: " + method.name + " " + method.desc + " - (Deobf)"); if (motionxNode != null) { for (var14 = 0; var14 < 6; ++var14) { motionxNode = motionxNode.getNext(); method.instructions.remove(motionxNode.getPrevious()); } Constants.LOGGER.info("Patching EntityLivingBase.motionX"); var15 = new InsnList(); var15.add(new VarInsnNode(Opcodes.ALOAD, 0)); var15.add(new InsnNode(Opcodes.DUP)); var15.add(new FieldInsnNode(Opcodes.GETFIELD, "net/minecraft/entity/EntityLivingBase", "motionX", "D")); var15.add(new MethodInsnNode(Opcodes.INVOKESTATIC, "net/lyonlancer5/mcmp/karasu/asm/KarasuFeatherMetadata", "modifyHorizontalVel", "()D", false)); var15.add(new InsnNode(Opcodes.DMUL)); var15.add(new FieldInsnNode(Opcodes.PUTFIELD, "net/minecraft/entity/EntityLivingBase", "motionX", "D")); method.instructions.insertBefore(motionxNode, var15); Constants.LOGGER.info("Patched EntityLivingBase.motionX"); } if (motionzNode != null) { for (var14 = 0; var14 < 6; ++var14) { motionzNode = motionzNode.getNext(); method.instructions.remove(motionzNode.getPrevious()); } Constants.LOGGER.info("Patching EntityLivingBase.motionZ"); var15 = new InsnList(); var15.add(new VarInsnNode(Opcodes.ALOAD, 0)); var15.add(new InsnNode(Opcodes.DUP)); var15.add(new FieldInsnNode(Opcodes.GETFIELD, "net/minecraft/entity/EntityLivingBase", "motionZ", "D")); var15.add(new MethodInsnNode(Opcodes.INVOKESTATIC, "net/lyonlancer5/mcmp/karasu/asm/KarasuFeatherMetadata", "modifyHorizontalVel", "()D", false)); var15.add(new InsnNode(Opcodes.DMUL)); var15.add(new FieldInsnNode(Opcodes.PUTFIELD, "net/minecraft/entity/EntityLivingBase", "motionZ", "D")); method.instructions.insertBefore(motionzNode, var15); Constants.LOGGER.info("Patched EntityLivingBase.motionZ"); } if (movefNode != null) { for (var14 = 0; var14 < 14; ++var14) { movefNode = movefNode.getNext(); method.instructions.remove(movefNode.getPrevious()); } var15 = new InsnList(); var15.add(new VarInsnNode(Opcodes.ALOAD, 0)); var15.add(new VarInsnNode(Opcodes.FLOAD, 1)); var15.add(new VarInsnNode(Opcodes.FLOAD, 2)); var15.add(new MethodInsnNode(Opcodes.INVOKESTATIC, "net/lyonlancer5/mcmp/karasu/asm/KarasuFeatherMetadata", "modifyVerticalVel", "()F", false)); var15.add(new MethodInsnNode(Opcodes.INVOKEVIRTUAL, "net/minecraft/entity/EntityLivingBase", "moveFlying", "(FFF)V", false)); method.instructions.insertBefore(movefNode, var15); Constants.LOGGER.info("Patched method - EntityLivingBase.moveFlying (FFF)V"); } Constants.LOGGER.info("Patch success!"); return; } else if (method.name.equals("func_70612_e")) { Constants.LOGGER.info("Found matching method: " + method.name + " " + method.desc + " - (srg)"); if (motionxNode != null) { for (var14 = 0; var14 < 6; ++var14) { motionxNode = motionxNode.getNext(); method.instructions.remove(motionxNode.getPrevious()); } Constants.LOGGER.info("Patching EntityLivingBase.field_70159_w"); var15 = new InsnList(); var15.add(new VarInsnNode(Opcodes.ALOAD, 0)); var15.add(new InsnNode(Opcodes.DUP)); var15.add(new FieldInsnNode(Opcodes.GETFIELD, "net/minecraft/entity/EntityLivingBase", "field_70159_w", "D")); var15.add(new MethodInsnNode(Opcodes.INVOKESTATIC, "net/lyonlancer5/mcmp/karasu/asm/KarasuFeatherMetadata", "modifyHorizontalVel", "()D", false)); var15.add(new InsnNode(Opcodes.DMUL)); var15.add(new FieldInsnNode(Opcodes.PUTFIELD, "net/minecraft/entity/EntityLivingBase", "field_70159_w", "D")); method.instructions.insertBefore(motionxNode, var15); Constants.LOGGER.info("Patched EntityLivingBase.field_70159_w"); } if (motionzNode != null) { for (var14 = 0; var14 < 6; ++var14) { motionzNode = motionzNode.getNext(); method.instructions.remove(motionzNode.getPrevious()); } Constants.LOGGER.info("Patching EntityLivingBase.field_70179_y"); var15 = new InsnList(); var15.add(new VarInsnNode(Opcodes.ALOAD, 0)); var15.add(new InsnNode(Opcodes.DUP)); var15.add(new FieldInsnNode(Opcodes.GETFIELD, "net/minecraft/entity/EntityLivingBase", "field_70179_y", "D")); var15.add(new MethodInsnNode(Opcodes.INVOKESTATIC, "net/lyonlancer5/mcmp/karasu/asm/KarasuFeatherMetadata", "modifyHorizontalVel", "()D", false)); var15.add(new InsnNode(Opcodes.DMUL)); var15.add(new FieldInsnNode(Opcodes.PUTFIELD, "net/minecraft/entity/EntityLivingBase", "field_70179_y", "D")); method.instructions.insertBefore(motionzNode, var15); Constants.LOGGER.info("Patched EntityLivingBase.field_70179_y"); } if (movefNode != null) { for (var14 = 0; var14 < 14; ++var14) { movefNode = movefNode.getNext(); method.instructions.remove(movefNode.getPrevious()); } var15 = new InsnList(); var15.add(new VarInsnNode(Opcodes.ALOAD, 0)); var15.add(new VarInsnNode(Opcodes.FLOAD, 1)); var15.add(new VarInsnNode(Opcodes.FLOAD, 2)); var15.add(new MethodInsnNode(Opcodes.INVOKESTATIC, "net/lyonlancer5/mcmp/karasu/asm/KarasuFeatherMetadata", "modifyVerticalVel", "()F", false)); var15.add(new MethodInsnNode(Opcodes.INVOKEVIRTUAL, "net/minecraft/entity/EntityLivingBase", "func_70060_a", "(FFF)V", false)); method.instructions.insertBefore(movefNode, var15); Constants.LOGGER.info("Patched method - EntityLivingBase.func_70060_a (FFF)V"); } Constants.LOGGER.info("Patch success!"); return; } } } // #OVERKILL throw new RuntimeException("Patch FAILED -- No matching method found"); }
From source file:net.minecraftforge.fml.common.asm.transformers.SoundEngineFixTransformer.java
License:Open Source License
@Override public byte[] transform(String name, String transformedName, byte[] basicClass) { if (transformedName.equals("paulscode.sound.Source")) { ClassNode classNode = new ClassNode(); ClassReader classReader = new ClassReader(basicClass); classReader.accept(classNode, 0); classNode.fields.add(new FieldNode(Opcodes.ACC_PUBLIC, "removed", "Z", null, null)); // adding field 'public boolean removed;' ClassWriter writer = new ClassWriter(ClassWriter.COMPUTE_MAXS); classNode.accept(writer);/*w w w . j ava 2s. c om*/ return writer.toByteArray(); } else if (transformedName.equals("paulscode.sound.Library")) { ClassNode classNode = new ClassNode(); ClassReader classReader = new ClassReader(basicClass); classReader.accept(classNode, 0); MethodNode method = null; for (MethodNode m : classNode.methods) { if (m.name.equals("removeSource") && m.desc.equals("(Ljava/lang/String;)V")) // trying to find paulscode.sound.Library.removeSource(String) { method = m; break; } } if (method == null) throw new RuntimeException( "Error processing " + transformedName + " - no removeSource method found"); AbstractInsnNode referenceNode = null; for (Iterator<AbstractInsnNode> iterator = method.instructions.iterator(); iterator.hasNext();) { AbstractInsnNode insn = iterator.next(); if (insn instanceof MethodInsnNode && ((MethodInsnNode) insn).owner.equals("paulscode/sound/Source") // searching for mySource.cleanup() node (line 1086) && ((MethodInsnNode) insn).name.equals("cleanup")) { referenceNode = insn; break; } } if (referenceNode != null) { LabelNode after = (LabelNode) referenceNode.getNext(); AbstractInsnNode beginning = referenceNode.getPrevious(); int varIndex = ((VarInsnNode) beginning).var; method.instructions.insertBefore(beginning, new VarInsnNode(Opcodes.ALOAD, varIndex)); // adding extra if (mySource.toStream) method.instructions.insertBefore(beginning, new FieldInsnNode(Opcodes.GETFIELD, "paulscode/sound/Source", "toStream", "Z")); LabelNode elseNode = new LabelNode(); method.instructions.insertBefore(beginning, new JumpInsnNode(Opcodes.IFEQ, elseNode)); // if fails (else) -> go to mySource.cleanup(); method.instructions.insertBefore(beginning, new VarInsnNode(Opcodes.ALOAD, varIndex)); // if (mySource.toStream) { mySource.removed = true; } method.instructions.insertBefore(beginning, new InsnNode(Opcodes.ICONST_1)); method.instructions.insertBefore(beginning, new FieldInsnNode(Opcodes.PUTFIELD, "paulscode/sound/Source", "removed", "Z")); method.instructions.insertBefore(beginning, new JumpInsnNode(Opcodes.GOTO, after)); // still inside if -> jump to sourceMap.remove( sourcename ); method.instructions.insertBefore(beginning, elseNode); } ClassWriter writer = new ClassWriter(ClassWriter.COMPUTE_MAXS); classNode.accept(writer); return writer.toByteArray(); } else if (transformedName.equals("paulscode.sound.StreamThread")) { ClassNode classNode = new ClassNode(); ClassReader classReader = new ClassReader(basicClass); classReader.accept(classNode, 0); MethodNode method = null; for (MethodNode m : classNode.methods) { if (m.name.equals("run") && m.desc.equals("()V")) // trying to find paulscode.sound.StreamThread.run(); { method = m; break; } } if (method == null) throw new RuntimeException("Error processing " + transformedName + " - no run method found"); AbstractInsnNode referenceNode = null; for (Iterator<AbstractInsnNode> iterator = method.instructions.iterator(); iterator.hasNext();) { AbstractInsnNode insn = iterator.next(); if (insn instanceof MethodInsnNode && ((MethodInsnNode) insn).owner.equals("java/util/ListIterator") // searching for 'src = iter.next();' node (line 110) && ((MethodInsnNode) insn).name.equals("next")) { referenceNode = insn.getNext().getNext(); break; } } if (referenceNode != null) { int varIndex = ((VarInsnNode) referenceNode).var; LabelNode after = (LabelNode) referenceNode.getNext(); method.instructions.insertBefore(after, new VarInsnNode(Opcodes.ALOAD, varIndex)); // add if(removed) method.instructions.insertBefore(after, new FieldInsnNode(Opcodes.GETFIELD, "paulscode/sound/Source", "removed", "Z")); method.instructions.insertBefore(after, new JumpInsnNode(Opcodes.IFEQ, after)); // if the source has been marked as removed, clean it up and set the variable to null so it will be removed from the list method.instructions.insertBefore(after, new VarInsnNode(Opcodes.ALOAD, varIndex)); // src.cleanup(); method.instructions.insertBefore(after, new MethodInsnNode(Opcodes.INVOKEVIRTUAL, "paulscode/sound/Source", "cleanup", "()V", false)); method.instructions.insertBefore(after, new InsnNode(Opcodes.ACONST_NULL)); // src = null; method.instructions.insertBefore(after, new VarInsnNode(Opcodes.ASTORE, varIndex)); } ClassWriter writer = new ClassWriter(ClassWriter.COMPUTE_MAXS); classNode.accept(writer); return writer.toByteArray(); } return basicClass; }
From source file:nova.core.wrapper.mc.forge.v17.asm.transformers.ChunkTransformer.java
License:Open Source License
@Override public void transform(ClassNode cnode) { System.out.println("[NOVA] Transforming Chunk class for chunkModified event."); ObfMapping obfMap = new ObfMapping("apx", "a", "(IIILaji;I)Z"); ObfMapping srgMap = new ObfMapping("net/minecraft/world/chunk/Chunk", "func_150807_a", "(IIILnet/minecraft/block/Block;I)Z"); MethodNode method = ASMHelper.findMethod(obfMap, cnode); if (method == null) { System.out.println("[NOVA] Lookup " + obfMap + " failed. You are probably in a deobf environment."); method = ASMHelper.findMethod(srgMap, cnode); if (method == null) { System.out.println("[NOVA] Lookup " + srgMap + " failed!"); }/* w w w . ja v a2s . c om*/ } System.out.println("[NOVA] Found method " + method.name); InsnList list = new InsnList(); list.add(new VarInsnNode(ALOAD, 0)); list.add(new VarInsnNode(ILOAD, 1)); list.add(new VarInsnNode(ILOAD, 2)); list.add(new VarInsnNode(ILOAD, 3)); list.add(new VarInsnNode(ALOAD, 8)); list.add(new VarInsnNode(ILOAD, 9)); list.add(new VarInsnNode(ALOAD, 4)); list.add(new VarInsnNode(ILOAD, 5)); list.add(new MethodInsnNode(INVOKESTATIC, "nova/core/wrapper/mc/forge/v17/asm/StaticForwarder", "chunkSetBlockEvent", "(Lnet/minecraft/world/chunk/Chunk;IIILnet/minecraft/block/Block;ILnet/minecraft/block/Block;I)V", false)); AbstractInsnNode lastInsn = method.instructions.getLast(); while (lastInsn instanceof LabelNode || lastInsn instanceof LineNumberNode) { lastInsn = lastInsn.getPrevious(); } if (ASMHelper.isReturn(lastInsn)) { method.instructions.insertBefore(lastInsn, list); } else { method.instructions.insert(list); } System.out.println("[NOVA] Injected instruction to method: " + method.name); }
From source file:nova.core.wrapper.mc.forge.v18.asm.transformers.ChunkTransformer.java
License:Open Source License
@Override public void transform(ClassNode cnode) { System.out.println("[NOVA] Transforming Chunk class for chunkModified event."); //obf name: func_177436_a MethodNode method = ASMHelper.findMethod(new ObfMapping("net/minecraft/world/chunk/Chunk", "setBlockState", "(Lnet/minecraft/util/BlockPos;Lnet/minecraft/block/state/IBlockState;)Lnet/minecraft/block/state/IBlockState;"), cnode);// ww w. j av a 2 s .com System.out.println("[NOVA] Found method " + method.name); InsnList list = new InsnList(); list.add(new VarInsnNode(ALOAD, 0)); //this list.add(new VarInsnNode(ALOAD, 1)); //BlockPos list.add(new VarInsnNode(ALOAD, 8)); //oldBlock IBlockState list.add(new VarInsnNode(ALOAD, 2)); //newBlock IBlockState list.add(new MethodInsnNode(INVOKESTATIC, "nova/core/wrapper/mc/forge/v18/asm/StaticForwarder", "chunkSetBlockEvent", "(Lnet/minecraft/world/chunk/Chunk;Lnet/minecraft/util/BlockPos;Lnet/minecraft/block/state/IBlockState;Lnet/minecraft/block/state/IBlockState;)V", false)); AbstractInsnNode lastInsn = method.instructions.getLast(); while (lastInsn instanceof LabelNode || lastInsn instanceof LineNumberNode) { lastInsn = lastInsn.getPrevious(); } if (ASMHelper.isReturn(lastInsn)) { method.instructions.insertBefore(lastInsn, list); } else { method.instructions.insert(list); } System.out.println("[NOVA] Injected instruction to method: " + method.name); }
From source file:org.coldswap.asm.field.PrivateStaticFieldReplacer.java
License:Open Source License
/** * Removes any initializing reference of the field. * * @param classNode containing the old class. * @param fieldNode containing the old field. * @return the initializing list of instructions. *//* ww w. ja v a2 s . c o m*/ @SuppressWarnings("unchecked") private InsnList cleanClInit(ClassNode classNode, FieldNode fieldNode) { List<MethodNode> methodNodes = classNode.methods; AbstractInsnNode firstInst = null; int counter = 0; for (MethodNode methodNode : methodNodes) { if (methodNode.name.equals("<clinit>")) { // search for PUTSTATIC InsnList insnList = methodNode.instructions; Iterator iterator1 = insnList.iterator(); while (iterator1.hasNext()) { AbstractInsnNode ins2 = (AbstractInsnNode) iterator1.next(); // if a initializing has been found, then copy everything from // the corresponding label to the PUTSTATIC if (ins2.getOpcode() == Opcodes.PUTSTATIC) { final Boolean[] fieldFound = { false }; final FieldNode fNode = fieldNode; ins2.accept(new MethodVisitor(Opcodes.ASM5) { @Override public void visitFieldInsn(int i, String s, String s2, String s3) { if (s2.equals(fNode.name)) { fieldFound[0] = true; } super.visitFieldInsn(i, s, s2, s3); } }); if (fieldFound[0]) { // find the first PUTSTATIC before this one. boolean staticFound = false; while (!staticFound) { AbstractInsnNode tmpInst = ins2.getPrevious(); if (tmpInst != null) { if (tmpInst.getOpcode() != Opcodes.F_NEW) { if (tmpInst.getOpcode() == Opcodes.PUTSTATIC) { staticFound = true; } else { firstInst = tmpInst; counter++; } } } else { staticFound = true; } ins2 = tmpInst; } break; } } } if (firstInst != null) { InsnList iList = new InsnList(); iList.add(firstInst.clone(null)); counter--; while (counter > 0) { AbstractInsnNode ain = firstInst.getNext(); iList.add(ain.clone(null)); counter--; insnList.remove(firstInst); firstInst = ain; } // remove last instruction and the putstatic instruction AbstractInsnNode putStatic = firstInst.getNext(); insnList.remove(firstInst); insnList.remove(putStatic); return iList; } } } return null; }
From source file:org.coldswap.asm.field.ProtectedStaticFieldReplacer.java
License:Open Source License
/** * Removes any initializing reference of the field. * * @param classNode containing the old class. * @param fieldNode containing the old field. * @param canRemove <code>true</code> if this method should remove the initializing code and return it * or <code>false</code> if you only want to return the init code. * @return the initializing list of instructions. *///ww w . j a va2 s . co m @SuppressWarnings("unchecked") private InsnList cleanClInit(ClassNode classNode, FieldNode fieldNode, boolean canRemove) { List<MethodNode> methodNodes = classNode.methods; AbstractInsnNode firstInst = null; int counter = 0; for (MethodNode methodNode : methodNodes) { if (methodNode.name.equals("<clinit>")) { // search for PUTSTATIC InsnList insnList = methodNode.instructions; Iterator iterator1 = insnList.iterator(); while (iterator1.hasNext()) { AbstractInsnNode ins2 = (AbstractInsnNode) iterator1.next(); // if a initializing has been found, then copy everything from // the coresponding label to the PUTSTATIC if (ins2.getOpcode() == Opcodes.PUTSTATIC) { final Boolean[] fieldFound = { false }; final FieldNode fNode = fieldNode; ins2.accept(new MethodVisitor(Opcodes.ASM5) { @Override public void visitFieldInsn(int i, String s, String s2, String s3) { if (s2.equals(fNode.name)) { fieldFound[0] = true; } super.visitFieldInsn(i, s, s2, s3); } }); if (fieldFound[0]) { // find the first PUTSTATIC before this one. boolean staticFound = false; while (!staticFound) { AbstractInsnNode tmpInst = ins2.getPrevious(); if (tmpInst != null) { if (tmpInst.getOpcode() != Opcodes.F_NEW) { if (tmpInst.getOpcode() == Opcodes.PUTSTATIC) { staticFound = true; } else { firstInst = tmpInst; counter++; } } } else { staticFound = true; } ins2 = tmpInst; } break; } } } if (firstInst != null) { InsnList iList = new InsnList(); iList.add(firstInst.clone(null)); counter--; while (counter > 0) { AbstractInsnNode ain = firstInst.getNext(); iList.add(ain.clone(null)); counter--; if (canRemove) { insnList.remove(firstInst); } firstInst = ain; } if (canRemove) { // remove last instruction and the putstatic instruction AbstractInsnNode putStatic = firstInst.getNext(); insnList.remove(firstInst); insnList.remove(putStatic); } return iList; } } } return null; }
From source file:org.diorite.inject.controller.TransformerInjectTracker.java
License:Open Source License
private AbstractInsnNode skipCheckCastBackwards(AbstractInsnNode node) { // skip possible (?) ALOAD 0 if not static if (!this.isStatic && (node instanceof VarInsnNode) && (node.getOpcode() == ALOAD) && (((VarInsnNode) node).var == 0)) { node = node.getPrevious(); }//from w w w .j a va 2s. c o m // skip possible check cast if ((node instanceof TypeInsnNode) && (node.getOpcode() == CHECKCAST)) { node = node.getPrevious(); } // skip possible (?) ALOAD 0 if not static if (!this.isStatic && (node instanceof VarInsnNode) && (node.getOpcode() == ALOAD) && (((VarInsnNode) node).var == 0)) { node = node.getPrevious(); } return node; }