2626
2727#include " gc/shared/barrierSetNMethod.hpp"
2828#include " gc/shenandoah/shenandoahAsserts.hpp"
29+ #include " gc/shenandoah/shenandoahBarrierSet.hpp"
2930#include " gc/shenandoah/shenandoahClosures.hpp"
31+ #include " gc/shenandoah/shenandoahEvacOOMHandler.inline.hpp"
3032#include " gc/shenandoah/shenandoahHeap.inline.hpp"
3133#include " gc/shenandoah/shenandoahNMethod.inline.hpp"
3234#include " oops/compressedOops.inline.hpp"
@@ -64,6 +66,30 @@ BoolObjectClosure* ShenandoahIsAliveSelector::is_alive_closure() {
6466 reinterpret_cast <BoolObjectClosure*>(&_alive_cl);
6567}
6668
69+ ShenandoahKeepAliveClosure::ShenandoahKeepAliveClosure () :
70+ _bs(static_cast <ShenandoahBarrierSet*>(BarrierSet::barrier_set())) {
71+ }
72+
73+ void ShenandoahKeepAliveClosure::do_oop (oop* p) {
74+ do_oop_work (p);
75+ }
76+
77+ void ShenandoahKeepAliveClosure::do_oop (narrowOop* p) {
78+ do_oop_work (p);
79+ }
80+
81+ template <typename T>
82+ void ShenandoahKeepAliveClosure::do_oop_work (T* p) {
83+ assert (ShenandoahHeap::heap ()->is_concurrent_mark_in_progress (), " Only for concurrent marking phase" );
84+ assert (!ShenandoahHeap::heap ()->has_forwarded_objects (), " Not expected" );
85+
86+ T o = RawAccess<>::oop_load (p);
87+ if (!CompressedOops::is_null (o)) {
88+ oop obj = CompressedOops::decode_not_null (o);
89+ _bs->enqueue (obj);
90+ }
91+ }
92+
6793ShenandoahUpdateRefsClosure::ShenandoahUpdateRefsClosure () :
6894 _heap(ShenandoahHeap::heap()) {
6995}
@@ -81,16 +107,17 @@ void ShenandoahUpdateRefsClosure::do_oop(oop* p) { do_oop_work(p); }
81107void ShenandoahUpdateRefsClosure::do_oop (narrowOop* p) { do_oop_work (p); }
82108
83109template <DecoratorSet MO>
84- ShenandoahEvacuateUpdateRootsClosure <MO>::ShenandoahEvacuateUpdateRootsClosure () :
110+ ShenandoahEvacuateUpdateMetadataClosure <MO>::ShenandoahEvacuateUpdateMetadataClosure () :
85111 _heap (ShenandoahHeap::heap()), _thread(Thread::current()) {
86112}
87113
88114template <DecoratorSet MO>
89115template <class T >
90- void ShenandoahEvacuateUpdateRootsClosure <MO>::do_oop_work(T* p) {
116+ void ShenandoahEvacuateUpdateMetadataClosure <MO>::do_oop_work(T* p) {
91117 assert (_heap->is_concurrent_weak_root_in_progress () ||
92118 _heap->is_concurrent_strong_root_in_progress (),
93119 " Only do this in root processing phase" );
120+ assert (_thread == Thread::current (), " Wrong thread" );
94121
95122 T o = RawAccess<>::oop_load (p);
96123 if (! CompressedOops::is_null (o)) {
@@ -107,41 +134,64 @@ void ShenandoahEvacuateUpdateRootsClosure<MO>::do_oop_work(T* p) {
107134 }
108135}
109136template <DecoratorSet MO>
110- void ShenandoahEvacuateUpdateRootsClosure <MO>::do_oop(oop* p) {
137+ void ShenandoahEvacuateUpdateMetadataClosure <MO>::do_oop(oop* p) {
111138 do_oop_work (p);
112139}
113140
114141template <DecoratorSet MO>
115- void ShenandoahEvacuateUpdateRootsClosure <MO>::do_oop(narrowOop* p) {
142+ void ShenandoahEvacuateUpdateMetadataClosure <MO>::do_oop(narrowOop* p) {
116143 do_oop_work (p);
117144}
118145
119- ShenandoahEvacUpdateOopStorageRootsClosure::ShenandoahEvacUpdateOopStorageRootsClosure () :
120- _heap(ShenandoahHeap::heap()), _thread(Thread::current()) {
146+ ShenandoahEvacuateUpdateRootsClosure::ShenandoahEvacuateUpdateRootsClosure () :
147+ _heap(ShenandoahHeap::heap()) {
121148}
122149
123- void ShenandoahEvacUpdateOopStorageRootsClosure::do_oop (oop* p) {
150+ template <typename T>
151+ void ShenandoahEvacuateUpdateRootsClosure::do_oop_work (T* p, Thread* t) {
124152 assert (_heap->is_concurrent_weak_root_in_progress () ||
125153 _heap->is_concurrent_strong_root_in_progress (),
126154 " Only do this in root processing phase" );
155+ assert (t == Thread::current (), " Wrong thread" );
127156
128- oop obj = RawAccess<>::oop_load (p);
129- if (! CompressedOops::is_null (obj)) {
157+ T o = RawAccess<>::oop_load (p);
158+ if (!CompressedOops::is_null (o)) {
159+ oop obj = CompressedOops::decode_not_null (o);
130160 if (_heap->in_collection_set (obj)) {
131161 assert (_heap->is_evacuation_in_progress (), " Only do this when evacuation is in progress" );
132162 shenandoah_assert_marked (p, obj);
133163 oop resolved = ShenandoahBarrierSet::resolve_forwarded_not_null (obj);
134164 if (resolved == obj) {
135- resolved = _heap->evacuate_object (obj, _thread );
165+ resolved = _heap->evacuate_object (obj, t );
136166 }
137-
138- Atomic::cmpxchg (p, obj, resolved);
167+ _heap->cas_oop (resolved, p, o);
139168 }
140169 }
141170}
142171
143- void ShenandoahEvacUpdateOopStorageRootsClosure::do_oop (narrowOop* p) {
144- ShouldNotReachHere ();
172+ void ShenandoahEvacuateUpdateRootsClosure::do_oop (oop* p) {
173+ ShenandoahEvacOOMScope scope;
174+ do_oop_work (p, Thread::current ());
175+ }
176+
177+ void ShenandoahEvacuateUpdateRootsClosure::do_oop (narrowOop* p) {
178+ ShenandoahEvacOOMScope scope;
179+ do_oop_work (p, Thread::current ());
180+ }
181+
182+ ShenandoahContextEvacuateUpdateRootsClosure::ShenandoahContextEvacuateUpdateRootsClosure () :
183+ ShenandoahEvacuateUpdateRootsClosure(),
184+ _thread(Thread::current()) {
185+ }
186+
187+ void ShenandoahContextEvacuateUpdateRootsClosure::do_oop (oop* p) {
188+ ShenandoahEvacOOMScope scope;
189+ do_oop_work (p, _thread);
190+ }
191+
192+ void ShenandoahContextEvacuateUpdateRootsClosure::do_oop (narrowOop* p) {
193+ ShenandoahEvacOOMScope scope;
194+ do_oop_work (p, _thread);
145195}
146196
147197template <bool CONCURRENT, typename IsAlive, typename KeepAlive>
0 commit comments