Skip to content

Commit 333471d

Browse files
Cleanups.
1 parent 40b566f commit 333471d

File tree

8 files changed

+607
-487
lines changed

8 files changed

+607
-487
lines changed

substratevm/src/com.oracle.svm.core.genscavenge/src/com/oracle/svm/core/genscavenge/AbstractCollectionPolicy.java

Lines changed: 17 additions & 443 deletions
Large diffs are not rendered by default.

substratevm/src/com.oracle.svm.core.genscavenge/src/com/oracle/svm/core/genscavenge/AdaptiveCollectionPolicy.java

Lines changed: 29 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,7 @@
3030

3131
import com.oracle.svm.core.Isolates;
3232
import com.oracle.svm.core.heap.GCCause;
33+
import com.oracle.svm.core.thread.VMOperation;
3334
import com.oracle.svm.core.util.BasedOnJDKFile;
3435
import com.oracle.svm.core.util.TimeUtils;
3536
import com.oracle.svm.core.util.Timer;
@@ -264,45 +265,45 @@ private void computeSurvivorSpaceSizeAndThreshold(boolean isSurvivorOverflow, Un
264265
}
265266

266267
protected void computeEdenSpaceSize(@SuppressWarnings("unused") boolean completeCollection, @SuppressWarnings("unused") GCCause cause) {
267-
UnsignedWord curEdenSize = sizes.getEdenSize();
268-
UnsignedWord curPromoSize = sizes.getPromoSize();
268+
UnsignedWord curEden = sizes.getEdenSize();
269+
UnsignedWord curPromo = sizes.getPromoSize();
269270

270271
boolean expansionReducesCost = true; // general assumption
271272
if (shouldUseEstimator(youngGenChangeForMinorThroughput, minorGcCost())) {
272-
expansionReducesCost = expansionSignificantlyReducesTotalCost(minorCostEstimator, curEdenSize, majorGcCost(), curPromoSize);
273+
expansionReducesCost = expansionSignificantlyReducesTotalCost(minorCostEstimator, curEden, majorGcCost(), curPromo);
273274
/*
274275
* Note that if the estimator thinks expanding does not lead to significant improvement,
275276
* shrink so to not get stuck in a supposed optimum and to keep collecting data points.
276277
*/
277278
}
278279

279-
UnsignedWord desiredEdenSize = curEdenSize;
280+
UnsignedWord desiredEdenSize = curEden;
280281
if (expansionReducesCost && adjustedMutatorCost() < THROUGHPUT_GOAL && gcCost() > 0) {
281282
// from adjust_eden_for_throughput():
282-
UnsignedWord edenHeapDelta = edenIncrementWithSupplementAlignedUp(curEdenSize);
283+
UnsignedWord edenHeapDelta = edenIncrementWithSupplementAlignedUp(curEden);
283284
double scaleByRatio = minorGcCost() / gcCost();
284285
assert scaleByRatio >= 0 && scaleByRatio <= 1;
285286
UnsignedWord scaledEdenHeapDelta = UnsignedUtils.fromDouble(scaleByRatio * UnsignedUtils.toDouble(edenHeapDelta));
286287

287288
desiredEdenSize = alignUp(desiredEdenSize.add(scaledEdenHeapDelta));
288-
desiredEdenSize = UnsignedUtils.max(desiredEdenSize, curEdenSize);
289+
desiredEdenSize = UnsignedUtils.max(desiredEdenSize, curEden);
289290
youngGenChangeForMinorThroughput++;
290291
}
291292
if (!expansionReducesCost || (USE_ADAPTIVE_SIZE_POLICY_FOOTPRINT_GOAL && youngGenPolicyIsReady && adjustedMutatorCost() >= THROUGHPUT_GOAL)) {
292-
UnsignedWord desiredSum = curEdenSize.add(curPromoSize);
293-
desiredEdenSize = adjustEdenForFootprint(curEdenSize, desiredSum);
293+
UnsignedWord desiredSum = curEden.add(curPromo);
294+
desiredEdenSize = adjustEdenForFootprint(curEden, desiredSum);
294295
}
295296
assert isAligned(desiredEdenSize);
296297
desiredEdenSize = minSpaceSize(desiredEdenSize);
297298

298-
UnsignedWord edenLimit = getMaximumEdenSize();
299+
UnsignedWord edenLimit = computeEdenLimit();
299300
if (desiredEdenSize.aboveThan(edenLimit)) {
300301
/*
301302
* If the policy says to get a larger eden but is hitting the limit, don't decrease
302303
* eden. This can lead to a general drifting down of the eden size. Let the tenuring
303304
* calculation push more into the old gen.
304305
*/
305-
desiredEdenSize = UnsignedUtils.max(edenLimit, curEdenSize);
306+
desiredEdenSize = UnsignedUtils.max(edenLimit, curEden);
306307
}
307308
sizes.setEdenSize(desiredEdenSize);
308309
}
@@ -486,40 +487,40 @@ public void onCollectionEnd(boolean completeCollection, GCCause cause) { // {maj
486487
}
487488

