hotspot/src/share/vm/memory/cardTableRS.cpp
Print this page
rev 611 : Merge
@@ -1,10 +1,10 @@
#ifdef USE_PRAGMA_IDENT_SRC
#pragma ident "@(#)cardTableRS.cpp 1.45 07/05/25 12:54:50 JVM"
#endif
/*
- * Copyright 2001-2006 Sun Microsystems, Inc. All Rights Reserved.
+ * Copyright 2001-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
@@ -28,35 +28,49 @@
# include "incls/_precompiled.incl"
# include "incls/_cardTableRS.cpp.incl"
CardTableRS::CardTableRS(MemRegion whole_heap,
int max_covered_regions) :
- GenRemSet(&_ct_bs),
- _ct_bs(whole_heap, max_covered_regions),
- _cur_youngergen_card_val(youngergenP1_card)
+ GenRemSet(),
+ _cur_youngergen_card_val(youngergenP1_card),
+ _regions_to_iterate(max_covered_regions - 1)
{
+#ifndef SERIALGC
+ if (UseG1GC) {
+ if (G1RSBarrierUseQueue) {
+ _ct_bs = new G1SATBCardTableLoggingModRefBS(whole_heap,
+ max_covered_regions);
+ } else {
+ _ct_bs = new G1SATBCardTableModRefBS(whole_heap, max_covered_regions);
+ }
+ } else {
+ _ct_bs = new CardTableModRefBSForCTRS(whole_heap, max_covered_regions);
+ }
+#else
+ _ct_bs = new CardTableModRefBSForCTRS(whole_heap, max_covered_regions);
+#endif
+ set_bs(_ct_bs);
_last_cur_val_in_gen = new jbyte[GenCollectedHeap::max_gens + 1];
if (_last_cur_val_in_gen == NULL) {
vm_exit_during_initialization("Could not last_cur_val_in_gen array.");
}
for (int i = 0; i < GenCollectedHeap::max_gens + 1; i++) {
_last_cur_val_in_gen[i] = clean_card_val();
}
- _ct_bs.set_CTRS(this);
+ _ct_bs->set_CTRS(this);
}
void CardTableRS::resize_covered_region(MemRegion new_region) {
- _ct_bs.resize_covered_region(new_region);
+ _ct_bs->resize_covered_region(new_region);
}
jbyte CardTableRS::find_unused_youngergenP_card_value() {
- GenCollectedHeap* gch = GenCollectedHeap::heap();
for (jbyte v = youngergenP1_card;
v < cur_youngergen_and_prev_nonclean_card;
v++) {
bool seen = false;
- for (int g = 0; g < gch->n_gens()+1; g++) {
+ for (int g = 0; g < _regions_to_iterate; g++) {
if (_last_cur_val_in_gen[g] == v) {
seen = true;
break;
}
}
@@ -192,11 +206,11 @@
// dirty ==> cur_youngergen_and_prev_nonclean_card
// precleaned ==> cur_youngergen_and_prev_nonclean_card
// prev-younger-gen ==> cur_youngergen_and_prev_nonclean_card
// cur-younger-gen ==> cur_younger_gen
// cur_youngergen_and_prev_nonclean_card ==> no change.
-void CardTableRS::write_ref_field_gc_par(oop* field, oop new_val) {
+void CardTableRS::write_ref_field_gc_par(void* field, oop new_val) {
jbyte* entry = ct_bs()->byte_for(field);
do {
jbyte entry_val = *entry;
// We put this first because it's probably the most common case.
if (entry_val == clean_card_val()) {
@@ -222,15 +236,15 @@
} while (true);
}
void CardTableRS::younger_refs_in_space_iterate(Space* sp,
OopsInGenClosure* cl) {
- DirtyCardToOopClosure* dcto_cl = sp->new_dcto_cl(cl, _ct_bs.precision(),
+ DirtyCardToOopClosure* dcto_cl = sp->new_dcto_cl(cl, _ct_bs->precision(),
cl->gen_boundary());
ClearNoncleanCardWrapper clear_cl(dcto_cl, this);
- _ct_bs.non_clean_card_iterate(sp, sp->used_region_at_save_marks(),
+ _ct_bs->non_clean_card_iterate(sp, sp->used_region_at_save_marks(),
dcto_cl, &clear_cl, false);
}
void CardTableRS::clear_into_younger(Generation* gen, bool clear_perm) {
GenCollectedHeap* gch = GenCollectedHeap::heap();
@@ -291,32 +305,40 @@
}
}
class VerifyCleanCardClosure: public OopClosure {
- HeapWord* boundary;
- HeapWord* begin; HeapWord* end;
-public:
- void do_oop(oop* p) {
+private:
+ HeapWord* _boundary;
+ HeapWord* _begin;
+ HeapWord* _end;
+protected:
+ template <class T> void do_oop_work(T* p) {
HeapWord* jp = (HeapWord*)p;
- if (jp >= begin && jp < end) {
- guarantee(*p == NULL || (HeapWord*)p < boundary
- || (HeapWord*)(*p) >= boundary,
+ if (jp >= _begin && jp < _end) {
+ oop obj = oopDesc::load_decode_heap_oop(p);
+ guarantee(obj == NULL ||
+ (HeapWord*)p < _boundary ||
+ (HeapWord*)obj >= _boundary,
"pointer on clean card crosses boundary");
}
}
- VerifyCleanCardClosure(HeapWord* b, HeapWord* _begin, HeapWord* _end) :
- boundary(b), begin(_begin), end(_end) {}
+public:
+ VerifyCleanCardClosure(HeapWord* b, HeapWord* begin, HeapWord* end) :
+ _boundary(b), _begin(begin), _end(end) {}
+ virtual void do_oop(oop* p) { VerifyCleanCardClosure::do_oop_work(p); }
+ virtual void do_oop(narrowOop* p) { VerifyCleanCardClosure::do_oop_work(p); }
};
class VerifyCTSpaceClosure: public SpaceClosure {
+private:
CardTableRS* _ct;
HeapWord* _boundary;
public:
VerifyCTSpaceClosure(CardTableRS* ct, HeapWord* boundary) :
_ct(ct), _boundary(boundary) {}
- void do_space(Space* s) { _ct->verify_space(s, _boundary); }
+ virtual void do_space(Space* s) { _ct->verify_space(s, _boundary); }
};
class VerifyCTGenClosure: public GenCollectedHeap::GenClosure {
CardTableRS* _ct;
public:
@@ -542,11 +564,11 @@
Generation* pg = SharedHeap::heap()->perm_gen();
HeapWord* pg_boundary = pg->reserved().start();
if (ch->kind() == CollectedHeap::GenCollectedHeap) {
GenCollectedHeap::heap()->generation_iterate(&blk, false);
- _ct_bs.verify();
+ _ct_bs->verify();
// If the old gen collections also collect perm, then we are only
// interested in perm-to-young pointers, not perm-to-old pointers.
GenCollectedHeap* gch = GenCollectedHeap::heap();
CollectorPolicy* cp = gch->collector_policy();
@@ -557,14 +579,20 @@
VerifyCTSpaceClosure perm_space_blk(this, pg_boundary);
SharedHeap::heap()->perm_gen()->space_iterate(&perm_space_blk, true);
}
-void CardTableRS::verify_empty(MemRegion mr) {
+void CardTableRS::verify_aligned_region_empty(MemRegion mr) {
if (!mr.is_empty()) {
jbyte* cur_entry = byte_for(mr.start());
jbyte* limit = byte_after(mr.last());
+ // The region mr may not start on a card boundary so
+ // the first card may reflect a write to the space
+ // just prior to mr.
+ if (!is_aligned(mr.start())) {
+ cur_entry++;
+ }
for (;cur_entry < limit; cur_entry++) {
guarantee(*cur_entry == CardTableModRefBS::clean_card,
"Unexpected dirty card found");
}
}