提交 315bb061 编写于 作者: T twisti

7108383: JSR 292: JRuby bench_define_method_methods.rb: assert(slow_jvms !=...

7108383: JSR 292: JRuby bench_define_method_methods.rb: assert(slow_jvms != NULL) failed: miss path must not
Reviewed-by: kvn, never
上级 3ad2a9b9
...@@ -295,12 +295,6 @@ class ciMethod : public ciObject { ...@@ -295,12 +295,6 @@ class ciMethod : public ciObject {
// Print the name of this method in various incarnations. // Print the name of this method in various incarnations.
void print_name(outputStream* st = tty); void print_name(outputStream* st = tty);
void print_short_name(outputStream* st = tty); void print_short_name(outputStream* st = tty);
methodOop get_method_handle_target() {
KlassHandle receiver_limit; int flags = 0;
methodHandle m = MethodHandles::decode_method(get_oop(), receiver_limit, flags);
return m();
}
}; };
#endif // SHARE_VM_CI_CIMETHOD_HPP #endif // SHARE_VM_CI_CIMETHOD_HPP
...@@ -318,17 +318,17 @@ CallGenerator* CallGenerator::for_direct_call(ciMethod* m, bool separate_io_proj ...@@ -318,17 +318,17 @@ CallGenerator* CallGenerator::for_direct_call(ciMethod* m, bool separate_io_proj
return new DirectCallGenerator(m, separate_io_proj); return new DirectCallGenerator(m, separate_io_proj);
} }
CallGenerator* CallGenerator::for_dynamic_call(ciMethod* m) {
assert(m->is_method_handle_invoke() || m->is_method_handle_adapter(), "for_dynamic_call mismatch");
return new DynamicCallGenerator(m);
}
CallGenerator* CallGenerator::for_virtual_call(ciMethod* m, int vtable_index) { CallGenerator* CallGenerator::for_virtual_call(ciMethod* m, int vtable_index) {
assert(!m->is_static(), "for_virtual_call mismatch"); assert(!m->is_static(), "for_virtual_call mismatch");
assert(!m->is_method_handle_invoke(), "should be a direct call"); assert(!m->is_method_handle_invoke(), "should be a direct call");
return new VirtualCallGenerator(m, vtable_index); return new VirtualCallGenerator(m, vtable_index);
} }
CallGenerator* CallGenerator::for_dynamic_call(ciMethod* m) {
assert(m->is_method_handle_invoke() || m->is_method_handle_adapter(), "for_dynamic_call mismatch");
return new DynamicCallGenerator(m);
}
// Allow inlining decisions to be delayed // Allow inlining decisions to be delayed
class LateInlineCallGenerator : public DirectCallGenerator { class LateInlineCallGenerator : public DirectCallGenerator {
CallGenerator* _inline_cg; CallGenerator* _inline_cg;
...@@ -576,7 +576,9 @@ JVMState* PredictedCallGenerator::generate(JVMState* jvms) { ...@@ -576,7 +576,9 @@ JVMState* PredictedCallGenerator::generate(JVMState* jvms) {
kit.set_control(slow_ctl); kit.set_control(slow_ctl);
if (!kit.stopped()) { if (!kit.stopped()) {
slow_jvms = _if_missed->generate(kit.sync_jvms()); slow_jvms = _if_missed->generate(kit.sync_jvms());
assert(slow_jvms != NULL, "miss path must not fail to generate"); if (kit.failing())
return NULL; // might happen because of NodeCountInliningCutoff
assert(slow_jvms != NULL, "must be");
kit.add_exception_states_from(slow_jvms); kit.add_exception_states_from(slow_jvms);
kit.set_map(slow_jvms->map()); kit.set_map(slow_jvms->map());
if (!kit.stopped()) if (!kit.stopped())
...@@ -682,6 +684,15 @@ CallGenerator* CallGenerator::for_predicted_dynamic_call(ciMethodHandle* predict ...@@ -682,6 +684,15 @@ CallGenerator* CallGenerator::for_predicted_dynamic_call(ciMethodHandle* predict
} }
CallGenerator* CallGenerator::for_method_handle_call(Node* method_handle, JVMState* jvms,
ciMethod* caller, ciMethod* callee, ciCallProfile profile) {
assert(callee->is_method_handle_invoke() || callee->is_method_handle_adapter(), "for_method_handle_call mismatch");
CallGenerator* cg = CallGenerator::for_method_handle_inline(method_handle, jvms, caller, callee, profile);
if (cg != NULL)
return cg;
return CallGenerator::for_direct_call(callee);
}
CallGenerator* CallGenerator::for_method_handle_inline(Node* method_handle, JVMState* jvms, CallGenerator* CallGenerator::for_method_handle_inline(Node* method_handle, JVMState* jvms,
ciMethod* caller, ciMethod* callee, ciCallProfile profile) { ciMethod* caller, ciMethod* callee, ciCallProfile profile) {
if (method_handle->Opcode() == Op_ConP) { if (method_handle->Opcode() == Op_ConP) {
...@@ -721,8 +732,8 @@ CallGenerator* CallGenerator::for_method_handle_inline(Node* method_handle, JVMS ...@@ -721,8 +732,8 @@ CallGenerator* CallGenerator::for_method_handle_inline(Node* method_handle, JVMS
// Generate a guard so that each can be inlined. We might want to // Generate a guard so that each can be inlined. We might want to
// do more inputs at later point but this gets the most common // do more inputs at later point but this gets the most common
// case. // case.
CallGenerator* cg1 = for_method_handle_inline(method_handle->in(1), jvms, caller, callee, profile.rescale(1.0 - prob)); CallGenerator* cg1 = for_method_handle_call(method_handle->in(1), jvms, caller, callee, profile.rescale(1.0 - prob));
CallGenerator* cg2 = for_method_handle_inline(method_handle->in(2), jvms, caller, callee, profile.rescale(prob)); CallGenerator* cg2 = for_method_handle_call(method_handle->in(2), jvms, caller, callee, profile.rescale(prob));
if (cg1 != NULL && cg2 != NULL) { if (cg1 != NULL && cg2 != NULL) {
const TypeOopPtr* oop_ptr = method_handle->in(1)->bottom_type()->is_oopptr(); const TypeOopPtr* oop_ptr = method_handle->in(1)->bottom_type()->is_oopptr();
ciObject* const_oop = oop_ptr->const_oop(); ciObject* const_oop = oop_ptr->const_oop();
...@@ -733,6 +744,17 @@ CallGenerator* CallGenerator::for_method_handle_inline(Node* method_handle, JVMS ...@@ -733,6 +744,17 @@ CallGenerator* CallGenerator::for_method_handle_inline(Node* method_handle, JVMS
return NULL; return NULL;
} }
CallGenerator* CallGenerator::for_invokedynamic_call(JVMState* jvms, ciMethod* caller, ciMethod* callee, ciCallProfile profile) {
assert(callee->is_method_handle_invoke() || callee->is_method_handle_adapter(), "for_invokedynamic_call mismatch");
// Get the CallSite object.
ciBytecodeStream str(caller);
str.force_bci(jvms->bci()); // Set the stream to the invokedynamic bci.
ciCallSite* call_site = str.get_call_site();
CallGenerator* cg = CallGenerator::for_invokedynamic_inline(call_site, jvms, caller, callee, profile);
if (cg != NULL)
return cg;
return CallGenerator::for_dynamic_call(callee);
}
CallGenerator* CallGenerator::for_invokedynamic_inline(ciCallSite* call_site, JVMState* jvms, CallGenerator* CallGenerator::for_invokedynamic_inline(ciCallSite* call_site, JVMState* jvms,
ciMethod* caller, ciMethod* callee, ciCallProfile profile) { ciMethod* caller, ciMethod* callee, ciCallProfile profile) {
...@@ -819,7 +841,9 @@ JVMState* PredictedDynamicCallGenerator::generate(JVMState* jvms) { ...@@ -819,7 +841,9 @@ JVMState* PredictedDynamicCallGenerator::generate(JVMState* jvms) {
kit.set_control(slow_ctl); kit.set_control(slow_ctl);
if (!kit.stopped()) { if (!kit.stopped()) {
slow_jvms = _if_missed->generate(kit.sync_jvms()); slow_jvms = _if_missed->generate(kit.sync_jvms());
assert(slow_jvms != NULL, "miss path must not fail to generate"); if (kit.failing())
return NULL; // might happen because of NodeCountInliningCutoff
assert(slow_jvms != NULL, "must be");
kit.add_exception_states_from(slow_jvms); kit.add_exception_states_from(slow_jvms);
kit.set_map(slow_jvms->map()); kit.set_map(slow_jvms->map());
if (!kit.stopped()) if (!kit.stopped())
......
...@@ -108,8 +108,11 @@ class CallGenerator : public ResourceObj { ...@@ -108,8 +108,11 @@ class CallGenerator : public ResourceObj {
// How to generate vanilla out-of-line call sites: // How to generate vanilla out-of-line call sites:
static CallGenerator* for_direct_call(ciMethod* m, bool separate_io_projs = false); // static, special static CallGenerator* for_direct_call(ciMethod* m, bool separate_io_projs = false); // static, special
static CallGenerator* for_dynamic_call(ciMethod* m); // invokedynamic
static CallGenerator* for_virtual_call(ciMethod* m, int vtable_index); // virtual, interface static CallGenerator* for_virtual_call(ciMethod* m, int vtable_index); // virtual, interface
static CallGenerator* for_dynamic_call(ciMethod* m); // invokedynamic
static CallGenerator* for_method_handle_call(Node* method_handle, JVMState* jvms, ciMethod* caller, ciMethod* callee, ciCallProfile profile);
static CallGenerator* for_invokedynamic_call( JVMState* jvms, ciMethod* caller, ciMethod* callee, ciCallProfile profile);
static CallGenerator* for_method_handle_inline(Node* method_handle, JVMState* jvms, ciMethod* caller, ciMethod* callee, ciCallProfile profile); static CallGenerator* for_method_handle_inline(Node* method_handle, JVMState* jvms, ciMethod* caller, ciMethod* callee, ciCallProfile profile);
static CallGenerator* for_invokedynamic_inline(ciCallSite* call_site, JVMState* jvms, ciMethod* caller, ciMethod* callee, ciCallProfile profile); static CallGenerator* for_invokedynamic_inline(ciCallSite* call_site, JVMState* jvms, ciMethod* caller, ciMethod* callee, ciCallProfile profile);
......
...@@ -62,7 +62,6 @@ void trace_type_profile(ciMethod *method, int depth, int bci, ciMethod *prof_met ...@@ -62,7 +62,6 @@ void trace_type_profile(ciMethod *method, int depth, int bci, ciMethod *prof_met
CallGenerator* Compile::call_generator(ciMethod* call_method, int vtable_index, bool call_is_virtual, CallGenerator* Compile::call_generator(ciMethod* call_method, int vtable_index, bool call_is_virtual,
JVMState* jvms, bool allow_inline, JVMState* jvms, bool allow_inline,
float prof_factor) { float prof_factor) {
CallGenerator* cg;
ciMethod* caller = jvms->method(); ciMethod* caller = jvms->method();
int bci = jvms->bci(); int bci = jvms->bci();
Bytecodes::Code bytecode = caller->java_code_at_bci(bci); Bytecodes::Code bytecode = caller->java_code_at_bci(bci);
...@@ -110,7 +109,7 @@ CallGenerator* Compile::call_generator(ciMethod* call_method, int vtable_index, ...@@ -110,7 +109,7 @@ CallGenerator* Compile::call_generator(ciMethod* call_method, int vtable_index,
// We do this before the strict f.p. check below because the // We do this before the strict f.p. check below because the
// intrinsics handle strict f.p. correctly. // intrinsics handle strict f.p. correctly.
if (allow_inline) { if (allow_inline) {
cg = find_intrinsic(call_method, call_is_virtual); CallGenerator* cg = find_intrinsic(call_method, call_is_virtual);
if (cg != NULL) return cg; if (cg != NULL) return cg;
} }
...@@ -121,33 +120,16 @@ CallGenerator* Compile::call_generator(ciMethod* call_method, int vtable_index, ...@@ -121,33 +120,16 @@ CallGenerator* Compile::call_generator(ciMethod* call_method, int vtable_index,
if (call_method->is_method_handle_invoke()) { if (call_method->is_method_handle_invoke()) {
if (bytecode != Bytecodes::_invokedynamic) { if (bytecode != Bytecodes::_invokedynamic) {
GraphKit kit(jvms); GraphKit kit(jvms);
Node* n = kit.argument(0); Node* method_handle = kit.argument(0);
return CallGenerator::for_method_handle_call(method_handle, jvms, caller, call_method, profile);
CallGenerator* cg = CallGenerator::for_method_handle_inline(n, jvms, caller, call_method, profile);
if (cg != NULL) {
return cg;
}
return CallGenerator::for_direct_call(call_method);
} }
else { else {
// Get the CallSite object. return CallGenerator::for_invokedynamic_call(jvms, caller, call_method, profile);
ciMethod* caller_method = jvms->method();
ciBytecodeStream str(caller_method);
str.force_bci(jvms->bci()); // Set the stream to the invokedynamic bci.
ciCallSite* call_site = str.get_call_site();
CallGenerator* cg = CallGenerator::for_invokedynamic_inline(call_site, jvms, caller, call_method, profile);
if (cg != NULL) {
return cg;
}
// If something failed, generate a normal dynamic call.
return CallGenerator::for_dynamic_call(call_method);
} }
} }
// Do not inline strict fp into non-strict code, or the reverse // Do not inline strict fp into non-strict code, or the reverse
bool caller_method_is_strict = jvms->method()->is_strict(); if (caller->is_strict() ^ call_method->is_strict()) {
if( caller_method_is_strict ^ call_method->is_strict() ) {
allow_inline = false; allow_inline = false;
} }
...@@ -258,7 +240,7 @@ CallGenerator* Compile::call_generator(ciMethod* call_method, int vtable_index, ...@@ -258,7 +240,7 @@ CallGenerator* Compile::call_generator(ciMethod* call_method, int vtable_index,
} }
if (miss_cg != NULL) { if (miss_cg != NULL) {
NOT_PRODUCT(trace_type_profile(jvms->method(), jvms->depth() - 1, jvms->bci(), receiver_method, profile.receiver(0), site_count, receiver_count)); NOT_PRODUCT(trace_type_profile(jvms->method(), jvms->depth() - 1, jvms->bci(), receiver_method, profile.receiver(0), site_count, receiver_count));
cg = CallGenerator::for_predicted_call(profile.receiver(0), miss_cg, hit_cg, profile.receiver_prob(0)); CallGenerator* cg = CallGenerator::for_predicted_call(profile.receiver(0), miss_cg, hit_cg, profile.receiver_prob(0));
if (cg != NULL) return cg; if (cg != NULL) return cg;
} }
} }
......
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册