类加载器?

类加载器?_第1张图片
深入理解JVM.png
类加载器?_第2张图片
类加载器.png
  • 自定义ClassLoader代码
package com.cqu.test;

import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;

public class ClassLoaderTest extends ClassLoader{
    private String mlibPath;
    public ClassLoaderTest(String path) {
        this.mlibPath=path;
    }
    @Override
    protected Class findClass(String name) throws ClassNotFoundException {
        String fileName=getFileName(name);
        File file=new File(mlibPath,fileName);
        try {
            FileInputStream is=new FileInputStream(file);
            ByteArrayOutputStream bos=new ByteArrayOutputStream();
            int len=0;
            try {
                while((len = is.read()) != -1) {
                    bos.write(len);
                }
            }catch (IOException e) {
                e.printStackTrace();
            }
            byte[] data=bos.toByteArray();
            is.close();
            bos.close();
            return defineClass(name, data, 0,data.length);
        }catch (IOException e) {
            e.printStackTrace();
        }
        
        return super.findClass(name);
    }
    private String getFileName(String name) {
        int index=name.lastIndexOf('.');
        if(index==-1) {
            return name+".class";
        }else {
            return name.substring(index+1)+".class";
        }
        
    }
    
    
    public static void main(String[] args) {
        ClassLoaderTest diskLoader=new ClassLoaderTest("E:\\Temp");
        try {
            Class c=diskLoader.loadClass("com.cqu.test.Test");
            if(c!=null) {
                try {
                    Object object=c.newInstance();
                    Method method=c.getDeclaredMethod("say", null);
                    method.invoke(object, null);
                }catch (InstantiationException | IllegalAccessException | NoSuchMethodException | SecurityException | IllegalArgumentException | InvocationTargetException e) {
                    e.printStackTrace();
                }
            }
        }catch (ClassNotFoundException e) {
            e.printStackTrace();
        }
    }
}

  • 控制台输出
Say Hello

类加载器玩出点花样

  • 给程序加密,生成的字节码文件只能由我们自己的类加载器加载,没有我们的类加载器,谁都不能运行我们的代码!
  • FileUtils.java
package com.cqu.test;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileNotFoundException;
import java.io.FileOutputStream;
import java.io.IOException;

/**
 * @author Rush
 *加密工具类
 */
public class FileUtils {
    public static void test(String path) {
        File file=new File(path);
        try {
            FileInputStream fis=new FileInputStream(file);
            FileOutputStream fos=new FileOutputStream(path+"en");
            int b=0;
            int b1=0;
            try {
                while((b = fis.read()) != -1) {
                    fos.write(b^2);
                }
                fos.close();
                fis.close();
            }catch (IOException e) {
                e.printStackTrace();
            }
        }catch (FileNotFoundException e) {
            e.printStackTrace();
        }
    }
    public static void main(String[] args) {
        FileUtils fileUtils=new FileUtils();
        fileUtils.test("E:\\Temp\\Test.class");
    }
}

  • 关键部分
fos.write(b^2);

对字节码进行异或操作加密。

  • DeClassLoader.java
package com.cqu.test;

import java.io.ByteArrayOutputStream;
import java.io.File;
import java.io.FileInputStream;
import java.io.IOException;

public class DeClassLoader extends ClassLoader{
    private String mlibPath;
    public DeClassLoader(String path) {
        mlibPath=path;
    }
    @Override
    protected Class findClass(String name) throws ClassNotFoundException {
        String fileName=getFileName(name);
        File file=new File(mlibPath,fileName);
        try {
            FileInputStream is=new FileInputStream(file);
            ByteArrayOutputStream bos=new ByteArrayOutputStream();
            int len=0;
            byte b=0;
            try {
                while((len=is.read())!=-1) {
                    b=(byte)(len^2);
                    bos.write(b);
                }
            }catch (IOException e) {
                e.printStackTrace();
            }
            byte[] data=bos.toByteArray();
            is.close();
            bos.close();
            return defineClass(name, data, 0,data.length);
        }catch (IOException e) {
            e.printStackTrace();
        }
        
        return super.findClass(name);
    }
    
    private String getFileName(String name) {
        int index=name.lastIndexOf('.');
        if(index!=-1) {
            return name+".classen";
        }else {
            return name.substring(index+1)+".classen";
        }
    }
    
}

  • TestDeClassLoader.java
package com.cqu.test;

import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;

public class TestDeClassLoader {
    
    public static void main(String[] args) {
        DeClassLoader diskLoader=new DeClassLoader("E:\\Temp");
        try {
            Class c =diskLoader.loadClass("com.cqu.test.Test");
            if(c!=null) {
                try {
                    Object obj=c.newInstance();
                    Method method=c.getDeclaredMethod("say", null);
                    method.invoke(obj, null);
                }catch (InstantiationException | IllegalAccessException | NoSuchMethodException | SecurityException | IllegalArgumentException | InvocationTargetException e) {
                    e.printStackTrace();
                }
            }
        }catch(ClassNotFoundException e) {
            e.printStackTrace();
        } 
    }
    }
    

你可能感兴趣的:(类加载器?)