提交 d7727789 编写于 作者: J johnc

6921087: G1: remove per-GC-thread expansion tables from the fine-grain remembered sets

Summary: Remove the per-thread expansion tables (PosParPRT) and associated expansion and compaction from the fine grain RSet entries. This code has been unused for a while.
Reviewed-by: johnc, brutisso
Contributed-by: NThomas Schatzl <thomas.schatzl@jku.at>
上级 c5915c64
...@@ -4750,9 +4750,6 @@ public: ...@@ -4750,9 +4750,6 @@ public:
_g1h->g1_policy()->record_thread_age_table(pss.age_table()); _g1h->g1_policy()->record_thread_age_table(pss.age_table());
_g1h->update_surviving_young_words(pss.surviving_young_words()+1); _g1h->update_surviving_young_words(pss.surviving_young_words()+1);
// Clean up any par-expanded rem sets.
HeapRegionRemSet::par_cleanup();
if (ParallelGCVerbose) { if (ParallelGCVerbose) {
MutexLocker x(stats_lock()); MutexLocker x(stats_lock());
pss.print_termination_stats(worker_id); pss.print_termination_stats(worker_id);
......
...@@ -53,6 +53,9 @@ ...@@ -53,6 +53,9 @@
develop(bool, G1TraceMarkStackOverflow, false, \ develop(bool, G1TraceMarkStackOverflow, false, \
"If true, extra debugging code for CM restart for ovflw.") \ "If true, extra debugging code for CM restart for ovflw.") \
\ \
develop(bool, G1TraceHeapRegionRememberedSet, false, \
"Enables heap region remembered set debug logs") \
\
diagnostic(bool, G1SummarizeConcMark, false, \ diagnostic(bool, G1SummarizeConcMark, false, \
"Summarize concurrent mark info") \ "Summarize concurrent mark info") \
\ \
......
...@@ -30,13 +30,10 @@ ...@@ -30,13 +30,10 @@
#include "gc_implementation/g1/heapRegionSeq.inline.hpp" #include "gc_implementation/g1/heapRegionSeq.inline.hpp"
#include "memory/allocation.hpp" #include "memory/allocation.hpp"
#include "memory/space.inline.hpp" #include "memory/space.inline.hpp"
#include "oops/oop.inline.hpp"
#include "utilities/bitMap.inline.hpp" #include "utilities/bitMap.inline.hpp"
#include "utilities/globalDefinitions.hpp" #include "utilities/globalDefinitions.hpp"
#define HRRS_VERBOSE 0
#define PRT_COUNT_OCCUPIED 1
// OtherRegionsTable // OtherRegionsTable
class PerRegionTable: public CHeapObj { class PerRegionTable: public CHeapObj {
...@@ -45,14 +42,10 @@ class PerRegionTable: public CHeapObj { ...@@ -45,14 +42,10 @@ class PerRegionTable: public CHeapObj {
HeapRegion* _hr; HeapRegion* _hr;
BitMap _bm; BitMap _bm;
#if PRT_COUNT_OCCUPIED
jint _occupied; jint _occupied;
#endif
PerRegionTable* _next_free;
PerRegionTable* next_free() { return _next_free; }
void set_next_free(PerRegionTable* prt) { _next_free = prt; }
// next pointer for free/allocated lis
PerRegionTable* _next;
static PerRegionTable* _free_list; static PerRegionTable* _free_list;
...@@ -69,63 +62,25 @@ protected: ...@@ -69,63 +62,25 @@ protected:
// We need access in order to union things into the base table. // We need access in order to union things into the base table.
BitMap* bm() { return &_bm; } BitMap* bm() { return &_bm; }
#if PRT_COUNT_OCCUPIED
void recount_occupied() { void recount_occupied() {
_occupied = (jint) bm()->count_one_bits(); _occupied = (jint) bm()->count_one_bits();
} }
#endif
PerRegionTable(HeapRegion* hr) : PerRegionTable(HeapRegion* hr) :
_hr(hr), _hr(hr),
#if PRT_COUNT_OCCUPIED
_occupied(0), _occupied(0),
#endif
_bm(HeapRegion::CardsPerRegion, false /* in-resource-area */) _bm(HeapRegion::CardsPerRegion, false /* in-resource-area */)
{} {}
static void free(PerRegionTable* prt) {
while (true) {
PerRegionTable* fl = _free_list;
prt->set_next_free(fl);
PerRegionTable* res =
(PerRegionTable*)
Atomic::cmpxchg_ptr(prt, &_free_list, fl);
if (res == fl) return;
}
ShouldNotReachHere();
}
static PerRegionTable* alloc(HeapRegion* hr) {
PerRegionTable* fl = _free_list;
while (fl != NULL) {
PerRegionTable* nxt = fl->next_free();
PerRegionTable* res =
(PerRegionTable*)
Atomic::cmpxchg_ptr(nxt, &_free_list, fl);
if (res == fl) {
fl->init(hr);
return fl;
} else {
fl = _free_list;
}
}
assert(fl == NULL, "Loop condition.");
return new PerRegionTable(hr);
}
void add_card_work(CardIdx_t from_card, bool par) { void add_card_work(CardIdx_t from_card, bool par) {
if (!_bm.at(from_card)) { if (!_bm.at(from_card)) {
if (par) { if (par) {
if (_bm.par_at_put(from_card, 1)) { if (_bm.par_at_put(from_card, 1)) {
#if PRT_COUNT_OCCUPIED
Atomic::inc(&_occupied); Atomic::inc(&_occupied);
#endif
} }
} else { } else {
_bm.at_put(from_card, 1); _bm.at_put(from_card, 1);
#if PRT_COUNT_OCCUPIED
_occupied++; _occupied++;
#endif
} }
} }
} }
...@@ -134,10 +89,13 @@ protected: ...@@ -134,10 +89,13 @@ protected:
// Must make this robust in case "from" is not in "_hr", because of // Must make this robust in case "from" is not in "_hr", because of
// concurrency. // concurrency.
#if HRRS_VERBOSE if (G1TraceHeapRegionRememberedSet) {
gclog_or_tty->print_cr(" PRT::Add_reference_work(" PTR_FORMAT "->" PTR_FORMAT").", gclog_or_tty->print_cr(" PRT::Add_reference_work(" PTR_FORMAT "->" PTR_FORMAT").",
from, *from); from,
#endif UseCompressedOops
? oopDesc::load_decode_heap_oop((narrowOop*)from)
: oopDesc::load_decode_heap_oop((oop*)from));
}
HeapRegion* loc_hr = hr(); HeapRegion* loc_hr = hr();
// If the test below fails, then this table was reused concurrently // If the test below fails, then this table was reused concurrently
...@@ -162,23 +120,16 @@ public: ...@@ -162,23 +120,16 @@ public:
HeapRegion* hr() const { return _hr; } HeapRegion* hr() const { return _hr; }
#if PRT_COUNT_OCCUPIED
jint occupied() const { jint occupied() const {
// Overkill, but if we ever need it... // Overkill, but if we ever need it...
// guarantee(_occupied == _bm.count_one_bits(), "Check"); // guarantee(_occupied == _bm.count_one_bits(), "Check");
return _occupied; return _occupied;
} }
#else
jint occupied() const {
return _bm.count_one_bits();
}
#endif
void init(HeapRegion* hr) { void init(HeapRegion* hr) {
_hr = hr; _hr = hr;
#if PRT_COUNT_OCCUPIED _next = NULL;
_occupied = 0; _occupied = 0;
#endif
_bm.clear(); _bm.clear();
} }
...@@ -194,9 +145,7 @@ public: ...@@ -194,9 +145,7 @@ public:
HeapWord* hr_bot = hr()->bottom(); HeapWord* hr_bot = hr()->bottom();
size_t hr_first_card_index = ctbs->index_for(hr_bot); size_t hr_first_card_index = ctbs->index_for(hr_bot);
bm()->set_intersection_at_offset(*card_bm, hr_first_card_index); bm()->set_intersection_at_offset(*card_bm, hr_first_card_index);
#if PRT_COUNT_OCCUPIED
recount_occupied(); recount_occupied();
#endif
} }
void add_card(CardIdx_t from_card_index) { void add_card(CardIdx_t from_card_index) {
...@@ -218,16 +167,6 @@ public: ...@@ -218,16 +167,6 @@ public:
return sizeof(this) + _bm.size_in_words() * HeapWordSize; return sizeof(this) + _bm.size_in_words() * HeapWordSize;
} }
static size_t fl_mem_size() {
PerRegionTable* cur = _free_list;
size_t res = 0;
while (cur != NULL) {
res += sizeof(PerRegionTable);
cur = cur->next_free();
}
return res;
}
// Requires "from" to be in "hr()". // Requires "from" to be in "hr()".
bool contains_reference(OopOrNarrowOopStar from) const { bool contains_reference(OopOrNarrowOopStar from) const {
assert(hr()->is_in_reserved(from), "Precondition."); assert(hr()->is_in_reserved(from), "Precondition.");
...@@ -235,122 +174,29 @@ public: ...@@ -235,122 +174,29 @@ public:
CardTableModRefBS::card_size); CardTableModRefBS::card_size);
return _bm.at(card_ind); return _bm.at(card_ind);
} }
};
PerRegionTable* PerRegionTable::_free_list = NULL;
#define COUNT_PAR_EXPANDS 0
#if COUNT_PAR_EXPANDS
static jint n_par_expands = 0;
static jint n_par_contracts = 0;
static jint par_expand_list_len = 0;
static jint max_par_expand_list_len = 0;
static void print_par_expand() {
Atomic::inc(&n_par_expands);
Atomic::inc(&par_expand_list_len);
if (par_expand_list_len > max_par_expand_list_len) {
max_par_expand_list_len = par_expand_list_len;
}
if ((n_par_expands % 10) == 0) {
gclog_or_tty->print_cr("\n\n%d par expands: %d contracts, "
"len = %d, max_len = %d\n.",
n_par_expands, n_par_contracts, par_expand_list_len,
max_par_expand_list_len);
}
}
#endif
class PosParPRT: public PerRegionTable {
PerRegionTable** _par_tables;
enum SomePrivateConstants {
ReserveParTableExpansion = 1
};
void par_contract() {
assert(_par_tables != NULL, "Precondition.");
int n = HeapRegionRemSet::num_par_rem_sets()-1;
for (int i = 0; i < n; i++) {
_par_tables[i]->union_bitmap_into(bm());
PerRegionTable::free(_par_tables[i]);
_par_tables[i] = NULL;
}
#if PRT_COUNT_OCCUPIED
// We must recount the "occupied."
recount_occupied();
#endif
FREE_C_HEAP_ARRAY(PerRegionTable*, _par_tables);
_par_tables = NULL;
#if COUNT_PAR_EXPANDS
Atomic::inc(&n_par_contracts);
Atomic::dec(&par_expand_list_len);
#endif
}
static PerRegionTable** _par_table_fl;
PosParPRT* _next;
static PosParPRT* _free_list;
PerRegionTable** par_tables() const {
assert(uintptr_t(NULL) == 0, "Assumption.");
if (uintptr_t(_par_tables) <= ReserveParTableExpansion)
return NULL;
else
return _par_tables;
}
PosParPRT* _next_par_expanded;
PosParPRT* next_par_expanded() { return _next_par_expanded; }
void set_next_par_expanded(PosParPRT* ppprt) { _next_par_expanded = ppprt; }
static PosParPRT* _par_expanded_list;
public:
PosParPRT(HeapRegion* hr) : PerRegionTable(hr), _par_tables(NULL) {}
jint occupied() const { PerRegionTable* next() const { return _next; }
jint res = PerRegionTable::occupied(); void set_next(PerRegionTable* nxt) { _next = nxt; }
if (par_tables() != NULL) { PerRegionTable** next_addr() { return &_next; }
for (int i = 0; i < HeapRegionRemSet::num_par_rem_sets()-1; i++) {
res += par_tables()[i]->occupied();
}
}
return res;
}
void init(HeapRegion* hr) {
PerRegionTable::init(hr);
_next = NULL;
if (par_tables() != NULL) {
for (int i = 0; i < HeapRegionRemSet::num_par_rem_sets()-1; i++) {
par_tables()[i]->init(hr);
}
}
}
static void free(PosParPRT* prt) { static void free(PerRegionTable* prt) {
while (true) { while (true) {
PosParPRT* fl = _free_list; PerRegionTable* fl = _free_list;
prt->set_next(fl); prt->set_next(fl);
PosParPRT* res = PerRegionTable* res =
(PosParPRT*) (PerRegionTable*)
Atomic::cmpxchg_ptr(prt, &_free_list, fl); Atomic::cmpxchg_ptr(prt, &_free_list, fl);
if (res == fl) return; if (res == fl) return;
} }
ShouldNotReachHere(); ShouldNotReachHere();
} }
static PosParPRT* alloc(HeapRegion* hr) { static PerRegionTable* alloc(HeapRegion* hr) {
PosParPRT* fl = _free_list; PerRegionTable* fl = _free_list;
while (fl != NULL) { while (fl != NULL) {
PosParPRT* nxt = fl->next(); PerRegionTable* nxt = fl->next();
PosParPRT* res = PerRegionTable* res =
(PosParPRT*) (PerRegionTable*)
Atomic::cmpxchg_ptr(nxt, &_free_list, fl); Atomic::cmpxchg_ptr(nxt, &_free_list, fl);
if (res == fl) { if (res == fl) {
fl->init(hr); fl->init(hr);
...@@ -360,148 +206,26 @@ public: ...@@ -360,148 +206,26 @@ public:
} }
} }
assert(fl == NULL, "Loop condition."); assert(fl == NULL, "Loop condition.");
return new PosParPRT(hr); return new PerRegionTable(hr);
}
PosParPRT* next() const { return _next; }
void set_next(PosParPRT* nxt) { _next = nxt; }
PosParPRT** next_addr() { return &_next; }
bool should_expand(int tid) {
// Given that we now defer RSet updates for after a GC we don't
// really need to expand the tables any more. This code should be
// cleaned up in the future (see CR 6921087).
return false;
}
void par_expand() {
int n = HeapRegionRemSet::num_par_rem_sets()-1;
if (n <= 0) return;
if (_par_tables == NULL) {
PerRegionTable* res =
(PerRegionTable*)
Atomic::cmpxchg_ptr((PerRegionTable*)ReserveParTableExpansion,
&_par_tables, NULL);
if (res != NULL) return;
// Otherwise, we reserved the right to do the expansion.
PerRegionTable** ptables = NEW_C_HEAP_ARRAY(PerRegionTable*, n);
for (int i = 0; i < n; i++) {
PerRegionTable* ptable = PerRegionTable::alloc(hr());
ptables[i] = ptable;
}
// Here we do not need an atomic.
_par_tables = ptables;
#if COUNT_PAR_EXPANDS
print_par_expand();
#endif
// We must put this table on the expanded list.
PosParPRT* exp_head = _par_expanded_list;
while (true) {
set_next_par_expanded(exp_head);
PosParPRT* res =
(PosParPRT*)
Atomic::cmpxchg_ptr(this, &_par_expanded_list, exp_head);
if (res == exp_head) return;
// Otherwise.
exp_head = res;
}
ShouldNotReachHere();
}
}
void add_reference(OopOrNarrowOopStar from, int tid) {
// Expand if necessary.
PerRegionTable** pt = par_tables();
if (pt != NULL) {
// We always have to assume that mods to table 0 are in parallel,
// because of the claiming scheme in parallel expansion. A thread
// with tid != 0 that finds the table to be NULL, but doesn't succeed
// in claiming the right of expanding it, will end up in the else
// clause of the above if test. That thread could be delayed, and a
// thread 0 add reference could see the table expanded, and come
// here. Both threads would be adding in parallel. But we get to
// not use atomics for tids > 0.
if (tid == 0) {
PerRegionTable::add_reference(from);
} else {
pt[tid-1]->seq_add_reference(from);
}
} else {
// Not expanded -- add to the base table.
PerRegionTable::add_reference(from);
}
}
void scrub(CardTableModRefBS* ctbs, BitMap* card_bm) {
assert(_par_tables == NULL, "Precondition");
PerRegionTable::scrub(ctbs, card_bm);
}
size_t mem_size() const {
size_t res =
PerRegionTable::mem_size() + sizeof(this) - sizeof(PerRegionTable);
if (_par_tables != NULL) {
for (int i = 0; i < HeapRegionRemSet::num_par_rem_sets()-1; i++) {
res += _par_tables[i]->mem_size();
}
}
return res;
} }
static size_t fl_mem_size() { static size_t fl_mem_size() {
PosParPRT* cur = _free_list; PerRegionTable* cur = _free_list;
size_t res = 0; size_t res = 0;
while (cur != NULL) { while (cur != NULL) {
res += sizeof(PosParPRT); res += sizeof(PerRegionTable);
cur = cur->next(); cur = cur->next();
} }
return res; return res;
} }
bool contains_reference(OopOrNarrowOopStar from) const {
if (PerRegionTable::contains_reference(from)) return true;
if (_par_tables != NULL) {
for (int i = 0; i < HeapRegionRemSet::num_par_rem_sets()-1; i++) {
if (_par_tables[i]->contains_reference(from)) return true;
}
}
return false;
}
static void par_contract_all();
}; };
void PosParPRT::par_contract_all() { PerRegionTable* PerRegionTable::_free_list = NULL;
PosParPRT* hd = _par_expanded_list;
while (hd != NULL) {
PosParPRT* nxt = hd->next_par_expanded();
PosParPRT* res =
(PosParPRT*)
Atomic::cmpxchg_ptr(nxt, &_par_expanded_list, hd);
if (res == hd) {
// We claimed the right to contract this table.
hd->set_next_par_expanded(NULL);
hd->par_contract();
hd = _par_expanded_list;
} else {
hd = res;
}
}
}
PosParPRT* PosParPRT::_free_list = NULL;
PosParPRT* PosParPRT::_par_expanded_list = NULL;
jint OtherRegionsTable::_cache_probes = 0;
jint OtherRegionsTable::_cache_hits = 0;
size_t OtherRegionsTable::_max_fine_entries = 0; size_t OtherRegionsTable::_max_fine_entries = 0;
size_t OtherRegionsTable::_mod_max_fine_entries_mask = 0; size_t OtherRegionsTable::_mod_max_fine_entries_mask = 0;
#if SAMPLE_FOR_EVICTION
size_t OtherRegionsTable::_fine_eviction_stride = 0; size_t OtherRegionsTable::_fine_eviction_stride = 0;
size_t OtherRegionsTable::_fine_eviction_sample_size = 0; size_t OtherRegionsTable::_fine_eviction_sample_size = 0;
#endif
OtherRegionsTable::OtherRegionsTable(HeapRegion* hr) : OtherRegionsTable::OtherRegionsTable(HeapRegion* hr) :
_g1h(G1CollectedHeap::heap()), _g1h(G1CollectedHeap::heap()),
...@@ -511,34 +235,36 @@ OtherRegionsTable::OtherRegionsTable(HeapRegion* hr) : ...@@ -511,34 +235,36 @@ OtherRegionsTable::OtherRegionsTable(HeapRegion* hr) :
false /* in-resource-area */), false /* in-resource-area */),
_fine_grain_regions(NULL), _fine_grain_regions(NULL),
_n_fine_entries(0), _n_coarse_entries(0), _n_fine_entries(0), _n_coarse_entries(0),
#if SAMPLE_FOR_EVICTION
_fine_eviction_start(0), _fine_eviction_start(0),
#endif
_sparse_table(hr) _sparse_table(hr)
{ {
typedef PosParPRT* PosParPRTPtr; typedef PerRegionTable* PerRegionTablePtr;
if (_max_fine_entries == 0) { if (_max_fine_entries == 0) {
assert(_mod_max_fine_entries_mask == 0, "Both or none."); assert(_mod_max_fine_entries_mask == 0, "Both or none.");
size_t max_entries_log = (size_t)log2_long((jlong)G1RSetRegionEntries); size_t max_entries_log = (size_t)log2_long((jlong)G1RSetRegionEntries);
_max_fine_entries = (size_t)(1 << max_entries_log); _max_fine_entries = (size_t)(1 << max_entries_log);
_mod_max_fine_entries_mask = _max_fine_entries - 1; _mod_max_fine_entries_mask = _max_fine_entries - 1;
#if SAMPLE_FOR_EVICTION
assert(_fine_eviction_sample_size == 0 assert(_fine_eviction_sample_size == 0
&& _fine_eviction_stride == 0, "All init at same time."); && _fine_eviction_stride == 0, "All init at same time.");
_fine_eviction_sample_size = MAX2((size_t)4, max_entries_log); _fine_eviction_sample_size = MAX2((size_t)4, max_entries_log);
_fine_eviction_stride = _max_fine_entries / _fine_eviction_sample_size; _fine_eviction_stride = _max_fine_entries / _fine_eviction_sample_size;
#endif
} }
_fine_grain_regions = new PosParPRTPtr[_max_fine_entries];
if (_fine_grain_regions == NULL) _fine_grain_regions = new PerRegionTablePtr[_max_fine_entries];
if (_fine_grain_regions == NULL) {
vm_exit_out_of_memory(sizeof(void*)*_max_fine_entries, vm_exit_out_of_memory(sizeof(void*)*_max_fine_entries,
"Failed to allocate _fine_grain_entries."); "Failed to allocate _fine_grain_entries.");
}
for (size_t i = 0; i < _max_fine_entries; i++) { for (size_t i = 0; i < _max_fine_entries; i++) {
_fine_grain_regions[i] = NULL; _fine_grain_regions[i] = NULL;
} }
} }
int** OtherRegionsTable::_from_card_cache = NULL; int** OtherRegionsTable::_from_card_cache = NULL;
size_t OtherRegionsTable::_from_card_cache_max_regions = 0; size_t OtherRegionsTable::_from_card_cache_max_regions = 0;
size_t OtherRegionsTable::_from_card_cache_mem_size = 0; size_t OtherRegionsTable::_from_card_cache_mem_size = 0;
...@@ -579,38 +305,26 @@ void OtherRegionsTable::print_from_card_cache() { ...@@ -579,38 +305,26 @@ void OtherRegionsTable::print_from_card_cache() {
void OtherRegionsTable::add_reference(OopOrNarrowOopStar from, int tid) { void OtherRegionsTable::add_reference(OopOrNarrowOopStar from, int tid) {
size_t cur_hrs_ind = (size_t) hr()->hrs_index(); size_t cur_hrs_ind = (size_t) hr()->hrs_index();
#if HRRS_VERBOSE if (G1TraceHeapRegionRememberedSet) {
gclog_or_tty->print_cr("ORT::add_reference_work(" PTR_FORMAT "->" PTR_FORMAT ").", gclog_or_tty->print_cr("ORT::add_reference_work(" PTR_FORMAT "->" PTR_FORMAT ").",
from, from,
UseCompressedOops UseCompressedOops
? oopDesc::load_decode_heap_oop((narrowOop*)from) ? oopDesc::load_decode_heap_oop((narrowOop*)from)
: oopDesc::load_decode_heap_oop((oop*)from)); : oopDesc::load_decode_heap_oop((oop*)from));
#endif }
int from_card = (int)(uintptr_t(from) >> CardTableModRefBS::card_shift); int from_card = (int)(uintptr_t(from) >> CardTableModRefBS::card_shift);
#if HRRS_VERBOSE if (G1TraceHeapRegionRememberedSet) {
gclog_or_tty->print_cr("Table for [" PTR_FORMAT "...): card %d (cache = %d)", gclog_or_tty->print_cr("Table for [" PTR_FORMAT "...): card %d (cache = %d)",
hr()->bottom(), from_card, hr()->bottom(), from_card,
_from_card_cache[tid][cur_hrs_ind]); _from_card_cache[tid][cur_hrs_ind]);
#endif
#define COUNT_CACHE 0
#if COUNT_CACHE
jint p = Atomic::add(1, &_cache_probes);
if ((p % 10000) == 0) {
jint hits = _cache_hits;
gclog_or_tty->print_cr("%d/%d = %5.2f%% RS cache hits.",
_cache_hits, p, 100.0* (float)hits/(float)p);
} }
#endif
if (from_card == _from_card_cache[tid][cur_hrs_ind]) { if (from_card == _from_card_cache[tid][cur_hrs_ind]) {
#if HRRS_VERBOSE if (G1TraceHeapRegionRememberedSet) {
gclog_or_tty->print_cr(" from-card cache hit."); gclog_or_tty->print_cr(" from-card cache hit.");
#endif }
#if COUNT_CACHE
Atomic::inc(&_cache_hits);
#endif
assert(contains_reference(from), "We just added it!"); assert(contains_reference(from), "We just added it!");
return; return;
} else { } else {
...@@ -623,16 +337,16 @@ void OtherRegionsTable::add_reference(OopOrNarrowOopStar from, int tid) { ...@@ -623,16 +337,16 @@ void OtherRegionsTable::add_reference(OopOrNarrowOopStar from, int tid) {
// If the region is already coarsened, return. // If the region is already coarsened, return.
if (_coarse_map.at(from_hrs_ind)) { if (_coarse_map.at(from_hrs_ind)) {
#if HRRS_VERBOSE if (G1TraceHeapRegionRememberedSet) {
gclog_or_tty->print_cr(" coarse map hit."); gclog_or_tty->print_cr(" coarse map hit.");
#endif }
assert(contains_reference(from), "We just added it!"); assert(contains_reference(from), "We just added it!");
return; return;
} }
// Otherwise find a per-region table to add it to. // Otherwise find a per-region table to add it to.
size_t ind = from_hrs_ind & _mod_max_fine_entries_mask; size_t ind = from_hrs_ind & _mod_max_fine_entries_mask;
PosParPRT* prt = find_region_table(ind, from_hr); PerRegionTable* prt = find_region_table(ind, from_hr);
if (prt == NULL) { if (prt == NULL) {
MutexLockerEx x(&_m, Mutex::_no_safepoint_check_flag); MutexLockerEx x(&_m, Mutex::_no_safepoint_check_flag);
// Confirm that it's really not there... // Confirm that it's really not there...
...@@ -649,35 +363,35 @@ void OtherRegionsTable::add_reference(OopOrNarrowOopStar from, int tid) { ...@@ -649,35 +363,35 @@ void OtherRegionsTable::add_reference(OopOrNarrowOopStar from, int tid) {
_sparse_table.add_card(from_hrs_ind, card_index)) { _sparse_table.add_card(from_hrs_ind, card_index)) {
if (G1RecordHRRSOops) { if (G1RecordHRRSOops) {
HeapRegionRemSet::record(hr(), from); HeapRegionRemSet::record(hr(), from);
#if HRRS_VERBOSE if (G1TraceHeapRegionRememberedSet) {
gclog_or_tty->print(" Added card " PTR_FORMAT " to region " gclog_or_tty->print(" Added card " PTR_FORMAT " to region "
"[" PTR_FORMAT "...) for ref " PTR_FORMAT ".\n", "[" PTR_FORMAT "...) for ref " PTR_FORMAT ".\n",
align_size_down(uintptr_t(from), align_size_down(uintptr_t(from),
CardTableModRefBS::card_size), CardTableModRefBS::card_size),
hr()->bottom(), from); hr()->bottom(), from);
#endif }
}
if (G1TraceHeapRegionRememberedSet) {
gclog_or_tty->print_cr(" added card to sparse table.");
} }
#if HRRS_VERBOSE
gclog_or_tty->print_cr(" added card to sparse table.");
#endif
assert(contains_reference_locked(from), "We just added it!"); assert(contains_reference_locked(from), "We just added it!");
return; return;
} else { } else {
#if HRRS_VERBOSE if (G1TraceHeapRegionRememberedSet) {
gclog_or_tty->print_cr(" [tid %d] sparse table entry " gclog_or_tty->print_cr(" [tid %d] sparse table entry "
"overflow(f: %d, t: %d)", "overflow(f: %d, t: %d)",
tid, from_hrs_ind, cur_hrs_ind); tid, from_hrs_ind, cur_hrs_ind);
#endif }
} }
if (_n_fine_entries == _max_fine_entries) { if (_n_fine_entries == _max_fine_entries) {
prt = delete_region_table(); prt = delete_region_table();
} else { } else {
prt = PosParPRT::alloc(from_hr); prt = PerRegionTable::alloc(from_hr);
} }
prt->init(from_hr); prt->init(from_hr);
PosParPRT* first_prt = _fine_grain_regions[ind]; PerRegionTable* first_prt = _fine_grain_regions[ind];
prt->set_next(first_prt); // XXX Maybe move to init? prt->set_next(first_prt); // XXX Maybe move to init?
_fine_grain_regions[ind] = prt; _fine_grain_regions[ind] = prt;
_n_fine_entries++; _n_fine_entries++;
...@@ -704,38 +418,25 @@ void OtherRegionsTable::add_reference(OopOrNarrowOopStar from, int tid) { ...@@ -704,38 +418,25 @@ void OtherRegionsTable::add_reference(OopOrNarrowOopStar from, int tid) {
// OtherRegionsTable for why this is OK. // OtherRegionsTable for why this is OK.
assert(prt != NULL, "Inv"); assert(prt != NULL, "Inv");
if (prt->should_expand(tid)) { prt->add_reference(from);
MutexLockerEx x(&_m, Mutex::_no_safepoint_check_flag);
HeapRegion* prt_hr = prt->hr();
if (prt_hr == from_hr) {
// Make sure the table still corresponds to the same region
prt->par_expand();
prt->add_reference(from, tid);
}
// else: The table has been concurrently coarsened, evicted, and
// the table data structure re-used for another table. So, we
// don't need to add the reference any more given that the table
// has been coarsened and the whole region will be scanned anyway.
} else {
prt->add_reference(from, tid);
}
if (G1RecordHRRSOops) { if (G1RecordHRRSOops) {
HeapRegionRemSet::record(hr(), from); HeapRegionRemSet::record(hr(), from);
#if HRRS_VERBOSE if (G1TraceHeapRegionRememberedSet) {
gclog_or_tty->print("Added card " PTR_FORMAT " to region " gclog_or_tty->print("Added card " PTR_FORMAT " to region "
"[" PTR_FORMAT "...) for ref " PTR_FORMAT ".\n", "[" PTR_FORMAT "...) for ref " PTR_FORMAT ".\n",
align_size_down(uintptr_t(from), align_size_down(uintptr_t(from),
CardTableModRefBS::card_size), CardTableModRefBS::card_size),
hr()->bottom(), from); hr()->bottom(), from);
#endif }
} }
assert(contains_reference(from), "We just added it!"); assert(contains_reference(from), "We just added it!");
} }
PosParPRT* PerRegionTable*
OtherRegionsTable::find_region_table(size_t ind, HeapRegion* hr) const { OtherRegionsTable::find_region_table(size_t ind, HeapRegion* hr) const {
assert(0 <= ind && ind < _max_fine_entries, "Preconditions."); assert(0 <= ind && ind < _max_fine_entries, "Preconditions.");
PosParPRT* prt = _fine_grain_regions[ind]; PerRegionTable* prt = _fine_grain_regions[ind];
while (prt != NULL && prt->hr() != hr) { while (prt != NULL && prt->hr() != hr) {
prt = prt->next(); prt = prt->next();
} }
...@@ -743,32 +444,16 @@ OtherRegionsTable::find_region_table(size_t ind, HeapRegion* hr) const { ...@@ -743,32 +444,16 @@ OtherRegionsTable::find_region_table(size_t ind, HeapRegion* hr) const {
return prt; return prt;
} }
#define DRT_CENSUS 0
#if DRT_CENSUS
static const int HistoSize = 6;
static int global_histo[HistoSize] = { 0, 0, 0, 0, 0, 0 };
static int coarsenings = 0;
static int occ_sum = 0;
#endif
jint OtherRegionsTable::_n_coarsenings = 0; jint OtherRegionsTable::_n_coarsenings = 0;
PosParPRT* OtherRegionsTable::delete_region_table() { PerRegionTable* OtherRegionsTable::delete_region_table() {
#if DRT_CENSUS
int histo[HistoSize] = { 0, 0, 0, 0, 0, 0 };
const int histo_limits[] = { 1, 4, 16, 64, 256, 2048 };
#endif
assert(_m.owned_by_self(), "Precondition"); assert(_m.owned_by_self(), "Precondition");
assert(_n_fine_entries == _max_fine_entries, "Precondition"); assert(_n_fine_entries == _max_fine_entries, "Precondition");
PosParPRT* max = NULL; PerRegionTable* max = NULL;
jint max_occ = 0; jint max_occ = 0;
PosParPRT** max_prev; PerRegionTable** max_prev;
size_t max_ind; size_t max_ind;
#if SAMPLE_FOR_EVICTION
size_t i = _fine_eviction_start; size_t i = _fine_eviction_start;
for (size_t k = 0; k < _fine_eviction_sample_size; k++) { for (size_t k = 0; k < _fine_eviction_sample_size; k++) {
size_t ii = i; size_t ii = i;
...@@ -778,8 +463,8 @@ PosParPRT* OtherRegionsTable::delete_region_table() { ...@@ -778,8 +463,8 @@ PosParPRT* OtherRegionsTable::delete_region_table() {
if (ii == _max_fine_entries) ii = 0; if (ii == _max_fine_entries) ii = 0;
guarantee(ii != i, "We must find one."); guarantee(ii != i, "We must find one.");
} }
PosParPRT** prev = &_fine_grain_regions[ii]; PerRegionTable** prev = &_fine_grain_regions[ii];
PosParPRT* cur = *prev; PerRegionTable* cur = *prev;
while (cur != NULL) { while (cur != NULL) {
jint cur_occ = cur->occupied(); jint cur_occ = cur->occupied();
if (max == NULL || cur_occ > max_occ) { if (max == NULL || cur_occ > max_occ) {
...@@ -794,64 +479,27 @@ PosParPRT* OtherRegionsTable::delete_region_table() { ...@@ -794,64 +479,27 @@ PosParPRT* OtherRegionsTable::delete_region_table() {
i = i + _fine_eviction_stride; i = i + _fine_eviction_stride;
if (i >= _n_fine_entries) i = i - _n_fine_entries; if (i >= _n_fine_entries) i = i - _n_fine_entries;
} }
_fine_eviction_start++; _fine_eviction_start++;
if (_fine_eviction_start >= _n_fine_entries)
if (_fine_eviction_start >= _n_fine_entries) {
_fine_eviction_start -= _n_fine_entries; _fine_eviction_start -= _n_fine_entries;
#else
for (int i = 0; i < _max_fine_entries; i++) {
PosParPRT** prev = &_fine_grain_regions[i];
PosParPRT* cur = *prev;
while (cur != NULL) {
jint cur_occ = cur->occupied();
#if DRT_CENSUS
for (int k = 0; k < HistoSize; k++) {
if (cur_occ <= histo_limits[k]) {
histo[k]++; global_histo[k]++; break;
}
}
#endif
if (max == NULL || cur_occ > max_occ) {
max = cur;
max_prev = prev;
max_ind = i;
max_occ = cur_occ;
}
prev = cur->next_addr();
cur = cur->next();
}
} }
#endif
// XXX
guarantee(max != NULL, "Since _n_fine_entries > 0"); guarantee(max != NULL, "Since _n_fine_entries > 0");
#if DRT_CENSUS
gclog_or_tty->print_cr("In a coarsening: histo of occs:");
for (int k = 0; k < HistoSize; k++) {
gclog_or_tty->print_cr(" <= %4d: %5d.", histo_limits[k], histo[k]);
}
coarsenings++;
occ_sum += max_occ;
if ((coarsenings % 100) == 0) {
gclog_or_tty->print_cr("\ncoarsenings = %d; global summary:", coarsenings);
for (int k = 0; k < HistoSize; k++) {
gclog_or_tty->print_cr(" <= %4d: %5d.", histo_limits[k], global_histo[k]);
}
gclog_or_tty->print_cr("Avg occ of deleted region = %6.2f.",
(float)occ_sum/(float)coarsenings);
}
#endif
// Set the corresponding coarse bit. // Set the corresponding coarse bit.
size_t max_hrs_index = (size_t) max->hr()->hrs_index(); size_t max_hrs_index = (size_t) max->hr()->hrs_index();
if (!_coarse_map.at(max_hrs_index)) { if (!_coarse_map.at(max_hrs_index)) {
_coarse_map.at_put(max_hrs_index, true); _coarse_map.at_put(max_hrs_index, true);
_n_coarse_entries++; _n_coarse_entries++;
#if 0 if (G1TraceHeapRegionRememberedSet) {
gclog_or_tty->print("Coarsened entry in region [" PTR_FORMAT "...] " gclog_or_tty->print("Coarsened entry in region [" PTR_FORMAT "...] "
"for region [" PTR_FORMAT "...] (%d coarse entries).\n", "for region [" PTR_FORMAT "...] (%d coarse entries).\n",
hr()->bottom(), hr()->bottom(),
max->hr()->bottom(), max->hr()->bottom(),
_n_coarse_entries); _n_coarse_entries);
#endif }
} }
// Unsplice. // Unsplice.
...@@ -883,10 +531,10 @@ void OtherRegionsTable::scrub(CardTableModRefBS* ctbs, ...@@ -883,10 +531,10 @@ void OtherRegionsTable::scrub(CardTableModRefBS* ctbs,
// Now do the fine-grained maps. // Now do the fine-grained maps.
for (size_t i = 0; i < _max_fine_entries; i++) { for (size_t i = 0; i < _max_fine_entries; i++) {
PosParPRT* cur = _fine_grain_regions[i]; PerRegionTable* cur = _fine_grain_regions[i];
PosParPRT** prev = &_fine_grain_regions[i]; PerRegionTable** prev = &_fine_grain_regions[i];
while (cur != NULL) { while (cur != NULL) {
PosParPRT* nxt = cur->next(); PerRegionTable* nxt = cur->next();
// If the entire region is dead, eliminate. // If the entire region is dead, eliminate.
if (G1RSScrubVerbose) { if (G1RSScrubVerbose) {
gclog_or_tty->print_cr(" For other region %u:", gclog_or_tty->print_cr(" For other region %u:",
...@@ -899,7 +547,7 @@ void OtherRegionsTable::scrub(CardTableModRefBS* ctbs, ...@@ -899,7 +547,7 @@ void OtherRegionsTable::scrub(CardTableModRefBS* ctbs,
if (G1RSScrubVerbose) { if (G1RSScrubVerbose) {
gclog_or_tty->print_cr(" deleted via region map."); gclog_or_tty->print_cr(" deleted via region map.");
} }
PosParPRT::free(cur); PerRegionTable::free(cur);
} else { } else {
// Do fine-grain elimination. // Do fine-grain elimination.
if (G1RSScrubVerbose) { if (G1RSScrubVerbose) {
...@@ -914,7 +562,7 @@ void OtherRegionsTable::scrub(CardTableModRefBS* ctbs, ...@@ -914,7 +562,7 @@ void OtherRegionsTable::scrub(CardTableModRefBS* ctbs,
*prev = nxt; *prev = nxt;
cur->set_next(NULL); cur->set_next(NULL);
_n_fine_entries--; _n_fine_entries--;
PosParPRT::free(cur); PerRegionTable::free(cur);
} else { } else {
prev = cur->next_addr(); prev = cur->next_addr();
} }
...@@ -940,7 +588,7 @@ size_t OtherRegionsTable::occupied() const { ...@@ -940,7 +588,7 @@ size_t OtherRegionsTable::occupied() const {
size_t OtherRegionsTable::occ_fine() const { size_t OtherRegionsTable::occ_fine() const {
size_t sum = 0; size_t sum = 0;
for (size_t i = 0; i < _max_fine_entries; i++) { for (size_t i = 0; i < _max_fine_entries; i++) {
PosParPRT* cur = _fine_grain_regions[i]; PerRegionTable* cur = _fine_grain_regions[i];
while (cur != NULL) { while (cur != NULL) {
sum += cur->occupied(); sum += cur->occupied();
cur = cur->next(); cur = cur->next();
...@@ -962,13 +610,13 @@ size_t OtherRegionsTable::mem_size() const { ...@@ -962,13 +610,13 @@ size_t OtherRegionsTable::mem_size() const {
MutexLockerEx x((Mutex*)&_m, Mutex::_no_safepoint_check_flag); MutexLockerEx x((Mutex*)&_m, Mutex::_no_safepoint_check_flag);
size_t sum = 0; size_t sum = 0;
for (size_t i = 0; i < _max_fine_entries; i++) { for (size_t i = 0; i < _max_fine_entries; i++) {
PosParPRT* cur = _fine_grain_regions[i]; PerRegionTable* cur = _fine_grain_regions[i];
while (cur != NULL) { while (cur != NULL) {
sum += cur->mem_size(); sum += cur->mem_size();
cur = cur->next(); cur = cur->next();
} }
} }
sum += (sizeof(PosParPRT*) * _max_fine_entries); sum += (sizeof(PerRegionTable*) * _max_fine_entries);
sum += (_coarse_map.size_in_words() * HeapWordSize); sum += (_coarse_map.size_in_words() * HeapWordSize);
sum += (_sparse_table.mem_size()); sum += (_sparse_table.mem_size());
sum += sizeof(*this) - sizeof(_sparse_table); // Avoid double counting above. sum += sizeof(*this) - sizeof(_sparse_table); // Avoid double counting above.
...@@ -980,7 +628,7 @@ size_t OtherRegionsTable::static_mem_size() { ...@@ -980,7 +628,7 @@ size_t OtherRegionsTable::static_mem_size() {
} }
size_t OtherRegionsTable::fl_mem_size() { size_t OtherRegionsTable::fl_mem_size() {
return PerRegionTable::fl_mem_size() + PosParPRT::fl_mem_size(); return PerRegionTable::fl_mem_size();
} }
void OtherRegionsTable::clear_fcc() { void OtherRegionsTable::clear_fcc() {
...@@ -992,10 +640,10 @@ void OtherRegionsTable::clear_fcc() { ...@@ -992,10 +640,10 @@ void OtherRegionsTable::clear_fcc() {
void OtherRegionsTable::clear() { void OtherRegionsTable::clear() {
MutexLockerEx x(&_m, Mutex::_no_safepoint_check_flag); MutexLockerEx x(&_m, Mutex::_no_safepoint_check_flag);
for (size_t i = 0; i < _max_fine_entries; i++) { for (size_t i = 0; i < _max_fine_entries; i++) {
PosParPRT* cur = _fine_grain_regions[i]; PerRegionTable* cur = _fine_grain_regions[i];
while (cur != NULL) { while (cur != NULL) {
PosParPRT* nxt = cur->next(); PerRegionTable* nxt = cur->next();
PosParPRT::free(cur); PerRegionTable::free(cur);
cur = nxt; cur = nxt;
} }
_fine_grain_regions[i] = NULL; _fine_grain_regions[i] = NULL;
...@@ -1035,8 +683,8 @@ void OtherRegionsTable::clear_incoming_entry(HeapRegion* from_hr) { ...@@ -1035,8 +683,8 @@ void OtherRegionsTable::clear_incoming_entry(HeapRegion* from_hr) {
bool OtherRegionsTable::del_single_region_table(size_t ind, bool OtherRegionsTable::del_single_region_table(size_t ind,
HeapRegion* hr) { HeapRegion* hr) {
assert(0 <= ind && ind < _max_fine_entries, "Preconditions."); assert(0 <= ind && ind < _max_fine_entries, "Preconditions.");
PosParPRT** prev_addr = &_fine_grain_regions[ind]; PerRegionTable** prev_addr = &_fine_grain_regions[ind];
PosParPRT* prt = *prev_addr; PerRegionTable* prt = *prev_addr;
while (prt != NULL && prt->hr() != hr) { while (prt != NULL && prt->hr() != hr) {
prev_addr = prt->next_addr(); prev_addr = prt->next_addr();
prt = prt->next(); prt = prt->next();
...@@ -1044,7 +692,7 @@ bool OtherRegionsTable::del_single_region_table(size_t ind, ...@@ -1044,7 +692,7 @@ bool OtherRegionsTable::del_single_region_table(size_t ind,
if (prt != NULL) { if (prt != NULL) {
assert(prt->hr() == hr, "Loop postcondition."); assert(prt->hr() == hr, "Loop postcondition.");
*prev_addr = prt->next(); *prev_addr = prt->next();
PosParPRT::free(prt); PerRegionTable::free(prt);
_n_fine_entries--; _n_fine_entries--;
return true; return true;
} else { } else {
...@@ -1065,7 +713,7 @@ bool OtherRegionsTable::contains_reference_locked(OopOrNarrowOopStar from) const ...@@ -1065,7 +713,7 @@ bool OtherRegionsTable::contains_reference_locked(OopOrNarrowOopStar from) const
// Is this region in the coarse map? // Is this region in the coarse map?
if (_coarse_map.at(hr_ind)) return true; if (_coarse_map.at(hr_ind)) return true;
PosParPRT* prt = find_region_table(hr_ind & _mod_max_fine_entries_mask, PerRegionTable* prt = find_region_table(hr_ind & _mod_max_fine_entries_mask,
hr); hr);
if (prt != NULL) { if (prt != NULL) {
return prt->contains_reference(from); return prt->contains_reference(from);
...@@ -1145,7 +793,7 @@ void HeapRegionRemSet::print() const { ...@@ -1145,7 +793,7 @@ void HeapRegionRemSet::print() const {
G1CollectedHeap::heap()->bot_shared()->address_for_index(card_index); G1CollectedHeap::heap()->bot_shared()->address_for_index(card_index);
gclog_or_tty->print_cr(" Card " PTR_FORMAT, card_start); gclog_or_tty->print_cr(" Card " PTR_FORMAT, card_start);
} }
// XXX
if (iter.n_yielded() != occupied()) { if (iter.n_yielded() != occupied()) {
gclog_or_tty->print_cr("Yielded disagrees with occupied:"); gclog_or_tty->print_cr("Yielded disagrees with occupied:");
gclog_or_tty->print_cr(" %6d yielded (%6d coarse, %6d fine).", gclog_or_tty->print_cr(" %6d yielded (%6d coarse, %6d fine).",
...@@ -1163,10 +811,6 @@ void HeapRegionRemSet::cleanup() { ...@@ -1163,10 +811,6 @@ void HeapRegionRemSet::cleanup() {
SparsePRT::cleanup_all(); SparsePRT::cleanup_all();
} }
void HeapRegionRemSet::par_cleanup() {
PosParPRT::par_contract_all();
}
void HeapRegionRemSet::clear() { void HeapRegionRemSet::clear() {
_other_regions.clear(); _other_regions.clear();
assert(occupied() == 0, "Should be clear."); assert(occupied() == 0, "Should be clear.");
......
/* /*
* Copyright (c) 2001, 2011, Oracle and/or its affiliates. All rights reserved. * Copyright (c) 2001, 2012, Oracle and/or its affiliates. All rights reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
* *
* This code is free software; you can redistribute it and/or modify it * This code is free software; you can redistribute it and/or modify it
...@@ -35,7 +35,7 @@ class G1CollectedHeap; ...@@ -35,7 +35,7 @@ class G1CollectedHeap;
class G1BlockOffsetSharedArray; class G1BlockOffsetSharedArray;
class HeapRegion; class HeapRegion;
class HeapRegionRemSetIterator; class HeapRegionRemSetIterator;
class PosParPRT; class PerRegionTable;
class SparsePRT; class SparsePRT;
// Essentially a wrapper around SparsePRTCleanupTask. See // Essentially a wrapper around SparsePRTCleanupTask. See
...@@ -79,15 +79,14 @@ class OtherRegionsTable VALUE_OBJ_CLASS_SPEC { ...@@ -79,15 +79,14 @@ class OtherRegionsTable VALUE_OBJ_CLASS_SPEC {
size_t _n_coarse_entries; size_t _n_coarse_entries;
static jint _n_coarsenings; static jint _n_coarsenings;
PosParPRT** _fine_grain_regions; PerRegionTable** _fine_grain_regions;
size_t _n_fine_entries; size_t _n_fine_entries;
#define SAMPLE_FOR_EVICTION 1 // Used to sample a subset of the fine grain PRTs to determine which
#if SAMPLE_FOR_EVICTION // PRT to evict and coarsen.
size_t _fine_eviction_start; size_t _fine_eviction_start;
static size_t _fine_eviction_stride; static size_t _fine_eviction_stride;
static size_t _fine_eviction_sample_size; static size_t _fine_eviction_sample_size;
#endif
SparsePRT _sparse_table; SparsePRT _sparse_table;
...@@ -98,21 +97,18 @@ class OtherRegionsTable VALUE_OBJ_CLASS_SPEC { ...@@ -98,21 +97,18 @@ class OtherRegionsTable VALUE_OBJ_CLASS_SPEC {
// Requires "prt" to be the first element of the bucket list appropriate // Requires "prt" to be the first element of the bucket list appropriate
// for "hr". If this list contains an entry for "hr", return it, // for "hr". If this list contains an entry for "hr", return it,
// otherwise return "NULL". // otherwise return "NULL".
PosParPRT* find_region_table(size_t ind, HeapRegion* hr) const; PerRegionTable* find_region_table(size_t ind, HeapRegion* hr) const;
// Find, delete, and return a candidate PosParPRT, if any exists, // Find, delete, and return a candidate PerRegionTable, if any exists,
// adding the deleted region to the coarse bitmap. Requires the caller // adding the deleted region to the coarse bitmap. Requires the caller
// to hold _m, and the fine-grain table to be full. // to hold _m, and the fine-grain table to be full.
PosParPRT* delete_region_table(); PerRegionTable* delete_region_table();
// If a PRT for "hr" is in the bucket list indicated by "ind" (which must // If a PRT for "hr" is in the bucket list indicated by "ind" (which must
// be the correct index for "hr"), delete it and return true; else return // be the correct index for "hr"), delete it and return true; else return
// false. // false.
bool del_single_region_table(size_t ind, HeapRegion* hr); bool del_single_region_table(size_t ind, HeapRegion* hr);
static jint _cache_probes;
static jint _cache_hits;
// Indexed by thread X heap region, to minimize thread contention. // Indexed by thread X heap region, to minimize thread contention.
static int** _from_card_cache; static int** _from_card_cache;
static size_t _from_card_cache_max_regions; static size_t _from_card_cache_max_regions;
...@@ -127,10 +123,6 @@ public: ...@@ -127,10 +123,6 @@ public:
// sense. // sense.
void add_reference(OopOrNarrowOopStar from, int tid); void add_reference(OopOrNarrowOopStar from, int tid);
void add_reference(OopOrNarrowOopStar from) {
return add_reference(from, 0);
}
// Removes any entries shown by the given bitmaps to contain only dead // Removes any entries shown by the given bitmaps to contain only dead
// objects. // objects.
void scrub(CardTableModRefBS* ctbs, BitMap* region_bm, BitMap* card_bm); void scrub(CardTableModRefBS* ctbs, BitMap* region_bm, BitMap* card_bm);
...@@ -233,14 +225,12 @@ public: ...@@ -233,14 +225,12 @@ public:
static jint n_coarsenings() { return OtherRegionsTable::n_coarsenings(); } static jint n_coarsenings() { return OtherRegionsTable::n_coarsenings(); }
/* Used in the sequential case. Returns "true" iff this addition causes // Used in the sequential case.
the size limit to be reached. */
void add_reference(OopOrNarrowOopStar from) { void add_reference(OopOrNarrowOopStar from) {
_other_regions.add_reference(from); _other_regions.add_reference(from, 0);
} }
/* Used in the parallel case. Returns "true" iff this addition causes // Used in the parallel case.
the size limit to be reached. */
void add_reference(OopOrNarrowOopStar from, int tid) { void add_reference(OopOrNarrowOopStar from, int tid) {
_other_regions.add_reference(from, tid); _other_regions.add_reference(from, tid);
} }
...@@ -253,15 +243,6 @@ public: ...@@ -253,15 +243,6 @@ public:
// entries for this region in other remsets. // entries for this region in other remsets.
void clear(); void clear();
// Forget any entries due to pointers from "from_hr".
void clear_incoming_entry(HeapRegion* from_hr) {
_other_regions.clear_incoming_entry(from_hr);
}
#if 0
virtual void cleanup() = 0;
#endif
// Attempt to claim the region. Returns true iff this call caused an // Attempt to claim the region. Returns true iff this call caused an
// atomic transition from Unclaimed to Claimed. // atomic transition from Unclaimed to Claimed.
bool claim_iter(); bool claim_iter();
...@@ -290,12 +271,6 @@ public: ...@@ -290,12 +271,6 @@ public:
// Initialize the given iterator to iterate over this rem set. // Initialize the given iterator to iterate over this rem set.
void init_iterator(HeapRegionRemSetIterator* iter) const; void init_iterator(HeapRegionRemSetIterator* iter) const;
#if 0
// Apply the "do_card" method to the start address of every card in the
// rem set. Returns false if some application of the closure aborted.
virtual bool card_iterate(CardClosure* iter) = 0;
#endif
// The actual # of bytes this hr_remset takes up. // The actual # of bytes this hr_remset takes up.
size_t mem_size() { size_t mem_size() {
return _other_regions.mem_size() return _other_regions.mem_size()
...@@ -322,10 +297,7 @@ public: ...@@ -322,10 +297,7 @@ public:
void print() const; void print() const;
// Called during a stop-world phase to perform any deferred cleanups. // Called during a stop-world phase to perform any deferred cleanups.
// The second version may be called by parallel threads after then finish
// collection work.
static void cleanup(); static void cleanup();
static void par_cleanup();
// Declare the heap size (in # of regions) to the HeapRegionRemSet(s). // Declare the heap size (in # of regions) to the HeapRegionRemSet(s).
// (Uses it to initialize from_card_cache). // (Uses it to initialize from_card_cache).
...@@ -367,7 +339,7 @@ class HeapRegionRemSetIterator : public CHeapObj { ...@@ -367,7 +339,7 @@ class HeapRegionRemSetIterator : public CHeapObj {
// Local caching of HRRS fields. // Local caching of HRRS fields.
const BitMap* _coarse_map; const BitMap* _coarse_map;
PosParPRT** _fine_grain_regions; PerRegionTable** _fine_grain_regions;
G1BlockOffsetSharedArray* _bosa; G1BlockOffsetSharedArray* _bosa;
G1CollectedHeap* _g1h; G1CollectedHeap* _g1h;
...@@ -404,8 +376,9 @@ class HeapRegionRemSetIterator : public CHeapObj { ...@@ -404,8 +376,9 @@ class HeapRegionRemSetIterator : public CHeapObj {
// Index of bucket-list we're working on. // Index of bucket-list we're working on.
int _fine_array_index; int _fine_array_index;
// Per Region Table we're doing within current bucket list. // Per Region Table we're doing within current bucket list.
PosParPRT* _fine_cur_prt; PerRegionTable* _fine_cur_prt;
/* SparsePRT::*/ SparsePRTIter _sparse_iter; /* SparsePRT::*/ SparsePRTIter _sparse_iter;
...@@ -435,12 +408,4 @@ public: ...@@ -435,12 +408,4 @@ public:
} }
}; };
#if 0
class CardClosure: public Closure {
public:
virtual void do_card(HeapWord* card_start) = 0;
};
#endif
#endif // SHARE_VM_GC_IMPLEMENTATION_G1_HEAPREGIONREMSET_HPP #endif // SHARE_VM_GC_IMPLEMENTATION_G1_HEAPREGIONREMSET_HPP
Markdown is supported
0% .
You are about to add 0 people to the discussion. Proceed with caution.
先完成此消息的编辑!
想要评论请 注册