8153134: Infinite loop in handle_wrong_method in jmod
Use Patching_lock to synchronize access between set_code() and clear_code(). Reviewed-by: kvn, dlong
This commit is contained in:
parent
614320ba5e
commit
4bb6761600
@ -2041,7 +2041,6 @@ void ClassLoader::compile_the_world_in(char* name, Handle loader, TRAPS) {
|
||||
if (nm != NULL && !m->is_method_handle_intrinsic()) {
|
||||
// Throw out the code so that the code cache doesn't fill up
|
||||
nm->make_not_entrant();
|
||||
m->clear_code();
|
||||
}
|
||||
CompileBroker::compile_method(m, InvocationEntryBci, CompLevel_full_optimization,
|
||||
methodHandle(), 0, CompileTask::Reason_CTW, THREAD);
|
||||
@ -2060,7 +2059,6 @@ void ClassLoader::compile_the_world_in(char* name, Handle loader, TRAPS) {
|
||||
if (nm != NULL && !m->is_method_handle_intrinsic()) {
|
||||
// Throw out the code so that the code cache doesn't fill up
|
||||
nm->make_not_entrant();
|
||||
m->clear_code();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1252,7 +1252,7 @@ bool nmethod::make_not_entrant_or_zombie(unsigned int state) {
|
||||
if (method() != NULL && (method()->code() == this ||
|
||||
method()->from_compiled_entry() == verified_entry_point())) {
|
||||
HandleMark hm;
|
||||
method()->clear_code();
|
||||
method()->clear_code(false /* already owns Patching_lock */);
|
||||
}
|
||||
} // leave critical region under Patching_lock
|
||||
|
||||
|
@ -97,7 +97,7 @@ Method::Method(ConstMethod* xconst, AccessFlags access_flags) {
|
||||
// Fix and bury in Method*
|
||||
set_interpreter_entry(NULL); // sets i2i entry and from_int
|
||||
set_adapter_entry(NULL);
|
||||
clear_code(); // from_c/from_i get set to c2i/i2i
|
||||
clear_code(false /* don't need a lock */); // from_c/from_i get set to c2i/i2i
|
||||
|
||||
if (access_flags.is_native()) {
|
||||
clear_native_function();
|
||||
@ -907,8 +907,8 @@ void Method::set_not_osr_compilable(int comp_level, bool report, const char* rea
|
||||
}
|
||||
|
||||
// Revert to using the interpreter and clear out the nmethod
|
||||
void Method::clear_code() {
|
||||
|
||||
void Method::clear_code(bool acquire_lock /* = true */) {
|
||||
MutexLockerEx pl(acquire_lock ? Patching_lock : NULL, Mutex::_no_safepoint_check_flag);
|
||||
// this may be NULL if c2i adapters have not been made yet
|
||||
// Only should happen at allocate time.
|
||||
if (adapter() == NULL) {
|
||||
@ -1077,6 +1077,7 @@ bool Method::check_code() const {
|
||||
|
||||
// Install compiled code. Instantly it can execute.
|
||||
void Method::set_code(methodHandle mh, CompiledMethod *code) {
|
||||
MutexLockerEx pl(Patching_lock, Mutex::_no_safepoint_check_flag);
|
||||
assert( code, "use clear_code to remove code" );
|
||||
assert( mh->check_code(), "" );
|
||||
|
||||
|
@ -436,7 +436,7 @@ class Method : public Metadata {
|
||||
address verified_code_entry();
|
||||
bool check_code() const; // Not inline to avoid circular ref
|
||||
CompiledMethod* volatile code() const { assert( check_code(), "" ); return (CompiledMethod *)OrderAccess::load_ptr_acquire(&_code); }
|
||||
void clear_code(); // Clear out any compiled code
|
||||
void clear_code(bool acquire_lock = true); // Clear out any compiled code
|
||||
static void set_code(methodHandle mh, CompiledMethod* code);
|
||||
void set_adapter_entry(AdapterHandlerEntry* adapter) {
|
||||
constMethod()->set_adapter_entry(adapter);
|
||||
|
Loading…
x
Reference in New Issue
Block a user