8222895: StackOverflowError in custom security manager that relies on ClassSpecializer
Reviewed-by: alanb
--- a/make/jdk/src/classes/build/tools/classlist/HelloClasslist.java Wed May 01 20:48:19 2019 -0400
+++ b/make/jdk/src/classes/build/tools/classlist/HelloClasslist.java Thu May 02 10:38:00 2019 +0200
@@ -72,6 +72,8 @@
String SC = String.valueOf(args.length) + "string";
String SCS = String.valueOf(args.length) + "string" + String.valueOf(args.length);
String CSS = "string" + String.valueOf(args.length) + String.valueOf(args.length);
+ String CSC = "string" + String.valueOf(args.length) + "string";
+ String SSC = String.valueOf(args.length) + String.valueOf(args.length) + "string";
String CSCS = "string" + String.valueOf(args.length) + "string" + String.valueOf(args.length);
String SCSC = String.valueOf(args.length) + "string" + String.valueOf(args.length) + "string";
String CSCSC = "string" + String.valueOf(args.length) + "string" + String.valueOf(args.length) + "string";
--- a/src/java.base/share/classes/java/lang/invoke/ClassSpecializer.java Wed May 01 20:48:19 2019 -0400
+++ b/src/java.base/share/classes/java/lang/invoke/ClassSpecializer.java Thu May 02 10:38:00 2019 +0200
@@ -25,6 +25,7 @@
package java.lang.invoke;
+import jdk.internal.access.SharedSecrets;
import jdk.internal.loader.BootLoader;
import jdk.internal.org.objectweb.asm.ClassWriter;
import jdk.internal.org.objectweb.asm.FieldVisitor;
@@ -37,6 +38,7 @@
import java.lang.reflect.Modifier;
import java.security.AccessController;
import java.security.PrivilegedAction;
+import java.security.ProtectionDomain;
import java.util.ArrayList;
import java.util.Collections;
import java.util.List;
@@ -575,19 +577,19 @@
// load class
InvokerBytecodeGenerator.maybeDump(classBCName(className), classFile);
- Class<?> speciesCode;
-
- MethodHandles.Lookup lookup = IMPL_LOOKUP.in(topClass());
- speciesCode = AccessController.doPrivileged(new PrivilegedAction<>() {
- @Override
- public Class<?> run() {
- try {
- return lookup.defineClass(classFile);
- } catch (Exception ex) {
- throw newInternalError(ex);
- }
- }
- });
+ ClassLoader cl = topClass.getClassLoader();
+ ProtectionDomain pd = null;
+ if (cl != null) {
+ pd = AccessController.doPrivileged(
+ new PrivilegedAction<>() {
+ @Override
+ public ProtectionDomain run() {
+ return topClass().getProtectionDomain();
+ }
+ });
+ }
+ Class<?> speciesCode = SharedSecrets.getJavaLangAccess()
+ .defineClass(cl, className, classFile, pd, "_ClassSpecializer_generateConcreteSpeciesCode");
return speciesCode.asSubclass(topClass());
}
--- a/test/jdk/java/lang/String/concat/WithSecurityManager.java Wed May 01 20:48:19 2019 -0400
+++ b/test/jdk/java/lang/String/concat/WithSecurityManager.java Thu May 02 10:38:00 2019 +0200
@@ -26,7 +26,7 @@
/**
* @test
* @summary String concatenation fails with a custom SecurityManager that uses concatenation
- * @bug 8155090 8158851
+ * @bug 8155090 8158851 8222895
* @requires !vm.graal.enabled
*
* @compile WithSecurityManager.java
@@ -55,12 +55,17 @@
@Override
public void checkPermission(Permission perm) {
String abc = "abc";
- String full = abc + "def";
+ int ival = perm.hashCode();
+ String full = abc + "abc";
+ // Contorted to avoid sweeping cases where we've
+ // pre-generated commonly used species under the rug
+ full = "abc" + ival + "def" + abc + "def" + abc + "def" +
+ abc + "def" + ival + "def" + abc + "def" +
+ abc + "def" + abc + "def" + abc + "def";
}
};
System.setSecurityManager(sm);
- ClassLoader cl = new ClassLoader() {
- };
+ ClassLoader cl = new ClassLoader() {};
}
// Second time should succeed to run after bootstrapping
@@ -69,12 +74,19 @@
@Override
public void checkPermission(Permission perm) {
String abc = "abc";
- String full = abc + "def";
+ int ival = perm.hashCode();
+ String full = abc + "abc";
+ // Contorted variant to avoid sweeping cases where we've
+ // pre-generated commonly used species under the rug
+ full = "abc" + ival + "def" + abc + "def" + abc + "def" +
+ abc + "def" + ival + "def" + abc + "def" +
+ abc + "def" + abc + "def" + abc + "def";
}
};
+
+ // Provoke checkPermission invocation
System.setSecurityManager(sm);
- ClassLoader cl = new ClassLoader() {
- };
+ ClassLoader cl = new ClassLoader() {};
}
}
}