1 /*
2 * Copyright (c) 2025, Oracle and/or its affiliates. All rights reserved.
3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4 *
5 * This code is free software; you can redistribute it and/or modify it
6 * under the terms of the GNU General Public License version 2 only, as
7 * published by the Free Software Foundation.
8 *
9 * This code is distributed in the hope that it will be useful, but WITHOUT
10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
12 * version 2 for more details (a copy is included in the LICENSE file that
13 * accompanied this code).
14 *
15 * You should have received a copy of the GNU General Public License version
16 * 2 along with this work; if not, write to the Free Software Foundation,
17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
18 *
19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
20 * or visit www.oracle.com if you need additional information or have any
21 * questions.
22 *
23 */
24
25 /**
26 * @test
27 * @summary Sanity test of combinations of the AOT Code Caching diagnostic flags
28 * @requires vm.cds.supports.aot.code.caching
29 * @requires vm.compiler1.enabled & vm.compiler2.enabled
30 * @comment Both C1 and C2 JIT compilers are required because the test verifies
31 * compiler's runtime blobs generation.
32 * @requires vm.opt.VerifyOops == null | vm.opt.VerifyOops == false
33 * @comment VerifyOops flag switch off AOT code generation. Skip it.
34 * @library /test/lib /test/setup_aot
35 * @build AOTCodeFlags JavacBenchApp
36 * @run driver jdk.test.lib.helpers.ClassFileInstaller -jar app.jar
37 * JavacBenchApp
38 * JavacBenchApp$ClassFile
39 * JavacBenchApp$FileManager
40 * JavacBenchApp$SourceFile
41 * @run driver AOTCodeFlags
42 */
43
44 import java.util.ArrayList;
45 import java.util.List;
46
47 import jdk.test.lib.cds.CDSAppTester;
48 import jdk.test.lib.process.OutputAnalyzer;
49
50 public class AOTCodeFlags {
51 public static void main(String... args) throws Exception {
52 Tester t = new Tester();
53 // Run only 2 modes (0 - no AOT code, 1 - AOT adapters) until JDK-8357398 is fixed
54 for (int mode = 0; mode < 2; mode++) {
55 t.setTestMode(mode);
56 t.run(new String[] {"AOT", "--two-step-training"});
57 }
58 }
59 static class Tester extends CDSAppTester {
60 private int testMode;
61
62 public Tester() {
63 super("AOTCodeFlags");
64 testMode = 0;
65 }
66
67 boolean isAdapterCachingOn() {
68 return (testMode & 0x1) != 0;
69 }
70
71 boolean isStubCachingOn() {
72 return (testMode & 0x2) != 0;
73 }
74
75 public void setTestMode(int mode) {
76 testMode = mode;
77 }
78
79 public List<String> getVMArgsForTestMode() {
80 List<String> list = new ArrayList<String>();
81 list.add("-XX:+UnlockDiagnosticVMOptions");
82 list.add(isAdapterCachingOn() ? "-XX:+AOTAdapterCaching" : "-XX:-AOTAdapterCaching");
83 list.add(isStubCachingOn() ? "-XX:+AOTStubCaching" : "-XX:-AOTStubCaching");
84 return list;
85 }
86
87 @Override
88 public String classpath(RunMode runMode) {
89 return "app.jar";
90 }
91
92 @Override
93 public String[] vmArgs(RunMode runMode) {
94 switch (runMode) {
95 case RunMode.ASSEMBLY:
96 case RunMode.PRODUCTION: {
97 List<String> args = getVMArgsForTestMode();
98 args.addAll(List.of("-Xlog:aot+codecache+init=debug",
99 "-Xlog:aot+codecache+exit=debug"));
100 return args.toArray(new String[0]);
101 }
102 }
103 return new String[] {};
104 }
105
106 @Override
107 public String[] appCommandLine(RunMode runMode) {
108 return new String[] {
109 "JavacBenchApp", "10"
110 };
111 }
112
113 @Override
114 public void checkExecution(OutputAnalyzer out, RunMode runMode) throws Exception {
115 if (!isAdapterCachingOn() && !isStubCachingOn()) { // this is equivalent to completely disable AOT code cache
116 switch (runMode) {
117 case RunMode.ASSEMBLY:
118 case RunMode.PRODUCTION:
119 out.shouldNotMatch("Adapters:\\s+total");
120 out.shouldNotMatch("Shared Blobs:\\s+total");
121 out.shouldNotMatch("C1 Blobs:\\s+total");
122 out.shouldNotMatch("C2 Blobs:\\s+total");
123 break;
124 }
125 } else {
126 if (isAdapterCachingOn()) {
127 switch (runMode) {
128 case RunMode.ASSEMBLY:
129 case RunMode.PRODUCTION:
130 // AOTAdapterCaching is on, non-zero adapters should be stored/loaded
131 out.shouldMatch("Adapters:\\s+total=[1-9][0-9]+");
132 break;
133 }
134 } else {
135 switch (runMode) {
136 case RunMode.ASSEMBLY:
137 case RunMode.PRODUCTION:
138 // AOTAdapterCaching is off, no adapters should be stored/loaded
139 out.shouldMatch("Adapters:\\s+total=0");
140 break;
141 }
142 }
143 if (isStubCachingOn()) {
144 switch (runMode) {
145 case RunMode.ASSEMBLY:
146 case RunMode.PRODUCTION:
147 // AOTStubCaching is on, non-zero stubs should be stored/loaded
148 out.shouldMatch("Shared Blobs:\\s+total=[1-9][0-9]+");
149 out.shouldMatch("C1 Blobs:\\s+total=[1-9][0-9]+");
150 out.shouldMatch("C2 Blobs:\\s+total=[1-9][0-9]+");
151 break;
152 }
153 } else {
154 switch (runMode) {
155 case RunMode.ASSEMBLY:
156 case RunMode.PRODUCTION:
157 // AOTStubCaching is off, no stubs should be stored/loaded
158 out.shouldMatch("Shared Blobs:\\s+total=0");
159 out.shouldMatch("C1 Blobs:\\s+total=0");
160 out.shouldMatch("C2 Blobs:\\s+total=0");
161 break;
162 }
163 }
164 }
165 }
166 }
167 }