75 76 // Prevent method compilation 77 @Retention(RetentionPolicy.RUNTIME) 78 @interface DontCompile { } 79 80 // Number of warmup iterations 81 @Retention(RetentionPolicy.RUNTIME) 82 @interface Warmup { 83 int value(); 84 } 85 86 public abstract class ValueTypeTest { 87 // Run "jtreg -Dtest.c1=true" to enable experimental C1 testing. 88 static final boolean TEST_C1 = Boolean.getBoolean("test.c1"); 89 90 // Random test values 91 public static final int rI = Utils.getRandomInstance().nextInt() % 1000; 92 public static final long rL = Utils.getRandomInstance().nextLong() % 1000; 93 94 // User defined settings 95 private static final boolean PRINT_GRAPH = true; 96 private static final boolean PRINT_TIMES = Boolean.parseBoolean(System.getProperty("PrintTimes", "false")); 97 private static boolean VERIFY_IR = Boolean.parseBoolean(System.getProperty("VerifyIR", "true")) && (!TEST_C1); 98 private static final boolean VERIFY_VM = Boolean.parseBoolean(System.getProperty("VerifyVM", "false")); 99 private static final String SCENARIOS = System.getProperty("Scenarios", ""); 100 private static final String TESTLIST = System.getProperty("Testlist", ""); 101 private static final String EXCLUDELIST = System.getProperty("Exclude", ""); 102 private static final int WARMUP = Integer.parseInt(System.getProperty("Warmup", "251")); 103 private static final boolean DUMP_REPLAY = Boolean.parseBoolean(System.getProperty("DumpReplay", "false")); 104 105 // Pre-defined settings 106 private static final List<String> defaultFlags = Arrays.asList( 107 "-XX:-BackgroundCompilation", "-XX:CICompilerCount=1", 108 "-XX:+PrintCompilation", "-XX:+PrintIdeal", "-XX:+PrintOptoAssembly", 109 "-XX:CompileCommand=quiet", 110 "-XX:CompileCommand=compileonly,java.lang.invoke.*::*", 111 "-XX:CompileCommand=compileonly,java.lang.Long::sum", 112 "-XX:CompileCommand=compileonly,java.lang.Object::<init>", 113 "-XX:CompileCommand=compileonly,compiler.valhalla.valuetypes.*::*"); 114 private static final List<String> verifyFlags = Arrays.asList( 115 "-XX:+VerifyOops", "-XX:+VerifyStack", "-XX:+VerifyLastFrame", "-XX:+VerifyBeforeGC", "-XX:+VerifyAfterGC", 116 "-XX:+VerifyDuringGC", "-XX:+VerifyAdapterSharing", "-XX:+StressValueTypeReturnedAsFields"); 117 118 protected static final WhiteBox WHITE_BOX = WhiteBox.getWhiteBox(); 119 protected static final int ValueTypePassFieldsAsArgsOn = 0x1; 120 protected static final int ValueTypePassFieldsAsArgsOff = 0x2; 121 protected static final int ValueTypeArrayFlattenOn = 0x4; 122 protected static final int ValueTypeArrayFlattenOff = 0x8; 123 protected static final int ValueTypeReturnedAsFieldsOn = 0x10; 124 protected static final int ValueTypeReturnedAsFieldsOff = 0x20; 125 static final int AllFlags = ValueTypePassFieldsAsArgsOn | ValueTypePassFieldsAsArgsOff | ValueTypeArrayFlattenOn | ValueTypeArrayFlattenOff | ValueTypeReturnedAsFieldsOn; 126 protected static final boolean ValueTypePassFieldsAsArgs = (Boolean)WHITE_BOX.getVMFlag("ValueTypePassFieldsAsArgs"); 127 protected static final boolean ValueTypeArrayFlatten = (Boolean)WHITE_BOX.getVMFlag("ValueArrayFlatten"); 128 protected static final boolean ValueTypeReturnedAsFields = (Boolean)WHITE_BOX.getVMFlag("ValueTypeReturnedAsFields"); 129 protected static final int COMP_LEVEL_ANY = -2; 130 protected static final int COMP_LEVEL_FULL_OPTIMIZATION = TEST_C1 ? 1 : 4; 131 protected static final Hashtable<String, Method> tests = new Hashtable<String, Method>(); 132 protected static final boolean USE_COMPILER = WHITE_BOX.getBooleanVMFlag("UseCompiler"); 133 protected static final boolean PRINT_IDEAL = WHITE_BOX.getBooleanVMFlag("PrintIdeal"); 134 protected static final boolean XCOMP = Platform.isComp(); 135 136 // Regular expressions used to match nodes in the PrintIdeal output 137 protected static final String START = "(\\d+\\t(.*"; 138 protected static final String MID = ".*)+\\t===.*"; 139 protected static final String END = ")|"; 140 protected static final String ALLOC = "(.*precise klass compiler/valhalla/valuetypes/MyValue.*\\R(.*(nop|spill).*\\R)*.*_new_instance_Java" + END; 141 protected static final String ALLOCA = "(.*precise klass \\[Lcompiler/valhalla/valuetypes/MyValue.*\\R(.*(nop|spill).*\\R)*.*_new_array_Java" + END; 142 protected static final String LOAD = START + "Load(B|S|I|L|F|D|P|N)" + MID + "@compiler/valhalla/valuetypes/MyValue.*" + END; 143 protected static final String LOADK = START + "LoadK" + MID + END; 144 protected static final String STORE = START + "Store(B|S|I|L|F|D|P|N)" + MID + "@compiler/valhalla/valuetypes/MyValue.*" + END; 145 protected static final String LOOP = START + "Loop" + MID + "" + END; 146 protected static final String TRAP = START + "CallStaticJava" + MID + "uncommon_trap.*(unstable_if|predicate)" + END; 147 protected static final String RETURN = START + "Return" + MID + "returns" + END; 148 protected static final String LINKTOSTATIC = START + "CallStaticJava" + MID + "linkToStatic" + END; 149 protected static final String NPE = START + "CallStaticJava" + MID + "null_check" + END; 150 protected static final String CALL = START + "CallStaticJava" + MID + END; 151 protected static final String STOREVALUETYPEFIELDS = START + "CallStaticJava" + MID + "store_value_type_fields" + END; 152 protected static final String SCOBJ = "(.*# ScObj.*" + END; 153 154 public static String[] concat(String prefix[], String... extra) { 292 ((list == null || list.contains(m.getName())) && (exclude == null || !exclude.contains(m.getName())))) { 293 tests.put(getClass().getSimpleName() + "::" + m.getName(), m); 294 } 295 } 296 } 297 298 protected void run(String[] args, Class<?>... classes) throws Throwable { 299 if (args.length == 0) { 300 // Spawn a new VM instance 301 execute_vm(); 302 } else { 303 // Execute tests 304 run(classes); 305 } 306 } 307 308 private void execute_vm() throws Throwable { 309 Asserts.assertFalse(tests.isEmpty(), "no tests to execute"); 310 ArrayList<String> args = new ArrayList<String>(defaultFlags); 311 String[] vmInputArgs = InputArguments.getVmInputArgs(); 312 if (VERIFY_IR) { 313 for (String arg : vmInputArgs) { 314 if (arg.startsWith("-XX:CompileThreshold")) { 315 // Disable IR verification if 316 VERIFY_IR = false; 317 } 318 // Check if the JVM supports value type specific default arguments from the test's run commands 319 if (arg.startsWith("-XX:+ValueTypePassFieldsAsArgs") || 320 arg.startsWith("-XX:+ValueTypeReturnedAsFields")) { 321 Boolean value = (Boolean)WHITE_BOX.getVMFlag(arg.substring(5)); 322 if (!value) { 323 System.out.println("WARNING: could not enable " + arg.substring(5) + ". Skipping IR verification."); 324 VERIFY_IR = false; 325 } 326 } else if (arg.startsWith("-XX:-ValueTypePassFieldsAsArgs") || 327 arg.startsWith("-XX:-ValueTypeReturnedAsFields")) { 328 Boolean value = (Boolean)WHITE_BOX.getVMFlag(arg.substring(5)); 329 if (value) { 330 System.out.println("WARNING: could not disable " + arg.substring(5) + ". Skipping IR verification."); 331 VERIFY_IR = false; 332 } 333 } 334 } 335 // Always trap for exception throwing to not confuse IR verification 336 args.add("-XX:-OmitStackTraceInFastThrow"); 337 } 338 if (VERIFY_VM) { 339 args.addAll(verifyFlags); 340 } 341 // Run tests in own process and verify output 342 args.add(getClass().getName()); 343 args.add("run"); 344 // Spawn process with default JVM options from the test's run command 345 String[] cmds = Arrays.copyOf(vmInputArgs, vmInputArgs.length + args.size()); 346 System.arraycopy(args.toArray(), 0, cmds, vmInputArgs.length, args.size()); 347 OutputAnalyzer oa = ProcessTools.executeTestJvm(cmds); 348 // If ideal graph printing is enabled/supported, verify output 349 String output = oa.getOutput(); 350 oa.shouldHaveExitValue(0); 351 if (VERIFY_IR) { 352 if (output.contains("PrintIdeal enabled")) { 353 parseOutput(output); 354 } else { 398 // Parse graph using regular expressions to determine if it contains forbidden nodes 399 Test[] annos = test.getAnnotationsByType(Test.class); 400 Test anno = null; 401 for (Test a : annos) { 402 if ((a.valid() & ValueTypePassFieldsAsArgsOn) != 0 && ValueTypePassFieldsAsArgs) { 403 assert anno == null; 404 anno = a; 405 } else if ((a.valid() & ValueTypePassFieldsAsArgsOff) != 0 && !ValueTypePassFieldsAsArgs) { 406 assert anno == null; 407 anno = a; 408 } else if ((a.valid() & ValueTypeArrayFlattenOn) != 0 && ValueTypeArrayFlatten) { 409 assert anno == null; 410 anno = a; 411 } else if ((a.valid() & ValueTypeArrayFlattenOff) != 0 && !ValueTypeArrayFlatten) { 412 assert anno == null; 413 anno = a; 414 } else if ((a.valid() & ValueTypeReturnedAsFieldsOn) != 0 && ValueTypeReturnedAsFields) { 415 assert anno == null; 416 anno = a; 417 } else if ((a.valid() & ValueTypeReturnedAsFieldsOff) != 0 && !ValueTypeReturnedAsFields) { 418 assert anno == null; 419 anno = a; 420 } 421 } 422 assert anno != null; 423 String regexFail = anno.failOn(); 424 if (!regexFail.isEmpty()) { 425 Pattern pattern = Pattern.compile(regexFail.substring(0, regexFail.length()-1)); 426 Matcher matcher = pattern.matcher(graph); 427 boolean found = matcher.find(); 428 Asserts.assertFalse(found, "Graph for '" + testName + "' contains forbidden node:\n" + (found ? matcher.group() : "")); 429 } 430 String[] regexMatch = anno.match(); 431 int[] matchCount = anno.matchCount(); 432 for (int i = 0; i < regexMatch.length; ++i) { 433 Pattern pattern = Pattern.compile(regexMatch[i].substring(0, regexMatch[i].length()-1)); 434 Matcher matcher = pattern.matcher(graph); 435 int count = 0; 436 String nodes = ""; 437 while (matcher.find()) { | 75 76 // Prevent method compilation 77 @Retention(RetentionPolicy.RUNTIME) 78 @interface DontCompile { } 79 80 // Number of warmup iterations 81 @Retention(RetentionPolicy.RUNTIME) 82 @interface Warmup { 83 int value(); 84 } 85 86 public abstract class ValueTypeTest { 87 // Run "jtreg -Dtest.c1=true" to enable experimental C1 testing. 88 static final boolean TEST_C1 = Boolean.getBoolean("test.c1"); 89 90 // Random test values 91 public static final int rI = Utils.getRandomInstance().nextInt() % 1000; 92 public static final long rL = Utils.getRandomInstance().nextLong() % 1000; 93 94 // User defined settings 95 protected static final boolean XCOMP = Platform.isComp(); 96 private static final boolean PRINT_GRAPH = true; 97 private static final boolean PRINT_TIMES = Boolean.parseBoolean(System.getProperty("PrintTimes", "false")); 98 private static boolean VERIFY_IR = Boolean.parseBoolean(System.getProperty("VerifyIR", "true")) && !TEST_C1 && !XCOMP; 99 private static final boolean VERIFY_VM = Boolean.parseBoolean(System.getProperty("VerifyVM", "false")); 100 private static final String SCENARIOS = System.getProperty("Scenarios", ""); 101 private static final String TESTLIST = System.getProperty("Testlist", ""); 102 private static final String EXCLUDELIST = System.getProperty("Exclude", ""); 103 private static final int WARMUP = Integer.parseInt(System.getProperty("Warmup", "251")); 104 private static final boolean DUMP_REPLAY = Boolean.parseBoolean(System.getProperty("DumpReplay", "false")); 105 106 // Pre-defined settings 107 private static final List<String> defaultFlags = Arrays.asList( 108 "-XX:-BackgroundCompilation", "-XX:CICompilerCount=1", 109 "-XX:CompileCommand=quiet", 110 "-XX:CompileCommand=compileonly,java.lang.invoke.*::*", 111 "-XX:CompileCommand=compileonly,java.lang.Long::sum", 112 "-XX:CompileCommand=compileonly,java.lang.Object::<init>", 113 "-XX:CompileCommand=compileonly,compiler.valhalla.valuetypes.*::*"); 114 private static final List<String> printFlags = Arrays.asList( 115 "-XX:+PrintCompilation", "-XX:+PrintIdeal", "-XX:+PrintOptoAssembly"); 116 private static final List<String> verifyFlags = Arrays.asList( 117 "-XX:+VerifyOops", "-XX:+VerifyStack", "-XX:+VerifyLastFrame", "-XX:+VerifyBeforeGC", "-XX:+VerifyAfterGC", 118 "-XX:+VerifyDuringGC", "-XX:+VerifyAdapterSharing", "-XX:+StressValueTypeReturnedAsFields"); 119 120 protected static final WhiteBox WHITE_BOX = WhiteBox.getWhiteBox(); 121 protected static final int ValueTypePassFieldsAsArgsOn = 0x1; 122 protected static final int ValueTypePassFieldsAsArgsOff = 0x2; 123 protected static final int ValueTypeArrayFlattenOn = 0x4; 124 protected static final int ValueTypeArrayFlattenOff = 0x8; 125 protected static final int ValueTypeReturnedAsFieldsOn = 0x10; 126 protected static final int ValueTypeReturnedAsFieldsOff = 0x20; 127 protected static final int AlwaysIncrementalInlineOn = 0x40; 128 protected static final int AlwaysIncrementalInlineOff = 0x80; 129 static final int AllFlags = ValueTypePassFieldsAsArgsOn | ValueTypePassFieldsAsArgsOff | ValueTypeArrayFlattenOn | ValueTypeArrayFlattenOff | ValueTypeReturnedAsFieldsOn; 130 protected static final boolean ValueTypePassFieldsAsArgs = (Boolean)WHITE_BOX.getVMFlag("ValueTypePassFieldsAsArgs"); 131 protected static final boolean ValueTypeArrayFlatten = (Boolean)WHITE_BOX.getVMFlag("ValueArrayFlatten"); 132 protected static final boolean ValueTypeReturnedAsFields = (Boolean)WHITE_BOX.getVMFlag("ValueTypeReturnedAsFields"); 133 protected static final boolean AlwaysIncrementalInline = (Boolean)WHITE_BOX.getVMFlag("AlwaysIncrementalInline"); 134 protected static final int COMP_LEVEL_ANY = -2; 135 protected static final int COMP_LEVEL_FULL_OPTIMIZATION = TEST_C1 ? 1 : 4; 136 protected static final Hashtable<String, Method> tests = new Hashtable<String, Method>(); 137 protected static final boolean USE_COMPILER = WHITE_BOX.getBooleanVMFlag("UseCompiler"); 138 protected static final boolean PRINT_IDEAL = WHITE_BOX.getBooleanVMFlag("PrintIdeal"); 139 140 // Regular expressions used to match nodes in the PrintIdeal output 141 protected static final String START = "(\\d+\\t(.*"; 142 protected static final String MID = ".*)+\\t===.*"; 143 protected static final String END = ")|"; 144 protected static final String ALLOC = "(.*precise klass compiler/valhalla/valuetypes/MyValue.*\\R(.*(nop|spill).*\\R)*.*_new_instance_Java" + END; 145 protected static final String ALLOCA = "(.*precise klass \\[Lcompiler/valhalla/valuetypes/MyValue.*\\R(.*(nop|spill).*\\R)*.*_new_array_Java" + END; 146 protected static final String LOAD = START + "Load(B|S|I|L|F|D|P|N)" + MID + "@compiler/valhalla/valuetypes/MyValue.*" + END; 147 protected static final String LOADK = START + "LoadK" + MID + END; 148 protected static final String STORE = START + "Store(B|S|I|L|F|D|P|N)" + MID + "@compiler/valhalla/valuetypes/MyValue.*" + END; 149 protected static final String LOOP = START + "Loop" + MID + "" + END; 150 protected static final String TRAP = START + "CallStaticJava" + MID + "uncommon_trap.*(unstable_if|predicate)" + END; 151 protected static final String RETURN = START + "Return" + MID + "returns" + END; 152 protected static final String LINKTOSTATIC = START + "CallStaticJava" + MID + "linkToStatic" + END; 153 protected static final String NPE = START + "CallStaticJava" + MID + "null_check" + END; 154 protected static final String CALL = START + "CallStaticJava" + MID + END; 155 protected static final String STOREVALUETYPEFIELDS = START + "CallStaticJava" + MID + "store_value_type_fields" + END; 156 protected static final String SCOBJ = "(.*# ScObj.*" + END; 157 158 public static String[] concat(String prefix[], String... extra) { 296 ((list == null || list.contains(m.getName())) && (exclude == null || !exclude.contains(m.getName())))) { 297 tests.put(getClass().getSimpleName() + "::" + m.getName(), m); 298 } 299 } 300 } 301 302 protected void run(String[] args, Class<?>... classes) throws Throwable { 303 if (args.length == 0) { 304 // Spawn a new VM instance 305 execute_vm(); 306 } else { 307 // Execute tests 308 run(classes); 309 } 310 } 311 312 private void execute_vm() throws Throwable { 313 Asserts.assertFalse(tests.isEmpty(), "no tests to execute"); 314 ArrayList<String> args = new ArrayList<String>(defaultFlags); 315 String[] vmInputArgs = InputArguments.getVmInputArgs(); 316 for (String arg : vmInputArgs) { 317 if (arg.startsWith("-XX:CompileThreshold")) { 318 // Disable IR verification if non-default CompileThreshold is set 319 VERIFY_IR = false; 320 } 321 } 322 if (VERIFY_IR) { 323 // Add print flags for IR verification 324 args.addAll(printFlags); 325 // Always trap for exception throwing to not confuse IR verification 326 args.add("-XX:-OmitStackTraceInFastThrow"); 327 } 328 if (VERIFY_VM) { 329 args.addAll(verifyFlags); 330 } 331 // Run tests in own process and verify output 332 args.add(getClass().getName()); 333 args.add("run"); 334 // Spawn process with default JVM options from the test's run command 335 String[] cmds = Arrays.copyOf(vmInputArgs, vmInputArgs.length + args.size()); 336 System.arraycopy(args.toArray(), 0, cmds, vmInputArgs.length, args.size()); 337 OutputAnalyzer oa = ProcessTools.executeTestJvm(cmds); 338 // If ideal graph printing is enabled/supported, verify output 339 String output = oa.getOutput(); 340 oa.shouldHaveExitValue(0); 341 if (VERIFY_IR) { 342 if (output.contains("PrintIdeal enabled")) { 343 parseOutput(output); 344 } else { 388 // Parse graph using regular expressions to determine if it contains forbidden nodes 389 Test[] annos = test.getAnnotationsByType(Test.class); 390 Test anno = null; 391 for (Test a : annos) { 392 if ((a.valid() & ValueTypePassFieldsAsArgsOn) != 0 && ValueTypePassFieldsAsArgs) { 393 assert anno == null; 394 anno = a; 395 } else if ((a.valid() & ValueTypePassFieldsAsArgsOff) != 0 && !ValueTypePassFieldsAsArgs) { 396 assert anno == null; 397 anno = a; 398 } else if ((a.valid() & ValueTypeArrayFlattenOn) != 0 && ValueTypeArrayFlatten) { 399 assert anno == null; 400 anno = a; 401 } else if ((a.valid() & ValueTypeArrayFlattenOff) != 0 && !ValueTypeArrayFlatten) { 402 assert anno == null; 403 anno = a; 404 } else if ((a.valid() & ValueTypeReturnedAsFieldsOn) != 0 && ValueTypeReturnedAsFields) { 405 assert anno == null; 406 anno = a; 407 } else if ((a.valid() & ValueTypeReturnedAsFieldsOff) != 0 && !ValueTypeReturnedAsFields) { 408 assert anno == null; 409 anno = a; 410 } else if ((a.valid() & AlwaysIncrementalInlineOn) != 0 && AlwaysIncrementalInline) { 411 assert anno == null; 412 anno = a; 413 } else if ((a.valid() & AlwaysIncrementalInlineOff) != 0 && !AlwaysIncrementalInline) { 414 assert anno == null; 415 anno = a; 416 } 417 } 418 assert anno != null; 419 String regexFail = anno.failOn(); 420 if (!regexFail.isEmpty()) { 421 Pattern pattern = Pattern.compile(regexFail.substring(0, regexFail.length()-1)); 422 Matcher matcher = pattern.matcher(graph); 423 boolean found = matcher.find(); 424 Asserts.assertFalse(found, "Graph for '" + testName + "' contains forbidden node:\n" + (found ? matcher.group() : "")); 425 } 426 String[] regexMatch = anno.match(); 427 int[] matchCount = anno.matchCount(); 428 for (int i = 0; i < regexMatch.length; ++i) { 429 Pattern pattern = Pattern.compile(regexMatch[i].substring(0, regexMatch[i].length()-1)); 430 Matcher matcher = pattern.matcher(graph); 431 int count = 0; 432 String nodes = ""; 433 while (matcher.find()) { |