Path: blob/master/test/hotspot/jtreg/gc/arguments/TestSurvivorRatioFlag.java
40942 views
/*1* Copyright (c) 2015, 2021, Oracle and/or its affiliates. All rights reserved.2* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.3*4* This code is free software; you can redistribute it and/or modify it5* under the terms of the GNU General Public License version 2 only, as6* published by the Free Software Foundation.7*8* This code is distributed in the hope that it will be useful, but WITHOUT9* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or10* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License11* version 2 for more details (a copy is included in the LICENSE file that12* accompanied this code).13*14* You should have received a copy of the GNU General Public License version15* 2 along with this work; if not, write to the Free Software Foundation,16* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.17*18* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA19* or visit www.oracle.com if you need additional information or have any20* questions.21*/2223package gc.arguments;2425/*26* @test TestSurvivorRatioFlag27* @summary Verify that actual survivor ratio is equal to specified SurvivorRatio value28* @requires vm.gc != "Z" & vm.gc != "Shenandoah"29* @library /test/lib30* @library /31* @modules java.base/jdk.internal.misc32* java.management33* @build sun.hotspot.WhiteBox34* @run driver jdk.test.lib.helpers.ClassFileInstaller sun.hotspot.WhiteBox35* @run driver gc.arguments.TestSurvivorRatioFlag36*/3738import java.lang.management.MemoryUsage;39import java.util.Arrays;40import java.util.Collections;41import java.util.LinkedList;42import jdk.test.lib.process.OutputAnalyzer;43import jdk.test.lib.process.ProcessTools;44import jdk.test.lib.Utils;45import sun.hotspot.WhiteBox;4647public class TestSurvivorRatioFlag {4849public static final long M = 1024 * 1024;50public static final long HEAP_SIZE = 200 * M;51public static final long NEW_SIZE = 100 * M;5253public static void main(String args[]) throws Exception {54LinkedList<String> options = new LinkedList<>(55Arrays.asList(Utils.getFilteredTestJavaOpts("-XX:[^ ]*SurvivorRatio=[^ ]+"))56);5758testSurvivorRatio(3, options);59testSurvivorRatio(6, options);60testSurvivorRatio(10, options);61testSurvivorRatio(15, options);62testSurvivorRatio(20, options);63}6465/**66* Verify that actual survivor ratio equal to specified.67*68* @param ratio survivor ratio that be verified69* @param options additional options to JVM70*/71public static void testSurvivorRatio(int ratio, LinkedList<String> options) throws Exception {7273LinkedList<String> vmOptions = new LinkedList<>(options);7475Collections.addAll(vmOptions,76"-Xbootclasspath/a:.",77"--add-exports=java.base/jdk.internal.misc=ALL-UNNAMED",78"-XX:+UnlockDiagnosticVMOptions",79"-XX:+WhiteBoxAPI",80"-XX:GCLockerEdenExpansionPercent=0",81"-XX:MaxNewSize=" + NEW_SIZE,82"-XX:NewSize=" + NEW_SIZE,83"-Xmx" + HEAP_SIZE,84"-Xms" + HEAP_SIZE,85"-XX:SurvivorRatio=" + ratio,86SurvivorRatioVerifier.class.getName(),87Integer.toString(ratio)88);8990ProcessBuilder procBuilder = GCArguments.createJavaProcessBuilder(vmOptions);91OutputAnalyzer analyzer = new OutputAnalyzer(procBuilder.start());92analyzer.shouldHaveExitValue(0);93}9495/**96* Class that verifies survivor ratio.97*/98public static class SurvivorRatioVerifier {99100static WhiteBox wb = WhiteBox.getWhiteBox();101102public static final int MAX_ITERATIONS = 10;103public static final int ARRAY_LENGTH = 10000;104public static final int CHUNK_SIZE = 10000;105106public static void main(String args[]) throws Exception {107if (args.length != 1) {108throw new IllegalArgumentException("Expected 1 arg: <ratio>");109}110final int ratio = Integer.valueOf(args[0]);111112AllocationHelper allocator = new AllocationHelper(MAX_ITERATIONS, ARRAY_LENGTH, CHUNK_SIZE, () -> (verifySurvivorRatio(ratio)));113allocator.allocateMemoryAndVerify();114}115116/**117* Verify that actual survivor ratio is equal to expected.118* Depending on selected young GC we verify that:119* - for DefNew and ParNew: eden_size / survivor_size is close to expectedRatio;120* - for PSNew: survivor_size equal to young_gen_size / expectedRatio;121* - for G1: survivor_regions <= young_list_length / expectedRatio.122*/123public static Void verifySurvivorRatio(int expectedRatio) {124GCTypes.YoungGCType type = GCTypes.YoungGCType.getYoungGCType();125switch (type) {126case DefNew:127verifyDefNewSurvivorRatio(expectedRatio);128break;129case PSNew:130verifyPSSurvivorRatio(expectedRatio);131break;132case G1:133verifyG1SurvivorRatio(expectedRatio);134break;135default:136throw new RuntimeException("Unexpected young GC type");137}138return null;139}140141private static void verifyDefNewSurvivorRatio(int expectedRatio) {142MemoryUsage edenUsage = HeapRegionUsageTool.getEdenUsage();143MemoryUsage survivorUsage = HeapRegionUsageTool.getSurvivorUsage();144145int actualRatio = (int) (edenUsage.getCommitted() / survivorUsage.getCommitted());146if (Math.abs(actualRatio - expectedRatio) > 1) {147throw new RuntimeException("Expected survivor ratio is: " + expectedRatio148+ ", but observed ratio is: " + actualRatio);149}150}151152private static void verifyPSSurvivorRatio(int expectedRatio) {153MemoryUsage edenUsage = HeapRegionUsageTool.getEdenUsage();154MemoryUsage survivorUsage = HeapRegionUsageTool.getSurvivorUsage();155156long youngGenSize = edenUsage.getMax() + 2 * survivorUsage.getMax();157// for Paralle GC Min/InitialSurvivorRatio = SurvivorRatio + 2158long expectedSize = HeapRegionUsageTool.alignDown(youngGenSize / (expectedRatio + 2),159wb.psHeapGenerationAlignment());160161if (expectedSize != survivorUsage.getCommitted()) {162throw new RuntimeException("Expected survivor size is: " + expectedSize163+ ", but observed size is: " + survivorUsage.getCommitted());164}165}166167private static void verifyG1SurvivorRatio(int expectedRatio) {168MemoryUsage survivorUsage = HeapRegionUsageTool.getSurvivorUsage();169170int regionSize = wb.g1RegionSize();171int youngListLength = (int) Math.max(NEW_SIZE / regionSize, 1);172int expectedSurvivorRegions = (int) Math.ceil(youngListLength / (double) expectedRatio);173int observedSurvivorRegions = (int) (survivorUsage.getCommitted() / regionSize);174175if (expectedSurvivorRegions < observedSurvivorRegions) {176throw new RuntimeException("Expected amount of G1 survivor regions is "177+ expectedSurvivorRegions + ", but observed "178+ observedSurvivorRegions);179}180}181}182}183184185