< prev index next > src/hotspot/share/runtime/synchronizer.cpp
Print this page
}
// -----------------------------------------------------------------------------
// Internal VM locks on java objects
// standard constructor, allows locking failures
- ObjectLocker::ObjectLocker(Handle obj, JavaThread* thread) : _npm(thread) {
- _thread = thread;
+ ObjectLocker::ObjectLocker(Handle obj, TRAPS) : _thread(THREAD), _obj(obj),
+ _npm(_thread, _thread->at_preemptable_init() /* ignore_mark */), _skip_exit(false) {
+ assert(!_thread->preempting(), "");
+
_thread->check_for_valid_safepoint_state();
- _obj = obj;
if (_obj() != nullptr) {
ObjectSynchronizer::enter(_obj, &_lock, _thread);
+
+ if (_thread->preempting()) {
+ // If preemption was cancelled we acquired the monitor after freezing
+ // the frames. Redoing the vm call laterĀ in thaw will require us to
+ // release it since the call should look like the original one. We
+ // do it in ~ObjectLocker to reduce the window of time we hold the
+ // monitor since we can't do anything useful with it now, and would
+ // otherwise just force other vthreads to preempt in case they try
+ // to acquire this monitor.
+ _skip_exit = !_thread->preemption_cancelled();
+ _thread->set_pending_preempted_exception();
+ }
}
}
ObjectLocker::~ObjectLocker() {
- if (_obj() != nullptr) {
+ if (_obj() != nullptr && !_skip_exit) {
ObjectSynchronizer::exit(_obj(), &_lock, _thread);
}
}
+ void ObjectLocker::wait_uninterruptibly(TRAPS) {
+ ObjectSynchronizer::waitUninterruptibly(_obj, 0, _thread);
+ if (_thread->preempting()) {
+ _skip_exit = true;
+ _thread->set_pending_preempted_exception();
+ _thread->set_class_to_be_initialized(nullptr);
+ }
+ }
// -----------------------------------------------------------------------------
// Wait/Notify/NotifyAll
// NOTE: must use heavy weight monitor to handle wait()
int ret_code = dtrace_waited_probe(monitor, obj, THREAD);
return ret_code;
}
void ObjectSynchronizer::waitUninterruptibly(Handle obj, jlong millis, TRAPS) {
- if (millis < 0) {
- THROW_MSG(vmSymbols::java_lang_IllegalArgumentException(), "timeout value is negative");
- }
+ assert(millis >= 0, "timeout value is negative");
ObjectMonitor* monitor;
if (LockingMode == LM_LIGHTWEIGHT) {
monitor = LightweightSynchronizer::inflate_locked_or_imse(obj(), inflate_cause_wait, CHECK);
} else {
< prev index next >