8247280: more fencing needed in async deflation for non-TSO machines

Reviewed-by: dholmes, pchilanomate
This commit is contained in:
Daniel D. Daugherty 2020-07-15 16:59:39 -04:00
parent d7c1bb1fb7
commit 62d77dc3fc
3 changed files with 19 additions and 2 deletions

View File

@ -27,6 +27,7 @@
#include "memory/allocation.hpp"
#include "memory/padded.hpp"
#include "metaprogramming/isRegisteredEnum.hpp"
#include "oops/markWord.hpp"
#include "runtime/os.hpp"
#include "runtime/park.hpp"
@ -330,8 +331,10 @@ class ObjectMonitor {
void* object() const;
void* object_addr();
void set_object(void* obj);
void release_set_allocation_state(AllocationState s);
void set_allocation_state(AllocationState s);
AllocationState allocation_state() const;
AllocationState allocation_state_acquire() const;
bool is_free() const;
bool is_old() const;
bool is_new() const;
@ -374,6 +377,9 @@ class ObjectMonitor {
void install_displaced_markword_in_object(const oop obj);
};
// Register for atomic operations.
template<> struct IsRegisteredEnum<ObjectMonitor::AllocationState> : public TrueType {};
// Macro to use guarantee() for more strict AsyncDeflateIdleMonitors
// checks and assert() otherwise.
#define ADIM_guarantee(p, ...) \

View File

@ -191,6 +191,10 @@ inline void* ObjectMonitor::try_set_owner_from(void* old_value, void* new_value)
return prev;
}
inline void ObjectMonitor::release_set_allocation_state(ObjectMonitor::AllocationState s) {
Atomic::release_store(&_allocation_state, s);
}
inline void ObjectMonitor::set_allocation_state(ObjectMonitor::AllocationState s) {
_allocation_state = s;
}
@ -199,12 +203,16 @@ inline ObjectMonitor::AllocationState ObjectMonitor::allocation_state() const {
return _allocation_state;
}
inline ObjectMonitor::AllocationState ObjectMonitor::allocation_state_acquire() const {
return Atomic::load_acquire(&_allocation_state);
}
inline bool ObjectMonitor::is_free() const {
return _allocation_state == Free;
}
inline bool ObjectMonitor::is_old() const {
return _allocation_state == Old;
return allocation_state_acquire() == Old;
}
inline bool ObjectMonitor::is_new() const {

View File

@ -1908,7 +1908,8 @@ ObjectMonitor* ObjectSynchronizer::inflate(Thread* self, oop object,
// Once ObjectMonitor is configured and the object is associated
// with the ObjectMonitor, it is safe to allow async deflation:
assert(m->is_new(), "freshly allocated monitor must be new");
m->set_allocation_state(ObjectMonitor::Old);
// Release semantics needed to keep allocation_state from floating up.
m->release_set_allocation_state(ObjectMonitor::Old);
// Hopefully the performance counters are allocated on distinct cache lines
// to avoid false sharing on MP systems ...
@ -1965,6 +1966,8 @@ ObjectMonitor* ObjectSynchronizer::inflate(Thread* self, oop object,
// Once the ObjectMonitor is configured and object is associated
// with the ObjectMonitor, it is safe to allow async deflation:
assert(m->is_new(), "freshly allocated monitor must be new");
// Release semantics are not needed to keep allocation_state from
// floating up since cas_set_mark() takes care of it.
m->set_allocation_state(ObjectMonitor::Old);
// Hopefully the performance counters are allocated on distinct