112 _oc->set_region(r);
113 MemRegion card_region(_bot->address_for_index(index), BOTConstants::N_words);
114 MemRegion pre_gc_allocated(r->bottom(), r->scan_top());
115 MemRegion mr = pre_gc_allocated.intersection(card_region);
116 if (!mr.is_empty() && !_ct_bs->is_card_claimed(index)) {
117 // We make the card as "claimed" lazily (so races are possible
118 // but they're benign), which reduces the number of duplicate
119 // scans (the rsets of the regions in the cset can intersect).
120 _ct_bs->set_card_claimed(index);
121 _cards_done++;
122 cl.do_MemRegion(mr);
123 }
124 }
125
126 void ScanRSClosure::scan_strong_code_roots(HeapRegion* r) {
127 double scan_start = os::elapsedTime();
128 r->strong_code_roots_do(_code_root_cl);
129 _strong_code_root_scan_time_sec += (os::elapsedTime() - scan_start);
130 }
131
132 bool ScanRSClosure::doHeapRegion(HeapRegion* r) {
133 assert(r->in_collection_set(), "should only be called on elements of CS.");
134 HeapRegionRemSet* hrrs = r->rem_set();
135 if (hrrs->iter_is_complete()) return false; // All done.
136 if (!_try_claimed && !hrrs->claim_iter()) return false;
137 // If we ever free the collection set concurrently, we should also
138 // clear the card table concurrently therefore we won't need to
139 // add regions of the collection set to the dirty cards region.
140 _g1h->push_dirty_cards_region(r);
141 // If we didn't return above, then
142 // _try_claimed || r->claim_iter()
143 // is true: either we're supposed to work on claimed-but-not-complete
144 // regions, or we successfully claimed the region.
145
146 HeapRegionRemSetIterator iter(hrrs);
147 size_t card_index;
148
149 // We claim cards in block so as to reduce the contention. The block size is determined by
150 // the G1RSetScanBlockSize parameter.
151 size_t jump_to_card = hrrs->iter_claimed_next(_block_size);
152 for (size_t current_card = 0; iter.has_next(card_index); current_card++) {
153 if (current_card >= jump_to_card + _block_size) {
154 jump_to_card = hrrs->iter_claimed_next(_block_size);
155 }
156 if (current_card < jump_to_card) continue;
158
159 HeapRegion* card_region = _g1h->heap_region_containing(card_start);
160 _cards++;
161
162 if (!card_region->is_on_dirty_cards_region_list()) {
163 _g1h->push_dirty_cards_region(card_region);
164 }
165
166 // If the card is dirty, then we will scan it during updateRS.
167 if (!card_region->in_collection_set() &&
168 !_ct_bs->is_card_dirty(card_index)) {
169 scanCard(card_index, card_region);
170 }
171 }
172 if (!_try_claimed) {
173 // Scan the strong code root list attached to the current region
174 scan_strong_code_roots(r);
175
176 hrrs->set_iter_complete();
177 }
178 return false;
179 }
180
181 size_t G1RemSet::scanRS(G1ParPushHeapRSClosure* oc,
182 CodeBlobClosure* heap_region_codeblobs,
183 uint worker_i) {
184 double rs_time_start = os::elapsedTime();
185
186 HeapRegion *startRegion = _g1->start_cset_region_for_worker(worker_i);
187
188 ScanRSClosure scanRScl(oc, heap_region_codeblobs, worker_i);
189
190 _g1->collection_set_iterate_from(startRegion, &scanRScl);
191 scanRScl.set_try_claimed();
192 _g1->collection_set_iterate_from(startRegion, &scanRScl);
193
194 double scan_rs_time_sec = (os::elapsedTime() - rs_time_start)
195 - scanRScl.strong_code_root_scan_time_sec();
196
197 _g1p->phase_times()->record_time_secs(G1GCPhaseTimes::ScanRS, worker_i, scan_rs_time_sec);
198 _g1p->phase_times()->record_time_secs(G1GCPhaseTimes::CodeRoots, worker_i, scanRScl.strong_code_root_scan_time_sec());
305
306 // Free any completed buffers in the DirtyCardQueueSet used to hold cards
307 // which contain references that point into the collection.
308 _into_cset_dirty_card_queue_set.clear();
309 assert(_into_cset_dirty_card_queue_set.completed_buffers_num() == 0,
310 "all buffers should be freed");
311 _into_cset_dirty_card_queue_set.clear_n_completed_buffers();
312 }
313
314 class ScrubRSClosure: public HeapRegionClosure {
315 G1CollectedHeap* _g1h;
316 BitMap* _region_bm;
317 BitMap* _card_bm;
318 CardTableModRefBS* _ctbs;
319 public:
320 ScrubRSClosure(BitMap* region_bm, BitMap* card_bm) :
321 _g1h(G1CollectedHeap::heap()),
322 _region_bm(region_bm), _card_bm(card_bm),
323 _ctbs(_g1h->g1_barrier_set()) {}
324
325 bool doHeapRegion(HeapRegion* r) {
326 if (!r->is_continues_humongous()) {
327 r->rem_set()->scrub(_ctbs, _region_bm, _card_bm);
328 }
329 return false;
330 }
331 };
332
333 void G1RemSet::scrub(BitMap* region_bm, BitMap* card_bm, uint worker_num, HeapRegionClaimer *hrclaimer) {
334 ScrubRSClosure scrub_cl(region_bm, card_bm);
335 _g1->heap_region_par_iterate(&scrub_cl, worker_num, hrclaimer);
336 }
337
338 G1TriggerClosure::G1TriggerClosure() :
339 _triggered(false) { }
340
341 G1InvokeIfNotTriggeredClosure::G1InvokeIfNotTriggeredClosure(G1TriggerClosure* t_cl,
342 OopClosure* oop_cl) :
343 _trigger_cl(t_cl), _oop_cl(oop_cl) { }
344
345 G1Mux2Closure::G1Mux2Closure(OopClosure *c1, OopClosure *c2) :
346 _c1(c1), _c2(c2) { }
347
348 G1UpdateRSOrPushRefOopClosure::
349 G1UpdateRSOrPushRefOopClosure(G1CollectedHeap* g1h,
|
112 _oc->set_region(r);
113 MemRegion card_region(_bot->address_for_index(index), BOTConstants::N_words);
114 MemRegion pre_gc_allocated(r->bottom(), r->scan_top());
115 MemRegion mr = pre_gc_allocated.intersection(card_region);
116 if (!mr.is_empty() && !_ct_bs->is_card_claimed(index)) {
117 // We make the card as "claimed" lazily (so races are possible
118 // but they're benign), which reduces the number of duplicate
119 // scans (the rsets of the regions in the cset can intersect).
120 _ct_bs->set_card_claimed(index);
121 _cards_done++;
122 cl.do_MemRegion(mr);
123 }
124 }
125
126 void ScanRSClosure::scan_strong_code_roots(HeapRegion* r) {
127 double scan_start = os::elapsedTime();
128 r->strong_code_roots_do(_code_root_cl);
129 _strong_code_root_scan_time_sec += (os::elapsedTime() - scan_start);
130 }
131
132 void ScanRSClosure::doHeapRegion(HeapRegion* r) {
133 assert(r->in_collection_set(), "should only be called on elements of CS.");
134 HeapRegionRemSet* hrrs = r->rem_set();
135 if (hrrs->iter_is_complete()) return; // All done.
136 if (!_try_claimed && !hrrs->claim_iter()) return;
137 // If we ever free the collection set concurrently, we should also
138 // clear the card table concurrently therefore we won't need to
139 // add regions of the collection set to the dirty cards region.
140 _g1h->push_dirty_cards_region(r);
141 // If we didn't return above, then
142 // _try_claimed || r->claim_iter()
143 // is true: either we're supposed to work on claimed-but-not-complete
144 // regions, or we successfully claimed the region.
145
146 HeapRegionRemSetIterator iter(hrrs);
147 size_t card_index;
148
149 // We claim cards in block so as to reduce the contention. The block size is determined by
150 // the G1RSetScanBlockSize parameter.
151 size_t jump_to_card = hrrs->iter_claimed_next(_block_size);
152 for (size_t current_card = 0; iter.has_next(card_index); current_card++) {
153 if (current_card >= jump_to_card + _block_size) {
154 jump_to_card = hrrs->iter_claimed_next(_block_size);
155 }
156 if (current_card < jump_to_card) continue;
158
159 HeapRegion* card_region = _g1h->heap_region_containing(card_start);
160 _cards++;
161
162 if (!card_region->is_on_dirty_cards_region_list()) {
163 _g1h->push_dirty_cards_region(card_region);
164 }
165
166 // If the card is dirty, then we will scan it during updateRS.
167 if (!card_region->in_collection_set() &&
168 !_ct_bs->is_card_dirty(card_index)) {
169 scanCard(card_index, card_region);
170 }
171 }
172 if (!_try_claimed) {
173 // Scan the strong code root list attached to the current region
174 scan_strong_code_roots(r);
175
176 hrrs->set_iter_complete();
177 }
178 }
179
180 size_t G1RemSet::scanRS(G1ParPushHeapRSClosure* oc,
181 CodeBlobClosure* heap_region_codeblobs,
182 uint worker_i) {
183 double rs_time_start = os::elapsedTime();
184
185 HeapRegion *startRegion = _g1->start_cset_region_for_worker(worker_i);
186
187 ScanRSClosure scanRScl(oc, heap_region_codeblobs, worker_i);
188
189 _g1->collection_set_iterate_from(startRegion, &scanRScl);
190 scanRScl.set_try_claimed();
191 _g1->collection_set_iterate_from(startRegion, &scanRScl);
192
193 double scan_rs_time_sec = (os::elapsedTime() - rs_time_start)
194 - scanRScl.strong_code_root_scan_time_sec();
195
196 _g1p->phase_times()->record_time_secs(G1GCPhaseTimes::ScanRS, worker_i, scan_rs_time_sec);
197 _g1p->phase_times()->record_time_secs(G1GCPhaseTimes::CodeRoots, worker_i, scanRScl.strong_code_root_scan_time_sec());
304
305 // Free any completed buffers in the DirtyCardQueueSet used to hold cards
306 // which contain references that point into the collection.
307 _into_cset_dirty_card_queue_set.clear();
308 assert(_into_cset_dirty_card_queue_set.completed_buffers_num() == 0,
309 "all buffers should be freed");
310 _into_cset_dirty_card_queue_set.clear_n_completed_buffers();
311 }
312
313 class ScrubRSClosure: public HeapRegionClosure {
314 G1CollectedHeap* _g1h;
315 BitMap* _region_bm;
316 BitMap* _card_bm;
317 CardTableModRefBS* _ctbs;
318 public:
319 ScrubRSClosure(BitMap* region_bm, BitMap* card_bm) :
320 _g1h(G1CollectedHeap::heap()),
321 _region_bm(region_bm), _card_bm(card_bm),
322 _ctbs(_g1h->g1_barrier_set()) {}
323
324 void doHeapRegion(HeapRegion* r) {
325 if (!r->is_continues_humongous()) {
326 r->rem_set()->scrub(_ctbs, _region_bm, _card_bm);
327 }
328 }
329 };
330
331 void G1RemSet::scrub(BitMap* region_bm, BitMap* card_bm, uint worker_num, HeapRegionClaimer *hrclaimer) {
332 ScrubRSClosure scrub_cl(region_bm, card_bm);
333 _g1->heap_region_par_iterate(&scrub_cl, worker_num, hrclaimer);
334 }
335
336 G1TriggerClosure::G1TriggerClosure() :
337 _triggered(false) { }
338
339 G1InvokeIfNotTriggeredClosure::G1InvokeIfNotTriggeredClosure(G1TriggerClosure* t_cl,
340 OopClosure* oop_cl) :
341 _trigger_cl(t_cl), _oop_cl(oop_cl) { }
342
343 G1Mux2Closure::G1Mux2Closure(OopClosure *c1, OopClosure *c2) :
344 _c1(c1), _c2(c2) { }
345
346 G1UpdateRSOrPushRefOopClosure::
347 G1UpdateRSOrPushRefOopClosure(G1CollectedHeap* g1h,
|