Skip to content
Permalink
Browse files

8235324: Dying objects are published from users of CollectedHeap::obj…

…ect_iterate

Reviewed-by: pliden, eosterlund, sjohanss, rkennke
  • Loading branch information
stefank committed Dec 4, 2019
1 parent dc0cc55 commit 5b155f05e75efb18444fcc990a73625c75be3183
@@ -2348,6 +2348,10 @@ void G1CollectedHeap::object_iterate(ObjectClosure* cl) {
heap_region_iterate(&blk);
}

void G1CollectedHeap::keep_alive(oop obj) {
G1BarrierSet::enqueue(obj);
}

void G1CollectedHeap::heap_region_iterate(HeapRegionClosure* cl) const {
_hrm->iterate(cl);
}
@@ -1170,6 +1170,9 @@ class G1CollectedHeap : public CollectedHeap {
// Iterate over all objects, calling "cl.do_object" on each.
virtual void object_iterate(ObjectClosure* cl);

// Keep alive an object that was loaded with AS_NO_KEEPALIVE.
virtual void keep_alive(oop obj);

// Iterate over heap regions, in address order, terminating the
// iteration early if the "do_heap_region" method returns "true".
void heap_region_iterate(HeapRegionClosure* blk) const;
@@ -387,6 +387,9 @@ class CollectedHeap : public CHeapObj<mtInternal> {
// Iterate over all objects, calling "cl.do_object" on each.
virtual void object_iterate(ObjectClosure* cl) = 0;

// Keep alive an object that was loaded with AS_NO_KEEPALIVE.
virtual void keep_alive(oop obj) {}

// Returns the longest time (in ms) that has elapsed since the last
// time that any part of the heap was examined by a garbage collection.
virtual jlong millis_since_last_gc() = 0;
@@ -1327,6 +1327,11 @@ void ShenandoahHeap::object_iterate(ObjectClosure* cl) {
}
}

// Keep alive an object that was loaded with AS_NO_KEEPALIVE.
void ShenandoahHeap::keep_alive(oop obj) {
ShenandoahBarrierSet::barrier_set()->enqueue(obj);
}

void ShenandoahHeap::heap_region_iterate(ShenandoahHeapRegionClosure* blk) const {
for (size_t i = 0; i < num_regions(); i++) {
ShenandoahHeapRegion* current = get_region(i);
@@ -560,6 +560,9 @@ class ShenandoahHeap : public CollectedHeap {
// Used for native heap walkers: heap dumpers, mostly
void object_iterate(ObjectClosure* cl);

// Keep alive an object that was loaded with AS_NO_KEEPALIVE.
void keep_alive(oop obj);

// Used by RMI
jlong millis_since_last_gc();

@@ -31,14 +31,6 @@
#include "runtime/safepoint.hpp"
#include "utilities/debug.hpp"

bool ZBarrier::during_mark() {
return ZGlobalPhase == ZPhaseMark;
}

bool ZBarrier::during_relocate() {
return ZGlobalPhase == ZPhaseRelocate;
}

template <bool finalizable>
bool ZBarrier::should_mark_through(uintptr_t addr) {
// Finalizable marked oops can still exists on the heap after marking
@@ -105,6 +105,7 @@ class ZBarrier : public AllStatic {
static void keep_alive_barrier_on_weak_oop_field(volatile oop* p);
static void keep_alive_barrier_on_phantom_oop_field(volatile oop* p);
static void keep_alive_barrier_on_phantom_root_oop_field(oop* p);
static void keep_alive_barrier_on_oop(oop o);

// Mark barrier
static void mark_barrier_on_oop_field(volatile oop* p, bool finalizable);
@@ -144,6 +144,14 @@ inline bool ZBarrier::is_weak_good_or_null_fast_path(uintptr_t addr) {
return ZAddress::is_weak_good_or_null(addr);
}

inline bool ZBarrier::during_mark() {
return ZGlobalPhase == ZPhaseMark;
}

inline bool ZBarrier::during_relocate() {
return ZGlobalPhase == ZPhaseRelocate;
}

//
// Load barrier
//
@@ -291,6 +299,12 @@ inline void ZBarrier::keep_alive_barrier_on_phantom_root_oop_field(oop* p) {
root_barrier<is_good_or_null_fast_path, keep_alive_barrier_on_phantom_oop_slow_path>(p, o);
}

inline void ZBarrier::keep_alive_barrier_on_oop(oop o) {
if (during_mark()) {
barrier<is_null_fast_path, mark_barrier_on_oop_slow_path>(NULL, o);
}
}

//
// Mark barrier
//
@@ -247,6 +247,10 @@ void ZCollectedHeap::object_iterate(ObjectClosure* cl) {
_heap.object_iterate(cl, true /* visit_weaks */);
}

void ZCollectedHeap::keep_alive(oop obj) {
_heap.keep_alive(obj);
}

void ZCollectedHeap::register_nmethod(nmethod* nm) {
ZNMethod::register_nmethod(nm);
}
@@ -99,6 +99,8 @@ class ZCollectedHeap : public CollectedHeap {

virtual void object_iterate(ObjectClosure* cl);

virtual void keep_alive(oop obj);

virtual void register_nmethod(nmethod* nm);
virtual void unregister_nmethod(nmethod* nm);
virtual void flush_nmethod(nmethod* nm);
@@ -322,6 +322,10 @@ bool ZHeap::mark_end() {
return true;
}

void ZHeap::keep_alive(oop obj) {
ZBarrier::keep_alive_barrier_on_oop(obj);
}

void ZHeap::set_soft_reference_policy(bool clear) {
_reference_processor.set_soft_reference_policy(clear);
}
@@ -137,6 +137,7 @@ class ZHeap {
void mark(bool initial);
void mark_flush_and_free(Thread* thread);
bool mark_end();
void keep_alive(oop obj);

// Relocation set
void select_relocation_set();
@@ -778,6 +778,10 @@ class FindInstanceClosure : public ObjectClosure {

void do_object(oop obj) {
if (obj->is_a(_klass)) {
// obj was read with AS_NO_KEEPALIVE, or equivalent.
// The object needs to be kept alive when it is published.
Universe::heap()->keep_alive(obj);

_result->append(obj);
}
}
@@ -483,6 +483,11 @@ JvmtiTagMap::~JvmtiTagMap() {
// is returned. Otherwise an new entry is allocated.
JvmtiTagHashmapEntry* JvmtiTagMap::create_entry(oop ref, jlong tag) {
assert(Thread::current()->is_VM_thread() || is_locked(), "checking");

// ref was read with AS_NO_KEEPALIVE, or equivalent.
// The object needs to be kept alive when it is published.
Universe::heap()->keep_alive(ref);

JvmtiTagHashmapEntry* entry;
if (_free_entries == NULL) {
entry = new JvmtiTagHashmapEntry(ref, tag);

0 comments on commit 5b155f0

Please sign in to comment.
You can’t perform that action at this time.