Skip to content

Commit 66f8987

Browse files
committed
8265298: Hard VM crash when deadlock between "access" and higher ranked lock is detected
Reviewed-by: pchilanomate, dholmes
1 parent 926e3bc commit 66f8987

File tree

2 files changed

+68
-1
lines changed

2 files changed

+68
-1
lines changed

src/hotspot/share/runtime/mutex.cpp

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -412,7 +412,12 @@ void Mutex::check_rank(Thread* thread) {
412412
// to acquire, then deadlock prevention rules require that the rank
413413
// of m2 be less than the rank of m1. This prevents circular waits.
414414
if (least != NULL && least->rank() <= this->rank()) {
415-
thread->print_owned_locks();
415+
if (least->rank() > Mutex::tty) {
416+
// Printing owned locks acquires tty lock. If the least rank was below or equal
417+
// tty, then deadlock detection code would circle back here, until we run
418+
// out of stack and crash hard. Print locks only when it is safe.
419+
thread->print_owned_locks();
420+
}
416421
assert(false, "Attempting to acquire lock %s/%d out of order with lock %s/%d -- "
417422
"possible deadlock", this->name(), this->rank(), least->name(), least->rank());
418423
}

test/hotspot/gtest/runtime/test_mutex_rank.cpp

Lines changed: 62 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -104,6 +104,36 @@ TEST_VM_ASSERT_MSG(MutexRank, mutex_trylock_rank_out_of_orderB,
104104
mutex_rankA->unlock();
105105
}
106106

107+
TEST_VM_ASSERT_MSG(MutexRank, mutex_lock_access_leaf,
108+
".* Attempting to acquire lock mutex_rank_leaf/11 out of order with lock mutex_rank_access/1 "
109+
"-- possible deadlock") {
110+
JavaThread* THREAD = JavaThread::current();
111+
ThreadInVMfromNative invm(THREAD);
112+
113+
Mutex* mutex_rank_access = new Mutex(Mutex::access, "mutex_rank_access", false, Mutex::_safepoint_check_never);
114+
Mutex* mutex_rank_leaf = new Mutex(Mutex::leaf, "mutex_rank_leaf", false, Mutex::_safepoint_check_never);
115+
116+
mutex_rank_access->lock_without_safepoint_check();
117+
mutex_rank_leaf->lock_without_safepoint_check();
118+
mutex_rank_leaf->unlock();
119+
mutex_rank_access->unlock();
120+
}
121+
122+
TEST_VM_ASSERT_MSG(MutexRank, mutex_lock_tty_special,
123+
".* Attempting to acquire lock mutex_rank_special/6 out of order with lock mutex_rank_tty/3 "
124+
"-- possible deadlock") {
125+
JavaThread* THREAD = JavaThread::current();
126+
ThreadInVMfromNative invm(THREAD);
127+
128+
Mutex* mutex_rank_tty = new Mutex(Mutex::tty, "mutex_rank_tty", false, Mutex::_safepoint_check_never);
129+
Mutex* mutex_rank_special = new Mutex(Mutex::special, "mutex_rank_special", false, Mutex::_safepoint_check_never);
130+
131+
mutex_rank_tty->lock_without_safepoint_check();
132+
mutex_rank_special->lock_without_safepoint_check();
133+
mutex_rank_special->unlock();
134+
mutex_rank_tty->unlock();
135+
}
136+
107137
TEST_OTHER_VM(MutexRank, monitor_wait_rank_in_order) {
108138
JavaThread* THREAD = JavaThread::current();
109139
ThreadInVMfromNative invm(THREAD);
@@ -165,4 +195,36 @@ TEST_VM_ASSERT_MSG(MutexRank, monitor_wait_rank_special,
165195
monitor_rank_special_minus_one->unlock();
166196
monitor_rank_special->unlock();
167197
}
198+
199+
TEST_VM_ASSERT_MSG(MutexRank, monitor_wait_access_leaf,
200+
".* Attempting to wait on monitor monitor_rank_access/1 while holding lock monitor_rank_tty/3 "
201+
"-- possible deadlock. Should not block\\(wait\\) while holding a lock of rank special.") {
202+
JavaThread* THREAD = JavaThread::current();
203+
ThreadInVMfromNative invm(THREAD);
204+
205+
Monitor* monitor_rank_tty = new Monitor(Mutex::tty, "monitor_rank_tty", false, Mutex::_safepoint_check_never);
206+
Monitor* monitor_rank_access = new Monitor(Mutex::access, "monitor_rank_access", false, Mutex::_safepoint_check_never);
207+
208+
monitor_rank_tty->lock_without_safepoint_check();
209+
monitor_rank_access->lock_without_safepoint_check();
210+
monitor_rank_access->wait_without_safepoint_check(1);
211+
monitor_rank_access->unlock();
212+
monitor_rank_tty->unlock();
213+
}
214+
215+
TEST_VM_ASSERT_MSG(MutexRank, monitor_wait_tty_special,
216+
".* Attempting to wait on monitor monitor_rank_tty/3 while holding lock monitor_rank_special/6 "
217+
"-- possible deadlock. Should not block\\(wait\\) while holding a lock of rank special.") {
218+
JavaThread* THREAD = JavaThread::current();
219+
ThreadInVMfromNative invm(THREAD);
220+
221+
Monitor* monitor_rank_special = new Monitor(Mutex::special, "monitor_rank_special", false, Mutex::_safepoint_check_never);
222+
Monitor* monitor_rank_tty = new Monitor(Mutex::tty, "monitor_rank_tty", false, Mutex::_safepoint_check_never);
223+
224+
monitor_rank_special->lock_without_safepoint_check();
225+
monitor_rank_tty->lock_without_safepoint_check();
226+
monitor_rank_tty->wait_without_safepoint_check(1);
227+
monitor_rank_tty->unlock();
228+
monitor_rank_special->unlock();
229+
}
168230
#endif // ASSERT

0 commit comments

Comments
 (0)