40 import java.util.ArrayList; 41 import java.util.Arrays; 42 import java.util.Hashtable; 43 import java.util.LinkedHashMap; 44 import java.util.List; 45 import java.util.Map; 46 import java.util.regex.Matcher; 47 import java.util.regex.Pattern; 48 import java.util.TreeMap; 49 50 // Mark method as test 51 @Retention(RetentionPolicy.RUNTIME) 52 @Repeatable(Tests.class) 53 @interface Test { 54 // Regular expression used to match forbidden IR nodes 55 // in the C2 IR emitted for this test. 56 String failOn() default ""; 57 // Regular expressions used to match and count IR nodes. 58 String[] match() default { }; 59 int[] matchCount() default { }; 60 int valid() default ValueTypeTest.AllFlags; 61 } 62 63 @Retention(RetentionPolicy.RUNTIME) 64 @interface Tests { 65 Test[] value(); 66 } 67 68 // Force method inlining during compilation 69 @Retention(RetentionPolicy.RUNTIME) 70 @interface ForceInline { } 71 72 // Prevent method inlining during compilation 73 @Retention(RetentionPolicy.RUNTIME) 74 @interface DontInline { } 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 // Should we execute tests that assume (ValueType[] <: Object[])? 91 static final boolean ENABLE_VALUE_ARRAY_COVARIANCE = Boolean.getBoolean("ValueArrayCovariance"); 92 93 // Random test values 94 public static final int rI = Utils.getRandomInstance().nextInt() % 1000; 95 public static final long rL = Utils.getRandomInstance().nextLong() % 1000; 96 97 // User defined settings 98 protected static final boolean XCOMP = Platform.isComp(); 99 private static final boolean PRINT_GRAPH = true; 100 private static final boolean PRINT_TIMES = Boolean.parseBoolean(System.getProperty("PrintTimes", "false")); 101 private static boolean VERIFY_IR = Boolean.parseBoolean(System.getProperty("VerifyIR", "true")) && !TEST_C1 && !XCOMP; 102 private static final boolean VERIFY_VM = Boolean.parseBoolean(System.getProperty("VerifyVM", "false")); 103 private static final String SCENARIOS = System.getProperty("Scenarios", ""); 104 private static final String TESTLIST = System.getProperty("Testlist", ""); 105 private static final String EXCLUDELIST = System.getProperty("Exclude", ""); 106 private static final int WARMUP = Integer.parseInt(System.getProperty("Warmup", "251")); 107 private static final boolean DUMP_REPLAY = Boolean.parseBoolean(System.getProperty("DumpReplay", "false")); 108 109 // Pre-defined settings 110 private static final List<String> defaultFlags = Arrays.asList( 111 "-XX:-BackgroundCompilation", "-XX:CICompilerCount=1", 112 "-XX:CompileCommand=quiet", 113 "-XX:CompileCommand=compileonly,java.lang.invoke.*::*", 114 "-XX:CompileCommand=compileonly,java.lang.Long::sum", 115 "-XX:CompileCommand=compileonly,java.lang.Object::<init>", 116 "-XX:CompileCommand=compileonly,compiler.valhalla.valuetypes.*::*"); 117 private static final List<String> printFlags = Arrays.asList( 118 "-XX:+PrintCompilation", "-XX:+PrintIdeal", "-XX:+PrintOptoAssembly"); 119 private static final List<String> verifyFlags = Arrays.asList( 120 "-XX:+VerifyOops", "-XX:+VerifyStack", "-XX:+VerifyLastFrame", "-XX:+VerifyBeforeGC", "-XX:+VerifyAfterGC", 121 "-XX:+VerifyDuringGC", "-XX:+VerifyAdapterSharing"); 122 123 protected static final WhiteBox WHITE_BOX = WhiteBox.getWhiteBox(); 124 protected static final int ValueTypePassFieldsAsArgsOn = 0x1; 125 protected static final int ValueTypePassFieldsAsArgsOff = 0x2; 126 protected static final int ValueTypeArrayFlattenOn = 0x4; 127 protected static final int ValueTypeArrayFlattenOff = 0x8; 128 protected static final int ValueTypeReturnedAsFieldsOn = 0x10; 129 protected static final int ValueTypeReturnedAsFieldsOff = 0x20; 130 protected static final int AlwaysIncrementalInlineOn = 0x40; 131 protected static final int AlwaysIncrementalInlineOff = 0x80; 132 static final int AllFlags = ValueTypePassFieldsAsArgsOn | ValueTypePassFieldsAsArgsOff | ValueTypeArrayFlattenOn | ValueTypeArrayFlattenOff | ValueTypeReturnedAsFieldsOn; 133 protected static final boolean ValueTypePassFieldsAsArgs = (Boolean)WHITE_BOX.getVMFlag("ValueTypePassFieldsAsArgs"); 134 protected static final boolean ValueTypeArrayFlatten = (WHITE_BOX.getIntxVMFlag("ValueArrayElemMaxFlatSize") == -1); // FIXME - fix this if default of ValueArrayElemMaxFlatSize is changed 135 protected static final boolean ValueTypeReturnedAsFields = (Boolean)WHITE_BOX.getVMFlag("ValueTypeReturnedAsFields"); 136 protected static final boolean AlwaysIncrementalInline = (Boolean)WHITE_BOX.getVMFlag("AlwaysIncrementalInline"); 137 protected static final int COMP_LEVEL_ANY = -2; 138 protected static final int COMP_LEVEL_FULL_OPTIMIZATION = TEST_C1 ? 1 : 4; 139 protected static final Hashtable<String, Method> tests = new Hashtable<String, Method>(); 140 protected static final boolean USE_COMPILER = WHITE_BOX.getBooleanVMFlag("UseCompiler"); 141 protected static final boolean PRINT_IDEAL = WHITE_BOX.getBooleanVMFlag("PrintIdeal"); 142 143 // Regular expressions used to match nodes in the PrintIdeal output 144 protected static final String START = "(\\d+\\t(.*"; 145 protected static final String MID = ".*)+\\t===.*"; 146 protected static final String END = ")|"; 147 protected static final String ALLOC = "(.*precise klass compiler/valhalla/valuetypes/MyValue.*\\R(.*(nop|spill).*\\R)*.*_new_instance_Java" + END; 148 protected static final String ALLOCA = "(.*precise klass \\[Lcompiler/valhalla/valuetypes/MyValue.*\\R(.*(nop|spill).*\\R)*.*_new_array_Java" + END; 149 protected static final String LOAD = START + "Load(B|S|I|L|F|D|P|N)" + MID + "@compiler/valhalla/valuetypes/MyValue.*" + END; 150 protected static final String LOADK = START + "LoadK" + MID + END; 151 protected static final String STORE = START + "Store(B|C|S|I|L|F|D|P|N)" + MID + "@compiler/valhalla/valuetypes/MyValue.*" + END; 152 protected static final String LOOP = START + "Loop" + MID + "" + END; 153 protected static final String TRAP = START + "CallStaticJava" + MID + "uncommon_trap.*(unstable_if|predicate)" + END; 154 protected static final String RETURN = START + "Return" + MID + "returns" + END; 155 protected static final String LINKTOSTATIC = START + "CallStaticJava" + MID + "linkToStatic" + END; 156 protected static final String NPE = START + "CallStaticJava" + MID + "null_check" + END; 157 protected static final String CALL = START + "CallStaticJava" + MID + END; 158 protected static final String STOREVALUETYPEFIELDS = START + "CallStaticJava" + MID + "store_value_type_fields" + END; 177 /** 178 * Override getNumScenarios and getVMParameters if you want to run with more than 179 * the 5 built-in scenarios 180 */ 181 public int getNumScenarios() { 182 if (TEST_C1) { 183 return 1; 184 } else { 185 return 6; 186 } 187 } 188 189 /** 190 * VM paramaters for the 5 built-in test scenarios. If your test needs to append 191 * extra parameters for (some of) these scenarios, override getExtraVMParameters(). 192 */ 193 public String[] getVMParameters(int scenario) { 194 if (TEST_C1) { 195 return new String[] { 196 "-XX:+EnableValhallaC1", 197 }; 198 } 199 200 switch (scenario) { 201 case 0: return new String[] { 202 "-XX:+AlwaysIncrementalInline", 203 "-XX:ValueArrayElemMaxFlatOops=-1", 204 "-XX:ValueArrayElemMaxFlatSize=-1", 205 "-XX:ValueFieldMaxFlatSize=-1", 206 "-XX:+ValueTypePassFieldsAsArgs", 207 "-XX:+ValueTypeReturnedAsFields"}; 208 case 1: return new String[] { 209 "-XX:-UseCompressedOops", 210 "-XX:ValueArrayElemMaxFlatOops=-1", 211 "-XX:ValueArrayElemMaxFlatSize=-1", 212 "-XX:ValueFieldMaxFlatSize=-1", 213 "-XX:-ValueTypePassFieldsAsArgs", 214 "-XX:-ValueTypeReturnedAsFields"}; 215 case 2: return new String[] { 216 "-DVerifyIR=false", 323 if (!TESTLIST.isEmpty()) { 324 list = Arrays.asList(TESTLIST.split(",")); 325 } 326 List<String> exclude = buildExcludeList(); 327 328 // Gather all test methods and put them in Hashtable 329 for (Method m : getClass().getDeclaredMethods()) { 330 Test[] annos = m.getAnnotationsByType(Test.class); 331 if (annos.length != 0 && 332 ((list == null || list.contains(m.getName())) && (exclude == null || !exclude.contains(m.getName())))) { 333 tests.put(getClass().getSimpleName() + "::" + m.getName(), m); 334 } 335 } 336 } 337 338 protected void run(String[] args, Class<?>... classes) throws Throwable { 339 if (args.length == 0) { 340 // Spawn a new VM instance 341 execute_vm(); 342 } else { 343 // Execute tests 344 run(classes); 345 } 346 } 347 348 private void execute_vm() throws Throwable { 349 Asserts.assertFalse(tests.isEmpty(), "no tests to execute"); 350 ArrayList<String> args = new ArrayList<String>(defaultFlags); 351 String[] vmInputArgs = InputArguments.getVmInputArgs(); 352 for (String arg : vmInputArgs) { 353 if (arg.startsWith("-XX:CompileThreshold")) { 354 // Disable IR verification if non-default CompileThreshold is set 355 VERIFY_IR = false; 356 } 357 } 358 if (VERIFY_IR) { 359 // Add print flags for IR verification 360 args.addAll(printFlags); 361 // Always trap for exception throwing to not confuse IR verification 362 args.add("-XX:-OmitStackTraceInFastThrow"); 363 } 364 if (VERIFY_VM) { 365 args.addAll(verifyFlags); 366 } 367 // Run tests in own process and verify output 368 args.add(getClass().getName()); 369 args.add("run"); 370 // Spawn process with default JVM options from the test's run command 371 String[] cmds = Arrays.copyOf(vmInputArgs, vmInputArgs.length + args.size()); 372 System.arraycopy(args.toArray(), 0, cmds, vmInputArgs.length, args.size()); 373 OutputAnalyzer oa = ProcessTools.executeTestJvm(cmds); 374 // If ideal graph printing is enabled/supported, verify output 375 String output = oa.getOutput(); 376 oa.shouldHaveExitValue(0); 377 if (VERIFY_IR) { 378 if (output.contains("PrintIdeal enabled")) { 379 parseOutput(output); 380 } else { 381 System.out.println(output); 382 System.out.println("WARNING: IR verification failed! Running with -Xint, -Xcomp or release build?"); 383 } 384 } 385 } 386 387 private void parseOutput(String output) throws Exception { 388 Pattern comp_re = Pattern.compile("\\n\\s+\\d+\\s+\\d+\\s+(%| )(s| )(!| )b(n| )\\s+\\S+\\.(?<name>[^.]+::\\S+)\\s+(?<osr>@ \\d+\\s+)?[(]\\d+ bytes[)]\\n"); 389 Matcher m = comp_re.matcher(output); 390 Map<String,String> compilations = new LinkedHashMap<>(); 391 int prev = 0; 392 String methodName = null; 494 return; 495 } 496 if (DUMP_REPLAY) { 497 // Generate replay compilation files 498 String directive = "[{ match: \"*.*\", DumpReplay: true }]"; 499 if (WHITE_BOX.addCompilerDirective(directive) != 1) { 500 throw new RuntimeException("Failed to add compiler directive"); 501 } 502 } 503 504 Method[] methods = clazz.getDeclaredMethods(); 505 for (Method m : methods) { 506 if (m.isAnnotationPresent(Test.class)) { 507 // Don't inline tests 508 WHITE_BOX.testSetDontInlineMethod(m, true); 509 } 510 if (m.isAnnotationPresent(DontCompile.class)) { 511 WHITE_BOX.makeMethodNotCompilable(m, COMP_LEVEL_ANY, true); 512 WHITE_BOX.makeMethodNotCompilable(m, COMP_LEVEL_ANY, false); 513 WHITE_BOX.testSetDontInlineMethod(m, true); 514 } 515 if (m.isAnnotationPresent(ForceInline.class)) { 516 WHITE_BOX.testSetForceInlineMethod(m, true); 517 } else if (m.isAnnotationPresent(DontInline.class)) { 518 WHITE_BOX.testSetDontInlineMethod(m, true); 519 } 520 } 521 522 // Compile class initializers 523 WHITE_BOX.enqueueInitializerForCompilation(clazz, COMP_LEVEL_FULL_OPTIMIZATION); 524 } 525 526 private void run(Class<?>... classes) throws Exception { 527 if (USE_COMPILER && PRINT_IDEAL && !XCOMP) { 528 System.out.println("PrintIdeal enabled"); 529 } 530 System.out.format("rI = %d, rL = %d\n", rI, rL); 531 532 setup(getClass()); 533 for (Class<?> clazz : classes) { 534 setup(clazz); 535 } 536 537 // Execute tests 538 TreeMap<Long, String> durations = PRINT_TIMES ? new TreeMap<Long, String>() : null; 539 for (Method test : tests.values()) { 540 long startTime = System.nanoTime(); 541 Method verifier = getClass().getMethod(test.getName() + "_verifier", boolean.class); 542 // Warmup using verifier method 543 Warmup anno = test.getAnnotation(Warmup.class); 544 int warmup = anno == null ? WARMUP : anno.value(); 545 for (int i = 0; i < warmup; ++i) { 546 verifier.invoke(this, true); 547 } 548 // Trigger compilation 549 WHITE_BOX.enqueueMethodForCompilation(test, COMP_LEVEL_FULL_OPTIMIZATION); 550 Asserts.assertTrue(!USE_COMPILER || WHITE_BOX.isMethodCompiled(test, false), test + " not compiled"); 551 // Check result 552 verifier.invoke(this, false); 553 if (PRINT_TIMES) { 554 long endTime = System.nanoTime(); 555 long duration = (endTime - startTime); 556 durations.put(duration, test.getName()); 557 } 558 } 559 560 // Print execution times 561 if (PRINT_TIMES) { 562 System.out.println("\n\nTest execution times:"); 563 for (Map.Entry<Long, String> entry : durations.entrySet()) { 564 System.out.format("%-10s%15d ns\n", entry.getValue() + ":", entry.getKey()); 565 } 566 } 567 } 568 } | 40 import java.util.ArrayList; 41 import java.util.Arrays; 42 import java.util.Hashtable; 43 import java.util.LinkedHashMap; 44 import java.util.List; 45 import java.util.Map; 46 import java.util.regex.Matcher; 47 import java.util.regex.Pattern; 48 import java.util.TreeMap; 49 50 // Mark method as test 51 @Retention(RetentionPolicy.RUNTIME) 52 @Repeatable(Tests.class) 53 @interface Test { 54 // Regular expression used to match forbidden IR nodes 55 // in the C2 IR emitted for this test. 56 String failOn() default ""; 57 // Regular expressions used to match and count IR nodes. 58 String[] match() default { }; 59 int[] matchCount() default { }; 60 int compLevel() default ValueTypeTest.COMP_LEVEL_ANY; 61 int valid() default ValueTypeTest.AllFlags; 62 } 63 64 @Retention(RetentionPolicy.RUNTIME) 65 @interface Tests { 66 Test[] value(); 67 } 68 69 // Force method inlining during compilation 70 @Retention(RetentionPolicy.RUNTIME) 71 @interface ForceInline { } 72 73 // Prevent method inlining during compilation 74 @Retention(RetentionPolicy.RUNTIME) 75 @interface DontInline { } 76 77 // Prevent method compilation 78 @Retention(RetentionPolicy.RUNTIME) 79 @interface DontCompile { } 80 81 // Force method compilation 82 @Retention(RetentionPolicy.RUNTIME) 83 @interface ForceCompile { 84 int compLevel() default ValueTypeTest.COMP_LEVEL_ANY; 85 } 86 87 // Number of warmup iterations 88 @Retention(RetentionPolicy.RUNTIME) 89 @interface Warmup { 90 int value(); 91 } 92 93 public abstract class ValueTypeTest { 94 // Run "jtreg -Dtest.c1=true" to enable experimental C1 testing. This forces all 95 // compilable methods to be compiled with C1, regardless of the @Test(compLevel=?) setting. 96 static final boolean TEST_C1 = Boolean.getBoolean("test.c1"); 97 98 // Should we execute tests that assume (ValueType[] <: Object[])? 99 static final boolean ENABLE_VALUE_ARRAY_COVARIANCE = Boolean.getBoolean("ValueArrayCovariance"); 100 101 // Random test values 102 public static final int rI = Utils.getRandomInstance().nextInt() % 1000; 103 public static final long rL = Utils.getRandomInstance().nextLong() % 1000; 104 105 // User defined settings 106 protected static final boolean XCOMP = Platform.isComp(); 107 private static final boolean PRINT_GRAPH = true; 108 private static final boolean PRINT_TIMES = Boolean.parseBoolean(System.getProperty("PrintTimes", "false")); 109 private static boolean VERIFY_IR = Boolean.parseBoolean(System.getProperty("VerifyIR", "true")) && !TEST_C1 && !XCOMP; 110 private static final boolean VERIFY_VM = Boolean.parseBoolean(System.getProperty("VerifyVM", "false")); 111 private static final String SCENARIOS = System.getProperty("Scenarios", ""); 112 private static final String TESTLIST = System.getProperty("Testlist", ""); 113 private static final String EXCLUDELIST = System.getProperty("Exclude", ""); 114 private static final int WARMUP = Integer.parseInt(System.getProperty("Warmup", "251")); 115 private static final boolean DUMP_REPLAY = Boolean.parseBoolean(System.getProperty("DumpReplay", "false")); 116 117 // Pre-defined settings 118 private static final String[] defaultFlags = { 119 "-XX:-BackgroundCompilation", "-XX:CICompilerCount=1", 120 "-XX:CompileCommand=quiet", 121 "-XX:CompileCommand=compileonly,java.lang.invoke.*::*", 122 "-XX:CompileCommand=compileonly,java.lang.Long::sum", 123 "-XX:CompileCommand=compileonly,java.lang.Object::<init>", 124 "-XX:CompileCommand=compileonly,compiler.valhalla.valuetypes.*::*"}; 125 private static final String[] printFlags = { 126 "-XX:+PrintCompilation", "-XX:+PrintIdeal", "-XX:+PrintOptoAssembly"}; 127 private static final String[] verifyFlags = { 128 "-XX:+VerifyOops", "-XX:+VerifyStack", "-XX:+VerifyLastFrame", "-XX:+VerifyBeforeGC", "-XX:+VerifyAfterGC", 129 "-XX:+VerifyDuringGC", "-XX:+VerifyAdapterSharing"}; 130 131 protected static final WhiteBox WHITE_BOX = WhiteBox.getWhiteBox(); 132 protected static final int ValueTypePassFieldsAsArgsOn = 0x1; 133 protected static final int ValueTypePassFieldsAsArgsOff = 0x2; 134 protected static final int ValueTypeArrayFlattenOn = 0x4; 135 protected static final int ValueTypeArrayFlattenOff = 0x8; 136 protected static final int ValueTypeReturnedAsFieldsOn = 0x10; 137 protected static final int ValueTypeReturnedAsFieldsOff = 0x20; 138 protected static final int AlwaysIncrementalInlineOn = 0x40; 139 protected static final int AlwaysIncrementalInlineOff = 0x80; 140 static final int AllFlags = ValueTypePassFieldsAsArgsOn | ValueTypePassFieldsAsArgsOff | ValueTypeArrayFlattenOn | ValueTypeArrayFlattenOff | ValueTypeReturnedAsFieldsOn; 141 protected static final boolean ValueTypePassFieldsAsArgs = (Boolean)WHITE_BOX.getVMFlag("ValueTypePassFieldsAsArgs"); 142 protected static final boolean ValueTypeArrayFlatten = (WHITE_BOX.getIntxVMFlag("ValueArrayElemMaxFlatSize") == -1); // FIXME - fix this if default of ValueArrayElemMaxFlatSize is changed 143 protected static final boolean ValueTypeReturnedAsFields = (Boolean)WHITE_BOX.getVMFlag("ValueTypeReturnedAsFields"); 144 protected static final boolean AlwaysIncrementalInline = (Boolean)WHITE_BOX.getVMFlag("AlwaysIncrementalInline"); 145 protected static final long TieredStopAtLevel = (Long)WHITE_BOX.getVMFlag("TieredStopAtLevel"); 146 protected static final int COMP_LEVEL_ANY = -2; 147 protected static final int COMP_LEVEL_ALL = -2; 148 protected static final int COMP_LEVEL_AOT = -1; 149 protected static final int COMP_LEVEL_NONE = 0; 150 protected static final int COMP_LEVEL_SIMPLE = 1; // C1 151 protected static final int COMP_LEVEL_LIMITED_PROFILE = 2; // C1, invocation & backedge counters 152 protected static final int COMP_LEVEL_FULL_PROFILE = 3; // C1, invocation & backedge counters + mdo 153 protected static final int COMP_LEVEL_FULL_OPTIMIZATION = 4; // C2 or JVMCI 154 155 protected static final Hashtable<String, Method> tests = new Hashtable<String, Method>(); 156 protected static final boolean USE_COMPILER = WHITE_BOX.getBooleanVMFlag("UseCompiler"); 157 protected static final boolean PRINT_IDEAL = WHITE_BOX.getBooleanVMFlag("PrintIdeal"); 158 159 // Regular expressions used to match nodes in the PrintIdeal output 160 protected static final String START = "(\\d+\\t(.*"; 161 protected static final String MID = ".*)+\\t===.*"; 162 protected static final String END = ")|"; 163 protected static final String ALLOC = "(.*precise klass compiler/valhalla/valuetypes/MyValue.*\\R(.*(nop|spill).*\\R)*.*_new_instance_Java" + END; 164 protected static final String ALLOCA = "(.*precise klass \\[Lcompiler/valhalla/valuetypes/MyValue.*\\R(.*(nop|spill).*\\R)*.*_new_array_Java" + END; 165 protected static final String LOAD = START + "Load(B|S|I|L|F|D|P|N)" + MID + "@compiler/valhalla/valuetypes/MyValue.*" + END; 166 protected static final String LOADK = START + "LoadK" + MID + END; 167 protected static final String STORE = START + "Store(B|C|S|I|L|F|D|P|N)" + MID + "@compiler/valhalla/valuetypes/MyValue.*" + END; 168 protected static final String LOOP = START + "Loop" + MID + "" + END; 169 protected static final String TRAP = START + "CallStaticJava" + MID + "uncommon_trap.*(unstable_if|predicate)" + END; 170 protected static final String RETURN = START + "Return" + MID + "returns" + END; 171 protected static final String LINKTOSTATIC = START + "CallStaticJava" + MID + "linkToStatic" + END; 172 protected static final String NPE = START + "CallStaticJava" + MID + "null_check" + END; 173 protected static final String CALL = START + "CallStaticJava" + MID + END; 174 protected static final String STOREVALUETYPEFIELDS = START + "CallStaticJava" + MID + "store_value_type_fields" + END; 193 /** 194 * Override getNumScenarios and getVMParameters if you want to run with more than 195 * the 5 built-in scenarios 196 */ 197 public int getNumScenarios() { 198 if (TEST_C1) { 199 return 1; 200 } else { 201 return 6; 202 } 203 } 204 205 /** 206 * VM paramaters for the 5 built-in test scenarios. If your test needs to append 207 * extra parameters for (some of) these scenarios, override getExtraVMParameters(). 208 */ 209 public String[] getVMParameters(int scenario) { 210 if (TEST_C1) { 211 return new String[] { 212 "-XX:+EnableValhallaC1", 213 "-XX:TieredStopAtLevel=1", 214 "-XX:-ValueTypePassFieldsAsArgs", 215 "-XX:-ValueTypeReturnedAsFields" 216 }; 217 } 218 219 switch (scenario) { 220 case 0: return new String[] { 221 "-XX:+AlwaysIncrementalInline", 222 "-XX:ValueArrayElemMaxFlatOops=-1", 223 "-XX:ValueArrayElemMaxFlatSize=-1", 224 "-XX:ValueFieldMaxFlatSize=-1", 225 "-XX:+ValueTypePassFieldsAsArgs", 226 "-XX:+ValueTypeReturnedAsFields"}; 227 case 1: return new String[] { 228 "-XX:-UseCompressedOops", 229 "-XX:ValueArrayElemMaxFlatOops=-1", 230 "-XX:ValueArrayElemMaxFlatSize=-1", 231 "-XX:ValueFieldMaxFlatSize=-1", 232 "-XX:-ValueTypePassFieldsAsArgs", 233 "-XX:-ValueTypeReturnedAsFields"}; 234 case 2: return new String[] { 235 "-DVerifyIR=false", 342 if (!TESTLIST.isEmpty()) { 343 list = Arrays.asList(TESTLIST.split(",")); 344 } 345 List<String> exclude = buildExcludeList(); 346 347 // Gather all test methods and put them in Hashtable 348 for (Method m : getClass().getDeclaredMethods()) { 349 Test[] annos = m.getAnnotationsByType(Test.class); 350 if (annos.length != 0 && 351 ((list == null || list.contains(m.getName())) && (exclude == null || !exclude.contains(m.getName())))) { 352 tests.put(getClass().getSimpleName() + "::" + m.getName(), m); 353 } 354 } 355 } 356 357 protected void run(String[] args, Class<?>... classes) throws Throwable { 358 if (args.length == 0) { 359 // Spawn a new VM instance 360 execute_vm(); 361 } else { 362 // Execute tests in the VM spawned by the above code. 363 Asserts.assertTrue(args.length == 1 && args[0].equals("run"), "must be"); 364 run(classes); 365 } 366 } 367 368 private void execute_vm() throws Throwable { 369 Asserts.assertFalse(tests.isEmpty(), "no tests to execute"); 370 String[] vmInputArgs = InputArguments.getVmInputArgs(); 371 for (String arg : vmInputArgs) { 372 if (arg.startsWith("-XX:CompileThreshold")) { 373 // Disable IR verification if non-default CompileThreshold is set 374 VERIFY_IR = false; 375 } 376 if (arg.startsWith("-XX:+EnableValhallaC1")) { 377 // Disable IR verification if C1 is used (FIXME!) 378 VERIFY_IR = false; 379 } 380 } 381 // Each VM is launched with flags in this order, so the later ones can override the earlier one: 382 // defaultFlags 383 // VERIFY_IR/VERIFY_VM flags specified below 384 // vmInputArgs, which consists of: 385 // @run options 386 // getVMParameters() 387 // getExtraVMParameters() 388 String cmds[] = defaultFlags; 389 if (VERIFY_IR) { 390 // Add print flags for IR verification 391 cmds = concat(cmds, printFlags); 392 // Always trap for exception throwing to not confuse IR verification 393 cmds = concat(cmds, "-XX:-OmitStackTraceInFastThrow"); 394 } 395 if (VERIFY_VM) { 396 cmds = concat(cmds, verifyFlags); 397 } 398 cmds = concat(cmds, vmInputArgs); 399 400 // Run tests in own process and verify output 401 cmds = concat(cmds, getClass().getName(), "run"); 402 OutputAnalyzer oa = ProcessTools.executeTestJvm(cmds); 403 // If ideal graph printing is enabled/supported, verify output 404 String output = oa.getOutput(); 405 oa.shouldHaveExitValue(0); 406 if (VERIFY_IR) { 407 if (output.contains("PrintIdeal enabled")) { 408 parseOutput(output); 409 } else { 410 System.out.println(output); 411 System.out.println("WARNING: IR verification failed! Running with -Xint, -Xcomp or release build?"); 412 } 413 } 414 } 415 416 private void parseOutput(String output) throws Exception { 417 Pattern comp_re = Pattern.compile("\\n\\s+\\d+\\s+\\d+\\s+(%| )(s| )(!| )b(n| )\\s+\\S+\\.(?<name>[^.]+::\\S+)\\s+(?<osr>@ \\d+\\s+)?[(]\\d+ bytes[)]\\n"); 418 Matcher m = comp_re.matcher(output); 419 Map<String,String> compilations = new LinkedHashMap<>(); 420 int prev = 0; 421 String methodName = null; 523 return; 524 } 525 if (DUMP_REPLAY) { 526 // Generate replay compilation files 527 String directive = "[{ match: \"*.*\", DumpReplay: true }]"; 528 if (WHITE_BOX.addCompilerDirective(directive) != 1) { 529 throw new RuntimeException("Failed to add compiler directive"); 530 } 531 } 532 533 Method[] methods = clazz.getDeclaredMethods(); 534 for (Method m : methods) { 535 if (m.isAnnotationPresent(Test.class)) { 536 // Don't inline tests 537 WHITE_BOX.testSetDontInlineMethod(m, true); 538 } 539 if (m.isAnnotationPresent(DontCompile.class)) { 540 WHITE_BOX.makeMethodNotCompilable(m, COMP_LEVEL_ANY, true); 541 WHITE_BOX.makeMethodNotCompilable(m, COMP_LEVEL_ANY, false); 542 WHITE_BOX.testSetDontInlineMethod(m, true); 543 } else if (m.isAnnotationPresent(ForceCompile.class)) { 544 int compLevel = getCompLevel(m.getAnnotation(ForceCompile.class)); 545 WHITE_BOX.enqueueMethodForCompilation(m, compLevel); 546 } 547 if (m.isAnnotationPresent(ForceInline.class)) { 548 WHITE_BOX.testSetForceInlineMethod(m, true); 549 } else if (m.isAnnotationPresent(DontInline.class)) { 550 WHITE_BOX.testSetDontInlineMethod(m, true); 551 } 552 } 553 554 // Compile class initializers 555 int compLevel = getCompLevel(null); 556 WHITE_BOX.enqueueInitializerForCompilation(clazz, compLevel); 557 } 558 559 private void run(Class<?>... classes) throws Exception { 560 if (USE_COMPILER && PRINT_IDEAL && !XCOMP) { 561 System.out.println("PrintIdeal enabled"); 562 } 563 System.out.format("rI = %d, rL = %d\n", rI, rL); 564 565 setup(getClass()); 566 for (Class<?> clazz : classes) { 567 setup(clazz); 568 } 569 570 // Execute tests 571 TreeMap<Long, String> durations = PRINT_TIMES ? new TreeMap<Long, String>() : null; 572 for (Method test : tests.values()) { 573 long startTime = System.nanoTime(); 574 Method verifier = getClass().getMethod(test.getName() + "_verifier", boolean.class); 575 // Warmup using verifier method 576 Warmup anno = test.getAnnotation(Warmup.class); 577 int warmup = anno == null ? WARMUP : anno.value(); 578 for (int i = 0; i < warmup; ++i) { 579 verifier.invoke(this, true); 580 } 581 int compLevel = getCompLevel(test.getAnnotation(Test.class)); 582 // Trigger compilation 583 WHITE_BOX.enqueueMethodForCompilation(test, compLevel); 584 Asserts.assertTrue(!USE_COMPILER || WHITE_BOX.isMethodCompiled(test, false), test + " not compiled"); 585 // Check result 586 verifier.invoke(this, false); 587 if (PRINT_TIMES) { 588 long endTime = System.nanoTime(); 589 long duration = (endTime - startTime); 590 durations.put(duration, test.getName()); 591 } 592 } 593 594 // Print execution times 595 if (PRINT_TIMES) { 596 System.out.println("\n\nTest execution times:"); 597 for (Map.Entry<Long, String> entry : durations.entrySet()) { 598 System.out.format("%-10s%15d ns\n", entry.getValue() + ":", entry.getKey()); 599 } 600 } 601 } 602 603 // Choose the appropriate compilation level for a method, according to the given annotation. 604 // 605 // Currently, if TEST_C1 is true, we always use COMP_LEVEL_SIMPLE. Otherwise, if the 606 // compLevel is unspecified, the default is COMP_LEVEL_FULL_OPTIMIZATION. 607 int getCompLevel(Object annotation) { 608 if (TEST_C1) { 609 return COMP_LEVEL_SIMPLE; 610 } 611 int compLevel; 612 if (annotation == null) { 613 compLevel = COMP_LEVEL_ANY; 614 } else if (annotation instanceof Test) { 615 compLevel = ((Test)annotation).compLevel(); 616 } else { 617 compLevel = ((ForceCompile)annotation).compLevel(); 618 } 619 if (compLevel == COMP_LEVEL_ANY) { 620 compLevel = COMP_LEVEL_FULL_OPTIMIZATION; 621 } 622 if (compLevel > (int)TieredStopAtLevel) { 623 compLevel = (int)TieredStopAtLevel; 624 } 625 return compLevel; 626 } 627 } |