20 * or visit www.oracle.com if you need additional information or have any |
20 * or visit www.oracle.com if you need additional information or have any |
21 * questions. |
21 * questions. |
22 */ |
22 */ |
23 |
23 |
24 #include "precompiled.hpp" |
24 #include "precompiled.hpp" |
25 #include "jvm.h" |
25 #include "compiler/compileBroker.hpp" |
26 #include "classfile/moduleEntry.hpp" |
26 #include "classfile/moduleEntry.hpp" |
27 #include "memory/oopFactory.hpp" |
|
28 #include "memory/resourceArea.hpp" |
|
29 #include "oops/oop.inline.hpp" |
|
30 #include "runtime/javaCalls.hpp" |
|
31 #include "runtime/handles.hpp" |
|
32 #include "jvmci/jvmciJavaClasses.hpp" |
|
33 #include "jvmci/jvmciCompiler.hpp" |
|
34 #include "jvmci/jvmciEnv.hpp" |
27 #include "jvmci/jvmciEnv.hpp" |
35 #include "jvmci/jvmciRuntime.hpp" |
28 #include "jvmci/jvmciRuntime.hpp" |
36 #include "runtime/compilationPolicy.hpp" |
|
37 #include "runtime/globals_extension.hpp" |
|
38 #include "runtime/handles.inline.hpp" |
29 #include "runtime/handles.inline.hpp" |
39 |
30 |
40 JVMCICompiler* JVMCICompiler::_instance = NULL; |
31 JVMCICompiler* JVMCICompiler::_instance = NULL; |
41 elapsedTimer JVMCICompiler::_codeInstallTimer; |
32 elapsedTimer JVMCICompiler::_codeInstallTimer; |
42 |
33 |
102 |
93 |
103 if (PrintBootstrap) { |
94 if (PrintBootstrap) { |
104 tty->print_cr(" in " JLONG_FORMAT " ms (compiled %d methods)", os::javaTimeMillis() - start, _methods_compiled); |
95 tty->print_cr(" in " JLONG_FORMAT " ms (compiled %d methods)", os::javaTimeMillis() - start, _methods_compiled); |
105 } |
96 } |
106 _bootstrapping = false; |
97 _bootstrapping = false; |
107 JVMCIRuntime::bootstrap_finished(CHECK); |
98 JVMCI::compiler_runtime()->bootstrap_finished(CHECK); |
108 } |
99 } |
109 |
100 |
110 #define CHECK_EXIT THREAD); \ |
101 bool JVMCICompiler::force_comp_at_level_simple(Method *method) { |
111 if (HAS_PENDING_EXCEPTION) { \ |
102 if (UseJVMCINativeLibrary) { |
112 char buf[256]; \ |
103 // This mechanism exists to force compilation of a JVMCI compiler by C1 |
113 jio_snprintf(buf, 256, "Uncaught exception at %s:%d", __FILE__, __LINE__); \ |
104 // to reduces the compilation time spent on the JVMCI compiler itself. In |
114 JVMCICompiler::exit_on_pending_exception(PENDING_EXCEPTION, buf); \ |
105 // +UseJVMCINativeLibrary mode, the JVMCI compiler is AOT compiled. |
115 return; \ |
106 return false; |
116 } \ |
|
117 (void)(0 |
|
118 |
|
119 void JVMCICompiler::compile_method(const methodHandle& method, int entry_bci, JVMCIEnv* env) { |
|
120 JVMCI_EXCEPTION_CONTEXT |
|
121 |
|
122 bool is_osr = entry_bci != InvocationEntryBci; |
|
123 if (_bootstrapping && is_osr) { |
|
124 // no OSR compilations during bootstrap - the compiler is just too slow at this point, |
|
125 // and we know that there are no endless loops |
|
126 env->set_failure(true, "No OSR during boostrap"); |
|
127 return; |
|
128 } |
107 } |
129 |
108 |
130 JVMCIRuntime::initialize_well_known_classes(CHECK_EXIT); |
109 if (_bootstrapping) { |
131 |
110 // When bootstrapping, the JVMCI compiler can compile its own methods. |
132 HandleMark hm; |
111 return false; |
133 Handle receiver = JVMCIRuntime::get_HotSpotJVMCIRuntime(CHECK_EXIT); |
|
134 |
|
135 JavaValue method_result(T_OBJECT); |
|
136 JavaCallArguments args; |
|
137 args.push_long((jlong) (address) method()); |
|
138 JavaCalls::call_static(&method_result, SystemDictionary::HotSpotResolvedJavaMethodImpl_klass(), |
|
139 vmSymbols::fromMetaspace_name(), vmSymbols::method_fromMetaspace_signature(), &args, THREAD); |
|
140 |
|
141 JavaValue result(T_OBJECT); |
|
142 if (!HAS_PENDING_EXCEPTION) { |
|
143 JavaCallArguments args; |
|
144 args.push_oop(receiver); |
|
145 args.push_oop(Handle(THREAD, (oop)method_result.get_jobject())); |
|
146 args.push_int(entry_bci); |
|
147 args.push_long((jlong) (address) env); |
|
148 args.push_int(env->task()->compile_id()); |
|
149 JavaCalls::call_special(&result, receiver->klass(), |
|
150 vmSymbols::compileMethod_name(), vmSymbols::compileMethod_signature(), &args, THREAD); |
|
151 } |
112 } |
152 |
113 |
153 // An uncaught exception was thrown during compilation. Generally these |
114 JVMCIRuntime* runtime = JVMCI::compiler_runtime(); |
154 // should be handled by the Java code in some useful way but if they leak |
115 if (runtime != NULL && runtime->is_HotSpotJVMCIRuntime_initialized()) { |
155 // through to here report them instead of dying or silently ignoring them. |
116 JavaThread* thread = JavaThread::current(); |
156 if (HAS_PENDING_EXCEPTION) { |
117 HandleMark hm(thread); |
157 Handle exception(THREAD, PENDING_EXCEPTION); |
118 THREAD_JVMCIENV(thread); |
158 CLEAR_PENDING_EXCEPTION; |
119 JVMCIObject receiver = runtime->get_HotSpotJVMCIRuntime(JVMCIENV); |
159 |
120 objArrayHandle excludeModules(thread, HotSpotJVMCI::HotSpotJVMCIRuntime::excludeFromJVMCICompilation(JVMCIENV, HotSpotJVMCI::resolve(receiver))); |
160 java_lang_Throwable::java_printStackTrace(exception, THREAD); |
121 if (excludeModules.not_null()) { |
161 if (HAS_PENDING_EXCEPTION) { |
122 ModuleEntry* moduleEntry = method->method_holder()->module(); |
162 CLEAR_PENDING_EXCEPTION; |
123 for (int i = 0; i < excludeModules->length(); i++) { |
163 } |
124 if (oopDesc::equals(excludeModules->obj_at(i), moduleEntry->module())) { |
164 |
125 return true; |
165 env->set_failure(false, "unexpected exception thrown"); |
|
166 } else { |
|
167 oop result_object = (oop) result.get_jobject(); |
|
168 if (result_object != NULL) { |
|
169 oop failure_message = HotSpotCompilationRequestResult::failureMessage(result_object); |
|
170 if (failure_message != NULL) { |
|
171 // Copy failure reason into resource memory first ... |
|
172 const char* failure_reason = java_lang_String::as_utf8_string(failure_message); |
|
173 // ... and then into the C heap. |
|
174 failure_reason = os::strdup(failure_reason, mtCompiler); |
|
175 bool retryable = HotSpotCompilationRequestResult::retry(result_object) != 0; |
|
176 env->set_failure(retryable, failure_reason, true); |
|
177 } else { |
|
178 if (env->task()->code() == NULL) { |
|
179 env->set_failure(true, "no nmethod produced"); |
|
180 } else { |
|
181 env->task()->set_num_inlined_bytecodes(HotSpotCompilationRequestResult::inlinedBytecodes(result_object)); |
|
182 Atomic::inc(&_methods_compiled); |
|
183 } |
126 } |
184 } |
127 } |
185 } else { |
|
186 assert(false, "JVMCICompiler.compileMethod should always return non-null"); |
|
187 } |
128 } |
188 } |
129 } |
189 if (_bootstrapping) { |
130 return false; |
190 _bootstrap_compilation_request_handled = true; |
|
191 } |
|
192 } |
|
193 |
|
194 void JVMCICompiler::exit_on_pending_exception(oop exception, const char* message) { |
|
195 JavaThread* THREAD = JavaThread::current(); |
|
196 CLEAR_PENDING_EXCEPTION; |
|
197 |
|
198 static volatile int report_error = 0; |
|
199 if (!report_error && Atomic::cmpxchg(1, &report_error, 0) == 0) { |
|
200 // Only report an error once |
|
201 tty->print_raw_cr(message); |
|
202 Handle ex(THREAD, exception); |
|
203 java_lang_Throwable::java_printStackTrace(ex, THREAD); |
|
204 } else { |
|
205 // Allow error reporting thread to print the stack trace. Windows |
|
206 // doesn't allow uninterruptible wait for JavaThreads |
|
207 const bool interruptible = true; |
|
208 os::sleep(THREAD, 200, interruptible); |
|
209 } |
|
210 |
|
211 before_exit(THREAD); |
|
212 vm_exit(-1); |
|
213 } |
131 } |
214 |
132 |
215 // Compilation entry point for methods |
133 // Compilation entry point for methods |
216 void JVMCICompiler::compile_method(ciEnv* env, ciMethod* target, int entry_bci, DirectiveSet* directive) { |
134 void JVMCICompiler::compile_method(ciEnv* env, ciMethod* target, int entry_bci, DirectiveSet* directive) { |
217 ShouldNotReachHere(); |
135 ShouldNotReachHere(); |
225 // Print compilation timers and statistics |
143 // Print compilation timers and statistics |
226 void JVMCICompiler::print_compilation_timers() { |
144 void JVMCICompiler::print_compilation_timers() { |
227 TRACE_jvmci_1("JVMCICompiler::print_timers"); |
145 TRACE_jvmci_1("JVMCICompiler::print_timers"); |
228 tty->print_cr(" JVMCI code install time: %6.3f s", _codeInstallTimer.seconds()); |
146 tty->print_cr(" JVMCI code install time: %6.3f s", _codeInstallTimer.seconds()); |
229 } |
147 } |
230 |
|
231 bool JVMCICompiler::force_comp_at_level_simple(Method *method) { |
|
232 JVMCI_EXCEPTION_CONTEXT |
|
233 |
|
234 if (_bootstrapping) { |
|
235 // When bootstrapping, the JVMCI compiler can compile its own methods. |
|
236 return false; |
|
237 } |
|
238 |
|
239 if (!JVMCIRuntime::is_HotSpotJVMCIRuntime_initialized()) { |
|
240 // JVMCI cannot participate in compilation scheduling until |
|
241 // JVMCI is initialized and indicates it wants to participate. |
|
242 return false; |
|
243 } |
|
244 // Support for graal.CompileGraalWithC1Only |
|
245 HandleMark hm(thread); |
|
246 jobject runtime = JVMCIRuntime::get_HotSpotJVMCIRuntime_jobject(CATCH); |
|
247 objArrayHandle excludeFromJVMCICompilation(thread, HotSpotJVMCIRuntime::excludeFromJVMCICompilation(runtime)); |
|
248 if (excludeFromJVMCICompilation.is_null()) { |
|
249 return false; |
|
250 } |
|
251 ModuleEntry *module = method->method_holder()->module(); |
|
252 for (int i = 0; i < excludeFromJVMCICompilation->length(); ++i) { |
|
253 if (module->module() == excludeFromJVMCICompilation->obj_at(i)) { |
|
254 return true; |
|
255 } |
|
256 } |
|
257 |
|
258 return false; |
|
259 } |
|