--- old/src/java.base/share/classes/jdk/internal/reflect/ReflectionFactory.java 2018-05-01 00:23:18.000000000 +0800 +++ new/src/java.base/share/classes/jdk/internal/reflect/ReflectionFactory.java 2018-05-01 00:23:17.000000000 +0800 @@ -173,6 +173,12 @@ */ public FieldAccessor newFieldAccessor(Field field, boolean override) { checkInitted(); + + // use the root Field that will not cache caller class + Field f = langReflectAccess.getRoot(field); + if (f != null) { + field = f; + } return UnsafeFieldAccessorFactory.newFieldAccessor(field, override); } @@ -186,6 +192,12 @@ } } + // use the root Method that will not cache caller class + Method m = langReflectAccess.getRoot(method); + if (m != null) { + method = m; + } + if (noInflation && !ReflectUtil.isVMAnonymousClass(method.getDeclaringClass())) { return new MethodAccessorGenerator(). generateMethod(method.getDeclaringClass(), @@ -215,6 +227,13 @@ return new InstantiationExceptionConstructorAccessorImpl ("Can not instantiate java.lang.Class"); } + + // use the root Constructor that will not cache caller class + Constructor ctr = langReflectAccess.getRoot(c); + if (ctr != null) { + c = ctr; + } + // Bootstrapping issue: since we use Class.newInstance() in // the ConstructorAccessor generation process, we have to // break the cycle here.