所以,我有一个自定义类加载器来将类从字节数组加载到内存中,我遇到了一个问题:当我尝试查看一个类是否可以从另一个(ClassLoader.isAssignableFrom)分配时,它返回 false,即使编译的类扩展或实现它。我假设因为它是由不同的自定义类加载器而不是系统加载的,所以我将如何解决这个问题?我需要这样做的原因是我想检查 jar 文件中的类文件是否是 ClassLoaders 本身,因为我正在为 jar 文件制作 Java 病毒扫描程序。自定义类加载器:
public class CL extends ClassLoader {
byte[] jar = null;
private HashMap<String, Class<?>> classes = new HashMap<String, Class<?>>();
private HashMap<String, byte[]> resources = new HashMap<String, byte[]>();
public CL(byte[] jar) {
this.jar = jar;
}
private JarInputStream getStream() {
try {
return new JarInputStream(new ByteArrayInputStream(jar));
}catch (IOException e) {
e.printStackTrace();
}
return null;
}
public InputStream getResourceAsStream(String name) {
if (!resources.containsKey(name)) {
try {
JarInputStream stream = getStream();
JarEntry entry = stream.getNextJarEntry();
ArrayList<JarEntry> ent = new ArrayList<JarEntry>();
while (entry != null) {
String en = entry.getName().replace("/", ".");
if (en.contains(".")) {
en = en.substring(0, en.lastIndexOf("."));
}
if (en.equals(name)) {
break;
}
ent.add(entry);
entry = stream.getNextJarEntry();
}
if (entry == null) {
for (JarEntry e : ent) {
String en = e.getName().replace("/", ".");
if (en.contains(".")) {
en = en.substring(0, en.lastIndexOf("."));
}
if (en.lastIndexOf(".") > 0 && en.substring(en.lastIndexOf(".") + 1).equals(name)) {
entry = e;
break;
}
}
}
if (entry == null) {
return null;
}
ent = null;
ByteArrayOutputStream byt = new ByteArrayOutputStream();
while (true) {
int r = stream.read();
if (r < 0) break;
byt.write(r);
}
stream.close();
byte[] reqc = byt.toByteArray();
return new ByteArrayInputStream(reqc);
}catch (IOException e) {
e.printStackTrace();
}
}else {
return new ByteArrayInputStream(resources.get(name));
}
return null;
}
public Class<?> findClass(String name) {
if (!classes.containsKey(name)) {
try {
JarInputStream stream = getStream();
JarEntry entry = stream.getNextJarEntry();
while (entry != null) {
String en = entry.getName().replace("/", ".");
if (en.contains(".")) {
en = en.substring(0, en.lastIndexOf("."));
}
if (en.equals(name)) {
break;
}
entry = stream.getNextJarEntry();
}
if (entry == null) {
return null;
}
ByteArrayOutputStream byt = new ByteArrayOutputStream();
while (true) {
int r = stream.read();
if (r < 0) break;
byt.write(r);
}
stream.close();
byte[] reqc = byt.toByteArray();
Class<?> c = defineClass(name, reqc, 0, reqc.length, CL.class.getProtectionDomain());
classes.put(name, c);
return c;
}catch (IOException e) {
e.printStackTrace();
}
}else {
return classes.get(name);
}
return null;
}
}
我用于检查是否可以从类加载器分配某些内容的代码(cl 是我的类加载器的一个实例):
Class<?> cls = cl.findClass(fname);
boolean isCL = false;
if (cls.isAssignableFrom(ClassLoader.class)) {
isCL = true;
}
boolean bCL = false;
for (Method m : cls.getMethods()) {
String mn = m.getName();
if (isCL) {
if (mn.contains("loadClass") || mn.contains("defineClass") || mn.contains("findClass")) {
bCL = true;
}
}
}
问题:isAssignableFrom 返回 false,即使它应该为 true。
那么,有没有办法解决这个问题?我不想切换类加载器,因为我最初是从 jar 加载的,但我希望能够在 jar 和 zip 中加载 jar。谢谢!