< prev index next >

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

Print this page
rev 52675 : 8213890: Implementation of JEP 344: Abortable Mixed Collections for G1
Reviewed-by:
Contributed-by: erik.helin@oracle.com, stefan.johansson@oracle.com
rev 52676 : imported patch AMGC-impl
rev 52677 : imported patch AMGC-tsch-rev1
rev 52678 : imported patch AMGC-tsch-rev1-optcset
rev 52680 : imported patch AMGC-tsch-rev2
rev 52681 : [mq]: AMGC-kbar-rev1


   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/g1CollectedHeap.inline.hpp"
  27 #include "gc/g1/g1CollectionSet.hpp"
  28 #include "gc/g1/g1CollectorState.hpp"

  29 #include "gc/g1/g1Policy.hpp"
  30 #include "gc/g1/heapRegion.inline.hpp"
  31 #include "gc/g1/heapRegionRemSet.hpp"
  32 #include "gc/g1/heapRegionSet.hpp"
  33 #include "logging/logStream.hpp"
  34 #include "utilities/debug.hpp"
  35 #include "utilities/globalDefinitions.hpp"
  36 #include "utilities/quickSort.hpp"
  37 
  38 G1CollectorState* G1CollectionSet::collector_state() {
  39   return _g1h->collector_state();
  40 }
  41 
  42 G1GCPhaseTimes* G1CollectionSet::phase_times() {
  43   return _policy->phase_times();
  44 }
  45 
  46 CollectionSetChooser* G1CollectionSet::cset_chooser() {
  47   return _cset_chooser;
  48 }


  87   assert_at_safepoint_on_vm_thread();
  88 
  89   _eden_region_length     = eden_cset_region_length;
  90   _survivor_region_length = survivor_cset_region_length;
  91 
  92   assert((size_t) young_region_length() == _collection_set_cur_length,
  93          "Young region length %u should match collection set length " SIZE_FORMAT, young_region_length(), _collection_set_cur_length);
  94 
  95   _old_region_length      = 0;
  96   _optional_region_length = 0;
  97 }
  98 
  99 void G1CollectionSet::initialize(uint max_region_length) {
 100   guarantee(_collection_set_regions == NULL, "Must only initialize once.");
 101   _collection_set_max_length = max_region_length;
 102   _collection_set_regions = NEW_C_HEAP_ARRAY(uint, max_region_length, mtGC);
 103 }
 104 
 105 void G1CollectionSet::initialize_optional(uint max_length) {
 106   assert(_optional_regions == NULL, "Already initialized");


 107   _optional_region_max_length = max_length;
 108   _optional_regions = NEW_C_HEAP_ARRAY(HeapRegion*, _optional_region_max_length, mtGC);
 109 }
 110 
 111 void G1CollectionSet::free_optional_regions() {
 112   _optional_region_length = 0;
 113   _optional_region_max_length = 0;
 114   if (_optional_regions != NULL) {
 115     FREE_C_HEAP_ARRAY(HeapRegion*, _optional_regions);
 116     _optional_regions = NULL;
 117   }
 118 }
 119 
 120 void G1CollectionSet::set_recorded_rs_lengths(size_t rs_lengths) {
 121   _recorded_rs_lengths = rs_lengths;
 122 }
 123 
 124 // Add the heap region at the head of the non-incremental collection set
 125 void G1CollectionSet::add_old_region(HeapRegion* hr) {
 126   assert_at_safepoint_on_vm_thread();


 432   double young_end_time_sec = os::elapsedTime();
 433   phase_times()->record_young_cset_choice_time_ms((young_end_time_sec - young_start_time_sec) * 1000.0);
 434 
 435   return time_remaining_ms;
 436 }
 437 
 438 void G1CollectionSet::add_as_old(HeapRegion* hr) {
 439   cset_chooser()->pop(); // already have region via peek()
 440   _g1h->old_set_remove(hr);
 441   add_old_region(hr);
 442 }
 443 
 444 void G1CollectionSet::add_as_optional(HeapRegion* hr) {
 445   assert(_optional_regions != NULL, "Must not be called before array is allocated");
 446   cset_chooser()->pop(); // already have region via peek()
 447   _g1h->old_set_remove(hr);
 448   add_optional_region(hr);
 449 }
 450 
 451 bool G1CollectionSet::optional_is_full() {

 452   return _optional_region_length == _optional_region_max_length;
 453 }
 454 
 455 void G1CollectionSet::clear_optional_region(const HeapRegion* hr) {
 456   assert(_optional_regions != NULL, "Must not be called before array is allocated");
 457   uint index = hr->index_in_opt_cset();
 458   _optional_regions[index] = NULL;
 459 }
 460 
 461 static int compare_region_idx(const uint a, const uint b) {
 462   if (a > b) {
 463     return 1;
 464   } else if (a == b) {
 465     return 0;
 466   } else {
 467     return -1;
 468   }
 469 }
 470 
 471 void G1CollectionSet::finalize_old_part(double time_remaining_ms) {


 613     HeapRegion* hr = region_at(i);
 614     _cset->clear_optional_region(hr);
 615     if (hr->evacuation_failed()){
 616       _evacuation_failed = true;
 617     }
 618   }
 619   _current_index = _current_limit;
 620 }
 621 
 622 bool G1OptionalCSet::evacuation_failed() {
 623   return _evacuation_failed;
 624 }
 625 
 626 G1OptionalCSet::~G1OptionalCSet() {
 627   G1CollectedHeap* g1h = G1CollectedHeap::heap();
 628   while (!is_empty()) {
 629     // We want to return regions not evacuated to the
 630     // chooser in reverse order to maintain the old order.
 631     HeapRegion* hr = _cset->remove_last_optional_region();
 632     assert(hr != NULL, "Should be valid region left");

 633     g1h->old_set_add(hr);
 634     g1h->clear_in_cset(hr);
 635     hr->set_index_in_opt_cset(InvalidCSetIndex);
 636     _cset->cset_chooser()->push(hr);
 637   }
 638   _cset->free_optional_regions();
 639 }
 640 
 641 uint G1OptionalCSet::size() {
 642   return _cset->optional_region_length() - _current_index;
 643 }
 644 
 645 bool G1OptionalCSet::is_empty() {
 646   return size() == 0;
 647 }
 648 
 649 void G1OptionalCSet::prepare_to_evacuate_optional_region(HeapRegion* hr) {
 650   log_trace(gc, cset)("Adding region %u for optional evacuation", hr->hrm_index());
 651   G1CollectedHeap::heap()->clear_in_cset(hr);
 652   _cset->add_old_region(hr);




   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/g1CollectedHeap.inline.hpp"
  27 #include "gc/g1/g1CollectionSet.hpp"
  28 #include "gc/g1/g1CollectorState.hpp"
  29 #include "gc/g1/g1ParScanThreadState.hpp"
  30 #include "gc/g1/g1Policy.hpp"
  31 #include "gc/g1/heapRegion.inline.hpp"
  32 #include "gc/g1/heapRegionRemSet.hpp"
  33 #include "gc/g1/heapRegionSet.hpp"
  34 #include "logging/logStream.hpp"
  35 #include "utilities/debug.hpp"
  36 #include "utilities/globalDefinitions.hpp"
  37 #include "utilities/quickSort.hpp"
  38 
  39 G1CollectorState* G1CollectionSet::collector_state() {
  40   return _g1h->collector_state();
  41 }
  42 
  43 G1GCPhaseTimes* G1CollectionSet::phase_times() {
  44   return _policy->phase_times();
  45 }
  46 
  47 CollectionSetChooser* G1CollectionSet::cset_chooser() {
  48   return _cset_chooser;
  49 }


  88   assert_at_safepoint_on_vm_thread();
  89 
  90   _eden_region_length     = eden_cset_region_length;
  91   _survivor_region_length = survivor_cset_region_length;
  92 
  93   assert((size_t) young_region_length() == _collection_set_cur_length,
  94          "Young region length %u should match collection set length " SIZE_FORMAT, young_region_length(), _collection_set_cur_length);
  95 
  96   _old_region_length      = 0;
  97   _optional_region_length = 0;
  98 }
  99 
 100 void G1CollectionSet::initialize(uint max_region_length) {
 101   guarantee(_collection_set_regions == NULL, "Must only initialize once.");
 102   _collection_set_max_length = max_region_length;
 103   _collection_set_regions = NEW_C_HEAP_ARRAY(uint, max_region_length, mtGC);
 104 }
 105 
 106 void G1CollectionSet::initialize_optional(uint max_length) {
 107   assert(_optional_regions == NULL, "Already initialized");
 108   assert(_optional_region_length == 0, "Already initialized");
 109   assert(_optional_region_max_length == 0, "Already initialized");
 110   _optional_region_max_length = max_length;
 111   _optional_regions = NEW_C_HEAP_ARRAY(HeapRegion*, _optional_region_max_length, mtGC);
 112 }
 113 
 114 void G1CollectionSet::free_optional_regions() {
 115   _optional_region_length = 0;
 116   _optional_region_max_length = 0;
 117   if (_optional_regions != NULL) {
 118     FREE_C_HEAP_ARRAY(HeapRegion*, _optional_regions);
 119     _optional_regions = NULL;
 120   }
 121 }
 122 
 123 void G1CollectionSet::set_recorded_rs_lengths(size_t rs_lengths) {
 124   _recorded_rs_lengths = rs_lengths;
 125 }
 126 
 127 // Add the heap region at the head of the non-incremental collection set
 128 void G1CollectionSet::add_old_region(HeapRegion* hr) {
 129   assert_at_safepoint_on_vm_thread();


 435   double young_end_time_sec = os::elapsedTime();
 436   phase_times()->record_young_cset_choice_time_ms((young_end_time_sec - young_start_time_sec) * 1000.0);
 437 
 438   return time_remaining_ms;
 439 }
 440 
 441 void G1CollectionSet::add_as_old(HeapRegion* hr) {
 442   cset_chooser()->pop(); // already have region via peek()
 443   _g1h->old_set_remove(hr);
 444   add_old_region(hr);
 445 }
 446 
 447 void G1CollectionSet::add_as_optional(HeapRegion* hr) {
 448   assert(_optional_regions != NULL, "Must not be called before array is allocated");
 449   cset_chooser()->pop(); // already have region via peek()
 450   _g1h->old_set_remove(hr);
 451   add_optional_region(hr);
 452 }
 453 
 454 bool G1CollectionSet::optional_is_full() {
 455   assert(_optional_region_length <= _optional_region_max_length, "Invariant");
 456   return _optional_region_length == _optional_region_max_length;
 457 }
 458 
 459 void G1CollectionSet::clear_optional_region(const HeapRegion* hr) {
 460   assert(_optional_regions != NULL, "Must not be called before array is allocated");
 461   uint index = hr->index_in_opt_cset();
 462   _optional_regions[index] = NULL;
 463 }
 464 
 465 static int compare_region_idx(const uint a, const uint b) {
 466   if (a > b) {
 467     return 1;
 468   } else if (a == b) {
 469     return 0;
 470   } else {
 471     return -1;
 472   }
 473 }
 474 
 475 void G1CollectionSet::finalize_old_part(double time_remaining_ms) {


 617     HeapRegion* hr = region_at(i);
 618     _cset->clear_optional_region(hr);
 619     if (hr->evacuation_failed()){
 620       _evacuation_failed = true;
 621     }
 622   }
 623   _current_index = _current_limit;
 624 }
 625 
 626 bool G1OptionalCSet::evacuation_failed() {
 627   return _evacuation_failed;
 628 }
 629 
 630 G1OptionalCSet::~G1OptionalCSet() {
 631   G1CollectedHeap* g1h = G1CollectedHeap::heap();
 632   while (!is_empty()) {
 633     // We want to return regions not evacuated to the
 634     // chooser in reverse order to maintain the old order.
 635     HeapRegion* hr = _cset->remove_last_optional_region();
 636     assert(hr != NULL, "Should be valid region left");
 637     _pset->free_unused_optional_region(hr);
 638     g1h->old_set_add(hr);
 639     g1h->clear_in_cset(hr);
 640     hr->set_index_in_opt_cset(InvalidCSetIndex);
 641     _cset->cset_chooser()->push(hr);
 642   }
 643   _cset->free_optional_regions();
 644 }
 645 
 646 uint G1OptionalCSet::size() {
 647   return _cset->optional_region_length() - _current_index;
 648 }
 649 
 650 bool G1OptionalCSet::is_empty() {
 651   return size() == 0;
 652 }
 653 
 654 void G1OptionalCSet::prepare_to_evacuate_optional_region(HeapRegion* hr) {
 655   log_trace(gc, cset)("Adding region %u for optional evacuation", hr->hrm_index());
 656   G1CollectedHeap::heap()->clear_in_cset(hr);
 657   _cset->add_old_region(hr);


< prev index next >