< prev index next >

src/share/vm/gc/g1/heapRegion.cpp

Print this page
rev 12906 : [mq]: gc_interface


  34 #include "gc/g1/heapRegionRemSet.hpp"
  35 #include "gc/g1/heapRegionTracer.hpp"
  36 #include "gc/shared/genOopClosures.inline.hpp"
  37 #include "gc/shared/space.inline.hpp"
  38 #include "logging/log.hpp"
  39 #include "memory/iterator.hpp"
  40 #include "memory/resourceArea.hpp"
  41 #include "oops/oop.inline.hpp"
  42 #include "runtime/atomic.hpp"
  43 #include "runtime/orderAccess.inline.hpp"
  44 
  45 int    HeapRegion::LogOfHRGrainBytes = 0;
  46 int    HeapRegion::LogOfHRGrainWords = 0;
  47 size_t HeapRegion::GrainBytes        = 0;
  48 size_t HeapRegion::GrainWords        = 0;
  49 size_t HeapRegion::CardsPerRegion    = 0;
  50 
  51 HeapRegionDCTOC::HeapRegionDCTOC(G1CollectedHeap* g1,
  52                                  HeapRegion* hr,
  53                                  G1ParPushHeapRSClosure* cl,
  54                                  CardTableModRefBS::PrecisionStyle precision) :
  55   DirtyCardToOopClosure(hr, cl, precision, NULL),
  56   _hr(hr), _rs_scan(cl), _g1(g1) { }
  57 
  58 void HeapRegionDCTOC::walk_mem_region(MemRegion mr,
  59                                       HeapWord* bottom,
  60                                       HeapWord* top) {
  61   G1CollectedHeap* g1h = _g1;
  62   size_t oop_size;
  63   HeapWord* cur = bottom;
  64 
  65   // Start filtering what we add to the remembered set. If the object is
  66   // not considered dead, either because it is marked (in the mark bitmap)
  67   // or it was allocated after marking finished, then we add it. Otherwise
  68   // we can safely ignore the object.
  69   if (!g1h->is_obj_dead(oop(cur))) {
  70     oop_size = oop(cur)->oop_iterate_size(_rs_scan, mr);
  71   } else {
  72     oop_size = _hr->block_size(cur);
  73   }
  74 


 131   region_size_log = log2_long((jlong) region_size);
 132 
 133   // Now, set up the globals.
 134   guarantee(LogOfHRGrainBytes == 0, "we should only set it once");
 135   LogOfHRGrainBytes = region_size_log;
 136 
 137   guarantee(LogOfHRGrainWords == 0, "we should only set it once");
 138   LogOfHRGrainWords = LogOfHRGrainBytes - LogHeapWordSize;
 139 
 140   guarantee(GrainBytes == 0, "we should only set it once");
 141   // The cast to int is safe, given that we've bounded region_size by
 142   // MIN_REGION_SIZE and MAX_REGION_SIZE.
 143   GrainBytes = region_size;
 144   log_info(gc, heap)("Heap region size: " SIZE_FORMAT "M", GrainBytes / M);
 145 
 146   guarantee(GrainWords == 0, "we should only set it once");
 147   GrainWords = GrainBytes >> LogHeapWordSize;
 148   guarantee((size_t) 1 << LogOfHRGrainWords == GrainWords, "sanity");
 149 
 150   guarantee(CardsPerRegion == 0, "we should only set it once");
 151   CardsPerRegion = GrainBytes >> CardTableModRefBS::card_shift;
 152 
 153   if (G1HeapRegionSize != GrainBytes) {
 154     FLAG_SET_ERGO(size_t, G1HeapRegionSize, GrainBytes);
 155   }
 156 }
 157 
 158 void HeapRegion::reset_after_compaction() {
 159   G1ContiguousSpace::reset_after_compaction();
 160   // After a compaction the mark bitmap is invalid, so we must
 161   // treat all objects as being inside the unmarked area.
 162   zero_marked_bytes();
 163   init_top_at_mark_start();
 164 }
 165 
 166 void HeapRegion::hr_clear(bool keep_remset, bool clear_space, bool locked) {
 167   assert(_humongous_start_region == NULL,
 168          "we should have already filtered out humongous regions");
 169   assert(!in_collection_set(),
 170          "Should not clear heap region %u in the collection set", hrm_index());
 171 


 178   if (!keep_remset) {
 179     if (locked) {
 180       rem_set()->clear_locked();
 181     } else {
 182       rem_set()->clear();
 183     }
 184   }
 185 
 186   zero_marked_bytes();
 187 
 188   init_top_at_mark_start();
 189   _gc_time_stamp = G1CollectedHeap::heap()->get_gc_time_stamp();
 190   if (clear_space) clear(SpaceDecorator::Mangle);
 191 }
 192 
 193 void HeapRegion::par_clear() {
 194   assert(used() == 0, "the region should have been already cleared");
 195   assert(capacity() == HeapRegion::GrainBytes, "should be back to normal");
 196   HeapRegionRemSet* hrrs = rem_set();
 197   hrrs->clear();
 198   CardTableModRefBS* ct_bs =
 199     barrier_set_cast<CardTableModRefBS>(G1CollectedHeap::heap()->barrier_set());
 200   ct_bs->clear(MemRegion(bottom(), end()));
 201 }
 202 
 203 void HeapRegion::calc_gc_efficiency() {
 204   // GC efficiency is the ratio of how much space would be
 205   // reclaimed over how long we predict it would take to reclaim it.
 206   G1CollectedHeap* g1h = G1CollectedHeap::heap();
 207   G1Policy* g1p = g1h->g1_policy();
 208 
 209   // Retrieve a prediction of the elapsed time for this region for
 210   // a mixed gc because the region will only be evacuated during a
 211   // mixed gc.
 212   double region_elapsed_time_ms =
 213     g1p->predict_region_elapsed_time_ms(this, false /* for_young_gc */);
 214   _gc_efficiency = (double) reclaimable_bytes() / region_elapsed_time_ms;
 215 }
 216 
 217 void HeapRegion::set_free() {
 218   report_region_type_change(G1HeapRegionTraceType::Free);
 219   _type.set_free();
 220 }


 601 void HeapRegion::print_on(outputStream* st) const {
 602   st->print("|%4u", this->_hrm_index);
 603   st->print("|" PTR_FORMAT ", " PTR_FORMAT ", " PTR_FORMAT,
 604             p2i(bottom()), p2i(top()), p2i(end()));
 605   st->print("|%3d%%", (int) ((double) used() * 100 / capacity()));
 606   st->print("|%2s", get_short_type_str());
 607   if (in_collection_set()) {
 608     st->print("|CS");
 609   } else {
 610     st->print("|  ");
 611   }
 612   st->print("|TS%3u", _gc_time_stamp);
 613   st->print("|AC%3u", allocation_context());
 614   st->print_cr("|TAMS " PTR_FORMAT ", " PTR_FORMAT "|",
 615                p2i(prev_top_at_mark_start()), p2i(next_top_at_mark_start()));
 616 }
 617 
 618 class G1VerificationClosure : public OopClosure {
 619 protected:
 620   G1CollectedHeap* _g1h;
 621   CardTableModRefBS* _bs;
 622   oop _containing_obj;
 623   bool _failures;
 624   int _n_failures;
 625   VerifyOption _vo;
 626 public:
 627   // _vo == UsePrevMarking -> use "prev" marking information,
 628   // _vo == UseNextMarking -> use "next" marking information,
 629   // _vo == UseMarkWord    -> use mark word from object header.
 630   G1VerificationClosure(G1CollectedHeap* g1h, VerifyOption vo) :
 631     _g1h(g1h), _bs(barrier_set_cast<CardTableModRefBS>(g1h->barrier_set())),
 632     _containing_obj(NULL), _failures(false), _n_failures(0), _vo(vo) {
 633   }
 634 
 635   void set_containing_obj(oop obj) {
 636     _containing_obj = obj;
 637   }
 638 
 639   bool failures() { return _failures; }
 640   int n_failures() { return _n_failures; }
 641 
 642   void print_object(outputStream* out, oop obj) {
 643 #ifdef PRODUCT
 644     Klass* k = obj->klass();
 645     const char* class_name = k->external_name();
 646     out->print_cr("class name %s", class_name);
 647 #else // PRODUCT
 648     obj->print_on(out);
 649 #endif // PRODUCT
 650   }
 651 };


 712 
 713   template <class T>
 714   void do_oop_work(T* p) {
 715     assert(_containing_obj != NULL, "Precondition");
 716     assert(!_g1h->is_obj_dead_cond(_containing_obj, _vo),
 717       "Precondition");
 718     verify_remembered_set(p);
 719   }
 720 
 721   template <class T>
 722   void verify_remembered_set(T* p) {
 723     T heap_oop = oopDesc::load_heap_oop(p);
 724     Log(gc, verify) log;
 725     if (!oopDesc::is_null(heap_oop)) {
 726       oop obj = oopDesc::decode_heap_oop_not_null(heap_oop);
 727       HeapRegion* from = _g1h->heap_region_containing((HeapWord*)p);
 728       HeapRegion* to = _g1h->heap_region_containing(obj);
 729       if (from != NULL && to != NULL &&
 730         from != to &&
 731         !to->is_pinned()) {
 732         jbyte cv_obj = *_bs->byte_for_const(_containing_obj);
 733         jbyte cv_field = *_bs->byte_for_const(p);
 734         const jbyte dirty = CardTableModRefBS::dirty_card_val();
 735 
 736         bool is_bad = !(from->is_young()
 737           || to->rem_set()->contains_reference(p)
 738           || !G1HRRSFlushLogBuffersOnVerify && // buffers were not flushed
 739           (_containing_obj->is_objArray() ?
 740           cv_field == dirty
 741           : cv_obj == dirty || cv_field == dirty));
 742         if (is_bad) {
 743           MutexLockerEx x(ParGCRareEvent_lock,
 744             Mutex::_no_safepoint_check_flag);
 745 
 746           if (!_failures) {
 747             log.error("----------");
 748           }
 749           log.error("Missing rem set entry:");
 750           log.error("Field " PTR_FORMAT " of obj " PTR_FORMAT ", in region " HR_FORMAT,
 751             p2i(p), p2i(_containing_obj), HR_FORMAT_PARAMS(from));
 752           ResourceMark rm;
 753           _containing_obj->print_on(log.error_stream());
 754           log.error("points to obj " PTR_FORMAT " in region " HR_FORMAT, p2i(obj), HR_FORMAT_PARAMS(to));


1062       blk->do_object(oop(p));
1063     }
1064     p += block_size(p);
1065   }
1066 }
1067 
1068 G1ContiguousSpace::G1ContiguousSpace(G1BlockOffsetTable* bot) :
1069   _bot_part(bot, this),
1070   _par_alloc_lock(Mutex::leaf, "OffsetTableContigSpace par alloc lock", true),
1071   _gc_time_stamp(0)
1072 {
1073 }
1074 
1075 void G1ContiguousSpace::initialize(MemRegion mr, bool clear_space, bool mangle_space) {
1076   CompactibleSpace::initialize(mr, clear_space, mangle_space);
1077   _top = bottom();
1078   _scan_top = bottom();
1079   set_saved_mark_word(NULL);
1080   reset_bot();
1081 }
1082 


  34 #include "gc/g1/heapRegionRemSet.hpp"
  35 #include "gc/g1/heapRegionTracer.hpp"
  36 #include "gc/shared/genOopClosures.inline.hpp"
  37 #include "gc/shared/space.inline.hpp"
  38 #include "logging/log.hpp"
  39 #include "memory/iterator.hpp"
  40 #include "memory/resourceArea.hpp"
  41 #include "oops/oop.inline.hpp"
  42 #include "runtime/atomic.hpp"
  43 #include "runtime/orderAccess.inline.hpp"
  44 
  45 int    HeapRegion::LogOfHRGrainBytes = 0;
  46 int    HeapRegion::LogOfHRGrainWords = 0;
  47 size_t HeapRegion::GrainBytes        = 0;
  48 size_t HeapRegion::GrainWords        = 0;
  49 size_t HeapRegion::CardsPerRegion    = 0;
  50 
  51 HeapRegionDCTOC::HeapRegionDCTOC(G1CollectedHeap* g1,
  52                                  HeapRegion* hr,
  53                                  G1ParPushHeapRSClosure* cl,
  54                                  CardTable::PrecisionStyle precision) :
  55   DirtyCardToOopClosure(hr, cl, precision, NULL),
  56   _hr(hr), _rs_scan(cl), _g1(g1) { }
  57 
  58 void HeapRegionDCTOC::walk_mem_region(MemRegion mr,
  59                                       HeapWord* bottom,
  60                                       HeapWord* top) {
  61   G1CollectedHeap* g1h = _g1;
  62   size_t oop_size;
  63   HeapWord* cur = bottom;
  64 
  65   // Start filtering what we add to the remembered set. If the object is
  66   // not considered dead, either because it is marked (in the mark bitmap)
  67   // or it was allocated after marking finished, then we add it. Otherwise
  68   // we can safely ignore the object.
  69   if (!g1h->is_obj_dead(oop(cur))) {
  70     oop_size = oop(cur)->oop_iterate_size(_rs_scan, mr);
  71   } else {
  72     oop_size = _hr->block_size(cur);
  73   }
  74 


 131   region_size_log = log2_long((jlong) region_size);
 132 
 133   // Now, set up the globals.
 134   guarantee(LogOfHRGrainBytes == 0, "we should only set it once");
 135   LogOfHRGrainBytes = region_size_log;
 136 
 137   guarantee(LogOfHRGrainWords == 0, "we should only set it once");
 138   LogOfHRGrainWords = LogOfHRGrainBytes - LogHeapWordSize;
 139 
 140   guarantee(GrainBytes == 0, "we should only set it once");
 141   // The cast to int is safe, given that we've bounded region_size by
 142   // MIN_REGION_SIZE and MAX_REGION_SIZE.
 143   GrainBytes = region_size;
 144   log_info(gc, heap)("Heap region size: " SIZE_FORMAT "M", GrainBytes / M);
 145 
 146   guarantee(GrainWords == 0, "we should only set it once");
 147   GrainWords = GrainBytes >> LogHeapWordSize;
 148   guarantee((size_t) 1 << LogOfHRGrainWords == GrainWords, "sanity");
 149 
 150   guarantee(CardsPerRegion == 0, "we should only set it once");
 151   CardsPerRegion = GrainBytes >> G1CardTable::card_shift;
 152 
 153   if (G1HeapRegionSize != GrainBytes) {
 154     FLAG_SET_ERGO(size_t, G1HeapRegionSize, GrainBytes);
 155   }
 156 }
 157 
 158 void HeapRegion::reset_after_compaction() {
 159   G1ContiguousSpace::reset_after_compaction();
 160   // After a compaction the mark bitmap is invalid, so we must
 161   // treat all objects as being inside the unmarked area.
 162   zero_marked_bytes();
 163   init_top_at_mark_start();
 164 }
 165 
 166 void HeapRegion::hr_clear(bool keep_remset, bool clear_space, bool locked) {
 167   assert(_humongous_start_region == NULL,
 168          "we should have already filtered out humongous regions");
 169   assert(!in_collection_set(),
 170          "Should not clear heap region %u in the collection set", hrm_index());
 171 


 178   if (!keep_remset) {
 179     if (locked) {
 180       rem_set()->clear_locked();
 181     } else {
 182       rem_set()->clear();
 183     }
 184   }
 185 
 186   zero_marked_bytes();
 187 
 188   init_top_at_mark_start();
 189   _gc_time_stamp = G1CollectedHeap::heap()->get_gc_time_stamp();
 190   if (clear_space) clear(SpaceDecorator::Mangle);
 191 }
 192 
 193 void HeapRegion::par_clear() {
 194   assert(used() == 0, "the region should have been already cleared");
 195   assert(capacity() == HeapRegion::GrainBytes, "should be back to normal");
 196   HeapRegionRemSet* hrrs = rem_set();
 197   hrrs->clear();
 198   G1CardTable* ct = G1CollectedHeap::heap()->g1_card_table();
 199   ct->clear(MemRegion(bottom(), end()));

 200 }
 201 
 202 void HeapRegion::calc_gc_efficiency() {
 203   // GC efficiency is the ratio of how much space would be
 204   // reclaimed over how long we predict it would take to reclaim it.
 205   G1CollectedHeap* g1h = G1CollectedHeap::heap();
 206   G1Policy* g1p = g1h->g1_policy();
 207 
 208   // Retrieve a prediction of the elapsed time for this region for
 209   // a mixed gc because the region will only be evacuated during a
 210   // mixed gc.
 211   double region_elapsed_time_ms =
 212     g1p->predict_region_elapsed_time_ms(this, false /* for_young_gc */);
 213   _gc_efficiency = (double) reclaimable_bytes() / region_elapsed_time_ms;
 214 }
 215 
 216 void HeapRegion::set_free() {
 217   report_region_type_change(G1HeapRegionTraceType::Free);
 218   _type.set_free();
 219 }


 600 void HeapRegion::print_on(outputStream* st) const {
 601   st->print("|%4u", this->_hrm_index);
 602   st->print("|" PTR_FORMAT ", " PTR_FORMAT ", " PTR_FORMAT,
 603             p2i(bottom()), p2i(top()), p2i(end()));
 604   st->print("|%3d%%", (int) ((double) used() * 100 / capacity()));
 605   st->print("|%2s", get_short_type_str());
 606   if (in_collection_set()) {
 607     st->print("|CS");
 608   } else {
 609     st->print("|  ");
 610   }
 611   st->print("|TS%3u", _gc_time_stamp);
 612   st->print("|AC%3u", allocation_context());
 613   st->print_cr("|TAMS " PTR_FORMAT ", " PTR_FORMAT "|",
 614                p2i(prev_top_at_mark_start()), p2i(next_top_at_mark_start()));
 615 }
 616 
 617 class G1VerificationClosure : public OopClosure {
 618 protected:
 619   G1CollectedHeap* _g1h;
 620   G1CardTable *_ct;
 621   oop _containing_obj;
 622   bool _failures;
 623   int _n_failures;
 624   VerifyOption _vo;
 625 public:
 626   // _vo == UsePrevMarking -> use "prev" marking information,
 627   // _vo == UseNextMarking -> use "next" marking information,
 628   // _vo == UseMarkWord    -> use mark word from object header.
 629   G1VerificationClosure(G1CollectedHeap* g1h, VerifyOption vo) :
 630     _g1h(g1h), _ct(g1h->g1_card_table()),
 631     _containing_obj(NULL), _failures(false), _n_failures(0), _vo(vo) {
 632   }
 633 
 634   void set_containing_obj(oop obj) {
 635     _containing_obj = obj;
 636   }
 637 
 638   bool failures() { return _failures; }
 639   int n_failures() { return _n_failures; }
 640 
 641   void print_object(outputStream* out, oop obj) {
 642 #ifdef PRODUCT
 643     Klass* k = obj->klass();
 644     const char* class_name = k->external_name();
 645     out->print_cr("class name %s", class_name);
 646 #else // PRODUCT
 647     obj->print_on(out);
 648 #endif // PRODUCT
 649   }
 650 };


 711 
 712   template <class T>
 713   void do_oop_work(T* p) {
 714     assert(_containing_obj != NULL, "Precondition");
 715     assert(!_g1h->is_obj_dead_cond(_containing_obj, _vo),
 716       "Precondition");
 717     verify_remembered_set(p);
 718   }
 719 
 720   template <class T>
 721   void verify_remembered_set(T* p) {
 722     T heap_oop = oopDesc::load_heap_oop(p);
 723     Log(gc, verify) log;
 724     if (!oopDesc::is_null(heap_oop)) {
 725       oop obj = oopDesc::decode_heap_oop_not_null(heap_oop);
 726       HeapRegion* from = _g1h->heap_region_containing((HeapWord*)p);
 727       HeapRegion* to = _g1h->heap_region_containing(obj);
 728       if (from != NULL && to != NULL &&
 729         from != to &&
 730         !to->is_pinned()) {
 731         jbyte cv_obj = *_ct->byte_for_const(_containing_obj);
 732         jbyte cv_field = *_ct->byte_for_const(p);
 733         const jbyte dirty = G1CardTable::dirty_card_val();
 734 
 735         bool is_bad = !(from->is_young()
 736           || to->rem_set()->contains_reference(p)
 737           || !G1HRRSFlushLogBuffersOnVerify && // buffers were not flushed
 738           (_containing_obj->is_objArray() ?
 739           cv_field == dirty
 740           : cv_obj == dirty || cv_field == dirty));
 741         if (is_bad) {
 742           MutexLockerEx x(ParGCRareEvent_lock,
 743             Mutex::_no_safepoint_check_flag);
 744 
 745           if (!_failures) {
 746             log.error("----------");
 747           }
 748           log.error("Missing rem set entry:");
 749           log.error("Field " PTR_FORMAT " of obj " PTR_FORMAT ", in region " HR_FORMAT,
 750             p2i(p), p2i(_containing_obj), HR_FORMAT_PARAMS(from));
 751           ResourceMark rm;
 752           _containing_obj->print_on(log.error_stream());
 753           log.error("points to obj " PTR_FORMAT " in region " HR_FORMAT, p2i(obj), HR_FORMAT_PARAMS(to));


1061       blk->do_object(oop(p));
1062     }
1063     p += block_size(p);
1064   }
1065 }
1066 
1067 G1ContiguousSpace::G1ContiguousSpace(G1BlockOffsetTable* bot) :
1068   _bot_part(bot, this),
1069   _par_alloc_lock(Mutex::leaf, "OffsetTableContigSpace par alloc lock", true),
1070   _gc_time_stamp(0)
1071 {
1072 }
1073 
1074 void G1ContiguousSpace::initialize(MemRegion mr, bool clear_space, bool mangle_space) {
1075   CompactibleSpace::initialize(mr, clear_space, mangle_space);
1076   _top = bottom();
1077   _scan_top = bottom();
1078   set_saved_mark_word(NULL);
1079   reset_bot();
1080 }

< prev index next >