如何在Java中创建启用SecurityManager的newInstance

3

我需要创建一个从不受信任的类文件中加载的类的新实例。 现在我做以下操作:

classLoader.loadClass(UNSTRUSTED_CLASS).newInstance()

问题在于,如果我启用了安全管理器,它将不允许调用newInstance方法,但是如果禁用了安全管理器,则可以将恶意代码放入初始化块中,并且可以毫无问题地执行。

如何创建不受信任类的新实例?


可能是 https://stackoverflow.com/questions/36091323/java-set-security-permission-of-created-instances 的副本。 - Akash
@Akash 我看了那个问题。我可以分离方法调用,但无法分离实例化,因为它们有足够的不同之处。不幸的是,那个问题的答案也没有帮助。 - krems
你不能将受信任的调用类型与潜在不受信任的被调用方隔离开来吗?这样前者的 ProtectionDomain 就可以通过 PolicyClassLoader 获得必要的实例化特权,而后者仍然受到(严格)访问控制的限制吗? - Uux
这就是我一直在努力实现的,但不知道如何做。 现在我知道了,并将其作为答案分享。 - krems
你为什么会拥有一个“SecurityManager”,却不希望它应用于不受信任的代码呢? - user207421
我想申请应用于受信任的代码,但不适用于我的代码(调用反射API)。因此,我的受信任的代码实例化了不受信任类的对象。我希望在执行不受信任类的初始化和构造函数时启用安全管理器,但允许我在我的代码中使用反射。 - krems
2个回答

0

类的静态初始化程序和构造函数将始终与该类一起在堆栈上执行,因此在AccessControlContext中适当的ProtectionDomain。这并不是说可能存在其他问题,例如从父类加载器获取类,从而允许访问当前Thread/ThreadGroup/AppContext/ThreadLocal

除此之外,三个参数的Class.forName允许加载一个类而不进行初始化。但是,使用父类加载器中的代码加载类可能更典型。


0

好的,我使用了自定义类加载器从特定位置加载不受信任的代码。我可以在策略文件中为我的可信代码定义代码库,并授予其使用反射的权限。因此,来自另一个代码库的不受信任的代码将没有这个权限。

grant codeBase "file:/C:/path/to/trusted/code/classes" {
     permission java.lang.reflect.ReflectPermission "suppressAccessChecks";
};

使用此策略文件,从除了 codeBase 指定的位置加载的所有代码都将没有任何权限。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接