comparison src/share/vm/gc_implementation/g1/heapRegionRemSet.cpp @ 3766:c3f1170908be

7045330: G1: Simplify/fix the HeapRegionSeq class 7042285: G1: native memory leak during humongous object allocation 6804436: G1: heap region indices should be size_t Summary: A series of fixes and improvements to the HeapRegionSeq class: a) replace the _regions growable array with a standard C array, b) avoid de-allocating / re-allocating HeapRegion instances when the heap shrinks / grows (fix for 7042285), c) introduce fast method to map address to HeapRegion via a "biased" array pointer, d) embed the _hrs object in G1CollectedHeap, instead of pointing to it via an indirection, e) assume that all the regions added to the HeapRegionSeq instance are contiguous, f) replace int's with size_t's for indexes (and expand that to HeapRegion as part of 6804436), g) remove unnecessary / unused methods, h) rename a couple of fields (_alloc_search_start and _seq_bottom), i) fix iterate_from() not to always start from index 0 irrespective of the region passed to it, j) add a verification method to check the HeapRegionSeq assumptions, k) always call the wrappers for _hrs.iterate(), _hrs_length(), and _hrs.at() from G1CollectedHeap, not those methods directly, and l) unify the code that expands the sequence (by either re-using or creating a new HeapRegion) and make it robust wrt to a HeapRegion allocation failing. Reviewed-by: stefank, johnc, brutisso
author tonyp
date Fri, 10 Jun 2011 13:16:40 -0400
parents 97ba643ea3ed
children e8b0b0392037
comparison
equal deleted inserted replaced
3765:ae5b2f1dcf12 3766:c3f1170908be
832 (float)occ_sum/(float)coarsenings); 832 (float)occ_sum/(float)coarsenings);
833 } 833 }
834 #endif 834 #endif
835 835
836 // Set the corresponding coarse bit. 836 // Set the corresponding coarse bit.
837 int max_hrs_index = max->hr()->hrs_index(); 837 size_t max_hrs_index = max->hr()->hrs_index();
838 if (!_coarse_map.at(max_hrs_index)) { 838 if (!_coarse_map.at(max_hrs_index)) {
839 _coarse_map.at_put(max_hrs_index, true); 839 _coarse_map.at_put(max_hrs_index, true);
840 _n_coarse_entries++; 840 _n_coarse_entries++;
841 #if 0 841 #if 0
842 gclog_or_tty->print("Coarsened entry in region [" PTR_FORMAT "...] " 842 gclog_or_tty->print("Coarsened entry in region [" PTR_FORMAT "...] "
858 // At present, this must be called stop-world single-threaded. 858 // At present, this must be called stop-world single-threaded.
859 void OtherRegionsTable::scrub(CardTableModRefBS* ctbs, 859 void OtherRegionsTable::scrub(CardTableModRefBS* ctbs,
860 BitMap* region_bm, BitMap* card_bm) { 860 BitMap* region_bm, BitMap* card_bm) {
861 // First eliminated garbage regions from the coarse map. 861 // First eliminated garbage regions from the coarse map.
862 if (G1RSScrubVerbose) 862 if (G1RSScrubVerbose)
863 gclog_or_tty->print_cr("Scrubbing region %d:", hr()->hrs_index()); 863 gclog_or_tty->print_cr("Scrubbing region "SIZE_FORMAT":",
864 hr()->hrs_index());
864 865
865 assert(_coarse_map.size() == region_bm->size(), "Precondition"); 866 assert(_coarse_map.size() == region_bm->size(), "Precondition");
866 if (G1RSScrubVerbose) 867 if (G1RSScrubVerbose)
867 gclog_or_tty->print(" Coarse map: before = %d...", _n_coarse_entries); 868 gclog_or_tty->print(" Coarse map: before = %d...", _n_coarse_entries);
868 _coarse_map.set_intersection(*region_bm); 869 _coarse_map.set_intersection(*region_bm);
876 PosParPRT** prev = &_fine_grain_regions[i]; 877 PosParPRT** prev = &_fine_grain_regions[i];
877 while (cur != NULL) { 878 while (cur != NULL) {
878 PosParPRT* nxt = cur->next(); 879 PosParPRT* nxt = cur->next();
879 // If the entire region is dead, eliminate. 880 // If the entire region is dead, eliminate.
880 if (G1RSScrubVerbose) 881 if (G1RSScrubVerbose)
881 gclog_or_tty->print_cr(" For other region %d:", cur->hr()->hrs_index()); 882 gclog_or_tty->print_cr(" For other region "SIZE_FORMAT":",
883 cur->hr()->hrs_index());
882 if (!region_bm->at(cur->hr()->hrs_index())) { 884 if (!region_bm->at(cur->hr()->hrs_index())) {
883 *prev = nxt; 885 *prev = nxt;
884 cur->set_next(NULL); 886 cur->set_next(NULL);
885 _n_fine_entries--; 887 _n_fine_entries--;
886 if (G1RSScrubVerbose) 888 if (G1RSScrubVerbose)
992 clear_fcc(); 994 clear_fcc();
993 } 995 }
994 996
995 void OtherRegionsTable::clear_incoming_entry(HeapRegion* from_hr) { 997 void OtherRegionsTable::clear_incoming_entry(HeapRegion* from_hr) {
996 MutexLockerEx x(&_m, Mutex::_no_safepoint_check_flag); 998 MutexLockerEx x(&_m, Mutex::_no_safepoint_check_flag);
997 size_t hrs_ind = (size_t)from_hr->hrs_index(); 999 size_t hrs_ind = from_hr->hrs_index();
998 size_t ind = hrs_ind & _mod_max_fine_entries_mask; 1000 size_t ind = hrs_ind & _mod_max_fine_entries_mask;
999 if (del_single_region_table(ind, from_hr)) { 1001 if (del_single_region_table(ind, from_hr)) {
1000 assert(!_coarse_map.at(hrs_ind), "Inv"); 1002 assert(!_coarse_map.at(hrs_ind), "Inv");
1001 } else { 1003 } else {
1002 _coarse_map.par_at_put(hrs_ind, 0); 1004 _coarse_map.par_at_put(hrs_ind, 0);
1003 } 1005 }
1004 // Check to see if any of the fcc entries come from here. 1006 // Check to see if any of the fcc entries come from here.
1005 int hr_ind = hr()->hrs_index(); 1007 size_t hr_ind = hr()->hrs_index();
1006 for (int tid = 0; tid < HeapRegionRemSet::num_par_rem_sets(); tid++) { 1008 for (int tid = 0; tid < HeapRegionRemSet::num_par_rem_sets(); tid++) {
1007 int fcc_ent = _from_card_cache[tid][hr_ind]; 1009 int fcc_ent = _from_card_cache[tid][hr_ind];
1008 if (fcc_ent != -1) { 1010 if (fcc_ent != -1) {
1009 HeapWord* card_addr = (HeapWord*) 1011 HeapWord* card_addr = (HeapWord*)
1010 (uintptr_t(fcc_ent) << CardTableModRefBS::card_shift); 1012 (uintptr_t(fcc_ent) << CardTableModRefBS::card_shift);