List of usage examples for org.objectweb.asm.tree MethodNode accept
public void accept(final MethodVisitor methodVisitor)
From source file:org.glowroot.weaving.WeavingClassVisitor.java
License:Apache License
@RequiresNonNull("type") private void addMixin(MixinType mixinType) { ClassReader cr = new ClassReader(mixinType.implementationBytes()); ClassNode cn = new ClassNode(); cr.accept(cn, ClassReader.EXPAND_FRAMES); // SuppressWarnings because generics are explicitly removed from asm binaries // see http://forge.ow2.org/tracker/?group_id=23&atid=100023&func=detail&aid=316377 @SuppressWarnings("unchecked") List<FieldNode> fieldNodes = cn.fields; for (FieldNode fieldNode : fieldNodes) { fieldNode.accept(this); }//from w w w . j ava 2 s . c o m // SuppressWarnings because generics are explicitly removed from asm binaries @SuppressWarnings("unchecked") List<MethodNode> methodNodes = cn.methods; for (MethodNode mn : methodNodes) { if (mn.name.equals("<init>")) { continue; } // SuppressWarnings because generics are explicitly removed from asm binaries @SuppressWarnings("unchecked") String[] exceptions = Iterables.toArray(mn.exceptions, String.class); MethodVisitor mv = cv.visitMethod(mn.access, mn.name, mn.desc, mn.signature, exceptions); checkNotNull(mv); mn.accept(new RemappingMethodAdapter(mn.access, mn.desc, mv, new SimpleRemapper(cn.name, type.getInternalName()))); } }
From source file:org.jacoco.core.internal.analysis.AC_MethodAnalyzerTest.java
License:Open Source License
@SuppressWarnings("unused") private void printMethod(MethodNode m) { Textifier t = new Textifier(); m.accept(new TraceMethodVisitor(t)); PrintWriter writer = new PrintWriter(System.out); t.print(writer);/*from w ww . j a va2s.co m*/ writer.flush(); }
From source file:org.jacoco.core.internal.flow.MethodSanitizerTest.java
License:Open Source License
private MethodRecorder dump(MethodNode node) { MethodRecorder rec = new MethodRecorder(); node.accept(rec.getVisitor()); return rec; }
From source file:org.jacoco.playground.filter.MethodDumper.java
License:Open Source License
private static void dump(MethodNode method) { final TestCaseDumper printer = new TestCaseDumper(); insertLabels(method.instructions, printer); final TraceMethodVisitor mv = new TraceMethodVisitor(printer); method.accept(mv); final PrintWriter writer = new PrintWriter(System.out); printer.print(writer);//from w w w . j a v a2 s. c o m writer.flush(); }
From source file:org.jephyr.activeobject.instrument.ActiveObjectClassAdapter.java
License:Open Source License
@Override public void visitEnd() { if (activeObject) { FieldVisitor fv = visitField(ACC_PRIVATE | ACC_STATIC | ACC_FINAL | ACC_SYNTHETIC, "activeObject$mailboxSupplier", "Ljava/util/function/Supplier;", null, null); fv.visitEnd();/*from w w w . j a v a 2 s.c om*/ FieldVisitor fv1 = visitField(ACC_PRIVATE | ACC_FINAL | ACC_SYNTHETIC, "activeObject$thread", "Lorg/jephyr/activeobject/support/ActiveObjectThread;", null, null); fv1.visitEnd(); if (!clinit) { MethodVisitor mv = super.visitMethod(ACC_STATIC, "<clinit>", "()V", null, null); mv.visitCode(); visitClinit(mv); mv.visitInsn(RETURN); mv.visitMaxs(2, 0); mv.visitEnd(); } MethodVisitor mv1 = super.visitMethod(ACC_PROTECTED, "activeObject$getThread", "()Lorg/jephyr/activeobject/support/ActiveObjectThread;", null, null); mv1.visitCode(); mv1.visitVarInsn(ALOAD, 0); mv1.visitFieldInsn(GETFIELD, name, "activeObject$thread", "Lorg/jephyr/activeobject/support/ActiveObjectThread;"); mv1.visitInsn(ARETURN); mv1.visitMaxs(1, 1); mv1.visitEnd(); for (MethodNode node : methodNodes) { node.accept(super.visitMethod(node.access, node.name, node.desc, node.signature, node.exceptions.toArray(new String[node.exceptions.size()]))); } } super.visitEnd(); }
From source file:org.moe.natj.processor.cxx.visitors.CxxClassVisitor.java
License:Apache License
@Override public MethodVisitor diagVisitMethod(int access, String name, String desc, String signature, String[] exceptions) {/*from ww w. ja va 2 s . c om*/ // Safe bridge methods for later if ((access & ACC_BRIDGE) == ACC_BRIDGE) { if (classInfo != null) { final MethodNode node = new MethodNode(access, name, desc, signature, exceptions); return new BridgeMethodVisitor(node, classInfo, this, () -> { if (getClassDiagInfo().version >= 52 /* Java 8 */) { node.accept(super.diagVisitMethod(access, name, desc, signature, exceptions)); } }); } else { return super.diagVisitMethod(access, name, desc, signature, exceptions); } } // Ignore non-static template methods if (isTemplateClass && (access & ACC_STATIC) == 0) { return super.diagVisitMethod(access, name, desc, signature, exceptions); } // Process methods final MethodNode node = new MethodNode(access, name, desc, signature, exceptions); return new CxxMethodVisitor(node, analyzer, classInfo, this); }
From source file:org.summer.aop.ltw.AspectWeaver.java
License:Open Source License
/** * Displaces the original method body to a corresponding private redirection method. However, if the visited class * has been mocked and the mock class overwrites this method, the original method body will be replaced entirely by * the corresponding mock method body./*from w w w .ja va 2 s . c o m*/ * <p/> * Note: As constructors are nothing else than methods, they are also taken into account. * * @param access the original method access * @param name the original method name * @param desc the original method description * @param signature the original method signature * @param exceptions the original exceptions * @return a method visitor that points to the private redirected method */ @Override public MethodVisitor visitMethod(int access, final String name, final String desc, String signature, String[] exceptions) { // If this class should be replaced, skip all original methods if (replacingClassNode != null && !isVisitEndReached) return null; // If this class should be merged and this method isn't the static initializer, and a corresponding merging method is defined, merge their exceptions if (mergingClassNode != null && !name.equals("<clinit>")) { for (Object methodNode : mergingClassNode.methods) { MethodNode mn = (MethodNode) methodNode; if (mn.name.equals(name) && mn.desc.equals(desc)) { List<String> mergedExceptions = exceptions == null ? new ArrayList<String>() : Arrays.asList(exceptions); for (Object e : mn.exceptions) { String ex = (String) e; if (!mergedExceptions.contains(ex)) mergedExceptions.add(ex); } exceptions = mergedExceptions.toArray(new String[mergedExceptions.size()]); break; } } } MethodVisitor mv; //Currently ALL constructors and methods will be transformed for retransformation purposes, because //the Java Instrumentation API doesn't yet allow the addition of new methods (or constructors). //If future Java versions cancel this restriction you can safely enable the following three lines in place of //the three lines after next! // List<Aspect> matchingAspects = getMatchingAspects(access,name,desc,signature,exceptions); // if(!isInterface && !matchingAspects.isEmpty()) // { if (!isInterface && !name.equals("<clinit>")) { List<Aspect> matchingAspects = getMatchingAspects(access, name, desc, signature, exceptions); if (name.equals("<init>")) { // Transform the constructor and add a constructor redirected method mv = new ConstructorSplitter(className, cv, access, ++constructorCounter, desc, signature, exceptions, matchingAspects); } else { // Rename original non-constructor methods mv = cv.visitMethod(toPrivateAccess(access), AOPContext.toRedirectedMethodName(name, -1), desc, signature, exceptions); } // Remember the intercepted original method details interceptedMethodInfos.add(new AspectWeaver.MethodInfo(access, name, name.equals("<init>") ? constructorCounter : -1, desc, signature, exceptions, matchingAspects)); // If this class should be merged... if (mergingClassNode != null) { if (name.equals("<init>")) { visitedMergingClassMethods.add(name + desc); // Merge the original constructor body with ALL those defined in the merging class return new AdviceAdapter(ASM4, mv, access, "<init>", desc) { @Override protected void onMethodExit(int opcode) { for (Object methodNode : mergingClassNode.methods) { MethodNode mn = (MethodNode) methodNode; if (mn.name.equals("<init>")) { // Insert everything between the super call invocation and RETURN or ATHROW instruction AbstractInsnNode insn = mn.instructions.getFirst(); while (!(insn instanceof MethodInsnNode) || !((MethodInsnNode) insn).owner.equals(mergingClassNode.superName) || ((MethodInsnNode) insn).getOpcode() != INVOKESPECIAL || !((MethodInsnNode) insn).name.equals("<init>")) { insn = insn.getNext(); } insn = insn.getNext(); while (!(insn instanceof InsnNode) || (((InsnNode) insn).getOpcode() != RETURN && ((InsnNode) insn).getOpcode() != ATHROW)) { if (insn instanceof MethodInsnNode && ((MethodInsnNode) insn).owner.equals(mergingClassNode.name)) ((MethodInsnNode) insn).owner = className; else if (insn instanceof FieldInsnNode && ((FieldInsnNode) insn).owner.equals(mergingClassNode.name)) ((FieldInsnNode) insn).owner = className; insn.accept(this); insn = insn.getNext(); } maxStack = Math.max(maxStack, mn.maxStack); maxLocals = Math.max(maxLocals, mn.maxLocals); for (Iterator<?> it = mn.localVariables.iterator(); it.hasNext();) { LocalVariableNode localVar = (LocalVariableNode) it.next(); if (localVar.desc.equals("L" + mergingClassNode.name + ";")) localVar.desc = "L" + className + ";"; } } } } @Override public void visitMaxs(int nStack, int nLocals) { super.visitMaxs(Math.max(nStack, maxStack), Math.max(nLocals, maxLocals)); } private int maxStack; private int maxLocals; }; } else { for (Object methodNode : mergingClassNode.methods) { MethodNode mn = (MethodNode) methodNode; if (mn.name.equals(name) && mn.desc.equals(desc)) { visitedMergingClassMethods.add(name + desc); if (shouldInsertRedirectionCondition) { // Insert a redirection condition, which is based on the STATIC_IS_MERGING_REVERTED_FIELD boolean value. // If the flag is false then call the original method and skip the merging one, otherwise do the opposite. Type returnType = Type.getReturnType(desc); boolean isVoid = returnType.getSort() == Type.VOID; int returnOpcode = isVoid ? RETURN : returnType.getOpcode(IRETURN); AbstractInsnNode first = mn.instructions.getFirst(); mn.instructions.insertBefore(first, new FieldInsnNode(GETSTATIC, className, AOPContext.STATIC_IS_MERGING_REVERTED_FIELD, "Z")); LabelNode labelNode = new LabelNode(); mn.instructions.insertBefore(first, new JumpInsnNode(IFEQ, labelNode)); boolean isStatic = (access & ACC_STATIC) != 0; int inc = 0; if (!isStatic) { mn.instructions.insertBefore(first, new VarInsnNode(ALOAD, 0)); mn.maxStack++; inc = 1; } Type[] argTypes = Type.getArgumentTypes(desc); for (int i = 0; i < argTypes.length; ++i) { mn.instructions.insertBefore(first, new VarInsnNode(argTypes[i].getOpcode(ILOAD), inc + i)); if (argTypes[i].getInternalName().equals("J") || argTypes[i].getInternalName().equals("D")) ++inc; } mn.instructions.insertBefore(first, new MethodInsnNode(isStatic ? INVOKESTATIC : INVOKEVIRTUAL, className, AOPContext.toMergedMethodName(name, -1), desc)); mn.instructions.insertBefore(first, new InsnNode(returnOpcode)); mn.instructions.insertBefore(first, labelNode); } // A corresponding merging method has been found, so let's replace the original method body // with the merging method body mn.accept(mv); // Rename the original method if existent, otherwise return null return shouldInsertRedirectionCondition ? cv.visitMethod(access, AOPContext.toMergedMethodName(name, -1), desc, signature, exceptions) : null; } } } } } else { mv = cv.visitMethod(access, name, desc, signature, exceptions); if (mergingClassNode != null) visitedMergingClassMethods.add(name + desc); if (name.equals("<clinit>")) { isStaticBlockVisited = true; mv = new AdviceAdapter(ASM4, mv, access, name, desc) { @Override protected void onMethodEnter() { initializeStaticAspectsField(this); if (mergingClassNode != null) initializeStaticIsMergingActiveField(this); } @Override protected void onMethodExit(int opcode) { if (mergingClassNode != null) { for (Object methodNode : mergingClassNode.methods) { MethodNode mn = (MethodNode) methodNode; if (mn.name.equals("<clinit>")) { AbstractInsnNode insn = mn.instructions.getFirst(); while (!(insn instanceof InsnNode) || (((InsnNode) insn).getOpcode() != RETURN && ((InsnNode) insn).getOpcode() != ATHROW)) { if (insn instanceof MethodInsnNode && ((MethodInsnNode) insn).owner.equals(mergingClassNode.name)) ((MethodInsnNode) insn).owner = className; else if (insn instanceof FieldInsnNode && ((FieldInsnNode) insn).owner.equals(mergingClassNode.name)) ((FieldInsnNode) insn).owner = className; insn.accept(this); insn = insn.getNext(); } maxStack = Math.max(maxStack, mn.maxStack); maxLocals = Math.max(maxLocals, mn.maxLocals); for (Iterator<?> it = mn.localVariables.iterator(); it.hasNext();) { LocalVariableNode localVar = (LocalVariableNode) it.next(); if (localVar.desc.equals("L" + mergingClassNode.name + ";")) localVar.desc = "L" + className + ";"; } break; } } } } @Override public void visitMaxs(int nStack, int nLocals) { if (mergingClassNode != null) super.visitMaxs(Math.max(nStack, maxStack), Math.max(nLocals, maxLocals)); else super.visitMaxs(nStack + 2, nLocals); } private int maxStack; private int maxLocals; }; } } return mv; }
From source file:org.summer.aop.ltw.AspectWeaver.java
License:Open Source License
@Override public void visitEnd() { isVisitEndReached = true;/*w w w. ja v a 2s. c o m*/ // If this class should be merged... if (mergingClassNode != null) { // Add all remaining non matching merging fields for (Object fieldNode : mergingClassNode.fields) { FieldNode fn = (FieldNode) fieldNode; if (!visitedMergingClassFields.contains(fn.name)) fn.accept(cv); } // Add all remaining non matching merging methods for (Object methodNode : mergingClassNode.methods) { shouldInsertRedirectionCondition = false; MethodNode mn = (MethodNode) methodNode; if (!visitedMergingClassMethods.contains(mn.name + mn.desc)) mn.accept(this); } } else if (replacingClassNode != null) // If this class should be replaced... { // Add all replacing fields for (Object fieldNode : replacingClassNode.fields) { ((FieldNode) fieldNode).accept(cv); } // Add all remaining replacing non matching replacing methods for (Object methodNode : replacingClassNode.methods) { MethodNode mn = (MethodNode) methodNode; if (!mn.name.equals("<clinit>")) mn.accept(this); } } MethodVisitor mv; // Split the advised methods for (AspectWeaver.MethodInfo info : interceptedMethodInfos) { if (!info.methodName.equals("<clinit>")) { int privateAccess = toPrivateAccess(info.access); // For non constructor methods replace the original method body if (!info.methodName.equals("<init>")) { mv = cv.visitMethod(info.access, info.methodName, info.desc, info.signature, info.exceptions); mv = new MethodReplacer(className, mv, privateAccess, info.methodName, info.desc, info.signature, info.exceptions, info.matchingAspects); mv.visitCode(); mv.visitMaxs(-1, -1); mv.visitEnd(); } // Add a corresponding proceeding method mv = cv.visitMethod(privateAccess, AOPContext.toProceedingMethodName(info.methodName, info.constructorNumber), info.desc, info.signature, info.exceptions); mv = new ProceedingMethodGenerator(className, mv, privateAccess, info.methodName, info.constructorNumber, info.desc, info.signature, info.exceptions, info.matchingAspects); mv.visitCode(); mv.visitMaxs(-1, -1); mv.visitEnd(); } } // Add the STATIC_ASPECTS_FIELD cv.visitField(ACC_PRIVATE + ACC_STATIC, AOPContext.STATIC_ASPECTS_FIELD, "Ljava/util/Map;", "Ljava/util/Map<Ljava/lang/String;Ljava/util/List<Ljava/lang/String;>;>;", null).visitEnd(); if (mergingClassNode != null) { // Add the STATIC_IS_MERGING_REVERTED_FIELD cv.visitField(ACC_PRIVATE + ACC_STATIC, AOPContext.STATIC_IS_MERGING_REVERTED_FIELD, "Z", null, null) .visitEnd(); } // Declare the static aspects field within the class' static block if not done yet if (!isStaticBlockVisited) { mv = cv.visitMethod(ACC_STATIC, "<clinit>", "()V", null, null); if (!tryToAppendReplacingClassStaticBlock(mv)) { mv.visitCode(); initializeStaticAspectsField(mv); int maxStack = 2; if (mergingClassNode != null) { initializeStaticIsMergingActiveField(mv); maxStack++; } mv.visitInsn(RETURN); mv.visitMaxs(maxStack, 0); mv.visitEnd(); } isStaticBlockVisited = true; } cv.visitInnerClass(anonymousInnerClassName, null, null, 0); cv.visitEnd(); // Instantiate the static aspects field via a dynamic anonymous inner class and populate it with // all advised methods and their matching aspects ClassWriter cw = new ClassWriter(0); // cv = new org.objectweb.asm.util.CheckClassAdapter(cw); // ASM Tree API (asm-tree.jar) is needed for this cw.visit(V1_5, ACC_PUBLIC, anonymousInnerClassName, "Ljava/util/HashMap<Ljava/lang/String;Ljava/util/List<Ljava/lang/String;>;>;", "java/util/HashMap", null); cw.visitOuterClass(className, null, null); cw.visitInnerClass(anonymousInnerClassName, null, null, 0); mv = cw.visitMethod(ACC_PUBLIC, "<init>", "()V", null, null); mv.visitCode(); mv.visitVarInsn(ALOAD, 0); mv.visitMethodInsn(INVOKESPECIAL, "java/util/HashMap", "<init>", "()V"); for (AspectWeaver.MethodInfo info : interceptedMethodInfos) { mv.visitTypeInsn(NEW, "java/util/LinkedList"); mv.visitInsn(DUP); mv.visitMethodInsn(INVOKESPECIAL, "java/util/LinkedList", "<init>", "()V"); mv.visitVarInsn(ASTORE, 1); for (Aspect aspect : info.matchingAspects) { mv.visitVarInsn(ALOAD, 1); mv.visitLdcInsn(aspect.getId()); mv.visitMethodInsn(INVOKEINTERFACE, "java/util/List", "add", "(Ljava/lang/Object;)Z"); mv.visitInsn(POP); } mv.visitVarInsn(ALOAD, 0); mv.visitLdcInsn(info.methodName + info.desc); mv.visitVarInsn(ALOAD, 1); mv.visitMethodInsn(INVOKEVIRTUAL, anonymousInnerClassName, "put", "(Ljava/lang/Object;Ljava/lang/Object;)Ljava/lang/Object;"); mv.visitInsn(POP); } mv.visitInsn(RETURN); mv.visitMaxs(3, 2); mv.visitEnd(); // Finish up class writer cw.visitEnd(); // Register the dynamic anonymous inner class within the top level class loader for further class resolving issues TopLevelClassLoader.registerAnonymousInnerClass(className, anonymousInnerClassCounter, cw.toByteArray()); }
From source file:org.summer.aop.ltw.AspectWeaver.java
License:Open Source License
private boolean tryToAppendReplacingClassStaticBlock(MethodVisitor staticBlockVisitor) { if (replacingClassNode != null) { for (Object methodNode : replacingClassNode.methods) { MethodNode mn = (MethodNode) methodNode; if (mn.name.equals("<clinit>")) { if (mn.instructions.size() > 0) { AbstractInsnNode first = mn.instructions.getFirst(); mn.instructions.insertBefore(first, new TypeInsnNode(NEW, anonymousInnerClassName)); mn.instructions.insertBefore(first, new InsnNode(DUP)); mn.instructions.insertBefore(first, new MethodInsnNode(INVOKESPECIAL, anonymousInnerClassName, "<init>", "()V")); mn.instructions.insertBefore(first, new FieldInsnNode(PUTSTATIC, className, AOPContext.STATIC_ASPECTS_FIELD, "Ljava/util/Map;")); }/*from w w w .ja v a2 s . c o m*/ mn.accept(staticBlockVisitor); return true; } } } return false; }
From source file:org.teavm.parsing.Parser.java
License:Apache License
public static MethodHolder parseMethod(MethodNode node, String className, String fileName) { MethodNode nodeWithoutJsr = new MethodNode(Opcodes.ASM5, node.access, node.name, node.desc, node.signature, node.exceptions.toArray(new String[0])); JSRInlinerAdapter adapter = new JSRInlinerAdapter(nodeWithoutJsr, node.access, node.name, node.desc, node.signature, node.exceptions.toArray(new String[0])); node.accept(adapter); node = nodeWithoutJsr;/*from ww w .ja v a2 s . c o m*/ ValueType[] signature = MethodDescriptor.parseSignature(node.desc); MethodHolder method = new MethodHolder(node.name, signature); parseModifiers(node.access, method); ProgramParser programParser = new ProgramParser(); programParser.setFileName(fileName); Program program = programParser.parse(node, className); new UnreachableBasicBlockEliminator().optimize(program); PhiUpdater phiUpdater = new PhiUpdater(); phiUpdater.updatePhis(program, applySignature(program, method.getParameterTypes())); method.setProgram(program); parseAnnotations(method.getAnnotations(), node.visibleAnnotations, node.invisibleAnnotations); while (program.variableCount() <= method.parameterCount()) { program.createVariable(); } if (node.annotationDefault != null) { method.setAnnotationDefault(parseAnnotationValue(node.annotationDefault)); } for (int i = 0; i < method.parameterCount(); ++i) { parseAnnotations(method.parameterAnnotation(i), node.visibleParameterAnnotations != null ? node.visibleParameterAnnotations[i] : null, node.invisibleParameterAnnotations != null ? node.invisibleParameterAnnotations[i] : null); } return method; }