8204169: Humongous continues region remembered set states do not match the one from the corresponding humongous start region

Make sure and verify that the remembered set state of humongous continues regions matches the one from the corresponding humongous start region.

Reviewed-by: kbarrett, sjohanss
This commit is contained in:
Thomas Schatzl 2018-06-14 13:07:33 +02:00
parent da3ff94812
commit 83aae3288e
2 changed files with 26 additions and 4 deletions

View File

@ -315,6 +315,20 @@ public:
guarantee(!r->is_young() || r->rem_set()->is_complete(), "Remembered set for Young region %u must be complete, is %s", r->hrm_index(), r->rem_set()->get_state_str());
// Humongous and old regions regions might be of any state, so can't check here.
guarantee(!r->is_free() || !r->rem_set()->is_tracked(), "Remembered set for free region %u must be untracked, is %s", r->hrm_index(), r->rem_set()->get_state_str());
// Verify that the continues humongous regions' remembered set state matches the
// one from the starts humongous region.
if (r->is_continues_humongous()) {
if (r->rem_set()->get_state_str() != r->humongous_start_region()->rem_set()->get_state_str()) {
log_error(gc, verify)("Remset states differ: Region %u (%s) remset %s with starts region %u (%s) remset %s",
r->hrm_index(),
r->get_short_type_str(),
r->rem_set()->get_state_str(),
r->humongous_start_region()->hrm_index(),
r->humongous_start_region()->get_short_type_str(),
r->humongous_start_region()->rem_set()->get_state_str());
_failures = true;
}
}
// For archive regions, verify there are no heap pointers to
// non-pinned regions. For all others, verify liveness info.
if (r->is_closed_archive()) {

View File

@ -30,7 +30,7 @@
#include "runtime/safepoint.hpp"
bool G1RemSetTrackingPolicy::is_interesting_humongous_region(HeapRegion* r) const {
return r->is_starts_humongous() && oop(r->bottom())->is_typeArray();
return r->is_humongous() && oop(r->humongous_start_region()->bottom())->is_typeArray();
}
bool G1RemSetTrackingPolicy::needs_scan_for_rebuild(HeapRegion* r) const {
@ -119,13 +119,21 @@ void G1RemSetTrackingPolicy::update_after_rebuild(HeapRegion* r) {
if (r->rem_set()->is_updating()) {
r->rem_set()->set_state_complete();
}
G1CollectedHeap* g1h = G1CollectedHeap::heap();
// We can drop remembered sets of humongous regions that have a too large remembered set:
// We will never try to eagerly reclaim or move them anyway until the next concurrent
// cycle as e.g. remembered set entries will always be added.
if (r->is_humongous() && !G1CollectedHeap::heap()->is_potential_eager_reclaim_candidate(r)) {
r->rem_set()->clear_locked(true /* only_cardset */);
if (r->is_starts_humongous() && !g1h->is_potential_eager_reclaim_candidate(r)) {
// Handle HC regions with the HS region.
uint const size_in_regions = (uint)g1h->humongous_obj_size_in_regions(oop(r->bottom())->size());
uint const region_idx = r->hrm_index();
for (uint j = region_idx; j < (region_idx + size_in_regions); j++) {
HeapRegion* const cur = g1h->region_at(j);
assert(!cur->is_continues_humongous() || cur->rem_set()->is_empty(),
"Continues humongous region %u remset should be empty", j);
cur->rem_set()->clear_locked(true /* only_cardset */);
}
}
assert(!r->is_continues_humongous() || r->rem_set()->is_empty(), "Continues humongous object remsets should be empty");
G1ConcurrentMark* cm = G1CollectedHeap::heap()->concurrent_mark();
log_trace(gc, remset, tracking)("After rebuild region %u "
"(ntams " PTR_FORMAT " "