Skip to content

Commit

Permalink
8324981: Shenandoah: Move commit and soft max heap changed methods in…
Browse files Browse the repository at this point in the history
…to heap

Reviewed-by: shade
  • Loading branch information
William Kemper authored and shipilev committed Jan 31, 2024
1 parent 1733d2e commit 2cd1ba6
Show file tree
Hide file tree
Showing 4 changed files with 54 additions and 58 deletions.
48 changes: 3 additions & 45 deletions src/hotspot/share/gc/shenandoah/shenandoahControlThread.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -84,11 +84,11 @@ void ShenandoahControlThread::run_service() {
bool explicit_gc_requested = is_gc_requested && is_explicit_gc(requested_gc_cause);
bool implicit_gc_requested = is_gc_requested && !is_explicit_gc(requested_gc_cause);

// This control loop iteration have seen this much allocations.
// This control loop iteration has seen this much allocation.
size_t allocs_seen = Atomic::xchg(&_allocs_seen, (size_t)0, memory_order_relaxed);

// Check if we have seen a new target for soft max heap size.
bool soft_max_changed = check_soft_max_changed();
bool soft_max_changed = heap->check_soft_max_changed();

// Choose which GC mode to run in. The block below should select a single mode.
GCMode mode = none;
Expand Down Expand Up @@ -287,7 +287,7 @@ void ShenandoahControlThread::run_service() {
heap->soft_max_capacity() :
heap->min_capacity();

service_uncommit(shrink_before, shrink_until);
heap->maybe_uncommit(shrink_before, shrink_until);
heap->phase_timings()->flush_cycle_to_global();
last_shrink_time = current;
}
Expand All @@ -310,25 +310,6 @@ void ShenandoahControlThread::run_service() {
}
}

bool ShenandoahControlThread::check_soft_max_changed() const {
ShenandoahHeap* heap = ShenandoahHeap::heap();
size_t new_soft_max = Atomic::load(&SoftMaxHeapSize);
size_t old_soft_max = heap->soft_max_capacity();
if (new_soft_max != old_soft_max) {
new_soft_max = MAX2(heap->min_capacity(), new_soft_max);
new_soft_max = MIN2(heap->max_capacity(), new_soft_max);
if (new_soft_max != old_soft_max) {
log_info(gc)("Soft Max Heap Size: " SIZE_FORMAT "%s -> " SIZE_FORMAT "%s",
byte_size_in_proper_unit(old_soft_max), proper_unit_for_byte_size(old_soft_max),
byte_size_in_proper_unit(new_soft_max), proper_unit_for_byte_size(new_soft_max)
);
heap->set_soft_max_capacity(new_soft_max);
return true;
}
}
return false;
}

