8222988: Use MonitorLocker rather than MutexLocker when wait/notify used
Fixed use cases in code except CMS. Reviewed-by: rehn, dcubed
This commit is contained in:
parent
ed9eac2bb9
commit
ccb2e9d925
@ -1,5 +1,5 @@
|
||||
//
|
||||
// Copyright (c) 2007, 2013, Oracle and/or its affiliates. All rights reserved.
|
||||
// Copyright (c) 2007, 2019, Oracle and/or its affiliates. All rights reserved.
|
||||
// DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
//
|
||||
// This code is free software; you can redistribute it and/or modify it
|
||||
@ -28,14 +28,14 @@
|
||||
|
||||
bool AbstractCompiler::should_perform_init() {
|
||||
if (_compiler_state != initialized) {
|
||||
MutexLocker only_one(CompileThread_lock);
|
||||
MonitorLocker only_one(CompileThread_lock);
|
||||
|
||||
if (_compiler_state == uninitialized) {
|
||||
_compiler_state = initializing;
|
||||
return true;
|
||||
} else {
|
||||
while (_compiler_state == initializing) {
|
||||
CompileThread_lock->wait();
|
||||
only_one.wait();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -402,7 +402,7 @@ CompileTask* CompileQueue::get() {
|
||||
methodHandle save_method;
|
||||
methodHandle save_hot_method;
|
||||
|
||||
MutexLocker locker(MethodCompileQueue_lock);
|
||||
MonitorLocker locker(MethodCompileQueue_lock);
|
||||
// If _first is NULL we have no more compile jobs. There are two reasons for
|
||||
// having no compile jobs: First, we compiled everything we wanted. Second,
|
||||
// we ran out of code cache so compilation has been disabled. In the latter
|
||||
@ -423,7 +423,7 @@ CompileTask* CompileQueue::get() {
|
||||
// We need a timed wait here, since compiler threads can exit if compilation
|
||||
// is disabled forever. We use 5 seconds wait time; the exiting of compiler threads
|
||||
// is not critical and we do not want idle compiler threads to wake up too often.
|
||||
MethodCompileQueue_lock->wait(5*1000);
|
||||
locker.wait(5*1000);
|
||||
|
||||
if (UseDynamicNumberOfCompilerThreads && _first == NULL) {
|
||||
// Still nothing to compile. Give caller a chance to stop this thread.
|
||||
@ -1496,11 +1496,11 @@ static const int JVMCI_COMPILATION_PROGRESS_WAIT_ATTEMPTS = 10;
|
||||
* @return true if this thread needs to free/recycle the task
|
||||
*/
|
||||
bool CompileBroker::wait_for_jvmci_completion(JVMCICompiler* jvmci, CompileTask* task, JavaThread* thread) {
|
||||
MutexLocker waiter(task->lock(), thread);
|
||||
MonitorLocker ml(task->lock(), thread);
|
||||
int progress_wait_attempts = 0;
|
||||
int methods_compiled = jvmci->methods_compiled();
|
||||
while (!task->is_complete() && !is_compilation_disabled_forever() &&
|
||||
task->lock()->wait(JVMCI_COMPILATION_PROGRESS_WAIT_TIMESLICE)) {
|
||||
ml.wait(JVMCI_COMPILATION_PROGRESS_WAIT_TIMESLICE)) {
|
||||
CompilerThread* jvmci_compiler_thread = task->jvmci_compiler_thread();
|
||||
|
||||
bool progress;
|
||||
@ -1558,10 +1558,10 @@ void CompileBroker::wait_for_completion(CompileTask* task) {
|
||||
} else
|
||||
#endif
|
||||
{
|
||||
MutexLocker waiter(task->lock(), thread);
|
||||
MonitorLocker ml(task->lock(), thread);
|
||||
free_task = true;
|
||||
while (!task->is_complete() && !is_compilation_disabled_forever()) {
|
||||
task->lock()->wait();
|
||||
ml.wait();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -338,9 +338,9 @@ bool G1CMRootRegions::wait_until_scan_finished() {
|
||||
}
|
||||
|
||||
{
|
||||
MutexLocker x(RootRegionScan_lock, Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker ml(RootRegionScan_lock, Mutex::_no_safepoint_check_flag);
|
||||
while (scan_in_progress()) {
|
||||
RootRegionScan_lock->wait_without_safepoint_check();
|
||||
ml.wait();
|
||||
}
|
||||
}
|
||||
return true;
|
||||
|
@ -407,9 +407,9 @@ void G1ConcurrentMarkThread::sleep_before_next_cycle() {
|
||||
// below while the world is otherwise stopped.
|
||||
assert(!in_progress(), "should have been cleared");
|
||||
|
||||
MutexLocker x(CGC_lock, Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker ml(CGC_lock, Mutex::_no_safepoint_check_flag);
|
||||
while (!started() && !should_terminate()) {
|
||||
CGC_lock->wait_without_safepoint_check();
|
||||
ml.wait();
|
||||
}
|
||||
|
||||
if (started()) {
|
||||
|
@ -59,9 +59,9 @@ G1ConcurrentRefineThread::G1ConcurrentRefineThread(G1ConcurrentRefine* cr, uint
|
||||
}
|
||||
|
||||
void G1ConcurrentRefineThread::wait_for_completed_buffers() {
|
||||
MutexLocker x(_monitor, Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker ml(_monitor, Mutex::_no_safepoint_check_flag);
|
||||
while (!should_terminate() && !is_active()) {
|
||||
_monitor->wait_without_safepoint_check();
|
||||
ml.wait();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -61,7 +61,7 @@ void G1RootProcessor::wait_until_all_strong_classes_discovered() {
|
||||
if ((uint)_n_workers_discovered_strong_classes != n_workers()) {
|
||||
MonitorLocker ml(&_lock, Mutex::_no_safepoint_check_flag);
|
||||
while ((uint)_n_workers_discovered_strong_classes != n_workers()) {
|
||||
_lock.wait_without_safepoint_check(0);
|
||||
ml.wait(0);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -191,10 +191,10 @@ void VM_G1CollectForAllocation::doit_epilogue() {
|
||||
JavaThread* jt = (JavaThread*)thr;
|
||||
ThreadToNativeFromVM native(jt);
|
||||
|
||||
MutexLocker x(FullGCCount_lock, Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker ml(FullGCCount_lock, Mutex::_no_safepoint_check_flag);
|
||||
while (g1h->old_marking_cycles_completed() <=
|
||||
_old_marking_cycles_completed_before) {
|
||||
FullGCCount_lock->wait_without_safepoint_check();
|
||||
ml.wait();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -47,10 +47,10 @@ G1YoungRemSetSamplingThread::G1YoungRemSetSamplingThread() :
|
||||
}
|
||||
|
||||
void G1YoungRemSetSamplingThread::sleep_before_next_cycle() {
|
||||
MutexLocker x(&_monitor, Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker ml(&_monitor, Mutex::_no_safepoint_check_flag);
|
||||
if (!should_terminate()) {
|
||||
uintx waitms = G1ConcRefinementServiceIntervalMillis;
|
||||
_monitor.wait_without_safepoint_check(waitms);
|
||||
ml.wait(waitms);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -654,7 +654,7 @@ void GCTaskManager::add_list(GCTaskQueue* list) {
|
||||
GCTask* GCTaskManager::get_task(uint which) {
|
||||
GCTask* result = NULL;
|
||||
// Grab the queue lock.
|
||||
MutexLocker ml(monitor(), Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker ml(monitor(), Mutex::_no_safepoint_check_flag);
|
||||
// Wait while the queue is block or
|
||||
// there is nothing to do, except maybe release resources.
|
||||
while (is_blocked() ||
|
||||
@ -671,7 +671,7 @@ GCTask* GCTaskManager::get_task(uint which) {
|
||||
tty->print_cr(" => (%s)->wait()",
|
||||
monitor()->name());
|
||||
}
|
||||
monitor()->wait_without_safepoint_check(0);
|
||||
ml.wait(0);
|
||||
}
|
||||
// We've reacquired the queue lock here.
|
||||
// Figure out which condition caused us to exit the loop above.
|
||||
@ -872,15 +872,15 @@ void IdleGCTask::do_it(GCTaskManager* manager, uint which) {
|
||||
log_trace(gc, task)("[" INTPTR_FORMAT "] IdleGCTask:::do_it() should_wait: %s",
|
||||
p2i(this), wait_helper->should_wait() ? "true" : "false");
|
||||
|
||||
MutexLocker ml(manager->monitor(), Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker ml(manager->monitor(), Mutex::_no_safepoint_check_flag);
|
||||
log_trace(gc, task)("--- idle %d", which);
|
||||
// Increment has to be done when the idle tasks are created.
|
||||
// manager->increment_idle_workers();
|
||||
manager->monitor()->notify_all();
|
||||
ml.notify_all();
|
||||
while (wait_helper->should_wait()) {
|
||||
log_trace(gc, task)("[" INTPTR_FORMAT "] IdleGCTask::do_it() [" INTPTR_FORMAT "] (%s)->wait()",
|
||||
p2i(this), p2i(manager->monitor()), manager->monitor()->name());
|
||||
manager->monitor()->wait_without_safepoint_check(0);
|
||||
ml.wait(0);
|
||||
}
|
||||
manager->decrement_idle_workers();
|
||||
|
||||
@ -991,7 +991,7 @@ void WaitHelper::wait_for(bool reset) {
|
||||
}
|
||||
{
|
||||
// Grab the lock and check again.
|
||||
MutexLocker ml(monitor(), Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker ml(monitor(), Mutex::_no_safepoint_check_flag);
|
||||
while (should_wait()) {
|
||||
if (TraceGCTaskManager) {
|
||||
tty->print_cr("[" INTPTR_FORMAT "]"
|
||||
@ -999,7 +999,7 @@ void WaitHelper::wait_for(bool reset) {
|
||||
" [" INTPTR_FORMAT "] (%s)->wait()",
|
||||
p2i(this), p2i(monitor()), monitor()->name());
|
||||
}
|
||||
monitor()->wait_without_safepoint_check(0);
|
||||
ml.wait(0);
|
||||
}
|
||||
// Reset the flag in case someone reuses this task.
|
||||
if (reset) {
|
||||
|
@ -1,5 +1,5 @@
|
||||
/*
|
||||
* Copyright (c) 1997, 2017, Oracle and/or its affiliates. All rights reserved.
|
||||
* Copyright (c) 1997, 2019, Oracle and/or its affiliates. All rights reserved.
|
||||
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
|
||||
*
|
||||
* This code is free software; you can redistribute it and/or modify it
|
||||
@ -102,7 +102,7 @@ bool GCLocker::check_active_before_gc() {
|
||||
|
||||
void GCLocker::stall_until_clear() {
|
||||
assert(!JavaThread::current()->in_critical(), "Would deadlock");
|
||||
MutexLocker ml(JNICritical_lock);
|
||||
MonitorLocker ml(JNICritical_lock);
|
||||
|
||||
if (needs_gc()) {
|
||||
log_debug_jni("Allocation failed. Thread stalled by JNI critical section.");
|
||||
@ -110,20 +110,20 @@ void GCLocker::stall_until_clear() {
|
||||
|
||||
// Wait for _needs_gc to be cleared
|
||||
while (needs_gc()) {
|
||||
JNICritical_lock->wait();
|
||||
ml.wait();
|
||||
}
|
||||
}
|
||||
|
||||
void GCLocker::jni_lock(JavaThread* thread) {
|
||||
assert(!thread->in_critical(), "shouldn't currently be in a critical region");
|
||||
MutexLocker mu(JNICritical_lock);
|
||||
MonitorLocker ml(JNICritical_lock);
|
||||
// Block entering threads if we know at least one thread is in a
|
||||
// JNI critical region and we need a GC.
|
||||
// We check that at least one thread is in a critical region before
|
||||
// blocking because blocked threads are woken up by a thread exiting
|
||||
// a JNI critical region.
|
||||
while (is_active_and_needs_gc() || _doing_gc) {
|
||||
JNICritical_lock->wait();
|
||||
ml.wait();
|
||||
}
|
||||
thread->enter_critical();
|
||||
_jni_lock_count++;
|
||||
|
@ -200,7 +200,7 @@ class MutexGangTaskDispatcher : public GangTaskDispatcher {
|
||||
}
|
||||
|
||||
void coordinator_execute_on_workers(AbstractGangTask* task, uint num_workers) {
|
||||
MutexLocker ml(_monitor, Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker ml(_monitor, Mutex::_no_safepoint_check_flag);
|
||||
|
||||
_task = task;
|
||||
_num_workers = num_workers;
|
||||
@ -210,7 +210,7 @@ class MutexGangTaskDispatcher : public GangTaskDispatcher {
|
||||
|
||||
// Wait for them to finish.
|
||||
while (_finished < _num_workers) {
|
||||
_monitor->wait_without_safepoint_check();
|
||||
ml.wait();
|
||||
}
|
||||
|
||||
_task = NULL;
|
||||
@ -367,7 +367,7 @@ void WorkGangBarrierSync::set_n_workers(uint n_workers) {
|
||||
}
|
||||
|
||||
bool WorkGangBarrierSync::enter() {
|
||||
MutexLocker x(monitor(), Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker ml(monitor(), Mutex::_no_safepoint_check_flag);
|
||||
if (should_reset()) {
|
||||
// The should_reset() was set and we are the first worker to enter
|
||||
// the sync barrier. We will zero the n_completed() count which
|
||||
@ -387,10 +387,10 @@ bool WorkGangBarrierSync::enter() {
|
||||
// should_reset() flag and the barrier will be reset the first
|
||||
// time a worker enters it again.
|
||||
set_should_reset(true);
|
||||
monitor()->notify_all();
|
||||
ml.notify_all();
|
||||
} else {
|
||||
while (n_completed() != n_workers() && !aborted()) {
|
||||
monitor()->wait_without_safepoint_check();
|
||||
ml.wait();
|
||||
}
|
||||
}
|
||||
return !aborted();
|
||||
|
@ -395,9 +395,9 @@ void JfrThreadSampler::on_javathread_suspend(JavaThread* thread) {
|
||||
JfrThreadLocal* const tl = thread->jfr_thread_local();
|
||||
tl->set_trace_block();
|
||||
{
|
||||
MutexLocker ml(transition_block(), Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker ml(transition_block(), Mutex::_no_safepoint_check_flag);
|
||||
while (thread->is_trace_suspend()) {
|
||||
transition_block()->wait_without_safepoint_check();
|
||||
ml.wait();
|
||||
}
|
||||
tl->clear_trace_block();
|
||||
}
|
||||
|
@ -110,14 +110,14 @@ void JfrPostBox::asynchronous_post(int msg) {
|
||||
void JfrPostBox::synchronous_post(int msg) {
|
||||
assert(is_synchronous(msg), "invariant");
|
||||
assert(!JfrMsg_lock->owned_by_self(), "should not hold JfrMsg_lock here!");
|
||||
MutexLocker msg_lock(JfrMsg_lock);
|
||||
MonitorLocker msg_lock(JfrMsg_lock);
|
||||
deposit(msg);
|
||||
// serial_id is used to check when what we send in has been processed.
|
||||
// _msg_read_serial is read under JfrMsg_lock protection.
|
||||
const uintptr_t serial_id = OrderAccess::load_acquire(&_msg_read_serial) + 1;
|
||||
JfrMsg_lock->notify_all();
|
||||
msg_lock.notify_all();
|
||||
while (!is_message_processed(serial_id)) {
|
||||
JfrMsg_lock->wait();
|
||||
msg_lock.wait();
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -90,14 +90,14 @@ static inline InstanceKlass* get_ik(jclass def) {
|
||||
// If any of the classes are being redefined, wait
|
||||
// Parallel constant pool merging leads to indeterminate constant pools.
|
||||
void VM_RedefineClasses::lock_classes() {
|
||||
MutexLocker ml(RedefineClasses_lock);
|
||||
MonitorLocker ml(RedefineClasses_lock);
|
||||
bool has_redefined;
|
||||
do {
|
||||
has_redefined = false;
|
||||
// Go through classes each time until none are being redefined.
|
||||
for (int i = 0; i < _class_count; i++) {
|
||||
if (get_ik(_class_defs[i].klass)->is_being_redefined()) {
|
||||
RedefineClasses_lock->wait();
|
||||
ml.wait();
|
||||
has_redefined = true;
|
||||
break; // for loop
|
||||
}
|
||||
@ -106,17 +106,17 @@ void VM_RedefineClasses::lock_classes() {
|
||||
for (int i = 0; i < _class_count; i++) {
|
||||
get_ik(_class_defs[i].klass)->set_is_being_redefined(true);
|
||||
}
|
||||
RedefineClasses_lock->notify_all();
|
||||
ml.notify_all();
|
||||
}
|
||||
|
||||
void VM_RedefineClasses::unlock_classes() {
|
||||
MutexLocker ml(RedefineClasses_lock);
|
||||
MonitorLocker ml(RedefineClasses_lock);
|
||||
for (int i = 0; i < _class_count; i++) {
|
||||
assert(get_ik(_class_defs[i].klass)->is_being_redefined(),
|
||||
"should be being redefined to get here");
|
||||
get_ik(_class_defs[i].klass)->set_is_being_redefined(false);
|
||||
}
|
||||
RedefineClasses_lock->notify_all();
|
||||
ml.notify_all();
|
||||
}
|
||||
|
||||
bool VM_RedefineClasses::doit_prologue() {
|
||||
|
@ -419,14 +419,14 @@ void before_exit(JavaThread* thread) {
|
||||
// A CAS or OSMutex would work just fine but then we need to manipulate
|
||||
// thread state for Safepoint. Here we use Monitor wait() and notify_all()
|
||||
// for synchronization.
|
||||
{ MutexLocker ml(BeforeExit_lock);
|
||||
{ MonitorLocker ml(BeforeExit_lock);
|
||||
switch (_before_exit_status) {
|
||||
case BEFORE_EXIT_NOT_RUN:
|
||||
_before_exit_status = BEFORE_EXIT_RUNNING;
|
||||
break;
|
||||
case BEFORE_EXIT_RUNNING:
|
||||
while (_before_exit_status == BEFORE_EXIT_RUNNING) {
|
||||
BeforeExit_lock->wait();
|
||||
ml.wait();
|
||||
}
|
||||
assert(_before_exit_status == BEFORE_EXIT_DONE, "invalid state");
|
||||
return;
|
||||
|
@ -216,9 +216,7 @@ void mutex_init() {
|
||||
def(ResolvedMethodTableWeakAlloc_lock , PaddedMutex , vmweak, true, Monitor::_safepoint_check_never);
|
||||
def(ResolvedMethodTableWeakActive_lock , PaddedMutex , vmweak-1, true, Monitor::_safepoint_check_never);
|
||||
|
||||
if (UseConcMarkSweepGC || UseG1GC) {
|
||||
def(FullGCCount_lock , PaddedMonitor, leaf, true, Monitor::_safepoint_check_never); // in support of ExplicitGCInvokesConcurrent
|
||||
}
|
||||
def(FullGCCount_lock , PaddedMonitor, leaf, true, Monitor::_safepoint_check_never); // in support of ExplicitGCInvokesConcurrent
|
||||
if (UseG1GC) {
|
||||
def(SATB_Q_CBL_mon , PaddedMonitor, access, true, Monitor::_safepoint_check_never);
|
||||
|
||||
|
@ -229,6 +229,7 @@ class MutexLocker: public StackObj {
|
||||
|
||||
// A MonitorLocker is like a MutexLocker above, except it allows
|
||||
// wait/notify as well which are delegated to the underlying Monitor.
|
||||
// It also disallows NULL.
|
||||
|
||||
class MonitorLocker: public MutexLocker {
|
||||
Mutex::SafepointCheckFlag _flag;
|
||||
@ -236,35 +237,31 @@ class MonitorLocker: public MutexLocker {
|
||||
MonitorLocker(Monitor* monitor, Mutex::SafepointCheckFlag flag = Mutex::_safepoint_check_flag) :
|
||||
MutexLocker(monitor, flag), _flag(flag) {
|
||||
// Superclass constructor did locking
|
||||
assert(_mutex != NULL, "NULL monitor not allowed");
|
||||
}
|
||||
|
||||
MonitorLocker(Monitor* monitor, Thread* thread, Mutex::SafepointCheckFlag flag = Mutex::_safepoint_check_flag) :
|
||||
MutexLocker(monitor, thread, flag), _flag(flag) {
|
||||
// Superclass constructor did locking
|
||||
assert(_mutex != NULL, "NULL monitor not allowed");
|
||||
}
|
||||
|
||||
bool wait(long timeout = 0,
|
||||
bool as_suspend_equivalent = !Mutex::_as_suspend_equivalent_flag) {
|
||||
if (_mutex != NULL) {
|
||||
if (_flag == Mutex::_safepoint_check_flag) {
|
||||
return _mutex->wait(timeout, as_suspend_equivalent);
|
||||
} else {
|
||||
return _mutex->wait_without_safepoint_check(timeout);
|
||||
}
|
||||
if (_flag == Mutex::_safepoint_check_flag) {
|
||||
return _mutex->wait(timeout, as_suspend_equivalent);
|
||||
} else {
|
||||
return _mutex->wait_without_safepoint_check(timeout);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void notify_all() {
|
||||
if (_mutex != NULL) {
|
||||
_mutex->notify_all();
|
||||
}
|
||||
_mutex->notify_all();
|
||||
}
|
||||
|
||||
void notify() {
|
||||
if (_mutex != NULL) {
|
||||
_mutex->notify();
|
||||
}
|
||||
_mutex->notify();
|
||||
}
|
||||
};
|
||||
|
||||
|
@ -341,9 +341,9 @@ void NMethodSweeper::sweeper_loop() {
|
||||
while (true) {
|
||||
{
|
||||
ThreadBlockInVM tbivm(JavaThread::current());
|
||||
MutexLocker waiter(CodeCache_lock, Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker waiter(CodeCache_lock, Mutex::_no_safepoint_check_flag);
|
||||
const long wait_time = 60*60*24 * 1000;
|
||||
timeout = CodeCache_lock->wait_without_safepoint_check(wait_time);
|
||||
timeout = waiter.wait(wait_time);
|
||||
}
|
||||
if (!timeout) {
|
||||
possibly_sweep();
|
||||
@ -369,7 +369,7 @@ void NMethodSweeper::notify(int code_blob_type) {
|
||||
*/
|
||||
void NMethodSweeper::force_sweep() {
|
||||
ThreadBlockInVM tbivm(JavaThread::current());
|
||||
MutexLocker waiter(CodeCache_lock, Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker waiter(CodeCache_lock, Mutex::_no_safepoint_check_flag);
|
||||
// Request forced sweep
|
||||
_force_sweep = true;
|
||||
while (_force_sweep) {
|
||||
@ -377,7 +377,7 @@ void NMethodSweeper::force_sweep() {
|
||||
// In case a sweep currently takes place we timeout and try again because
|
||||
// we want to enforce a full sweep.
|
||||
CodeCache_lock->notify();
|
||||
CodeCache_lock->wait_without_safepoint_check(1000);
|
||||
waiter.wait(1000);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -794,14 +794,12 @@ bool JavaThread::wait_for_ext_suspend_completion(int retries, int delay,
|
||||
// safepoint requests from the VMThread
|
||||
|
||||
{
|
||||
MutexLocker ml(SR_lock());
|
||||
Thread* t = Thread::current();
|
||||
MonitorLocker ml(SR_lock(),
|
||||
t->is_Java_thread() ? Mutex::_safepoint_check_flag : Mutex::_no_safepoint_check_flag);
|
||||
// wait with safepoint check (if we're a JavaThread - the WatcherThread
|
||||
// can also call this) and increase delay with each retry
|
||||
if (Thread::current()->is_Java_thread()) {
|
||||
SR_lock()->wait(i * delay);
|
||||
} else {
|
||||
SR_lock()->wait_without_safepoint_check(i * delay);
|
||||
}
|
||||
ml.wait(i * delay);
|
||||
|
||||
is_suspended = is_ext_suspend_completed(true /* called_by_wait */,
|
||||
delay, bits);
|
||||
@ -1405,7 +1403,7 @@ WatcherThread::WatcherThread() : NonJavaThread() {
|
||||
int WatcherThread::sleep() const {
|
||||
// The WatcherThread does not participate in the safepoint protocol
|
||||
// for the PeriodicTask_lock because it is not a JavaThread.
|
||||
MutexLocker ml(PeriodicTask_lock, Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker ml(PeriodicTask_lock, Mutex::_no_safepoint_check_flag);
|
||||
|
||||
if (_should_terminate) {
|
||||
// check for termination before we do any housekeeping or wait
|
||||
@ -1425,7 +1423,7 @@ int WatcherThread::sleep() const {
|
||||
jlong time_before_loop = os::javaTimeNanos();
|
||||
|
||||
while (true) {
|
||||
bool timedout = PeriodicTask_lock->wait_without_safepoint_check(remaining);
|
||||
bool timedout = ml.wait(remaining);
|
||||
jlong now = os::javaTimeNanos();
|
||||
|
||||
if (remaining == 0) {
|
||||
@ -1548,12 +1546,12 @@ void WatcherThread::stop() {
|
||||
}
|
||||
}
|
||||
|
||||
MutexLocker mu(Terminator_lock);
|
||||
MonitorLocker mu(Terminator_lock);
|
||||
|
||||
while (watcher_thread() != NULL) {
|
||||
// This wait should make safepoint checks, wait without a timeout,
|
||||
// and wait as a suspend-equivalent condition.
|
||||
Terminator_lock->wait(0, Mutex::_as_suspend_equivalent_flag);
|
||||
mu.wait(0, Mutex::_as_suspend_equivalent_flag);
|
||||
}
|
||||
}
|
||||
|
||||
@ -2424,7 +2422,7 @@ int JavaThread::java_suspend_self() {
|
||||
(is_Java_thread() && !((JavaThread*)this)->has_last_Java_frame()),
|
||||
"must have walkable stack");
|
||||
|
||||
MutexLocker ml(SR_lock(), Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker ml(SR_lock(), Mutex::_no_safepoint_check_flag);
|
||||
|
||||
assert(!this->is_ext_suspended(),
|
||||
"a thread trying to self-suspend should not already be suspended");
|
||||
@ -2452,7 +2450,7 @@ int JavaThread::java_suspend_self() {
|
||||
|
||||
// _ext_suspended flag is cleared by java_resume()
|
||||
while (is_ext_suspended()) {
|
||||
this->SR_lock()->wait_without_safepoint_check();
|
||||
ml.wait();
|
||||
}
|
||||
}
|
||||
return ret;
|
||||
@ -3844,10 +3842,10 @@ jint Threads::create_vm(JavaVMInitArgs* args, bool* canTryAgain) {
|
||||
// Wait for the VM thread to become ready, and VMThread::run to initialize
|
||||
// Monitors can have spurious returns, must always check another state flag
|
||||
{
|
||||
MutexLocker ml(Notify_lock);
|
||||
MonitorLocker ml(Notify_lock);
|
||||
os::start_thread(vmthread);
|
||||
while (vmthread->active_handles() == NULL) {
|
||||
Notify_lock->wait();
|
||||
ml.wait();
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -4325,11 +4323,11 @@ bool Threads::destroy_vm() {
|
||||
_vm_complete = false;
|
||||
#endif
|
||||
// Wait until we are the last non-daemon thread to execute
|
||||
{ MutexLocker nu(Threads_lock);
|
||||
{ MonitorLocker nu(Threads_lock);
|
||||
while (Threads::number_of_non_daemon_threads() > 1)
|
||||
// This wait should make safepoint checks, wait without a timeout,
|
||||
// and wait as a suspend-equivalent condition.
|
||||
Threads_lock->wait(0, Mutex::_as_suspend_equivalent_flag);
|
||||
nu.wait(0, Mutex::_as_suspend_equivalent_flag);
|
||||
}
|
||||
|
||||
EventShutdown e;
|
||||
@ -4465,7 +4463,7 @@ void Threads::remove(JavaThread* p, bool is_daemon) {
|
||||
|
||||
// Extra scope needed for Thread_lock, so we can check
|
||||
// that we do not remove thread without safepoint code notice
|
||||
{ MutexLocker ml(Threads_lock);
|
||||
{ MonitorLocker ml(Threads_lock);
|
||||
|
||||
assert(ThreadsSMRSupport::get_java_thread_list()->includes(p), "p must be present");
|
||||
|
||||
@ -4493,7 +4491,7 @@ void Threads::remove(JavaThread* p, bool is_daemon) {
|
||||
// Only one thread left, do a notify on the Threads_lock so a thread waiting
|
||||
// on destroy_vm will wake up.
|
||||
if (number_of_non_daemon_threads() == 1) {
|
||||
Threads_lock->notify_all();
|
||||
ml.notify_all();
|
||||
}
|
||||
}
|
||||
ThreadService::remove_thread(p, is_daemon);
|
||||
|
@ -450,8 +450,8 @@ int VM_Exit::wait_for_threads_in_native_to_block() {
|
||||
|
||||
attempts++;
|
||||
|
||||
MutexLocker ml(&timer, Mutex::_no_safepoint_check_flag);
|
||||
timer.wait_without_safepoint_check(10);
|
||||
MonitorLocker ml(&timer, Mutex::_no_safepoint_check_flag);
|
||||
ml.wait(10);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -342,9 +342,9 @@ void VMThread::run() {
|
||||
// but before it actually drops the lock and waits, the notification below
|
||||
// may get lost and we will have a hang. To avoid this, we need to use
|
||||
// Mutex::lock_without_safepoint_check().
|
||||
MutexLocker ml(_terminate_lock, Mutex::_no_safepoint_check_flag);
|
||||
MonitorLocker ml(_terminate_lock, Mutex::_no_safepoint_check_flag);
|
||||
_terminated = true;
|
||||
_terminate_lock->notify();
|
||||
ml.notify();
|
||||
}
|
||||
|
||||
// We are now racing with the VM termination being carried out in
|
||||
@ -373,9 +373,9 @@ void VMThread::wait_for_vm_thread_exit() {
|
||||
// Note: it should be OK to use Terminator_lock here. But this is called
|
||||
// at a very delicate time (VM shutdown) and we are operating in non- VM
|
||||
// thread at Safepoint. It's safer to not share lock with other threads.
|
||||
{ MutexLocker ml(_terminate_lock, Mutex::_no_safepoint_check_flag);
|
||||
{ MonitorLocker ml(_terminate_lock, Mutex::_no_safepoint_check_flag);
|
||||
while(!VMThread::is_terminated()) {
|
||||
_terminate_lock->wait_without_safepoint_check();
|
||||
ml.wait();
|
||||
}
|
||||
}
|
||||
}
|
||||
@ -476,8 +476,8 @@ void VMThread::loop() {
|
||||
// Wait for VM operation
|
||||
//
|
||||
// use no_safepoint_check to get lock without attempting to "sneak"
|
||||
{ MutexLocker mu_queue(VMOperationQueue_lock,
|
||||
Mutex::_no_safepoint_check_flag);
|
||||
{ MonitorLocker mu_queue(VMOperationQueue_lock,
|
||||
Mutex::_no_safepoint_check_flag);
|
||||
|
||||
// Look for new operation
|
||||
assert(_cur_vm_operation == NULL, "no current one should be executing");
|
||||
@ -494,7 +494,7 @@ void VMThread::loop() {
|
||||
while (!should_terminate() && _cur_vm_operation == NULL) {
|
||||
// wait with a timeout to guarantee safepoints at regular intervals
|
||||
bool timedout =
|
||||
VMOperationQueue_lock->wait_without_safepoint_check(GuaranteedSafepointInterval);
|
||||
mu_queue.wait(GuaranteedSafepointInterval);
|
||||
|
||||
// Support for self destruction
|
||||
if ((SelfDestructTimer != 0) && !VMError::is_error_reported() &&
|
||||
@ -718,13 +718,10 @@ void VMThread::execute(VM_Operation* op) {
|
||||
if (!concurrent) {
|
||||
// Wait for completion of request (non-concurrent)
|
||||
// Note: only a JavaThread triggers the safepoint check when locking
|
||||
MutexLocker mu(VMOperationRequest_lock);
|
||||
MonitorLocker ml(VMOperationRequest_lock,
|
||||
t->is_Java_thread() ? Mutex::_safepoint_check_flag : Mutex::_no_safepoint_check_flag);
|
||||
while(t->vm_operation_completed_count() < ticket) {
|
||||
if (t->is_Java_thread()) {
|
||||
VMOperationRequest_lock->wait();
|
||||
} else {
|
||||
VMOperationRequest_lock->wait_without_safepoint_check();
|
||||
}
|
||||
ml.wait();
|
||||
}
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user