< prev index next >

src/hotspot/share/gc/g1/g1RemSet.cpp

Print this page




   7  * published by the Free Software Foundation.
   8  *
   9  * This code is distributed in the hope that it will be useful, but WITHOUT
  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  *
  23  */
  24 
  25 #include "precompiled.hpp"
  26 #include "gc/g1/dirtyCardQueue.hpp"

  27 #include "gc/g1/g1BlockOffsetTable.inline.hpp"
  28 #include "gc/g1/g1CardTable.inline.hpp"
  29 #include "gc/g1/g1CollectedHeap.inline.hpp"
  30 #include "gc/g1/g1ConcurrentRefine.hpp"
  31 #include "gc/g1/g1FromCardCache.hpp"
  32 #include "gc/g1/g1GCPhaseTimes.hpp"
  33 #include "gc/g1/g1HotCardCache.hpp"
  34 #include "gc/g1/g1OopClosures.inline.hpp"
  35 #include "gc/g1/g1RemSet.hpp"
  36 #include "gc/g1/heapRegion.inline.hpp"
  37 #include "gc/g1/heapRegionManager.inline.hpp"
  38 #include "gc/g1/heapRegionRemSet.hpp"
  39 #include "gc/shared/gcTraceTime.inline.hpp"
  40 #include "gc/shared/suspendibleThreadSet.hpp"
  41 #include "memory/iterator.hpp"
  42 #include "memory/resourceArea.hpp"
  43 #include "oops/access.inline.hpp"
  44 #include "oops/oop.inline.hpp"
  45 #include "utilities/align.hpp"
  46 #include "utilities/globalDefinitions.hpp"


 471   // Apply the closure to all remaining log entries.
 472   _g1->iterate_dirty_card_closure(&refine_card_cl, worker_i);
 473 
 474   G1GCPhaseTimes* p = _g1p->phase_times();
 475   p->record_thread_work_item(G1GCPhaseTimes::UpdateRS, worker_i, refine_card_cl.cards_scanned(), G1GCPhaseTimes::UpdateRSScannedCards);
 476   p->record_thread_work_item(G1GCPhaseTimes::UpdateRS, worker_i, refine_card_cl.cards_skipped(), G1GCPhaseTimes::UpdateRSSkippedCards);
 477 }
 478 
 479 void G1RemSet::cleanupHRRS() {
 480   HeapRegionRemSet::cleanup();
 481 }
 482 
 483 void G1RemSet::oops_into_collection_set_do(G1ParScanThreadState* pss,
 484                                            CodeBlobClosure* heap_region_codeblobs,
 485                                            uint worker_i) {
 486   update_rem_set(pss, worker_i);
 487   scan_rem_set(pss, heap_region_codeblobs, worker_i);;
 488 }
 489 
 490 void G1RemSet::prepare_for_oops_into_collection_set_do() {
 491   DirtyCardQueueSet& dcqs = JavaThread::dirty_card_queue_set();
 492   dcqs.concatenate_logs();
 493 
 494   _scan_state->reset();
 495 }
 496 
 497 void G1RemSet::cleanup_after_oops_into_collection_set_do() {
 498   G1GCPhaseTimes* phase_times = _g1->g1_policy()->phase_times();
 499 
 500   // Set all cards back to clean.
 501   double start = os::elapsedTime();
 502   _scan_state->clear_card_table(_g1->workers());
 503   phase_times->record_clear_ct_time((os::elapsedTime() - start) * 1000.0);
 504 }
 505 
 506 inline void check_card_ptr(jbyte* card_ptr, G1CardTable* ct) {
 507 #ifdef ASSERT
 508   G1CollectedHeap* g1 = G1CollectedHeap::heap();
 509   assert(g1->is_in_exact(ct->addr_for(card_ptr)),
 510          "Card at " PTR_FORMAT " index " SIZE_FORMAT " representing heap at " PTR_FORMAT " (%u) must be in committed heap",
 511          p2i(card_ptr),


 624   assert(!dirty_region.is_empty(), "sanity");
 625 
 626   G1ConcurrentRefineOopClosure conc_refine_cl(_g1, worker_i);
 627 
 628   bool card_processed =
 629     r->oops_on_card_seq_iterate_careful<false>(dirty_region, &conc_refine_cl);
 630 
 631   // If unable to process the card then we encountered an unparsable
 632   // part of the heap (e.g. a partially allocated object) while
 633   // processing a stale card.  Despite the card being stale, redirty
 634   // and re-enqueue, because we've already cleaned the card.  Without
 635   // this we could incorrectly discard a non-stale card.
 636   if (!card_processed) {
 637     // The card might have gotten re-dirtied and re-enqueued while we
 638     // worked.  (In fact, it's pretty likely.)
 639     if (*card_ptr != G1CardTable::dirty_card_val()) {
 640       *card_ptr = G1CardTable::dirty_card_val();
 641       MutexLockerEx x(Shared_DirtyCardQ_lock,
 642                       Mutex::_no_safepoint_check_flag);
 643       DirtyCardQueue* sdcq =
 644         JavaThread::dirty_card_queue_set().shared_dirty_card_queue();
 645       sdcq->enqueue(card_ptr);
 646     }
 647   } else {
 648     _num_conc_refined_cards++; // Unsynchronized update, only used for logging.
 649   }
 650 }
 651 
 652 bool G1RemSet::refine_card_during_gc(jbyte* card_ptr,
 653                                      G1ScanObjsDuringUpdateRSClosure* update_rs_cl) {
 654   assert(_g1->is_gc_active(), "Only call during GC");
 655 
 656   check_card_ptr(card_ptr, _ct);
 657 
 658   // If the card is no longer dirty, nothing to do. This covers cards that were already
 659   // scanned as parts of the remembered sets.
 660   if (*card_ptr != G1CardTable::dirty_card_val()) {
 661     return false;
 662   }
 663 
 664   // We claim lazily (so races are possible but they're benign), which reduces the




   7  * published by the Free Software Foundation.
   8  *
   9  * This code is distributed in the hope that it will be useful, but WITHOUT
  10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
  11  * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
  12  * version 2 for more details (a copy is included in the LICENSE file that
  13  * accompanied this code).
  14  *
  15  * You should have received a copy of the GNU General Public License version
  16  * 2 along with this work; if not, write to the Free Software Foundation,
  17  * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
  18  *
  19  * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  20  * or visit www.oracle.com if you need additional information or have any
  21  * questions.
  22  *
  23  */
  24 
  25 #include "precompiled.hpp"
  26 #include "gc/g1/dirtyCardQueue.hpp"
  27 #include "gc/g1/g1BarrierSet.hpp"
  28 #include "gc/g1/g1BlockOffsetTable.inline.hpp"
  29 #include "gc/g1/g1CardTable.inline.hpp"
  30 #include "gc/g1/g1CollectedHeap.inline.hpp"
  31 #include "gc/g1/g1ConcurrentRefine.hpp"
  32 #include "gc/g1/g1FromCardCache.hpp"
  33 #include "gc/g1/g1GCPhaseTimes.hpp"
  34 #include "gc/g1/g1HotCardCache.hpp"
  35 #include "gc/g1/g1OopClosures.inline.hpp"
  36 #include "gc/g1/g1RemSet.hpp"
  37 #include "gc/g1/heapRegion.inline.hpp"
  38 #include "gc/g1/heapRegionManager.inline.hpp"
  39 #include "gc/g1/heapRegionRemSet.hpp"
  40 #include "gc/shared/gcTraceTime.inline.hpp"
  41 #include "gc/shared/suspendibleThreadSet.hpp"
  42 #include "memory/iterator.hpp"
  43 #include "memory/resourceArea.hpp"
  44 #include "oops/access.inline.hpp"
  45 #include "oops/oop.inline.hpp"
  46 #include "utilities/align.hpp"
  47 #include "utilities/globalDefinitions.hpp"


 472   // Apply the closure to all remaining log entries.
 473   _g1->iterate_dirty_card_closure(&refine_card_cl, worker_i);
 474 
 475   G1GCPhaseTimes* p = _g1p->phase_times();
 476   p->record_thread_work_item(G1GCPhaseTimes::UpdateRS, worker_i, refine_card_cl.cards_scanned(), G1GCPhaseTimes::UpdateRSScannedCards);
 477   p->record_thread_work_item(G1GCPhaseTimes::UpdateRS, worker_i, refine_card_cl.cards_skipped(), G1GCPhaseTimes::UpdateRSSkippedCards);
 478 }
 479 
 480 void G1RemSet::cleanupHRRS() {
 481   HeapRegionRemSet::cleanup();
 482 }
 483 
 484 void G1RemSet::oops_into_collection_set_do(G1ParScanThreadState* pss,
 485                                            CodeBlobClosure* heap_region_codeblobs,
 486                                            uint worker_i) {
 487   update_rem_set(pss, worker_i);
 488   scan_rem_set(pss, heap_region_codeblobs, worker_i);;
 489 }
 490 
 491 void G1RemSet::prepare_for_oops_into_collection_set_do() {
 492   DirtyCardQueueSet& dcqs = G1BarrierSet::dirty_card_queue_set();
 493   dcqs.concatenate_logs();
 494 
 495   _scan_state->reset();
 496 }
 497 
 498 void G1RemSet::cleanup_after_oops_into_collection_set_do() {
 499   G1GCPhaseTimes* phase_times = _g1->g1_policy()->phase_times();
 500 
 501   // Set all cards back to clean.
 502   double start = os::elapsedTime();
 503   _scan_state->clear_card_table(_g1->workers());
 504   phase_times->record_clear_ct_time((os::elapsedTime() - start) * 1000.0);
 505 }
 506 
 507 inline void check_card_ptr(jbyte* card_ptr, G1CardTable* ct) {
 508 #ifdef ASSERT
 509   G1CollectedHeap* g1 = G1CollectedHeap::heap();
 510   assert(g1->is_in_exact(ct->addr_for(card_ptr)),
 511          "Card at " PTR_FORMAT " index " SIZE_FORMAT " representing heap at " PTR_FORMAT " (%u) must be in committed heap",
 512          p2i(card_ptr),


 625   assert(!dirty_region.is_empty(), "sanity");
 626 
 627   G1ConcurrentRefineOopClosure conc_refine_cl(_g1, worker_i);
 628 
 629   bool card_processed =
 630     r->oops_on_card_seq_iterate_careful<false>(dirty_region, &conc_refine_cl);
 631 
 632   // If unable to process the card then we encountered an unparsable
 633   // part of the heap (e.g. a partially allocated object) while
 634   // processing a stale card.  Despite the card being stale, redirty
 635   // and re-enqueue, because we've already cleaned the card.  Without
 636   // this we could incorrectly discard a non-stale card.
 637   if (!card_processed) {
 638     // The card might have gotten re-dirtied and re-enqueued while we
 639     // worked.  (In fact, it's pretty likely.)
 640     if (*card_ptr != G1CardTable::dirty_card_val()) {
 641       *card_ptr = G1CardTable::dirty_card_val();
 642       MutexLockerEx x(Shared_DirtyCardQ_lock,
 643                       Mutex::_no_safepoint_check_flag);
 644       DirtyCardQueue* sdcq =
 645         G1BarrierSet::dirty_card_queue_set().shared_dirty_card_queue();
 646       sdcq->enqueue(card_ptr);
 647     }
 648   } else {
 649     _num_conc_refined_cards++; // Unsynchronized update, only used for logging.
 650   }
 651 }
 652 
 653 bool G1RemSet::refine_card_during_gc(jbyte* card_ptr,
 654                                      G1ScanObjsDuringUpdateRSClosure* update_rs_cl) {
 655   assert(_g1->is_gc_active(), "Only call during GC");
 656 
 657   check_card_ptr(card_ptr, _ct);
 658 
 659   // If the card is no longer dirty, nothing to do. This covers cards that were already
 660   // scanned as parts of the remembered sets.
 661   if (*card_ptr != G1CardTable::dirty_card_val()) {
 662     return false;
 663   }
 664 
 665   // We claim lazily (so races are possible but they're benign), which reduces the


< prev index next >