美文网首页
Java ASM 和范型(Version:asm3.2/5.0.

Java ASM 和范型(Version:asm3.2/5.0.

作者: MicoCube | 来源:发表于2019-01-10 17:01 被阅读0次
  • 依赖
    spring5.1.3 自带asm5.0.3,spring4.3.6 自带asm-3.2,还要需要一个jar:asm-commons,和asm版本一致就行
  • 测试类
import java.io.File;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.LinkedHashMap;
import java.util.List;

public class Abc<T, U> extends LinkedHashMap<T, U> implements Iterable<T> {
    public Abc() {
        super();
    }

    public Iterator iterator2(T var1, U var2) {
        return null;
    }

    public Iterator<T> iterator() {
        return null;
    }

    public Integer compareTo(Integer var1) {
        return var1;
    }

    public T getA(U var1) {
        return null;
    }

    public List<File> get() {
        ArrayList arrayList = new ArrayList();
        return arrayList;
    }

    public static void main(String[] var0) {
        System.out.println("aaa");
    }
}
  • 类加载器
import java.io.*;
import java.net.MalformedURLException;
import java.net.URL;
import java.util.ArrayList;
import java.util.StringTokenizer;


public class BinaryClassLoader {
    private final ArrayList m_bases;

    public BinaryClassLoader() {
        m_bases = new ArrayList();
    }

    public void addPaths(String list) {
        StringTokenizer tkzr = new StringTokenizer(list, File.pathSeparator);
        while (tkzr.hasMoreTokens()) {
            File file = new File(tkzr.nextToken());
            String spec = null;
            if (file.isFile() && file.getName().toLowerCase().endsWith(".jar")) {
                spec = "jar:file://" + file.getAbsolutePath() + "!/";
            } else if (file.exists()) {
                spec = "file://" + file.getAbsolutePath();
                if (!spec.endsWith("/")) {
                    spec += '/';
                }
            }
            if (spec != null) {
                m_bases.add(spec);
                System.out.println("add loader path:" + spec);
            }
        }
    }

    public byte[] getBytes(String name) {
        String pname = name.replace('.', '/') + ".class";
        for (int i = 0; i < m_bases.size(); i++) {
            String base = (String) m_bases.get(i);
            try {
                URL url = new URL(base + pname);
                InputStream is = url.openStream();

                // read the entire content into byte array
                ByteArrayOutputStream bos = new ByteArrayOutputStream();
                byte[] buff = new byte[1024];
                int length;
                while ((length = is.read(buff)) >= 0) {
                    bos.write(buff, 0, length);
                }
                return bos.toByteArray();

            } catch (MalformedURLException e) {
                e.printStackTrace();
            } catch (FileNotFoundException e) {
                // normal event when not found relative to current base
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        throw new IllegalArgumentException("Class not found: " + name);
    }
}
  • ClassVisitor(ASM3)
import org.objectweb.asm.FieldVisitor;
import org.objectweb.asm.MethodVisitor;
import org.objectweb.asm.commons.EmptyVisitor;
public class ShowSignaturesVisitor extends EmptyVisitor {
    public void visit(int version, int access, String name, String sig,
                      String sname, String[] inames) {
        System.out.println("Class " + name + " signature:");
        System.out.println(" " + sig);
        super.visit(version, access, name, sig, sname, inames);
    }

    public FieldVisitor visitField(int access, String name, String desc,
                                   String sig, Object value) {
        System.out.println("Field " + name + " descriptor and signature:");
        System.out.println(" " + desc);
        System.out.println(" " + sig);
        return super.visitField(access, name, desc, sig, value);
    }

    public MethodVisitor visitMethod(int access, String name, String desc,
                                     String sig, String[] exceptions) {
        System.out.println("Method " + name + "() descriptor and signature:");
        System.out.println(" " + desc);
        System.out.println(" " + sig);
        return super.visitMethod(access, name, desc, sig, exceptions);
    }
}
  • ClassVisitor(ASM5)
import org.objectweb.asm.ClassVisitor;
import org.objectweb.asm.FieldVisitor;
import org.objectweb.asm.MethodVisitor;

import static org.objectweb.asm.Opcodes.ASM4;
import static org.objectweb.asm.Opcodes.ASM5;

public class ShowSignaturesVisitor extends ClassVisitor {
    public ShowSignaturesVisitor() {
        super(ASM5);
    }

    public void visit(int version, int access, String name, String sig,
                      String sname, String[] inames) {
        System.out.println("Class " + name + " signature:");
        System.out.println(" " + sig);
        super.visit(version, access, name, sig, sname, inames);
    }

    public FieldVisitor visitField(int access, String name, String desc,
                                   String sig, Object value) {
        System.out.println("Field " + name + " descriptor and signature:");
        System.out.println(" " + desc);
        System.out.println(" " + sig);
        return super.visitField(access, name, desc, sig, value);
    }

    public MethodVisitor visitMethod(int access, String name, String desc,
                                     String sig, String[] exceptions) {
        System.out.println("Method " + name + "() descriptor and signature:");
        System.out.println(" " + desc);
        System.out.println(" " + sig);
        return super.visitMethod(access, name, desc, sig, exceptions);
    }
}
  • 主程序
import org.objectweb.asm.ClassReader;

import java.lang.reflect.Method;


public class PrintSignatures {
    public static void main(String[] args) {

//        args = new String[]{"com.coding.asm.check.Abc"};
        args = new String[]{"Abc"};
        System.getProperties().forEach((p,v) ->{
            System.out.println(p+":"+v);
        });
        if (args.length == 1) {
            try {

                // configure binary class loader from classpaths
                BinaryClassLoader loader = new BinaryClassLoader();
                loader.addPaths(System.getProperty("java.class.path"));
                loader.addPaths(System.getProperty("sun.boot.library.path"));


                // analyze the named class 加载类
                byte[] bytes = loader.getBytes(args[0]);
                ClassReader creader = new ClassReader(bytes);

                creader.accept(new ShowSignaturesVisitor(), 1);


                Class<?> abc = Class.forName("Abc");
                Object o = abc.getDeclaredConstructor(null).newInstance();
                Method print = abc.getDeclaredMethod("print", null);
                print.invoke(o,null);

            } catch (Exception e) {
                e.printStackTrace();
            }

        } else {
            System.out.println("Usage: class full name ");
        }
    }
}
  • 执行结果
Class Abc signature:
 <K:Ljava/lang/Object;V:Ljava/lang/Object;>Ljava/util/LinkedHashMap<TK;TV;>;Ljava/lang/Iterable<TK;>;
Field a descriptor and signature:
 I
 null
Field b descriptor and signature:
 D
 null
Field c descriptor and signature:
 Ljava/util/Map;
 Ljava/util/Map<TK;TV;>;
Method <init>() descriptor and signature:
 ()V
 ()V
Method iterator2() descriptor and signature:
 (Ljava/lang/Object;Ljava/lang/Object;)Ljava/util/Iterator;
 (TK;TV;)Ljava/util/Iterator;
Method iterator() descriptor and signature:
 ()Ljava/util/Iterator;
 ()Ljava/util/Iterator<TK;>;
Method compareTo() descriptor and signature:
 (Ljava/lang/Integer;)Ljava/lang/Integer;
 (Ljava/lang/Integer;)Ljava/lang/Integer;
Method getA() descriptor and signature:
 (Ljava/lang/Object;)Ljava/lang/Object;
 (TV;)TK;
Method get() descriptor and signature:
 ()Ljava/util/List;
 ()Ljava/util/List<Ljava/io/File;>;
Method main() descriptor and signature:
 ([Ljava/lang/String;)V
 ([Ljava/lang/String;)V
Method print() descriptor and signature:
 ()V
 ()V
Hello ASM!

相关文章

网友评论

      本文标题:Java ASM 和范型(Version:asm3.2/5.0.

      本文链接:https://www.haomeiwen.com/subject/iyqirqtx.html