mirror of
https://github.com/openjdk/jdk.git
synced 2025-08-26 22:34:27 +02:00
6914206: change way of permission checking for generated MethodHandle adapters
Put generated MH adapter in InvokeDynamic/MethodHandle classes to be able to indentify them easily in the compiler. Reviewed-by: kvn, never, jrose
This commit is contained in:
parent
8da8433a6f
commit
e5fb2ad1c4
11 changed files with 66 additions and 16 deletions
|
@ -1,5 +1,5 @@
|
||||||
/*
|
/*
|
||||||
* Copyright 1999-2009 Sun Microsystems, Inc. All Rights Reserved.
|
* Copyright 1999-2010 Sun Microsystems, Inc. All Rights Reserved.
|
||||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||||
*
|
*
|
||||||
* This code is free software; you can redistribute it and/or modify it
|
* This code is free software; you can redistribute it and/or modify it
|
||||||
|
@ -700,6 +700,12 @@ bool ciMethod::is_method_handle_invoke() const {
|
||||||
return flag;
|
return flag;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool ciMethod::is_method_handle_adapter() const {
|
||||||
|
check_is_loaded();
|
||||||
|
VM_ENTRY_MARK;
|
||||||
|
return get_methodOop()->is_method_handle_adapter();
|
||||||
|
}
|
||||||
|
|
||||||
ciInstance* ciMethod::method_handle_type() {
|
ciInstance* ciMethod::method_handle_type() {
|
||||||
check_is_loaded();
|
check_is_loaded();
|
||||||
VM_ENTRY_MARK;
|
VM_ENTRY_MARK;
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
/*
|
/*
|
||||||
* Copyright 1999-2009 Sun Microsystems, Inc. All Rights Reserved.
|
* Copyright 1999-2010 Sun Microsystems, Inc. All Rights Reserved.
|
||||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||||
*
|
*
|
||||||
* This code is free software; you can redistribute it and/or modify it
|
* This code is free software; you can redistribute it and/or modify it
|
||||||
|
@ -215,7 +215,10 @@ class ciMethod : public ciObject {
|
||||||
bool check_call(int refinfo_index, bool is_static) const;
|
bool check_call(int refinfo_index, bool is_static) const;
|
||||||
void build_method_data(); // make sure it exists in the VM also
|
void build_method_data(); // make sure it exists in the VM also
|
||||||
int scale_count(int count, float prof_factor = 1.); // make MDO count commensurate with IIC
|
int scale_count(int count, float prof_factor = 1.); // make MDO count commensurate with IIC
|
||||||
bool is_method_handle_invoke() const;
|
|
||||||
|
// JSR 292 support
|
||||||
|
bool is_method_handle_invoke() const;
|
||||||
|
bool is_method_handle_adapter() const;
|
||||||
ciInstance* method_handle_type();
|
ciInstance* method_handle_type();
|
||||||
|
|
||||||
// What kind of ciObject is this?
|
// What kind of ciObject is this?
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
/*
|
/*
|
||||||
* Copyright 1997-2009 Sun Microsystems, Inc. All Rights Reserved.
|
* Copyright 1997-2010 Sun Microsystems, Inc. All Rights Reserved.
|
||||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||||
*
|
*
|
||||||
* This code is free software; you can redistribute it and/or modify it
|
* This code is free software; you can redistribute it and/or modify it
|
||||||
|
@ -145,7 +145,7 @@ class SymbolPropertyTable;
|
||||||
template(Linkage_klass, java_dyn_Linkage, Opt) \
|
template(Linkage_klass, java_dyn_Linkage, Opt) \
|
||||||
template(CallSite_klass, java_dyn_CallSite, Opt) \
|
template(CallSite_klass, java_dyn_CallSite, Opt) \
|
||||||
template(InvokeDynamic_klass, java_dyn_InvokeDynamic, Opt) \
|
template(InvokeDynamic_klass, java_dyn_InvokeDynamic, Opt) \
|
||||||
/* Note: MethodHandle must be first, and Dynamic last in group */ \
|
/* Note: MethodHandle must be first, and InvokeDynamic last in group */ \
|
||||||
\
|
\
|
||||||
template(StringBuffer_klass, java_lang_StringBuffer, Pre) \
|
template(StringBuffer_klass, java_lang_StringBuffer, Pre) \
|
||||||
template(StringBuilder_klass, java_lang_StringBuilder, Pre) \
|
template(StringBuilder_klass, java_lang_StringBuilder, Pre) \
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
//
|
//
|
||||||
// Copyright 1997-2009 Sun Microsystems, Inc. All Rights Reserved.
|
// Copyright 1997-2010 Sun Microsystems, Inc. All Rights Reserved.
|
||||||
// DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
// DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||||
//
|
//
|
||||||
// This code is free software; you can redistribute it and/or modify it
|
// This code is free software; you can redistribute it and/or modify it
|
||||||
|
@ -3503,6 +3503,7 @@ reflection.cpp javaCalls.hpp
|
||||||
reflection.cpp javaClasses.hpp
|
reflection.cpp javaClasses.hpp
|
||||||
reflection.cpp jvm.h
|
reflection.cpp jvm.h
|
||||||
reflection.cpp linkResolver.hpp
|
reflection.cpp linkResolver.hpp
|
||||||
|
reflection.cpp methodHandleWalk.hpp
|
||||||
reflection.cpp objArrayKlass.hpp
|
reflection.cpp objArrayKlass.hpp
|
||||||
reflection.cpp objArrayOop.hpp
|
reflection.cpp objArrayOop.hpp
|
||||||
reflection.cpp oopFactory.hpp
|
reflection.cpp oopFactory.hpp
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
/*
|
/*
|
||||||
* Copyright 1997-2009 Sun Microsystems, Inc. All Rights Reserved.
|
* Copyright 1997-2010 Sun Microsystems, Inc. All Rights Reserved.
|
||||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||||
*
|
*
|
||||||
* This code is free software; you can redistribute it and/or modify it
|
* This code is free software; you can redistribute it and/or modify it
|
||||||
|
@ -821,6 +821,18 @@ jint* methodOopDesc::method_type_offsets_chain() {
|
||||||
return pchase;
|
return pchase;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//------------------------------------------------------------------------------
|
||||||
|
// methodOopDesc::is_method_handle_adapter
|
||||||
|
//
|
||||||
|
// Tests if this method is an internal adapter frame from the
|
||||||
|
// MethodHandleCompiler.
|
||||||
|
bool methodOopDesc::is_method_handle_adapter() const {
|
||||||
|
return ((name() == vmSymbols::invoke_name() &&
|
||||||
|
method_holder() == SystemDictionary::MethodHandle_klass())
|
||||||
|
||
|
||||||
|
method_holder() == SystemDictionary::InvokeDynamic_klass());
|
||||||
|
}
|
||||||
|
|
||||||
methodHandle methodOopDesc::make_invoke_method(KlassHandle holder,
|
methodHandle methodOopDesc::make_invoke_method(KlassHandle holder,
|
||||||
symbolHandle signature,
|
symbolHandle signature,
|
||||||
Handle method_type, TRAPS) {
|
Handle method_type, TRAPS) {
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
/*
|
/*
|
||||||
* Copyright 1997-2009 Sun Microsystems, Inc. All Rights Reserved.
|
* Copyright 1997-2010 Sun Microsystems, Inc. All Rights Reserved.
|
||||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||||
*
|
*
|
||||||
* This code is free software; you can redistribute it and/or modify it
|
* This code is free software; you can redistribute it and/or modify it
|
||||||
|
@ -525,6 +525,9 @@ class methodOopDesc : public oopDesc {
|
||||||
|
|
||||||
// JSR 292 support
|
// JSR 292 support
|
||||||
bool is_method_handle_invoke() const { return access_flags().is_method_handle_invoke(); }
|
bool is_method_handle_invoke() const { return access_flags().is_method_handle_invoke(); }
|
||||||
|
// Tests if this method is an internal adapter frame from the
|
||||||
|
// MethodHandleCompiler.
|
||||||
|
bool is_method_handle_adapter() const;
|
||||||
static methodHandle make_invoke_method(KlassHandle holder,
|
static methodHandle make_invoke_method(KlassHandle holder,
|
||||||
symbolHandle signature,
|
symbolHandle signature,
|
||||||
Handle method_type,
|
Handle method_type,
|
||||||
|
@ -538,6 +541,7 @@ class methodOopDesc : public oopDesc {
|
||||||
// all without checking for a stack overflow
|
// all without checking for a stack overflow
|
||||||
static int extra_stack_entries() { return (EnableMethodHandles ? (int)MethodHandlePushLimit : 0) + (EnableInvokeDynamic ? 3 : 0); }
|
static int extra_stack_entries() { return (EnableMethodHandles ? (int)MethodHandlePushLimit : 0) + (EnableInvokeDynamic ? 3 : 0); }
|
||||||
static int extra_stack_words(); // = extra_stack_entries() * Interpreter::stackElementSize()
|
static int extra_stack_words(); // = extra_stack_entries() * Interpreter::stackElementSize()
|
||||||
|
|
||||||
// RedefineClasses() support:
|
// RedefineClasses() support:
|
||||||
bool is_old() const { return access_flags().is_old(); }
|
bool is_old() const { return access_flags().is_old(); }
|
||||||
void set_is_old() { _access_flags.set_is_old(); }
|
void set_is_old() { _access_flags.set_is_old(); }
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
/*
|
/*
|
||||||
* Copyright 1999-2009 Sun Microsystems, Inc. All Rights Reserved.
|
* Copyright 1999-2010 Sun Microsystems, Inc. All Rights Reserved.
|
||||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||||
*
|
*
|
||||||
* This code is free software; you can redistribute it and/or modify it
|
* This code is free software; you can redistribute it and/or modify it
|
||||||
|
@ -3697,12 +3697,14 @@ bool LibraryCallKit::inline_native_Reflection_getCallerClass() {
|
||||||
|
|
||||||
// Helper routine for above
|
// Helper routine for above
|
||||||
bool LibraryCallKit::is_method_invoke_or_aux_frame(JVMState* jvms) {
|
bool LibraryCallKit::is_method_invoke_or_aux_frame(JVMState* jvms) {
|
||||||
|
ciMethod* method = jvms->method();
|
||||||
|
|
||||||
// Is this the Method.invoke method itself?
|
// Is this the Method.invoke method itself?
|
||||||
if (jvms->method()->intrinsic_id() == vmIntrinsics::_invoke)
|
if (method->intrinsic_id() == vmIntrinsics::_invoke)
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
// Is this a helper, defined somewhere underneath MethodAccessorImpl.
|
// Is this a helper, defined somewhere underneath MethodAccessorImpl.
|
||||||
ciKlass* k = jvms->method()->holder();
|
ciKlass* k = method->holder();
|
||||||
if (k->is_instance_klass()) {
|
if (k->is_instance_klass()) {
|
||||||
ciInstanceKlass* ik = k->as_instance_klass();
|
ciInstanceKlass* ik = k->as_instance_klass();
|
||||||
for (; ik != NULL; ik = ik->super()) {
|
for (; ik != NULL; ik = ik->super()) {
|
||||||
|
@ -3712,6 +3714,10 @@ bool LibraryCallKit::is_method_invoke_or_aux_frame(JVMState* jvms) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
else if (method->is_method_handle_adapter()) {
|
||||||
|
// This is an internal adapter frame from the MethodHandleCompiler -- skip it
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
|
@ -631,6 +631,7 @@ MethodHandleCompiler::MethodHandleCompiler(Handle root, methodHandle callee, boo
|
||||||
Handle first_mtype(THREAD, chain().method_type_oop());
|
Handle first_mtype(THREAD, chain().method_type_oop());
|
||||||
// _rklass is NULL for primitives.
|
// _rklass is NULL for primitives.
|
||||||
_rtype = java_lang_Class::as_BasicType(java_dyn_MethodType::rtype(first_mtype()), &_rklass);
|
_rtype = java_lang_Class::as_BasicType(java_dyn_MethodType::rtype(first_mtype()), &_rklass);
|
||||||
|
if (_rtype == T_ARRAY) _rtype = T_OBJECT;
|
||||||
|
|
||||||
int params = _callee->size_of_parameters(); // Incoming arguments plus receiver.
|
int params = _callee->size_of_parameters(); // Incoming arguments plus receiver.
|
||||||
_num_params = for_invokedynamic() ? params - 1 : params; // XXX Check if callee is static?
|
_num_params = for_invokedynamic() ? params - 1 : params; // XXX Check if callee is static?
|
||||||
|
@ -957,10 +958,13 @@ MethodHandleCompiler::make_invoke(methodOop m, vmIntrinsics::ID iid,
|
||||||
symbolOop name = m->name();
|
symbolOop name = m->name();
|
||||||
symbolOop signature = m->signature();
|
symbolOop signature = m->signature();
|
||||||
|
|
||||||
// This generated adapter method should be in the same class as the
|
|
||||||
// DMH target method (for accessability reasons).
|
|
||||||
if (tailcall) {
|
if (tailcall) {
|
||||||
_target_klass = klass;
|
// Actually, in order to make these methods more recognizable,
|
||||||
|
// let's put them in holder classes MethodHandle and InvokeDynamic.
|
||||||
|
// That way stack walkers and compiler heuristics can recognize them.
|
||||||
|
_target_klass = (for_invokedynamic()
|
||||||
|
? SystemDictionary::InvokeDynamic_klass()
|
||||||
|
: SystemDictionary::MethodHandle_klass());
|
||||||
}
|
}
|
||||||
|
|
||||||
// instanceKlass* ik = instanceKlass::cast(klass);
|
// instanceKlass* ik = instanceKlass::cast(klass);
|
||||||
|
@ -1017,6 +1021,7 @@ MethodHandleCompiler::make_invoke(methodOop m, vmIntrinsics::ID iid,
|
||||||
// If tailcall, we have walked all the way to a direct method handle.
|
// If tailcall, we have walked all the way to a direct method handle.
|
||||||
// Otherwise, make a recursive call to some helper routine.
|
// Otherwise, make a recursive call to some helper routine.
|
||||||
BasicType rbt = m->result_type();
|
BasicType rbt = m->result_type();
|
||||||
|
if (rbt == T_ARRAY) rbt = T_OBJECT;
|
||||||
ArgToken ret;
|
ArgToken ret;
|
||||||
if (tailcall) {
|
if (tailcall) {
|
||||||
if (rbt != _rtype) {
|
if (rbt != _rtype) {
|
||||||
|
|
|
@ -404,4 +404,10 @@ public:
|
||||||
|
|
||||||
// Compile the given MH chain into bytecode.
|
// Compile the given MH chain into bytecode.
|
||||||
methodHandle compile(TRAPS);
|
methodHandle compile(TRAPS);
|
||||||
|
|
||||||
|
// Tests if the given class is a MH adapter holder.
|
||||||
|
static bool klass_is_method_handle_adapter_holder(klassOop klass) {
|
||||||
|
return (klass == SystemDictionary::MethodHandle_klass() ||
|
||||||
|
klass == SystemDictionary::InvokeDynamic_klass());
|
||||||
|
}
|
||||||
};
|
};
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
/*
|
/*
|
||||||
* Copyright 1997-2009 Sun Microsystems, Inc. All Rights Reserved.
|
* Copyright 1997-2010 Sun Microsystems, Inc. All Rights Reserved.
|
||||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||||
*
|
*
|
||||||
* This code is free software; you can redistribute it and/or modify it
|
* This code is free software; you can redistribute it and/or modify it
|
||||||
|
@ -482,6 +482,11 @@ bool Reflection::can_relax_access_check_for(
|
||||||
under_host_klass(accessee_ik, accessor))
|
under_host_klass(accessee_ik, accessor))
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
|
// Adapter frames can access anything.
|
||||||
|
if (MethodHandleCompiler::klass_is_method_handle_adapter_holder(accessor))
|
||||||
|
// This is an internal adapter frame from the MethodHandleCompiler.
|
||||||
|
return true;
|
||||||
|
|
||||||
if (RelaxAccessControlCheck ||
|
if (RelaxAccessControlCheck ||
|
||||||
(accessor_ik->major_version() < JAVA_1_5_VERSION &&
|
(accessor_ik->major_version() < JAVA_1_5_VERSION &&
|
||||||
accessee_ik->major_version() < JAVA_1_5_VERSION)) {
|
accessee_ik->major_version() < JAVA_1_5_VERSION)) {
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
/*
|
/*
|
||||||
* Copyright 1997-2009 Sun Microsystems, Inc. All Rights Reserved.
|
* Copyright 1997-2010 Sun Microsystems, Inc. All Rights Reserved.
|
||||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||||
*
|
*
|
||||||
* This code is free software; you can redistribute it and/or modify it
|
* This code is free software; you can redistribute it and/or modify it
|
||||||
|
@ -432,6 +432,8 @@ void vframeStreamCommon::security_get_caller_frame(int depth) {
|
||||||
Klass::cast(method()->method_holder())
|
Klass::cast(method()->method_holder())
|
||||||
->is_subclass_of(SystemDictionary::reflect_MethodAccessorImpl_klass())) {
|
->is_subclass_of(SystemDictionary::reflect_MethodAccessorImpl_klass())) {
|
||||||
// This is an auxilary frame -- skip it
|
// This is an auxilary frame -- skip it
|
||||||
|
} else if (method()->is_method_handle_adapter()) {
|
||||||
|
// This is an internal adapter frame from the MethodHandleCompiler -- skip it
|
||||||
} else {
|
} else {
|
||||||
// This is non-excluded frame, we need to count it against the depth
|
// This is non-excluded frame, we need to count it against the depth
|
||||||
if (depth-- <= 0) {
|
if (depth-- <= 0) {
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue