java - 自定义系统类加载器和 MessageDigest 的奇怪行为

标签 java security classloader

我有一个使用自定义系统类加载器的应用程序,由 Djava.system.class.loader=class 参数设置。该应用程序使用 RMI。在 eclipse 中一切正常,但是如果我导出一个可运行的 jar,就会发生这个错误:

Caused by: java.lang.SecurityException: SHA MessageDigest not available
    at sun.rmi.server.Util.computeMethodHash(Unknown Source)
    at sun.rmi.server.UnicastServerRef$HashToMethod_Maps.computeValue(Unknown Source)
    at sun.rmi.server.UnicastServerRef$HashToMethod_Maps.computeValue(Unknown Source)
    at sun.rmi.server.WeakClassHashMap.get(Unknown Source)
    at sun.rmi.server.UnicastServerRef.exportObject(Unknown Source)
    at sun.rmi.registry.RegistryImpl.setup(Unknown Source)
    at sun.rmi.registry.RegistryImpl.<init>(Unknown Source)
    at java.rmi.registry.LocateRegistry.createRegistry(Unknown Source)

我很自然地试图解决这个问题,并写了一个简单的 MessageDigest md = MessageDigest.getInstance("SHA"); 作为我的 main.xml 文件的第一行。基本上是一样的。确切的错误是:

java.security.NoSuchAlgorithmException: SHA MessageDigest not available
    at sun.security.jca.GetInstance.getInstance(Unknown Source)
    at java.security.Security.getImpl(Unknown Source)
    at java.security.MessageDigest.getInstance(Unknown Source)

然后我尝试使用一个简单的 ClassLoader 作为 SystemClassloader。现在看起来像这样:

public class RootClassLoader extends ClassLoader{
    @Override
    public Class<?> loadClass(String name) throws ClassNotFoundException {
        return super.loadClass(name);
    }

    public RootClassLoader(ClassLoader loader){
        super(loader);
    }
}

还是一样。如果我将这个场景重建为一个新项目,一切都会按预期进行,所以显然还有其他东西坏了,但现在我不知道是什么。

我在程序的任何地方都没有使用安全管理器,我使用的是 oracle 的标准 jre7。

有什么我可能忽略的吗?

更新: 即使我根本不重写 loadClass 方法,也会发生错误......它似乎失败只是因为有一个非标准的系统类加载器,不管它实际做了什么

更新 2: 我列出了所有可用的安全提供程序/算法。当我在 eclipse 中执行代码时(仍然使用自定义类加载器),一切似乎都井井有条,但是在执行可运行的 jar 时,完整的 SUN version 1.7 Provider 似乎丢失了。没有自定义类加载器,一切都是一样的。在仅包含上述场景(并且有效)的环境中,一切看起来都一样,并且每个星座都有 SUN version 1.7 Provider。

更新 3: -verbose:class 显示包 sun.security.provider 等未加载。我不知道为什么,因为这两种选择都是从缺少包的来源 jsse.jar 加载类,并且都打印 [Opened C:\Program Files\Java\jre7\lib\jsse.jar](更新 4:实际上它确实被加载了。就在很久之后。甚至 sun.security.provider.SHA 都被加载到两个变体中。这更奇怪)

最佳答案

我找到了这个问题的根源。我不知道为什么以及如何发生这种情况,但似乎我使用的第 3 方库是罪魁祸首。当我删除 lib 时,一切正常。同样,我不知道这怎么可能

关于java - 自定义系统类加载器和 MessageDigest 的奇怪行为,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/18334751/

相关文章:

java - 垃圾收集器 : CMS abort preclean issue?

java - Hibernate 4.1 错误 : Could not create DynamicParameterizedType for type: org. hibernate.type.EnumType

java - WebSocket 安全 Java 配置

java - JVM什么时候加载注解类

java - 使用 IEnumertor 或 IEnumerable c# 接口(interface)?

java - 是否可以通过openid协议(protocol)认证印度不公平aadhar

.net - 将密码放在配置文件中的好方法是什么?

c - 相当简单的 C 代码中的安全漏洞

java - 多个类加载器和 VM 案例中的单例

java - URLClassLoader 无法在 Linux 上加载依赖项