java – 为什么Android类加载器允许从另一个包反射访问包私有类的公共字段?

似乎 Android应用程序类加载器允许反射性地获取对包私有类的公共静态字段的引用,即使从不同的包(不同于上述类被定义的包),而Sun JDK类加载器例如不是’吨.

更具体地说,给出以下类定义:

package org.example.a

class PackagePrivateClass {
    public static final Parcelable.Creator<PackagePrivateClass> CREATOR = generateCreator();
}

以下代码在一个单独的包中:

package org.example.b

public class TestClass {
    public void testMethod() {
        final Class classRef = Class.forName("org.example.a.PackagePrivateClass");
        final Field creatorFieldRef = classRef.getField("CREATOR");
        creatorFieldRef.get(null);  // throws here (unless on Android)
    }
}

在Sun JVM上执行时,它会在最后一行引发一个IllegalAccessException:

java.lang.IllegalAccessException: Class org.example.b.TestClass can not access a member of class org.example.a.PackagePrivateClass with modifiers "public static final"
at sun.reflect.Reflection.ensureMemberAccess(Reflection.java:102)
...

但是,当在Android设备(5.1 Lollipop FWIW)上运行时,它会执行而不会抛出,并且creatorFieldRef.get(null)实际上返回到CREATOR字段的有效引用.

我的问题是:为什么会这样?是Android类加载器的错误还是功能?
(或者,如果适用,我的例子中出了什么错误)

解决方法

似乎这是在 commit中修复的android运行时的错误:

Add access checks to Method and Field reflection.

在此提交之前,可以通过反射来以不受限制的方式访问字段,甚至可以设置the value of final fields.

访问检查是在运行时函数ValidateFieldAccess和ValidateAccess中实现的now.

以上是来客网为你收集整理的java – 为什么Android类加载器允许从另一个包反射访问包私有类的公共字段?全部内容,希望文章能够帮你解决java – 为什么Android类加载器允许从另一个包反射访问包私有类的公共字段?所遇到的程序开发问题。

如果觉得来客网网站内容还不错,欢迎将来客网网站推荐给程序员好友。