488489
private void computeOldGenSpaceSize(UnsignedWord oldLive) { // compute_old_gen_free_space
489-
UnsignedWord curEdenSize = sizes.getEdenSize();
490-
UnsignedWord curMaxOldSize = sizes.getMaxOldSize();
491-
UnsignedWord curPromoSize = sizes.getPromoSize();
490+
UnsignedWord curEden = sizes.getEdenSize();
491+
UnsignedWord curPromo = sizes.getPromoSize();
492+
UnsignedWord curMaxOld = sizes.getMaxOldSize();
492493

493494
avgOldLive.sample(oldLive);
494495

495496
// NOTE: if maxOldSize shrunk and difference is negative, unsigned conversion results in 0
496-
UnsignedWord promoLimit = UnsignedUtils.fromDouble(UnsignedUtils.toDouble(curMaxOldSize) - avgOldLive.getAverage());
497-
promoLimit = alignDown(UnsignedUtils.max(curPromoSize, promoLimit));
497+
UnsignedWord promoLimit = UnsignedUtils.fromDouble(UnsignedUtils.toDouble(curMaxOld) - avgOldLive.getAverage());
498+
promoLimit = alignDown(UnsignedUtils.max(curPromo, promoLimit));
498499

499500
boolean expansionReducesCost = true; // general assumption
500501
if (shouldUseEstimator(oldGenChangeForMajorThroughput, majorGcCost())) {
501-
expansionReducesCost = expansionSignificantlyReducesTotalCost(majorCostEstimator, curPromoSize, minorGcCost(), curEdenSize);
502+
expansionReducesCost = expansionSignificantlyReducesTotalCost(majorCostEstimator, curPromo, minorGcCost(), curEden);
502503
/*
503504
* Note that if the estimator thinks expanding does not lead to significant improvement,
504505
* shrink so to not get stuck in a supposed optimum and to keep collecting data points.
505506
*/
506507
}
507508

508-
UnsignedWord desiredPromoSize = curPromoSize;
509+
UnsignedWord desiredPromoSize = curPromo;
509510
if (expansionReducesCost && adjustedMutatorCost() < THROUGHPUT_GOAL && gcCost() > 0) {
510511
// from adjust_promo_for_throughput():
511-
UnsignedWord promoHeapDelta = promoIncrementWithSupplementAlignedUp(curPromoSize);
512+
UnsignedWord promoHeapDelta = promoIncrementWithSupplementAlignedUp(curPromo);
512513
double scaleByRatio = majorGcCost() / gcCost();
513514
assert scaleByRatio >= 0 && scaleByRatio <= 1;
514515
UnsignedWord scaledPromoHeapDelta = UnsignedUtils.fromDouble(scaleByRatio * UnsignedUtils.toDouble(promoHeapDelta));
515516

516-
desiredPromoSize = alignUp(curPromoSize.add(scaledPromoHeapDelta));
517-
desiredPromoSize = UnsignedUtils.max(desiredPromoSize, curPromoSize);
517+
desiredPromoSize = alignUp(curPromo.add(scaledPromoHeapDelta));
518+
desiredPromoSize = UnsignedUtils.max(desiredPromoSize, curPromo);
518519
oldGenChangeForMajorThroughput++;
519520
}
520521
if (!expansionReducesCost || (USE_ADAPTIVE_SIZE_POLICY_FOOTPRINT_GOAL && youngGenPolicyIsReady && adjustedMutatorCost() >= THROUGHPUT_GOAL)) {
521-
UnsignedWord desiredSum = curEdenSize.add(curPromoSize);
522-
desiredPromoSize = adjustPromoForFootprint(curPromoSize, desiredSum);
522+
UnsignedWord desiredSum = curEden.add(curPromo);
523+
desiredPromoSize = adjustPromoForFootprint(curPromo, desiredSum);
523524
}
524525
assert isAligned(desiredPromoSize);
525526
desiredPromoSize = minSpaceSize(desiredPromoSize);
@@ -530,7 +531,7 @@ private void computeOldGenSpaceSize(UnsignedWord oldLive) { // compute_old_gen_f
530531
// from PSOldGen::resize
531532
UnsignedWord desiredFreeSpace = calculatedOldFreeSizeInBytes();
532533
UnsignedWord desiredOldSize = alignUp(oldLive.add(desiredFreeSpace));
533-
sizes.setOldSize(UnsignedUtils.clamp(desiredOldSize, minSpaceSize(), curMaxOldSize));
534+
sizes.setOldSize(UnsignedUtils.clamp(desiredOldSize, minSpaceSize(), curMaxOld));
534535
}
535536

536537
UnsignedWord calculatedOldFreeSizeInBytes() {
@@ -580,6 +581,11 @@ protected boolean shouldUpdateStats(GCCause cause) { // should_update_{eden,prom
580581
return cause == GenScavengeGCCause.OnAllocation || USE_ADAPTIVE_SIZE_POLICY_WITH_SYSTEM_GC;
581582
}
582583

584+
protected UnsignedWord computeEdenLimit() {
585+
assert VMOperation.isGCInProgress() : "result wouldn't be consistent otherwise";
586+
return alignDown(sizes.getMaxYoungSize().subtract(sizes.getSurvivorSize().multiply(2)));
587+
}
588+
583589
private void updateCollectionEndAverages(AdaptiveWeightedAverage costAverage, AdaptivePaddedAverage pauseAverage, ReciprocalLeastSquareFit costEstimator,
584590
AdaptiveWeightedAverage intervalSeconds, GCCause cause, long mutatorNanos, long pauseNanos, UnsignedWord sizeBytes) {
585591
if (shouldUpdateStats(cause)) {

substratevm/src/com.oracle.svm.core.genscavenge/src/com/oracle/svm/core/genscavenge/HeapImpl.java

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -711,6 +711,7 @@ public void optionValueChanged(NotifyGCRuntimeOptionKey<?> key) {
711711
GCImpl.getPolicy().updateSizeParameters();
712712
}
713713

714+
/** For the GC policy, mainly heap-size-related GC options are relevant. */
714715
private static boolean isIrrelevantForGCPolicy(RuntimeOptionKey<?> key) {
715716
return key == SubstrateGCOptions.DisableExplicitGC ||
716717
key == SubstrateGCOptions.PrintGC ||

substratevm/src/com.oracle.svm.core.genscavenge/src/com/oracle/svm/core/genscavenge/LibGraalCollectionPolicy.java

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -142,19 +142,19 @@ protected boolean shouldUpdateStats(GCCause cause) {
142142
protected void computeEdenSpaceSize(boolean completeCollection, GCCause cause) {
143143
if (cause == GCCause.HintedGC) {
144144
if (completeCollection && lastGCCause == GCCause.HintedGC) {
145-
UnsignedWord curEdenSize = sizes.getEdenSize();
146-
UnsignedWord newEdenSize = UnsignedUtils.max(sizes.getInitialEdenSize(), alignUp(curEdenSize.unsignedDivide(2)));
147-
if (curEdenSize.aboveThan(newEdenSize)) {
148-
sizes.setEdenSize(newEdenSize);
145+
UnsignedWord curEden = sizes.getEdenSize();
146+
UnsignedWord newEden = UnsignedUtils.max(sizes.getInitialEdenSize(), alignUp(curEden.unsignedDivide(2)));
147+
if (curEden.aboveThan(newEden)) {
148+
sizes.setEdenSize(newEden);
149149
}
150150
}
151151
} else {
152152
UnsignedWord sizeAfter = GCImpl.getChunkBytes();
153153
if (sizeBefore.notEqual(0) && sizeBefore.belowThan(sizeAfter.multiply(2))) {
154-
UnsignedWord curEdenSize = sizes.getEdenSize();
155-
UnsignedWord newEdenSize = UnsignedUtils.min(getMaximumEdenSize(), alignUp(curEdenSize.multiply(2)));
156-
if (curEdenSize.belowThan(newEdenSize)) {
157-
sizes.setEdenSize(newEdenSize);
154+
UnsignedWord curEden = sizes.getEdenSize();
155+
UnsignedWord newEden = UnsignedUtils.min(computeEdenLimit(), alignUp(curEden.multiply(2)));
156+
if (curEden.belowThan(newEden)) {
157+
sizes.setEdenSize(newEden);
158158
}
159159
} else {
160160
super.computeEdenSpaceSize(completeCollection, cause);
Lines changed: 150 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,150 @@
1+
/*
2+
* Copyright (c) 2025, 2025, Oracle and/or its affiliates. All rights reserved.
3+
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
4+
*
5+
* This code is free software; you can redistribute it and/or modify it
6+
* under the terms of the GNU General Public License version 2 only, as
7+
* published by the Free Software Foundation. Oracle designates this
8+
* particular file as subject to the "Classpath" exception as provided
9+
* by Oracle in the LICENSE file that accompanied this code.
10+
*
11+
* This code is distributed in the hope that it will be useful, but WITHOUT
12+
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13+
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
14+
* version 2 for more details (a copy is included in the LICENSE file that
15+
* accompanied this code).
16+
*
17+
* You should have received a copy of the GNU General Public License version
18+
* 2 along with this work; if not, write to the Free Software Foundation,
19+
* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
20+
*
21+
* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
22+
* or visit www.oracle.com if you need additional information or have any
23+
* questions.
24+
*/
25+
package com.oracle.svm.core.genscavenge;
26+
27+
import org.graalvm.nativeimage.c.struct.RawField;
28+
import org.graalvm.nativeimage.c.struct.RawStructure;
29+
import org.graalvm.word.PointerBase;
30+
import org.graalvm.word.UnsignedWord;
31+
32+
/**
33+
* Struct that stores all GC-related sizes. See {@link SizeParameters} for more details on its
34+
* lifecycle. When adding fields to this struct, please also change
35+
* {@link RawSizeParametersOnStackAccess#initialize} and {@link SizeParameters#matches} accordingly.
36+
*/
37+
@RawStructure
38+
interface RawSizeParameters extends PointerBase {
39+
@RawField
40+
UnsignedWord getInitialEdenSize();
41+
42+
@RawField
43+
void setInitialEdenSize(UnsignedWord value);
44+
45+
@RawField
46+
UnsignedWord getEdenSize();
47+
48+
@RawField
49+
void setEdenSize(UnsignedWord value);
50+
51+
@RawField
52+
UnsignedWord getMaxEdenSize();
53+
54+
@RawField
55+
void setMaxEdenSize(UnsignedWord value);
56+
57+
@RawField
58+
UnsignedWord getInitialSurvivorSize();
59+
60+
@RawField
61+
void setInitialSurvivorSize(UnsignedWord value);
62+
63+
@RawField
64+
UnsignedWord getSurvivorSize();
65+
66+
@RawField
67+
void setSurvivorSize(UnsignedWord value);
68+
69+
@RawField
70+
UnsignedWord getMaxSurvivorSize();
71+
72+
@RawField
73+
void setMaxSurvivorSize(UnsignedWord value);
74+
75+
@RawField
76+
UnsignedWord getInitialYoungSize();
77+
78+
@RawField
79+
void setInitialYoungSize(UnsignedWord value);
80+
81+
@RawField
82+
UnsignedWord getYoungSize();
83+
84+
@RawField
85+
void setYoungSize(UnsignedWord value);
86+
87+
@RawField
88+
UnsignedWord getMaxYoungSize();
89+
90+
@RawField
91+
void setMaxYoungSize(UnsignedWord value);
92+
93+
@RawField
94+
UnsignedWord getInitialOldSize();
95+
96+
@RawField
97+
void setInitialOldSize(UnsignedWord value);
98+
99+
@RawField
100+
UnsignedWord getOldSize();
101+
102+
@RawField
103+
void setOldSize(UnsignedWord value);
104+
105+
@RawField
106+
UnsignedWord getMaxOldSize();
107+
108+
@RawField
109+
void setMaxOldSize(UnsignedWord value);
110+
111+
@RawField
112+
UnsignedWord getPromoSize();
113+
114+
@RawField
115+
void setPromoSize(UnsignedWord value);
116+
117+
@RawField
118+
UnsignedWord getMinHeapSize();
119+
120+
@RawField
121+
void setMinHeapSize(UnsignedWord value);
122+
123+
@RawField
124+
UnsignedWord getInitialHeapSize();
125+
126+
@RawField
127+
void setInitialHeapSize(UnsignedWord value);
128+
129+
@RawField
130+
UnsignedWord getHeapSize();
131+
132+
@RawField
133+
void setHeapSize(UnsignedWord value);
134+
135+
@RawField
136+
UnsignedWord getMaxHeapSize();
137+
138+
@RawField
139+
void setMaxHeapSize(UnsignedWord value);
140+
141+
/**
142+
* Either points to null or to an obsolete {@link RawSizeParameters} struct that wasn't freed
143+
* yet.
144+
*/
145+
@RawField
146+
RawSizeParameters getNext();
147+
148+
@RawField
149+
void setNext(RawSizeParameters value);
150+
}

0 commit comments

Comments
 (0)