364 "just checking");
365 }
366
367 int** FromCardCache::_cache = NULL;
368 uint FromCardCache::_max_regions = 0;
369 size_t FromCardCache::_static_mem_size = 0;
370
371 void FromCardCache::initialize(uint n_par_rs, uint max_num_regions) {
372 guarantee(_cache == NULL, "Should not call this multiple times");
373
374 _max_regions = max_num_regions;
375 _cache = Padded2DArray<int, mtGC>::create_unfreeable(n_par_rs,
376 _max_regions,
377 &_static_mem_size);
378
379 invalidate(0, _max_regions);
380 }
381
382 void FromCardCache::invalidate(uint start_idx, size_t new_num_regions) {
383 guarantee((size_t)start_idx + new_num_regions <= max_uintx,
384 err_msg("Trying to invalidate beyond maximum region, from %u size "SIZE_FORMAT,
385 start_idx, new_num_regions));
386 for (uint i = 0; i < HeapRegionRemSet::num_par_rem_sets(); i++) {
387 uint end_idx = (start_idx + (uint)new_num_regions);
388 assert(end_idx <= _max_regions, "Must be within max.");
389 for (uint j = start_idx; j < end_idx; j++) {
390 set(i, j, InvalidCard);
391 }
392 }
393 }
394
395 #ifndef PRODUCT
396 void FromCardCache::print(outputStream* out) {
397 for (uint i = 0; i < HeapRegionRemSet::num_par_rem_sets(); i++) {
398 for (uint j = 0; j < _max_regions; j++) {
399 out->print_cr("_from_card_cache["UINT32_FORMAT"]["UINT32_FORMAT"] = "INT32_FORMAT".",
400 i, j, at(i, j));
401 }
402 }
403 }
404 #endif
633 }
634
635 // Unsplice.
636 *max_prev = max->collision_list_next();
637 Atomic::inc(&_n_coarsenings);
638 _n_fine_entries--;
639 return max;
640 }
641
642
643 // At present, this must be called stop-world single-threaded.
644 void OtherRegionsTable::scrub(CardTableModRefBS* ctbs,
645 BitMap* region_bm, BitMap* card_bm) {
646 // First eliminated garbage regions from the coarse map.
647 if (G1RSScrubVerbose) {
648 gclog_or_tty->print_cr("Scrubbing region %u:", hr()->hrm_index());
649 }
650
651 assert(_coarse_map.size() == region_bm->size(), "Precondition");
652 if (G1RSScrubVerbose) {
653 gclog_or_tty->print(" Coarse map: before = "SIZE_FORMAT"...",
654 _n_coarse_entries);
655 }
656 _coarse_map.set_intersection(*region_bm);
657 _n_coarse_entries = _coarse_map.count_one_bits();
658 if (G1RSScrubVerbose) {
659 gclog_or_tty->print_cr(" after = "SIZE_FORMAT".", _n_coarse_entries);
660 }
661
662 // Now do the fine-grained maps.
663 for (size_t i = 0; i < _max_fine_entries; i++) {
664 PerRegionTable* cur = _fine_grain_regions[i];
665 PerRegionTable** prev = &_fine_grain_regions[i];
666 while (cur != NULL) {
667 PerRegionTable* nxt = cur->collision_list_next();
668 // If the entire region is dead, eliminate.
669 if (G1RSScrubVerbose) {
670 gclog_or_tty->print_cr(" For other region %u:",
671 cur->hr()->hrm_index());
672 }
673 if (!region_bm->at((size_t) cur->hr()->hrm_index())) {
674 *prev = nxt;
675 cur->set_collision_list_next(NULL);
676 _n_fine_entries--;
677 if (G1RSScrubVerbose) {
678 gclog_or_tty->print_cr(" deleted via region map.");
679 }
1035 }
1036
1037 bool HeapRegionRemSetIterator::fine_has_next(size_t& card_index) {
1038 if (fine_has_next()) {
1039 _cur_card_in_prt =
1040 _fine_cur_prt->_bm.get_next_one_offset(_cur_card_in_prt + 1);
1041 }
1042 if (_cur_card_in_prt == HeapRegion::CardsPerRegion) {
1043 // _fine_cur_prt may still be NULL in case if there are not PRTs at all for
1044 // the remembered set.
1045 if (_fine_cur_prt == NULL || _fine_cur_prt->next() == NULL) {
1046 return false;
1047 }
1048 PerRegionTable* next_prt = _fine_cur_prt->next();
1049 switch_to_prt(next_prt);
1050 _cur_card_in_prt = _fine_cur_prt->_bm.get_next_one_offset(_cur_card_in_prt + 1);
1051 }
1052
1053 card_index = _cur_region_card_offset + _cur_card_in_prt;
1054 guarantee(_cur_card_in_prt < HeapRegion::CardsPerRegion,
1055 err_msg("Card index "SIZE_FORMAT" must be within the region", _cur_card_in_prt));
1056 return true;
1057 }
1058
1059 bool HeapRegionRemSetIterator::fine_has_next() {
1060 return _cur_card_in_prt != HeapRegion::CardsPerRegion;
1061 }
1062
1063 void HeapRegionRemSetIterator::switch_to_prt(PerRegionTable* prt) {
1064 assert(prt != NULL, "Cannot switch to NULL prt");
1065 _fine_cur_prt = prt;
1066
1067 HeapWord* r_bot = _fine_cur_prt->hr()->bottom();
1068 _cur_region_card_offset = _bosa->index_for(r_bot);
1069
1070 // The bitmap scan for the PRT always scans from _cur_region_cur_card + 1.
1071 // To avoid special-casing this start case, and not miss the first bitmap
1072 // entry, initialize _cur_region_cur_card with -1 instead of 0.
1073 _cur_card_in_prt = (size_t)-1;
1074 }
1075
1204
1205 void HeapRegionRemSet::reset_for_cleanup_tasks() {
1206 SparsePRT::reset_for_cleanup_tasks();
1207 }
1208
1209 void HeapRegionRemSet::do_cleanup_work(HRRSCleanupTask* hrrs_cleanup_task) {
1210 _other_regions.do_cleanup_work(hrrs_cleanup_task);
1211 }
1212
1213 void
1214 HeapRegionRemSet::finish_cleanup_task(HRRSCleanupTask* hrrs_cleanup_task) {
1215 SparsePRT::finish_cleanup_task(hrrs_cleanup_task);
1216 }
1217
1218 #ifndef PRODUCT
1219 void PerRegionTable::test_fl_mem_size() {
1220 PerRegionTable* dummy = alloc(NULL);
1221
1222 size_t min_prt_size = sizeof(void*) + dummy->bm()->size_in_words() * HeapWordSize;
1223 assert(dummy->mem_size() > min_prt_size,
1224 err_msg("PerRegionTable memory usage is suspiciously small, only has "SIZE_FORMAT" bytes. "
1225 "Should be at least "SIZE_FORMAT" bytes.", dummy->mem_size(), min_prt_size));
1226 free(dummy);
1227 guarantee(dummy->mem_size() == fl_mem_size(), "fl_mem_size() does not return the correct element size");
1228 // try to reset the state
1229 _free_list = NULL;
1230 delete dummy;
1231 }
1232
1233 void HeapRegionRemSet::test_prt() {
1234 PerRegionTable::test_fl_mem_size();
1235 }
1236
1237 void HeapRegionRemSet::test() {
1238 os::sleep(Thread::current(), (jlong)5000, false);
1239 G1CollectedHeap* g1h = G1CollectedHeap::heap();
1240
1241 // Run with "-XX:G1LogRSetRegionEntries=2", so that 1 and 5 end up in same
1242 // hash bucket.
1243 HeapRegion* hr0 = g1h->region_at(0);
1244 HeapRegion* hr1 = g1h->region_at(1);
1245 HeapRegion* hr2 = g1h->region_at(5);
|
364 "just checking");
365 }
366
367 int** FromCardCache::_cache = NULL;
368 uint FromCardCache::_max_regions = 0;
369 size_t FromCardCache::_static_mem_size = 0;
370
371 void FromCardCache::initialize(uint n_par_rs, uint max_num_regions) {
372 guarantee(_cache == NULL, "Should not call this multiple times");
373
374 _max_regions = max_num_regions;
375 _cache = Padded2DArray<int, mtGC>::create_unfreeable(n_par_rs,
376 _max_regions,
377 &_static_mem_size);
378
379 invalidate(0, _max_regions);
380 }
381
382 void FromCardCache::invalidate(uint start_idx, size_t new_num_regions) {
383 guarantee((size_t)start_idx + new_num_regions <= max_uintx,
384 err_msg("Trying to invalidate beyond maximum region, from %u size " SIZE_FORMAT,
385 start_idx, new_num_regions));
386 for (uint i = 0; i < HeapRegionRemSet::num_par_rem_sets(); i++) {
387 uint end_idx = (start_idx + (uint)new_num_regions);
388 assert(end_idx <= _max_regions, "Must be within max.");
389 for (uint j = start_idx; j < end_idx; j++) {
390 set(i, j, InvalidCard);
391 }
392 }
393 }
394
395 #ifndef PRODUCT
396 void FromCardCache::print(outputStream* out) {
397 for (uint i = 0; i < HeapRegionRemSet::num_par_rem_sets(); i++) {
398 for (uint j = 0; j < _max_regions; j++) {
399 out->print_cr("_from_card_cache["UINT32_FORMAT"]["UINT32_FORMAT"] = "INT32_FORMAT".",
400 i, j, at(i, j));
401 }
402 }
403 }
404 #endif
633 }
634
635 // Unsplice.
636 *max_prev = max->collision_list_next();
637 Atomic::inc(&_n_coarsenings);
638 _n_fine_entries--;
639 return max;
640 }
641
642
643 // At present, this must be called stop-world single-threaded.
644 void OtherRegionsTable::scrub(CardTableModRefBS* ctbs,
645 BitMap* region_bm, BitMap* card_bm) {
646 // First eliminated garbage regions from the coarse map.
647 if (G1RSScrubVerbose) {
648 gclog_or_tty->print_cr("Scrubbing region %u:", hr()->hrm_index());
649 }
650
651 assert(_coarse_map.size() == region_bm->size(), "Precondition");
652 if (G1RSScrubVerbose) {
653 gclog_or_tty->print(" Coarse map: before = " SIZE_FORMAT "...",
654 _n_coarse_entries);
655 }
656 _coarse_map.set_intersection(*region_bm);
657 _n_coarse_entries = _coarse_map.count_one_bits();
658 if (G1RSScrubVerbose) {
659 gclog_or_tty->print_cr(" after = " SIZE_FORMAT ".", _n_coarse_entries);
660 }
661
662 // Now do the fine-grained maps.
663 for (size_t i = 0; i < _max_fine_entries; i++) {
664 PerRegionTable* cur = _fine_grain_regions[i];
665 PerRegionTable** prev = &_fine_grain_regions[i];
666 while (cur != NULL) {
667 PerRegionTable* nxt = cur->collision_list_next();
668 // If the entire region is dead, eliminate.
669 if (G1RSScrubVerbose) {
670 gclog_or_tty->print_cr(" For other region %u:",
671 cur->hr()->hrm_index());
672 }
673 if (!region_bm->at((size_t) cur->hr()->hrm_index())) {
674 *prev = nxt;
675 cur->set_collision_list_next(NULL);
676 _n_fine_entries--;
677 if (G1RSScrubVerbose) {
678 gclog_or_tty->print_cr(" deleted via region map.");
679 }
1035 }
1036
1037 bool HeapRegionRemSetIterator::fine_has_next(size_t& card_index) {
1038 if (fine_has_next()) {
1039 _cur_card_in_prt =
1040 _fine_cur_prt->_bm.get_next_one_offset(_cur_card_in_prt + 1);
1041 }
1042 if (_cur_card_in_prt == HeapRegion::CardsPerRegion) {
1043 // _fine_cur_prt may still be NULL in case if there are not PRTs at all for
1044 // the remembered set.
1045 if (_fine_cur_prt == NULL || _fine_cur_prt->next() == NULL) {
1046 return false;
1047 }
1048 PerRegionTable* next_prt = _fine_cur_prt->next();
1049 switch_to_prt(next_prt);
1050 _cur_card_in_prt = _fine_cur_prt->_bm.get_next_one_offset(_cur_card_in_prt + 1);
1051 }
1052
1053 card_index = _cur_region_card_offset + _cur_card_in_prt;
1054 guarantee(_cur_card_in_prt < HeapRegion::CardsPerRegion,
1055 err_msg("Card index " SIZE_FORMAT " must be within the region", _cur_card_in_prt));
1056 return true;
1057 }
1058
1059 bool HeapRegionRemSetIterator::fine_has_next() {
1060 return _cur_card_in_prt != HeapRegion::CardsPerRegion;
1061 }
1062
1063 void HeapRegionRemSetIterator::switch_to_prt(PerRegionTable* prt) {
1064 assert(prt != NULL, "Cannot switch to NULL prt");
1065 _fine_cur_prt = prt;
1066
1067 HeapWord* r_bot = _fine_cur_prt->hr()->bottom();
1068 _cur_region_card_offset = _bosa->index_for(r_bot);
1069
1070 // The bitmap scan for the PRT always scans from _cur_region_cur_card + 1.
1071 // To avoid special-casing this start case, and not miss the first bitmap
1072 // entry, initialize _cur_region_cur_card with -1 instead of 0.
1073 _cur_card_in_prt = (size_t)-1;
1074 }
1075
1204
1205 void HeapRegionRemSet::reset_for_cleanup_tasks() {
1206 SparsePRT::reset_for_cleanup_tasks();
1207 }
1208
1209 void HeapRegionRemSet::do_cleanup_work(HRRSCleanupTask* hrrs_cleanup_task) {
1210 _other_regions.do_cleanup_work(hrrs_cleanup_task);
1211 }
1212
1213 void
1214 HeapRegionRemSet::finish_cleanup_task(HRRSCleanupTask* hrrs_cleanup_task) {
1215 SparsePRT::finish_cleanup_task(hrrs_cleanup_task);
1216 }
1217
1218 #ifndef PRODUCT
1219 void PerRegionTable::test_fl_mem_size() {
1220 PerRegionTable* dummy = alloc(NULL);
1221
1222 size_t min_prt_size = sizeof(void*) + dummy->bm()->size_in_words() * HeapWordSize;
1223 assert(dummy->mem_size() > min_prt_size,
1224 err_msg("PerRegionTable memory usage is suspiciously small, only has " SIZE_FORMAT " bytes. "
1225 "Should be at least " SIZE_FORMAT " bytes.", dummy->mem_size(), min_prt_size));
1226 free(dummy);
1227 guarantee(dummy->mem_size() == fl_mem_size(), "fl_mem_size() does not return the correct element size");
1228 // try to reset the state
1229 _free_list = NULL;
1230 delete dummy;
1231 }
1232
1233 void HeapRegionRemSet::test_prt() {
1234 PerRegionTable::test_fl_mem_size();
1235 }
1236
1237 void HeapRegionRemSet::test() {
1238 os::sleep(Thread::current(), (jlong)5000, false);
1239 G1CollectedHeap* g1h = G1CollectedHeap::heap();
1240
1241 // Run with "-XX:G1LogRSetRegionEntries=2", so that 1 and 5 end up in same
1242 // hash bucket.
1243 HeapRegion* hr0 = g1h->region_at(0);
1244 HeapRegion* hr1 = g1h->region_at(1);
1245 HeapRegion* hr2 = g1h->region_at(5);
|