JAVA加密解密:自界说类加载器应用
副标题#e#最近在研究JAVA CLASS LOADING技能,已实现了一个自界说的加载器。对今朝自界说加载器的应用,还在探讨中。下面是自界说的CLASSLOADER在JAVA加密解密方面的一些研究。
JAVA安详
JAVA是表明执行的语言,对付差异的操纵平台都有相应的JVM对字节码文件举办表明执行。而这个字节码文件,也就是我们平时所看到的每一个.class文件。
这是我们各人都知道的知识,也就是由.java文件,颠末编译器编译,酿成JVM所能表明的.class文件。
而这个进程,在此刻果真的网络技能中,操作一个反编译器,任何人都可以很容易的获取它的源文件。这对付许多人来说是不但愿看到的。
对付加密解密技能,我懂的不多,有些可以操作某种技能“恍惚”JAVA类文件。这样可以或许使反编译的难度增加。但预计反编译器的技能程度也在不绝晋升,导致这种要领层层受阻。别的尚有许多其他的技能也可以实现对JAVA文件的加密解密。我此刻所想要研究的,就是个中的一种。
JAVA的机动性使反编译变得容易,同时,也让我们的加密解密的要领变得机动。
操作自界说的CLASSLOADER
参照:http://www.blogjava.net/realsmy/archive/2007/04/18/111582.html
JAVA中的每一个类都是通过类加载器加载到内存中的。对付类加载器的事情流程如下暗示:
1.searchfile()
找到我所要加载的类文件。(抛除JAR包的观念,此刻只是要加载一个.class文件)
2.loadDataClass()
读取这个类文件的字节码。
3.difineClass()
加载类文件。(加载的进程其实很巨大,我们此刻先不研究它。)
从这个进程中我们能很清楚的发明,自界说的类加载可以或许很轻松的节制每个类文件的加载进程。这样在第二步(loadDataClass)和第三步(difineClass)之间,我们将会有本身的空间机动的节制这个进程。
我们加密解密的技能就应用到这里。
加密解密
JAVA加密解密的技能有许多。JAVA本身提供了精采的类库对各类算法举办支持。对付回收哪种算法,网络上说法纷歧,本身去GOOGLE一下吧。
下面用DES对称加密算法(设定一个密钥,然后对所有的数据举办加密)来简朴举个例子。
首先,生成一个密钥KEY。
我把它生存到key.txt中。这个文件就象是一把钥匙。谁拥有它,谁就能解开我们的类文件。代码参考如下:
package com.neusoft.jiami; import java.io.File; import java.io.FileOutputStream; import java.security.SecureRandom; import javax.crypto.KeyGenerator; import javax.crypto.SecretKey; class Key { private String keyName; public Key(String keyName) { this.keyName = keyName; } public void createKey(String keyName) throws Exception { // 建设一个可信任的随机数源,DES算法需要 SecureRandom sr = new SecureRandom(); // 用DES算法建设一个KeyGenerator工具 KeyGenerator kg = KeyGenerator.getInstance("DES"); // 初始化此密钥生成器,使其具有确定的密钥长度 kg.init(sr); // 生成密匙 SecretKey key = kg.generateKey(); // 获取密钥数据 byte rawKeyData[] = key.getEncoded(); // 将获取到密钥数据生存到文件中,待解密时利用 FileOutputStream fo = new FileOutputStream(new File(keyName)); fo.write(rawKeyData); } public static void main(String args[]) { try { new Key("key.txt"); } catch (Exception e) { e.printStackTrace(); } }#p#副标题#e#
第二步,对我们所要举办加密的类文件举办加密。
好比我有一个DigestPass类,已经被正常编译好生成DigestPass.class文件。此时,这个类文件是任何人都可以用的。因为系统的类加载器可以自动的加载它。那么下一步,我们要做的就是把这个类文件加密。使系统的类加载器无法读取到正确的字节码文件。参考代码如下:
package com.neusoft.jiami; import java.io.File; import java.io.FileInputStream; import java.io.FileOutputStream; import java.security.SecureRandom; import javax.crypto.Cipher; import javax.crypto.SecretKey; import javax.crypto.SecretKeyFactory; import javax.crypto.spec.DESKeySpec; public class JiaMi { public static void main(String[] args) throws Exception { // DES算法要求有一个可信任的随机数源 SecureRandom sr = new SecureRandom(); // 得到密匙数据 FileInputStream fi = new FileInputStream(new File("key.txt")); byte rawKeyData[] = new byte[fi.available()]; fi.read(rawKeyData); fi.close(); // 从原始密匙数据建设DESKeySpec工具 DESKeySpec dks = new DESKeySpec(rawKeyData); // 建设一个密匙工场,然后用它把DESKeySpec转换成一个SecretKey工具 SecretKey key = SecretKeyFactory.getInstance("DES").generateSecret(dks); // Cipher工具实际完成加密操纵 Cipher cipher = Cipher.getInstance("DES"); // 用密匙初始化Cipher工具 cipher.init(Cipher.ENCRYPT_MODE, key, sr); // 此刻,获取要加密的文件数据 FileInputStream fi2 = new FileInputStream(new File("DigestPass.class")); byte data[] = new byte[fi2.available()]; fi2.read(data); fi2.close(); // 正式执行加密操纵 byte encryptedData[] = cipher.doFinal(data); // 用加密后的数据包围原文件 FileOutputStream fo = new FileOutputStream(new File("DigestPass.class")); fo.write(encryptedData); fo.close(); } } 第三步,用自界说的CLASSLOADER举办加载。参考代码如下: package com.neusoft.jiami; import java.io.File; import java.io.FileInputStream; import java.io.FileOutputStream; import java.security.SecureRandom; import javax.crypto.Cipher; import javax.crypto.SecretKey; import javax.crypto.SecretKeyFactory; import javax.crypto.spec.DESKeySpec; import com.neusoft.classloader.MyClassLoader; public class JieMi { public static void main(String[] args) throws Exception { // DES算法要求有一个可信任的随机数源 SecureRandom sr = new SecureRandom(); // 得到密匙数据 FileInputStream fi = new FileInputStream(new File("key.txt")); byte rawKeyData[] = new byte[fi.available()];// = new byte[5]; fi.read(rawKeyData); fi.close(); // 从原始密匙数据建设一个DESKeySpec工具 DESKeySpec dks = new DESKeySpec(rawKeyData); // 建设一个密匙工场,然后用它把DESKeySpec工具转换成一个SecretKey工具 SecretKey key = SecretKeyFactory.getInstance("DES").generateSecret(dks); // Cipher工具实际完成解密操纵 Cipher cipher = Cipher.getInstance("DES"); // 用密匙初始化Cipher工具 cipher.init(Cipher.DECRYPT_MODE, key, sr); // 此刻,获取数据并解密 FileInputStream fi2 = new FileInputStream(new File("DigestPass.class")); byte encryptedData[] = new byte[fi2.available()]; fi2.read(encryptedData); fi2.close(); // 正式执行解密操纵 byte decryptedData[] = cipher.doFinal(encryptedData); // 这时把数据还原成原有的类文件 // FileOutputStream fo = new FileOutputStream(new // File("DigestPass.class")); // fo.write(decryptedData); // 用解密后的数据加载类并应用 MyClassloader mcl = new MyClassloader("E:/"); Class cl = mcl.loadClass(decryptedData, "com.neusoft.jiami.DigestPass"); DigestPass dp = cl.newInstance(); } }
这样,我们就完成了类的加密解密。这个进程留给我们修改的空间还许多。我也在领略进程中。
总结
自界说的类加载器可以或许机动的节制类的加载进程。从而可以实现一些我们所要的成果。
#p#分页标题#e#
可是,纵然是这样的加密技能,对付某些好手来说,依然是懦弱的。我们所需要做的就是,领略这个中的进程,把握这样的技能,最终可以或许应用到我们本身的实际项目中来。