void ShenandoahControlThread::service_concurrent_normal_cycle(GCCause::Cause cause) {
// Normal cycle goes via all concurrent phases. If allocation failure (af) happens during
// any of the concurrent phases, it first degrades to Degenerated GC and completes GC there.
Expand Down Expand Up @@ -420,29 +401,6 @@ void ShenandoahControlThread::service_stw_degenerated_cycle(GCCause::Cause cause
gc.collect(cause);
}

void ShenandoahControlThread::service_uncommit(double shrink_before, size_t shrink_until) {
ShenandoahHeap* heap = ShenandoahHeap::heap();

// Determine if there is work to do. This avoids taking heap lock if there is
// no work available, avoids spamming logs with superfluous logging messages,
// and minimises the amount of work while locks are taken.

if (heap->committed() <= shrink_until) return;

bool has_work = false;
for (size_t i = 0; i < heap->num_regions(); i++) {
ShenandoahHeapRegion *r = heap->get_region(i);
if (r->is_empty_committed() && (r->empty_time() < shrink_before)) {
has_work = true;
break;
}
}

if (has_work) {
heap->entry_uncommit(shrink_before, shrink_until);
}
}

bool ShenandoahControlThread::is_explicit_gc(GCCause::Cause cause) const {
return GCCause::is_user_requested_gc(cause) ||
GCCause::is_serviceability_requested_gc(cause);
Expand Down
3 changes: 0 additions & 3 deletions src/hotspot/share/gc/shenandoah/shenandoahControlThread.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -72,7 +72,6 @@ class ShenandoahControlThread: public ConcurrentGCThread {
void service_concurrent_normal_cycle(GCCause::Cause cause);
void service_stw_full_cycle(GCCause::Cause cause);
void service_stw_degenerated_cycle(GCCause::Cause cause, ShenandoahGC::ShenandoahDegenPoint point);
void service_uncommit(double shrink_before, size_t shrink_until);

bool try_set_alloc_failure_gc();
void notify_alloc_failure_waiters();
Expand All @@ -90,8 +89,6 @@ class ShenandoahControlThread: public ConcurrentGCThread {

bool is_explicit_gc(GCCause::Cause cause) const;

bool check_soft_max_changed() const;

public:
// Constructor
ShenandoahControlThread();
Expand Down
53 changes: 45 additions & 8 deletions src/hotspot/share/gc/shenandoah/shenandoahHeap.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -754,6 +754,33 @@ bool ShenandoahHeap::is_in(const void* p) const {
return p >= heap_base && p < last_region_end;
}

void ShenandoahHeap::maybe_uncommit(double shrink_before, size_t shrink_until) {
assert (ShenandoahUncommit, "should be enabled");

// Determine if there is work to do. This avoids taking heap lock if there is
// no work available, avoids spamming logs with superfluous logging messages,
// and minimises the amount of work while locks are taken.

if (committed() <= shrink_until) return;

bool has_work = false;
for (size_t i = 0; i < num_regions(); i++) {
ShenandoahHeapRegion* r = get_region(i);
if (r->is_empty_committed() && (r->empty_time() < shrink_before)) {
has_work = true;
break;
}
}

if (has_work) {
static const char* msg = "Concurrent uncommit";
ShenandoahConcurrentPhase gcPhase(msg, ShenandoahPhaseTimings::conc_uncommit, true /* log_heap_usage */);
EventMark em("%s", msg);

op_uncommit(shrink_before, shrink_until);
}
}

void ShenandoahHeap::op_uncommit(double shrink_before, size_t shrink_until) {
assert (ShenandoahUncommit, "should be enabled");

Expand Down Expand Up @@ -784,6 +811,24 @@ void ShenandoahHeap::op_uncommit(double shrink_before, size_t shrink_until) {
}
}

bool ShenandoahHeap::check_soft_max_changed() {
size_t new_soft_max = Atomic::load(&SoftMaxHeapSize);
size_t old_soft_max = soft_max_capacity();
if (new_soft_max != old_soft_max) {
new_soft_max = MAX2(min_capacity(), new_soft_max);
new_soft_max = MIN2(max_capacity(), new_soft_max);
if (new_soft_max != old_soft_max) {
log_info(gc)("Soft Max Heap Size: " SIZE_FORMAT "%s -> " SIZE_FORMAT "%s",
byte_size_in_proper_unit(old_soft_max), proper_unit_for_byte_size(old_soft_max),
byte_size_in_proper_unit(new_soft_max), proper_unit_for_byte_size(new_soft_max)
);
set_soft_max_capacity(new_soft_max);
return true;
}
}
return false;
}

void ShenandoahHeap::notify_heap_changed() {
// Update monitoring counters when we took a new region. This amortizes the
// update costs on slow path.
Expand Down Expand Up @@ -2259,14 +2304,6 @@ void ShenandoahHeap::safepoint_synchronize_end() {
SuspendibleThreadSet::desynchronize();
}

void ShenandoahHeap::entry_uncommit(double shrink_before, size_t shrink_until) {
static const char *msg = "Concurrent uncommit";
ShenandoahConcurrentPhase gc_phase(msg, ShenandoahPhaseTimings::conc_uncommit, true /* log_heap_usage */);
EventMark em("%s", msg);

op_uncommit(shrink_before, shrink_until);
}

void ShenandoahHeap::try_inject_alloc_failure() {
if (ShenandoahAllocFailureALot && !cancelled_gc() && ((os::random() % 1000) > 950)) {
_inject_alloc_failure.set();
Expand Down
8 changes: 6 additions & 2 deletions src/hotspot/share/gc/shenandoah/shenandoahHeap.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -364,10 +364,14 @@ class ShenandoahHeap : public CollectedHeap, public ShenandoahSpaceInfo {
void cancel_gc(GCCause::Cause cause);

public:
// Elastic heap support
void entry_uncommit(double shrink_before, size_t shrink_until);
// These will uncommit empty regions if heap::committed > shrink_until
// and there exists at least one region which was made empty before shrink_before.
void maybe_uncommit(double shrink_before, size_t shrink_until);
void op_uncommit(double shrink_before, size_t shrink_until);

// Returns true if the soft maximum heap has been changed using management APIs.
bool check_soft_max_changed();

private:
// GC support
// Reset bitmap, prepare regions for new GC cycle
Expand Down

1 comment on commit 2cd1ba6

@openjdk-notifier
Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please sign in to comment.