mirror of
https://github.com/openjdk/jdk.git
synced 2025-08-28 07:14:30 +02:00
8218994: Consolidate indy and condy JVM information within a BootstrapInfo data structure
Introduce BootstrapInfo data structure and merge invocation of a bootstrap method for condy and indy into invoke_bootstrap_method. Co-authored-by: John Rose <john.r.rose@oracle.com> Reviewed-by: acorn, coleenp
This commit is contained in:
parent
fd3378a73e
commit
57aaf7a8cd
8 changed files with 534 additions and 325 deletions
|
@ -2750,106 +2750,61 @@ Handle SystemDictionary::link_method_handle_constant(Klass* caller,
|
|||
return Handle(THREAD, (oop) result.get_jobject());
|
||||
}
|
||||
|
||||
// Ask Java to compute a constant by invoking a BSM given a Dynamic_info CP entry
|
||||
Handle SystemDictionary::link_dynamic_constant(Klass* caller,
|
||||
int condy_index,
|
||||
Handle bootstrap_specifier,
|
||||
Symbol* name,
|
||||
Symbol* type,
|
||||
TRAPS) {
|
||||
Handle empty;
|
||||
Handle bsm, info;
|
||||
if (java_lang_invoke_MethodHandle::is_instance(bootstrap_specifier())) {
|
||||
bsm = bootstrap_specifier;
|
||||
} else {
|
||||
assert(bootstrap_specifier->is_objArray(), "");
|
||||
objArrayOop args = (objArrayOop) bootstrap_specifier();
|
||||
assert(args->length() == 2, "");
|
||||
bsm = Handle(THREAD, args->obj_at(0));
|
||||
info = Handle(THREAD, args->obj_at(1));
|
||||
}
|
||||
guarantee(java_lang_invoke_MethodHandle::is_instance(bsm()),
|
||||
"caller must supply a valid BSM");
|
||||
// Ask Java to run a bootstrap method, in order to create a dynamic call site
|
||||
// while linking an invokedynamic op, or compute a constant for Dynamic_info CP entry
|
||||
// with linkage results being stored back into the bootstrap specifier.
|
||||
void SystemDictionary::invoke_bootstrap_method(BootstrapInfo& bootstrap_specifier, TRAPS) {
|
||||
// Resolve the bootstrap specifier, its name, type, and static arguments
|
||||
bootstrap_specifier.resolve_bsm(CHECK);
|
||||
|
||||
// This should not happen. JDK code should take care of that.
|
||||
if (caller == NULL) {
|
||||
THROW_MSG_(vmSymbols::java_lang_InternalError(), "bad dynamic constant", empty);
|
||||
if (bootstrap_specifier.caller() == NULL || bootstrap_specifier.type_arg().is_null()) {
|
||||
THROW_MSG(vmSymbols::java_lang_InternalError(), "Invalid bootstrap method invocation with no caller or type argument");
|
||||
}
|
||||
|
||||
Handle constant_name = java_lang_String::create_from_symbol(name, CHECK_(empty));
|
||||
bool is_indy = bootstrap_specifier.is_method_call();
|
||||
objArrayHandle appendix_box;
|
||||
if (is_indy) {
|
||||
// Some method calls may require an appendix argument. Arrange to receive it.
|
||||
appendix_box = oopFactory::new_objArray_handle(SystemDictionary::Object_klass(), 1, CHECK);
|
||||
assert(appendix_box->obj_at(0) == NULL, "");
|
||||
}
|
||||
|
||||
// Resolve the constant type in the context of the caller class
|
||||
Handle type_mirror = find_java_mirror_for_type(type, caller, SignatureStream::NCDFError,
|
||||
CHECK_(empty));
|
||||
|
||||
// call java.lang.invoke.MethodHandleNatives::linkConstantDyanmic(caller, condy_index, bsm, type, info)
|
||||
// call condy: java.lang.invoke.MethodHandleNatives::linkDynamicConstant(caller, condy_index, bsm, type, info)
|
||||
// indy: java.lang.invoke.MethodHandleNatives::linkCallSite(caller, indy_index, bsm, name, mtype, info, &appendix)
|
||||
JavaCallArguments args;
|
||||
args.push_oop(Handle(THREAD, caller->java_mirror()));
|
||||
args.push_int(condy_index);
|
||||
args.push_oop(bsm);
|
||||
args.push_oop(constant_name);
|
||||
args.push_oop(type_mirror);
|
||||
args.push_oop(info);
|
||||
args.push_oop(Handle(THREAD, bootstrap_specifier.caller_mirror()));
|
||||
args.push_int(bootstrap_specifier.bss_index());
|
||||
args.push_oop(bootstrap_specifier.bsm());
|
||||
args.push_oop(bootstrap_specifier.name_arg());
|
||||
args.push_oop(bootstrap_specifier.type_arg());
|
||||
args.push_oop(bootstrap_specifier.arg_values());
|
||||
if (is_indy) {
|
||||
args.push_oop(appendix_box);
|
||||
}
|
||||
JavaValue result(T_OBJECT);
|
||||
JavaCalls::call_static(&result,
|
||||
SystemDictionary::MethodHandleNatives_klass(),
|
||||
vmSymbols::linkDynamicConstant_name(),
|
||||
vmSymbols::linkDynamicConstant_signature(),
|
||||
&args, CHECK_(empty));
|
||||
is_indy ? vmSymbols::linkCallSite_name() : vmSymbols::linkDynamicConstant_name(),
|
||||
is_indy ? vmSymbols::linkCallSite_signature() : vmSymbols::linkDynamicConstant_signature(),
|
||||
&args, CHECK);
|
||||
|
||||
return Handle(THREAD, (oop) result.get_jobject());
|
||||
}
|
||||
|
||||
// Ask Java code to find or construct a java.lang.invoke.CallSite for the given
|
||||
// name and signature, as interpreted relative to the given class loader.
|
||||
methodHandle SystemDictionary::find_dynamic_call_site_invoker(Klass* caller,
|
||||
int indy_index,
|
||||
Handle bootstrap_specifier,
|
||||
Symbol* name,
|
||||
Symbol* type,
|
||||
Handle *appendix_result,
|
||||
TRAPS) {
|
||||
methodHandle empty;
|
||||
Handle bsm, info;
|
||||
if (java_lang_invoke_MethodHandle::is_instance(bootstrap_specifier())) {
|
||||
bsm = bootstrap_specifier;
|
||||
Handle value(THREAD, (oop) result.get_jobject());
|
||||
if (is_indy) {
|
||||
Handle appendix;
|
||||
methodHandle method = unpack_method_and_appendix(value,
|
||||
bootstrap_specifier.caller(),
|
||||
appendix_box,
|
||||
&appendix, CHECK);
|
||||
bootstrap_specifier.set_resolved_method(method, appendix);
|
||||
} else {
|
||||
objArrayOop args = (objArrayOop) bootstrap_specifier();
|
||||
assert(args->length() == 2, "");
|
||||
bsm = Handle(THREAD, args->obj_at(0));
|
||||
info = Handle(THREAD, args->obj_at(1));
|
||||
}
|
||||
guarantee(java_lang_invoke_MethodHandle::is_instance(bsm()),
|
||||
"caller must supply a valid BSM");
|
||||
|
||||
Handle method_name = java_lang_String::create_from_symbol(name, CHECK_(empty));
|
||||
Handle method_type = find_method_handle_type(type, caller, CHECK_(empty));
|
||||
|
||||
// This should not happen. JDK code should take care of that.
|
||||
if (caller == NULL || method_type.is_null()) {
|
||||
THROW_MSG_(vmSymbols::java_lang_InternalError(), "bad invokedynamic", empty);
|
||||
bootstrap_specifier.set_resolved_value(value);
|
||||
}
|
||||
|
||||
objArrayHandle appendix_box = oopFactory::new_objArray_handle(SystemDictionary::Object_klass(), 1, CHECK_(empty));
|
||||
assert(appendix_box->obj_at(0) == NULL, "");
|
||||
|
||||
// call java.lang.invoke.MethodHandleNatives::linkCallSite(caller, indy_index, bsm, name, mtype, info, &appendix)
|
||||
JavaCallArguments args;
|
||||
args.push_oop(Handle(THREAD, caller->java_mirror()));
|
||||
args.push_int(indy_index);
|
||||
args.push_oop(bsm);
|
||||
args.push_oop(method_name);
|
||||
args.push_oop(method_type);
|
||||
args.push_oop(info);
|
||||
args.push_oop(appendix_box);
|
||||
JavaValue result(T_OBJECT);
|
||||
JavaCalls::call_static(&result,
|
||||
SystemDictionary::MethodHandleNatives_klass(),
|
||||
vmSymbols::linkCallSite_name(),
|
||||
vmSymbols::linkCallSite_signature(),
|
||||
&args, CHECK_(empty));
|
||||
Handle mname(THREAD, (oop) result.get_jobject());
|
||||
return unpack_method_and_appendix(mname, caller, appendix_box, appendix_result, THREAD);
|
||||
// sanity check
|
||||
assert(bootstrap_specifier.is_resolved() ||
|
||||
(bootstrap_specifier.is_method_call() &&
|
||||
bootstrap_specifier.resolved_method().not_null()), "bootstrap method call failed");
|
||||
}
|
||||
|
||||
// Protection domain cache table handling
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue