Mercurial > hg > graal-jvmci-8
comparison src/share/vm/gc_implementation/g1/g1OopClosures.inline.hpp @ 20804:7848fc12602b
Merge with jdk8u40-b25
author | Gilles Duboscq <gilles.m.duboscq@oracle.com> |
---|---|
date | Tue, 07 Apr 2015 14:58:49 +0200 |
parents | 52b4284cb496 eec72fa4b108 |
children | dd9cc155639c |
comparison
equal
deleted
inserted
replaced
20184:84105dcdb05b | 20804:7848fc12602b |
---|---|
26 #define SHARE_VM_GC_IMPLEMENTATION_G1_G1OOPCLOSURES_INLINE_HPP | 26 #define SHARE_VM_GC_IMPLEMENTATION_G1_G1OOPCLOSURES_INLINE_HPP |
27 | 27 |
28 #include "gc_implementation/g1/concurrentMark.inline.hpp" | 28 #include "gc_implementation/g1/concurrentMark.inline.hpp" |
29 #include "gc_implementation/g1/g1CollectedHeap.hpp" | 29 #include "gc_implementation/g1/g1CollectedHeap.hpp" |
30 #include "gc_implementation/g1/g1OopClosures.hpp" | 30 #include "gc_implementation/g1/g1OopClosures.hpp" |
31 #include "gc_implementation/g1/g1ParScanThreadState.inline.hpp" | |
31 #include "gc_implementation/g1/g1RemSet.hpp" | 32 #include "gc_implementation/g1/g1RemSet.hpp" |
32 #include "gc_implementation/g1/g1RemSet.inline.hpp" | 33 #include "gc_implementation/g1/g1RemSet.inline.hpp" |
33 #include "gc_implementation/g1/heapRegionRemSet.hpp" | 34 #include "gc_implementation/g1/heapRegionRemSet.hpp" |
35 #include "memory/iterator.inline.hpp" | |
36 #include "runtime/prefetch.inline.hpp" | |
34 | 37 |
35 /* | 38 /* |
36 * This really ought to be an inline function, but apparently the C++ | 39 * This really ought to be an inline function, but apparently the C++ |
37 * compiler sometimes sees fit to ignore inline declarations. Sigh. | 40 * compiler sometimes sees fit to ignore inline declarations. Sigh. |
38 */ | 41 */ |
39 | 42 |
40 template <class T> | 43 template <class T> |
41 inline void FilterIntoCSClosure::do_oop_nv(T* p) { | 44 inline void FilterIntoCSClosure::do_oop_nv(T* p) { |
42 T heap_oop = oopDesc::load_heap_oop(p); | 45 T heap_oop = oopDesc::load_heap_oop(p); |
43 if (!oopDesc::is_null(heap_oop) && | 46 if (!oopDesc::is_null(heap_oop) && |
44 _g1->obj_in_cs(oopDesc::decode_heap_oop_not_null(heap_oop))) { | 47 _g1->is_in_cset_or_humongous(oopDesc::decode_heap_oop_not_null(heap_oop))) { |
45 _oc->do_oop(p); | 48 _oc->do_oop(p); |
46 } | 49 } |
47 } | 50 } |
48 | 51 |
49 template <class T> | 52 template <class T> |
62 inline void G1ParScanClosure::do_oop_nv(T* p) { | 65 inline void G1ParScanClosure::do_oop_nv(T* p) { |
63 T heap_oop = oopDesc::load_heap_oop(p); | 66 T heap_oop = oopDesc::load_heap_oop(p); |
64 | 67 |
65 if (!oopDesc::is_null(heap_oop)) { | 68 if (!oopDesc::is_null(heap_oop)) { |
66 oop obj = oopDesc::decode_heap_oop_not_null(heap_oop); | 69 oop obj = oopDesc::decode_heap_oop_not_null(heap_oop); |
67 if (_g1->in_cset_fast_test(obj)) { | 70 G1CollectedHeap::in_cset_state_t state = _g1->in_cset_state(obj); |
71 if (state == G1CollectedHeap::InCSet) { | |
68 // We're not going to even bother checking whether the object is | 72 // We're not going to even bother checking whether the object is |
69 // already forwarded or not, as this usually causes an immediate | 73 // already forwarded or not, as this usually causes an immediate |
70 // stall. We'll try to prefetch the object (for write, given that | 74 // stall. We'll try to prefetch the object (for write, given that |
71 // we might need to install the forwarding reference) and we'll | 75 // we might need to install the forwarding reference) and we'll |
72 // get back to it when pop it from the queue | 76 // get back to it when pop it from the queue |
81 obj->forwardee() == oopDesc::load_decode_heap_oop(p)), | 85 obj->forwardee() == oopDesc::load_decode_heap_oop(p)), |
82 "p should still be pointing to obj or to its forwardee"); | 86 "p should still be pointing to obj or to its forwardee"); |
83 | 87 |
84 _par_scan_state->push_on_queue(p); | 88 _par_scan_state->push_on_queue(p); |
85 } else { | 89 } else { |
90 if (state == G1CollectedHeap::IsHumongous) { | |
91 _g1->set_humongous_is_live(obj); | |
92 } | |
86 _par_scan_state->update_rs(_from, p, _worker_id); | 93 _par_scan_state->update_rs(_from, p, _worker_id); |
87 } | 94 } |
88 } | 95 } |
89 } | 96 } |
90 | 97 |
92 inline void G1ParPushHeapRSClosure::do_oop_nv(T* p) { | 99 inline void G1ParPushHeapRSClosure::do_oop_nv(T* p) { |
93 T heap_oop = oopDesc::load_heap_oop(p); | 100 T heap_oop = oopDesc::load_heap_oop(p); |
94 | 101 |
95 if (!oopDesc::is_null(heap_oop)) { | 102 if (!oopDesc::is_null(heap_oop)) { |
96 oop obj = oopDesc::decode_heap_oop_not_null(heap_oop); | 103 oop obj = oopDesc::decode_heap_oop_not_null(heap_oop); |
97 if (_g1->in_cset_fast_test(obj)) { | 104 if (_g1->is_in_cset_or_humongous(obj)) { |
98 Prefetch::write(obj->mark_addr(), 0); | 105 Prefetch::write(obj->mark_addr(), 0); |
99 Prefetch::read(obj->mark_addr(), (HeapWordSize*2)); | 106 Prefetch::read(obj->mark_addr(), (HeapWordSize*2)); |
100 | 107 |
101 // Place on the references queue | 108 // Place on the references queue |
102 _par_scan_state->push_on_queue(p); | 109 _par_scan_state->push_on_queue(p); |
110 } else { | |
111 assert(!_g1->obj_in_cs(obj), "checking"); | |
103 } | 112 } |
104 } | 113 } |
105 } | 114 } |
106 | 115 |
107 template <class T> | 116 template <class T> |
108 inline void G1CMOopClosure::do_oop_nv(T* p) { | 117 inline void G1CMOopClosure::do_oop_nv(T* p) { |
109 assert(_g1h->is_in_g1_reserved((HeapWord*) p), "invariant"); | |
110 assert(!_g1h->is_on_master_free_list( | |
111 _g1h->heap_region_containing((HeapWord*) p)), "invariant"); | |
112 | |
113 oop obj = oopDesc::load_decode_heap_oop(p); | 118 oop obj = oopDesc::load_decode_heap_oop(p); |
114 if (_cm->verbose_high()) { | 119 if (_cm->verbose_high()) { |
115 gclog_or_tty->print_cr("[%u] we're looking at location " | 120 gclog_or_tty->print_cr("[%u] we're looking at location " |
116 "*"PTR_FORMAT" = "PTR_FORMAT, | 121 "*"PTR_FORMAT" = "PTR_FORMAT, |
117 _task->worker_id(), p2i(p), p2i((void*) obj)); | 122 _task->worker_id(), p2i(p), p2i((void*) obj)); |
123 inline void G1RootRegionScanClosure::do_oop_nv(T* p) { | 128 inline void G1RootRegionScanClosure::do_oop_nv(T* p) { |
124 T heap_oop = oopDesc::load_heap_oop(p); | 129 T heap_oop = oopDesc::load_heap_oop(p); |
125 if (!oopDesc::is_null(heap_oop)) { | 130 if (!oopDesc::is_null(heap_oop)) { |
126 oop obj = oopDesc::decode_heap_oop_not_null(heap_oop); | 131 oop obj = oopDesc::decode_heap_oop_not_null(heap_oop); |
127 HeapRegion* hr = _g1h->heap_region_containing((HeapWord*) obj); | 132 HeapRegion* hr = _g1h->heap_region_containing((HeapWord*) obj); |
128 if (hr != NULL) { | 133 _cm->grayRoot(obj, obj->size(), _worker_id, hr); |
129 _cm->grayRoot(obj, obj->size(), _worker_id, hr); | |
130 } | |
131 } | 134 } |
132 } | 135 } |
133 | 136 |
134 template <class T> | 137 template <class T> |
135 inline void G1Mux2Closure::do_oop_nv(T* p) { | 138 inline void G1Mux2Closure::do_oop_nv(T* p) { |
152 } | 155 } |
153 | 156 |
154 template <class T> | 157 template <class T> |
155 inline void G1UpdateRSOrPushRefOopClosure::do_oop_nv(T* p) { | 158 inline void G1UpdateRSOrPushRefOopClosure::do_oop_nv(T* p) { |
156 oop obj = oopDesc::load_decode_heap_oop(p); | 159 oop obj = oopDesc::load_decode_heap_oop(p); |
160 if (obj == NULL) { | |
161 return; | |
162 } | |
157 #ifdef ASSERT | 163 #ifdef ASSERT |
158 // can't do because of races | 164 // can't do because of races |
159 // assert(obj == NULL || obj->is_oop(), "expected an oop"); | 165 // assert(obj == NULL || obj->is_oop(), "expected an oop"); |
160 | 166 |
161 // Do the safe subset of is_oop | 167 // Do the safe subset of is_oop |
162 if (obj != NULL) { | |
163 #ifdef CHECK_UNHANDLED_OOPS | 168 #ifdef CHECK_UNHANDLED_OOPS |
164 oopDesc* o = obj.obj(); | 169 oopDesc* o = obj.obj(); |
165 #else | 170 #else |
166 oopDesc* o = obj; | 171 oopDesc* o = obj; |
167 #endif // CHECK_UNHANDLED_OOPS | 172 #endif // CHECK_UNHANDLED_OOPS |
168 assert((intptr_t)o % MinObjAlignmentInBytes == 0, "not oop aligned"); | 173 assert((intptr_t)o % MinObjAlignmentInBytes == 0, "not oop aligned"); |
169 assert(Universe::heap()->is_in_reserved(obj), "must be in heap"); | 174 assert(Universe::heap()->is_in_reserved(obj), "must be in heap"); |
170 } | |
171 #endif // ASSERT | 175 #endif // ASSERT |
172 | 176 |
173 assert(_from != NULL, "from region must be non-NULL"); | 177 assert(_from != NULL, "from region must be non-NULL"); |
174 assert(_from->is_in_reserved(p), "p is not in from"); | 178 assert(_from->is_in_reserved(p), "p is not in from"); |
175 | 179 |
176 HeapRegion* to = _g1->heap_region_containing(obj); | 180 HeapRegion* to = _g1->heap_region_containing(obj); |
177 if (to != NULL && _from != to) { | 181 if (_from == to) { |
178 // The _record_refs_into_cset flag is true during the RSet | 182 // Normally this closure should only be called with cross-region references. |
179 // updating part of an evacuation pause. It is false at all | 183 // But since Java threads are manipulating the references concurrently and we |
180 // other times: | 184 // reload the values things may have changed. |
181 // * rebuilding the rembered sets after a full GC | 185 return; |
182 // * during concurrent refinement. | 186 } |
183 // * updating the remembered sets of regions in the collection | 187 // The _record_refs_into_cset flag is true during the RSet |
184 // set in the event of an evacuation failure (when deferred | 188 // updating part of an evacuation pause. It is false at all |
185 // updates are enabled). | 189 // other times: |
186 | 190 // * rebuilding the remembered sets after a full GC |
187 if (_record_refs_into_cset && to->in_collection_set()) { | 191 // * during concurrent refinement. |
188 // We are recording references that point into the collection | 192 // * updating the remembered sets of regions in the collection |
189 // set and this particular reference does exactly that... | 193 // set in the event of an evacuation failure (when deferred |
190 // If the referenced object has already been forwarded | 194 // updates are enabled). |
191 // to itself, we are handling an evacuation failure and | 195 |
192 // we have already visited/tried to copy this object | 196 if (_record_refs_into_cset && to->in_collection_set()) { |
193 // there is no need to retry. | 197 // We are recording references that point into the collection |
194 if (!self_forwarded(obj)) { | 198 // set and this particular reference does exactly that... |
195 assert(_push_ref_cl != NULL, "should not be null"); | 199 // If the referenced object has already been forwarded |
196 // Push the reference in the refs queue of the G1ParScanThreadState | 200 // to itself, we are handling an evacuation failure and |
197 // instance for this worker thread. | 201 // we have already visited/tried to copy this object |
198 _push_ref_cl->do_oop(p); | 202 // there is no need to retry. |
199 } | 203 if (!self_forwarded(obj)) { |
200 | 204 assert(_push_ref_cl != NULL, "should not be null"); |
201 // Deferred updates to the CSet are either discarded (in the normal case), | 205 // Push the reference in the refs queue of the G1ParScanThreadState |
202 // or processed (if an evacuation failure occurs) at the end | 206 // instance for this worker thread. |
203 // of the collection. | 207 _push_ref_cl->do_oop(p); |
204 // See G1RemSet::cleanup_after_oops_into_collection_set_do(). | 208 } |
205 return; | 209 |
206 } | 210 // Deferred updates to the CSet are either discarded (in the normal case), |
207 | 211 // or processed (if an evacuation failure occurs) at the end |
212 // of the collection. | |
213 // See G1RemSet::cleanup_after_oops_into_collection_set_do(). | |
214 } else { | |
208 // We either don't care about pushing references that point into the | 215 // We either don't care about pushing references that point into the |
209 // collection set (i.e. we're not during an evacuation pause) _or_ | 216 // collection set (i.e. we're not during an evacuation pause) _or_ |
210 // the reference doesn't point into the collection set. Either way | 217 // the reference doesn't point into the collection set. Either way |
211 // we add the reference directly to the RSet of the region containing | 218 // we add the reference directly to the RSet of the region containing |
212 // the referenced object. | 219 // the referenced object. |