--- old/src/hotspot/share/runtime/objectMonitor.inline.hpp 2019-10-17 17:31:42.000000000 -0400 +++ new/src/hotspot/share/runtime/objectMonitor.inline.hpp 2019-10-17 17:31:42.000000000 -0400 @@ -25,6 +25,7 @@ #ifndef SHARE_RUNTIME_OBJECTMONITOR_INLINE_HPP #define SHARE_RUNTIME_OBJECTMONITOR_INLINE_HPP +#include "logging/log.hpp" #include "runtime/atomic.hpp" inline intptr_t ObjectMonitor::is_entered(TRAPS) const { @@ -118,8 +119,56 @@ return _contentions; } -inline void ObjectMonitor::set_owner(void* owner) { - _owner = owner; +// Set _owner field to new_value; current value must match old_value. +inline void ObjectMonitor::set_owner_from(void* new_value, void* old_value) { + void* prev = Atomic::cmpxchg(new_value, &_owner, old_value); + ADIM_guarantee(prev == old_value, "unexpected prev owner=" INTPTR_FORMAT + ", expected=" INTPTR_FORMAT, p2i(prev), p2i(old_value)); + log_trace(monitorinflation, owner)("mid=" INTPTR_FORMAT ", prev=" + INTPTR_FORMAT ", new=" INTPTR_FORMAT, + p2i(this), p2i(prev), p2i(new_value)); +} + +// Set _owner field to new_value; current value must match old_value1 or old_value2. +inline void ObjectMonitor::set_owner_from(void* new_value, void* old_value1, void* old_value2) { + void* prev = Atomic::cmpxchg(new_value, &_owner, old_value1); + if (prev != old_value1) { + prev = Atomic::cmpxchg(new_value, &_owner, old_value2); + } + ADIM_guarantee(prev == old_value1 || prev == old_value2, + "unexpected prev owner=" INTPTR_FORMAT ", expected1=" + INTPTR_FORMAT " or expected2=" INTPTR_FORMAT, p2i(prev), + p2i(old_value1), p2i(old_value2)); + log_trace(monitorinflation, owner)("mid=" INTPTR_FORMAT ", prev=" + INTPTR_FORMAT ", new=" INTPTR_FORMAT, + p2i(this), p2i(prev), p2i(new_value)); +} + +// Set _owner field to self; current value must match basic_lock_p. +inline void ObjectMonitor::set_owner_from_BasicLock(Thread* self, void* basic_lock_p) { + assert(self->is_lock_owned((address)basic_lock_p), "self=" INTPTR_FORMAT + " must own basic_lock_p=" INTPTR_FORMAT, p2i(self), p2i(basic_lock_p)); + void* prev = _owner; + ADIM_guarantee(prev == basic_lock_p, "unexpected prev owner=" INTPTR_FORMAT + ", expected=" INTPTR_FORMAT, p2i(prev), p2i(basic_lock_p)); + // Non-null owner field to non-null owner field is safe without + // cmpxchg() as long as all readers can tolerate either flavor. + _owner = self; + log_trace(monitorinflation, owner)("mid=" INTPTR_FORMAT ", prev=" + INTPTR_FORMAT ", new=" INTPTR_FORMAT, + p2i(this), p2i(prev), p2i(self)); +} + +// Try to set _owner field to new_value if the current value matches +// old_value. Otherwise, does not change the _owner field. +inline void* ObjectMonitor::try_set_owner_from(void* new_value, void* old_value) { + void* prev = Atomic::cmpxchg(new_value, &_owner, old_value); + if (prev == old_value) { + log_trace(monitorinflation, owner)("mid=" INTPTR_FORMAT ", prev=" + INTPTR_FORMAT ", new=" INTPTR_FORMAT, + p2i(this), p2i(prev), p2i(new_value)); + } + return prev; } inline void ObjectMonitor::set_allocation_state(ObjectMonitor::AllocationState s) {