comparison src/share/vm/gc_implementation/concurrentMarkSweep/concurrentMarkSweepGeneration.cpp @ 11973:7b06ae405d7b

6990419: CMS Remaining work for 6572569: consistently skewed work distribution in (long) re-mark pauses Reviewed-by: rasbold, tschatzl, jmasa Contributed-by: yamauchi@google.com
author jmasa
date Tue, 23 Jul 2013 09:49:11 -0700
parents 71180a6e5080
children ca9dedeebdec
comparison
equal deleted inserted replaced
11135:2285b4a0a4e6 11973:7b06ae405d7b
567 // Construct the is_alive_closure with _span & markBitMap 567 // Construct the is_alive_closure with _span & markBitMap
568 _is_alive_closure(_span, &_markBitMap), 568 _is_alive_closure(_span, &_markBitMap),
569 _restart_addr(NULL), 569 _restart_addr(NULL),
570 _overflow_list(NULL), 570 _overflow_list(NULL),
571 _stats(cmsGen), 571 _stats(cmsGen),
572 _eden_chunk_lock(new Mutex(Mutex::leaf + 1, "CMS_eden_chunk_lock", true)),
572 _eden_chunk_array(NULL), // may be set in ctor body 573 _eden_chunk_array(NULL), // may be set in ctor body
573 _eden_chunk_capacity(0), // -- ditto -- 574 _eden_chunk_capacity(0), // -- ditto --
574 _eden_chunk_index(0), // -- ditto -- 575 _eden_chunk_index(0), // -- ditto --
575 _survivor_plab_array(NULL), // -- ditto -- 576 _survivor_plab_array(NULL), // -- ditto --
576 _survivor_chunk_array(NULL), // -- ditto -- 577 _survivor_chunk_array(NULL), // -- ditto --
2135 // For a mark-sweep, compute_new_size() will be called 2136 // For a mark-sweep, compute_new_size() will be called
2136 // in the heap's do_collection() method. 2137 // in the heap's do_collection() method.
2137 } 2138 }
2138 2139
2139 2140
2141 void CMSCollector::print_eden_and_survivor_chunk_arrays() {
2142 DefNewGeneration* dng = _young_gen->as_DefNewGeneration();
2143 EdenSpace* eden_space = dng->eden();
2144 ContiguousSpace* from_space = dng->from();
2145 ContiguousSpace* to_space = dng->to();
2146 // Eden
2147 if (_eden_chunk_array != NULL) {
2148 gclog_or_tty->print_cr("eden " PTR_FORMAT "-" PTR_FORMAT "-" PTR_FORMAT "(" SIZE_FORMAT ")",
2149 eden_space->bottom(), eden_space->top(),
2150 eden_space->end(), eden_space->capacity());
2151 gclog_or_tty->print_cr("_eden_chunk_index=" SIZE_FORMAT ", "
2152 "_eden_chunk_capacity=" SIZE_FORMAT,
2153 _eden_chunk_index, _eden_chunk_capacity);
2154 for (size_t i = 0; i < _eden_chunk_index; i++) {
2155 gclog_or_tty->print_cr("_eden_chunk_array[" SIZE_FORMAT "]=" PTR_FORMAT,
2156 i, _eden_chunk_array[i]);
2157 }
2158 }
2159 // Survivor
2160 if (_survivor_chunk_array != NULL) {
2161 gclog_or_tty->print_cr("survivor " PTR_FORMAT "-" PTR_FORMAT "-" PTR_FORMAT "(" SIZE_FORMAT ")",
2162 from_space->bottom(), from_space->top(),
2163 from_space->end(), from_space->capacity());
2164 gclog_or_tty->print_cr("_survivor_chunk_index=" SIZE_FORMAT ", "
2165 "_survivor_chunk_capacity=" SIZE_FORMAT,
2166 _survivor_chunk_index, _survivor_chunk_capacity);
2167 for (size_t i = 0; i < _survivor_chunk_index; i++) {
2168 gclog_or_tty->print_cr("_survivor_chunk_array[" SIZE_FORMAT "]=" PTR_FORMAT,
2169 i, _survivor_chunk_array[i]);
2170 }
2171 }
2172 }
2173
2140 void CMSCollector::getFreelistLocks() const { 2174 void CMSCollector::getFreelistLocks() const {
2141 // Get locks for all free lists in all generations that this 2175 // Get locks for all free lists in all generations that this
2142 // collector is responsible for 2176 // collector is responsible for
2143 _cmsGen->freelistLock()->lock_without_safepoint_check(); 2177 _cmsGen->freelistLock()->lock_without_safepoint_check();
2144 } 2178 }
3643 ClassLoaderDataGraph::remember_new_clds(true); 3677 ClassLoaderDataGraph::remember_new_clds(true);
3644 3678
3645 // Whenever a CLD is found, it will be claimed before proceeding to mark 3679 // Whenever a CLD is found, it will be claimed before proceeding to mark
3646 // the klasses. The claimed marks need to be cleared before marking starts. 3680 // the klasses. The claimed marks need to be cleared before marking starts.
3647 ClassLoaderDataGraph::clear_claimed_marks(); 3681 ClassLoaderDataGraph::clear_claimed_marks();
3682
3683 if (CMSPrintEdenSurvivorChunks) {
3684 print_eden_and_survivor_chunk_arrays();
3685 }
3648 3686
3649 CMKlassClosure klass_closure(&notOlder); 3687 CMKlassClosure klass_closure(&notOlder);
3650 { 3688 {
3651 COMPILER2_PRESENT(DerivedPointerTableDeactivate dpt_deact;) 3689 COMPILER2_PRESENT(DerivedPointerTableDeactivate dpt_deact;)
3652 gch->rem_set()->prepare_for_younger_refs_iterate(false); // Not parallel. 3690 gch->rem_set()->prepare_for_younger_refs_iterate(false); // Not parallel.
4415 assert(Thread::current()->is_ConcurrentGC_thread(), "Wrong thread"); 4453 assert(Thread::current()->is_ConcurrentGC_thread(), "Wrong thread");
4416 verify_work_stacks_empty(); 4454 verify_work_stacks_empty();
4417 verify_overflow_empty(); 4455 verify_overflow_empty();
4418 _abort_preclean = false; 4456 _abort_preclean = false;
4419 if (CMSPrecleaningEnabled) { 4457 if (CMSPrecleaningEnabled) {
4420 _eden_chunk_index = 0; 4458 if (!CMSEdenChunksRecordAlways) {
4459 _eden_chunk_index = 0;
4460 }
4421 size_t used = get_eden_used(); 4461 size_t used = get_eden_used();
4422 size_t capacity = get_eden_capacity(); 4462 size_t capacity = get_eden_capacity();
4423 // Don't start sampling unless we will get sufficiently 4463 // Don't start sampling unless we will get sufficiently
4424 // many samples. 4464 // many samples.
4425 if (used < (capacity/(CMSScheduleRemarkSamplingRatio * 100) 4465 if (used < (capacity/(CMSScheduleRemarkSamplingRatio * 100)
4524 assert(ConcurrentMarkSweepThread::cms_thread_has_cms_token(), 4564 assert(ConcurrentMarkSweepThread::cms_thread_has_cms_token(),
4525 "Should collect samples while holding CMS token"); 4565 "Should collect samples while holding CMS token");
4526 if (!_start_sampling) { 4566 if (!_start_sampling) {
4527 return; 4567 return;
4528 } 4568 }
4529 if (_eden_chunk_array) { 4569 // When CMSEdenChunksRecordAlways is true, the eden chunk array
4570 // is populated by the young generation.
4571 if (_eden_chunk_array != NULL && !CMSEdenChunksRecordAlways) {
4530 if (_eden_chunk_index < _eden_chunk_capacity) { 4572 if (_eden_chunk_index < _eden_chunk_capacity) {
4531 _eden_chunk_array[_eden_chunk_index] = *_top_addr; // take sample 4573 _eden_chunk_array[_eden_chunk_index] = *_top_addr; // take sample
4532 assert(_eden_chunk_array[_eden_chunk_index] <= *_end_addr, 4574 assert(_eden_chunk_array[_eden_chunk_index] <= *_end_addr,
4533 "Unexpected state of Eden"); 4575 "Unexpected state of Eden");
4534 // We'd like to check that what we just sampled is an oop-start address; 4576 // We'd like to check that what we just sampled is an oop-start address;
5008 // so here just in case a scavenge did not happen. 5050 // so here just in case a scavenge did not happen.
5009 gch->ensure_parsability(false); // fill TLAB's, but no need to retire them 5051 gch->ensure_parsability(false); // fill TLAB's, but no need to retire them
5010 // Update the saved marks which may affect the root scans. 5052 // Update the saved marks which may affect the root scans.
5011 gch->save_marks(); 5053 gch->save_marks();
5012 5054
5055 if (CMSPrintEdenSurvivorChunks) {
5056 print_eden_and_survivor_chunk_arrays();
5057 }
5058
5013 { 5059 {
5014 COMPILER2_PRESENT(DerivedPointerTableDeactivate dpt_deact;) 5060 COMPILER2_PRESENT(DerivedPointerTableDeactivate dpt_deact;)
5015 5061
5016 // Note on the role of the mod union table: 5062 // Note on the role of the mod union table:
5017 // Since the marker in "markFromRoots" marks concurrently with 5063 // Since the marker in "markFromRoots" marks concurrently with
5526 gclog_or_tty->print("\n\t(%d: stole %d oops)", i, num_steals); 5572 gclog_or_tty->print("\n\t(%d: stole %d oops)", i, num_steals);
5527 } 5573 }
5528 ) 5574 )
5529 assert(work_q->size() == 0 && _collector->overflow_list_is_empty(), 5575 assert(work_q->size() == 0 && _collector->overflow_list_is_empty(),
5530 "Else our work is not yet done"); 5576 "Else our work is not yet done");
5577 }
5578
5579 // Record object boundaries in _eden_chunk_array by sampling the eden
5580 // top in the slow-path eden object allocation code path and record
5581 // the boundaries, if CMSEdenChunksRecordAlways is true. If
5582 // CMSEdenChunksRecordAlways is false, we use the other asynchronous
5583 // sampling in sample_eden() that activates during the part of the
5584 // preclean phase.
5585 void CMSCollector::sample_eden_chunk() {
5586 if (CMSEdenChunksRecordAlways && _eden_chunk_array != NULL) {
5587 if (_eden_chunk_lock->try_lock()) {
5588 // Record a sample. This is the critical section. The contents
5589 // of the _eden_chunk_array have to be non-decreasing in the
5590 // address order.
5591 _eden_chunk_array[_eden_chunk_index] = *_top_addr;
5592 assert(_eden_chunk_array[_eden_chunk_index] <= *_end_addr,
5593 "Unexpected state of Eden");
5594 if (_eden_chunk_index == 0 ||
5595 ((_eden_chunk_array[_eden_chunk_index] > _eden_chunk_array[_eden_chunk_index-1]) &&
5596 (pointer_delta(_eden_chunk_array[_eden_chunk_index],
5597 _eden_chunk_array[_eden_chunk_index-1]) >= CMSSamplingGrain))) {
5598 _eden_chunk_index++; // commit sample
5599 }
5600 _eden_chunk_lock->unlock();
5601 }
5602 }
5531 } 5603 }
5532 5604
5533 // Return a thread-local PLAB recording array, as appropriate. 5605 // Return a thread-local PLAB recording array, as appropriate.
5534 void* CMSCollector::get_data_recorder(int thr_num) { 5606 void* CMSCollector::get_data_recorder(int thr_num) {
5535 if (_survivor_plab_array != NULL && 5607 if (_survivor_plab_array != NULL &&
9375 9447
9376 default: 9448 default:
9377 ShouldNotReachHere(); 9449 ShouldNotReachHere();
9378 } 9450 }
9379 } 9451 }
9380