69 if (HasDecorator<decorators, IS_DEST_UNINITIALIZED>::value ||
70 HasDecorator<decorators, AS_NO_KEEPALIVE>::value) {
71 return;
72 }
73 if (ShenandoahSATBBarrier && _heap->is_concurrent_mark_in_progress()) {
74 T heap_oop = RawAccess<>::oop_load(field);
75 if (!CompressedOops::is_null(heap_oop)) {
76 enqueue(CompressedOops::decode(heap_oop));
77 }
78 }
79 }
80
81 inline void ShenandoahBarrierSet::satb_enqueue(oop value) {
82 assert(value != NULL, "checked before");
83 if (ShenandoahSATBBarrier && _heap->is_concurrent_mark_in_progress()) {
84 enqueue(value);
85 }
86 }
87
88 inline void ShenandoahBarrierSet::storeval_barrier(oop obj) {
89 if (obj != NULL && ShenandoahStoreValEnqueueBarrier) {
90 enqueue(obj);
91 }
92 }
93
94 inline void ShenandoahBarrierSet::keep_alive_if_weak(DecoratorSet decorators, oop value) {
95 assert((decorators & ON_UNKNOWN_OOP_REF) == 0, "Reference strength must be known");
96 const bool on_strong_oop_ref = (decorators & ON_STRONG_OOP_REF) != 0;
97 const bool peek = (decorators & AS_NO_KEEPALIVE) != 0;
98 if (!peek && !on_strong_oop_ref) {
99 satb_enqueue(value);
100 }
101 }
102
103 template <DecoratorSet decorators>
104 inline void ShenandoahBarrierSet::keep_alive_if_weak(oop value) {
105 assert((decorators & ON_UNKNOWN_OOP_REF) == 0, "Reference strength must be known");
106 if (!HasDecorator<decorators, ON_STRONG_OOP_REF>::value &&
107 !HasDecorator<decorators, AS_NO_KEEPALIVE>::value) {
108 satb_enqueue(value);
109 }
274 fwd = _heap->evacuate_object(obj, thread);
275 }
276 assert(obj != fwd || _heap->cancelled_gc(), "must be forwarded");
277 oop witness = ShenandoahHeap::cas_oop(fwd, elem_ptr, o);
278 obj = fwd;
279 }
280 if (ENQUEUE && !ctx->is_marked(obj)) {
281 queue.enqueue_known_active(obj);
282 }
283 }
284 }
285 }
286
287 template <class T>
288 void ShenandoahBarrierSet::arraycopy_barrier(T* src, T* dst, size_t count) {
289 if (count == 0) {
290 return;
291 }
292 int gc_state = _heap->gc_state();
293 if ((gc_state & ShenandoahHeap::MARKING) != 0) {
294 arraycopy_marking(dst, count);
295 } else if ((gc_state & ShenandoahHeap::EVACUATION) != 0) {
296 arraycopy_evacuation(src, count);
297 } else if ((gc_state & ShenandoahHeap::UPDATEREFS) != 0) {
298 arraycopy_update(src, count);
299 }
300 }
301
302 template <class T>
303 void ShenandoahBarrierSet::arraycopy_marking(T* array, size_t count) {
304 assert(_heap->is_concurrent_mark_in_progress(), "only during marking");
305 if (!_heap->marking_context()->allocated_after_mark_start(reinterpret_cast<HeapWord*>(array))) {
306 arraycopy_work<T, false, false, true>(array, count);
307 }
308 }
309
310 inline bool ShenandoahBarrierSet::need_bulk_update(HeapWord* ary) {
311 return ary < _heap->heap_region_containing(ary)->get_update_watermark();
312 }
313
314 template <class T>
315 void ShenandoahBarrierSet::arraycopy_evacuation(T* src, size_t count) {
316 assert(_heap->is_evacuation_in_progress(), "only during evacuation");
317 if (need_bulk_update(reinterpret_cast<HeapWord*>(src))) {
318 ShenandoahEvacOOMScope oom_evac;
319 arraycopy_work<T, true, true, false>(src, count);
320 }
321 }
322
323 template <class T>
324 void ShenandoahBarrierSet::arraycopy_update(T* src, size_t count) {
|
69 if (HasDecorator<decorators, IS_DEST_UNINITIALIZED>::value ||
70 HasDecorator<decorators, AS_NO_KEEPALIVE>::value) {
71 return;
72 }
73 if (ShenandoahSATBBarrier && _heap->is_concurrent_mark_in_progress()) {
74 T heap_oop = RawAccess<>::oop_load(field);
75 if (!CompressedOops::is_null(heap_oop)) {
76 enqueue(CompressedOops::decode(heap_oop));
77 }
78 }
79 }
80
81 inline void ShenandoahBarrierSet::satb_enqueue(oop value) {
82 assert(value != NULL, "checked before");
83 if (ShenandoahSATBBarrier && _heap->is_concurrent_mark_in_progress()) {
84 enqueue(value);
85 }
86 }
87
88 inline void ShenandoahBarrierSet::storeval_barrier(oop obj) {
89 if (ShenandoahStoreValEnqueueBarrier && obj != NULL && _heap->is_concurrent_mark_in_progress()) {
90 enqueue(obj);
91 }
92 }
93
94 inline void ShenandoahBarrierSet::keep_alive_if_weak(DecoratorSet decorators, oop value) {
95 assert((decorators & ON_UNKNOWN_OOP_REF) == 0, "Reference strength must be known");
96 const bool on_strong_oop_ref = (decorators & ON_STRONG_OOP_REF) != 0;
97 const bool peek = (decorators & AS_NO_KEEPALIVE) != 0;
98 if (!peek && !on_strong_oop_ref) {
99 satb_enqueue(value);
100 }
101 }
102
103 template <DecoratorSet decorators>
104 inline void ShenandoahBarrierSet::keep_alive_if_weak(oop value) {
105 assert((decorators & ON_UNKNOWN_OOP_REF) == 0, "Reference strength must be known");
106 if (!HasDecorator<decorators, ON_STRONG_OOP_REF>::value &&
107 !HasDecorator<decorators, AS_NO_KEEPALIVE>::value) {
108 satb_enqueue(value);
109 }
274 fwd = _heap->evacuate_object(obj, thread);
275 }
276 assert(obj != fwd || _heap->cancelled_gc(), "must be forwarded");
277 oop witness = ShenandoahHeap::cas_oop(fwd, elem_ptr, o);
278 obj = fwd;
279 }
280 if (ENQUEUE && !ctx->is_marked(obj)) {
281 queue.enqueue_known_active(obj);
282 }
283 }
284 }
285 }
286
287 template <class T>
288 void ShenandoahBarrierSet::arraycopy_barrier(T* src, T* dst, size_t count) {
289 if (count == 0) {
290 return;
291 }
292 int gc_state = _heap->gc_state();
293 if ((gc_state & ShenandoahHeap::MARKING) != 0) {
294 arraycopy_marking(src, dst, count);
295 } else if ((gc_state & ShenandoahHeap::EVACUATION) != 0) {
296 arraycopy_evacuation(src, count);
297 } else if ((gc_state & ShenandoahHeap::UPDATEREFS) != 0) {
298 arraycopy_update(src, count);
299 }
300 }
301
302 template <class T>
303 void ShenandoahBarrierSet::arraycopy_marking(T* src, T* dst, size_t count) {
304 assert(_heap->is_concurrent_mark_in_progress(), "only during marking");
305 T* array = ShenandoahSATBBarrier ? dst : src;
306 if (!_heap->marking_context()->allocated_after_mark_start(reinterpret_cast<HeapWord*>(array))) {
307 arraycopy_work<T, false, false, true>(array, count);
308 }
309 }
310
311 inline bool ShenandoahBarrierSet::need_bulk_update(HeapWord* ary) {
312 return ary < _heap->heap_region_containing(ary)->get_update_watermark();
313 }
314
315 template <class T>
316 void ShenandoahBarrierSet::arraycopy_evacuation(T* src, size_t count) {
317 assert(_heap->is_evacuation_in_progress(), "only during evacuation");
318 if (need_bulk_update(reinterpret_cast<HeapWord*>(src))) {
319 ShenandoahEvacOOMScope oom_evac;
320 arraycopy_work<T, true, true, false>(src, count);
321 }
322 }
323
324 template <class T>
325 void ShenandoahBarrierSet::arraycopy_update(T* src, size_t count) {
|