8319795: Static huge pages are not used for CodeCache

Reviewed-by: shade, simonis, thartmann, stuefe
This commit is contained in:
Evgeny Astigeevich 2023-12-21 18:51:50 +00:00
parent 1802601a12
commit 3b908c4781
8 changed files with 81 additions and 58 deletions
src/hotspot
test/hotspot/jtreg

@ -2112,11 +2112,6 @@ bool os::can_commit_large_page_memory() {
return false;
}
bool os::can_execute_large_page_memory() {
// Does not matter, we do not support huge pages.
return false;
}
char* os::pd_attempt_map_memory_to_file_at(char* requested_addr, size_t bytes, int file_desc) {
assert(file_desc >= 0, "file_desc is not valid");
char* result = nullptr;

@ -1787,11 +1787,6 @@ bool os::can_commit_large_page_memory() {
return false;
}
bool os::can_execute_large_page_memory() {
// Does not matter, we do not support huge pages.
return false;
}
char* os::pd_attempt_map_memory_to_file_at(char* requested_addr, size_t bytes, int file_desc) {
assert(file_desc >= 0, "file_desc is not valid");
char* result = pd_attempt_reserve_memory_at(requested_addr, bytes, !ExecMem);

@ -4078,10 +4078,6 @@ bool os::can_commit_large_page_memory() {
return UseTransparentHugePages;
}
bool os::can_execute_large_page_memory() {
return UseTransparentHugePages;
}
char* os::pd_attempt_map_memory_to_file_at(char* requested_addr, size_t bytes, int file_desc) {
assert(file_desc >= 0, "file_desc is not valid");
char* result = pd_attempt_reserve_memory_at(requested_addr, bytes, !ExecMem);

@ -3436,10 +3436,6 @@ bool os::can_commit_large_page_memory() {
return false;
}
bool os::can_execute_large_page_memory() {
return true;
}
static char* reserve_large_pages_individually(size_t size, char* req_addr, bool exec) {
log_debug(pagesize)("Reserving large pages individually.");

@ -355,16 +355,8 @@ void CodeCache::initialize_heaps() {
}
size_t CodeCache::page_size(bool aligned, size_t min_pages) {
if (os::can_execute_large_page_memory()) {
if (InitialCodeCacheSize < ReservedCodeCacheSize) {
// Make sure that the page size allows for an incremental commit of the reserved space
min_pages = MAX2(min_pages, (size_t)8);
}
return aligned ? os::page_size_for_region_aligned(ReservedCodeCacheSize, min_pages) :
os::page_size_for_region_unaligned(ReservedCodeCacheSize, min_pages);
} else {
return os::vm_page_size();
}
return aligned ? os::page_size_for_region_aligned(ReservedCodeCacheSize, min_pages) :
os::page_size_for_region_unaligned(ReservedCodeCacheSize, min_pages);
}
ReservedCodeSpace CodeCache::reserve_heap_memory(size_t size, size_t rs_ps) {
@ -1171,7 +1163,11 @@ void CodeCache::initialize() {
FLAG_SET_ERGO(NonNMethodCodeHeapSize, (uintx)os::vm_page_size());
FLAG_SET_ERGO(ProfiledCodeHeapSize, 0);
FLAG_SET_ERGO(NonProfiledCodeHeapSize, 0);
ReservedCodeSpace rs = reserve_heap_memory(ReservedCodeCacheSize, page_size(false, 8));
// If InitialCodeCacheSize is equal to ReservedCodeCacheSize, then it's more likely
// users want to use the largest available page.
const size_t min_pages = (InitialCodeCacheSize == ReservedCodeCacheSize) ? 1 : 8;
ReservedCodeSpace rs = reserve_heap_memory(ReservedCodeCacheSize, page_size(false, min_pages));
// Register CodeHeaps with LSan as we sometimes embed pointers to malloc memory.
LSAN_REGISTER_ROOT_REGION(rs.base(), rs.size());
add_heap(rs, "CodeCache", CodeBlobType::All);

@ -531,7 +531,6 @@ class os: AllStatic {
static void large_page_init();
static size_t large_page_size();
static bool can_commit_large_page_memory();
static bool can_execute_large_page_memory();
// Check if pointer points to readable memory (by 4-byte read access)
static bool is_readable_pointer(const void* p);

@ -72,8 +72,6 @@ compiler/vectorapi/VectorLogicalOpIdentityTest.java 8302459 linux-x64,windows-x6
compiler/jvmci/TestUncaughtErrorInCompileMethod.java 8309073 generic-all
compiler/codecache/CheckLargePages.java 8319795 linux-x64
compiler/floatingpoint/TestSubnormalFloat.java 8317810 generic-i586
compiler/floatingpoint/TestSubnormalDouble.java 8317810 generic-i586

@ -44,35 +44,83 @@ import java.util.Arrays;
import java.util.List;
public class CheckLargePages {
private final static WhiteBox WHITE_BOX = WhiteBox.getWhiteBox();
private final static long LP_1G = 1024 * 1024 * 1024;
private final static boolean LARGE_PAGES_ENABLED;
private final static long LARGE_PAGE_SIZE;
static {
WhiteBox whiteBox = WhiteBox.getWhiteBox();
LARGE_PAGES_ENABLED = whiteBox.getBooleanVMFlag("UseLargePages");
LARGE_PAGE_SIZE = (whiteBox.getBooleanVMFlag("UseLargePages")) ? whiteBox.getVMLargePageSize() : 0;
}
private static boolean isLargePageSizeEqual(long size) {
return LARGE_PAGE_SIZE == size;
}
private static void testSegmented2GbCodeCacheWith1GbPage() throws Exception {
ProcessBuilder pb = ProcessTools.createLimitedTestJavaProcessBuilder(
"-XX:+UseLargePages",
"-XX:+SegmentedCodeCache",
"-XX:InitialCodeCacheSize=2g",
"-XX:ReservedCodeCacheSize=2g",
"-XX:LargePageSizeInBytes=1g",
"-Xlog:pagesize=info",
"-version");
OutputAnalyzer out = new OutputAnalyzer(pb.start());
out.shouldMatch("Code cache size too small for \\S* pages\\. Reverting to smaller page size \\((\\S*)\\)\\.");
out.shouldHaveExitValue(0);
// Parse page sizes to find next biggest page
String sizes = out.firstMatch("Usable page sizes:([^.]+)", 1);
List<Long> sizeList = Arrays.stream(sizes.trim().split("\\s*,\\s*")).map(CheckLargePages::parseMemoryString)
.sorted().toList();
final int smallerPageSizeIndex = sizeList.indexOf(LARGE_PAGE_SIZE) - 1;
Asserts.assertGreaterThanOrEqual(smallerPageSizeIndex, 0);
final long smallerPageSize = sizeList.get(smallerPageSizeIndex);
// Retrieve reverted page size from code cache warning
String revertedSizeString = out.firstMatch(
"Code cache size too small for (\\S*) pages. Reverting to smaller page size \\((\\S*)\\)\\.", 2);
Asserts.assertEquals(parseMemoryString(revertedSizeString), smallerPageSize);
}
private static void testDefaultCodeCacheWith1GbLargePages() throws Exception {
ProcessBuilder pb = ProcessTools.createLimitedTestJavaProcessBuilder(
"-XX:+UseLargePages",
"-XX:LargePageSizeInBytes=1g",
"-XX:+PrintCodeCache",
"-version");
OutputAnalyzer out = new OutputAnalyzer(pb.start());
out.shouldHaveExitValue(0);
out.shouldContain("CodeHeap 'non-nmethods'");
out.shouldContain("CodeHeap 'profiled nmethods'");
out.shouldContain("CodeHeap 'non-profiled nmethods'");
}
private static void testNonSegmented1GbCodeCacheWith1GbLargePages() throws Exception {
ProcessBuilder pb = ProcessTools.createLimitedTestJavaProcessBuilder(
"-XX:+UseLargePages",
"-XX:LargePageSizeInBytes=1g",
"-XX:ReservedCodeCacheSize=1g",
"-XX:InitialCodeCacheSize=1g",
"-XX:+PrintCodeCache",
"-Xlog:pagesize=info",
"-version");
OutputAnalyzer out = new OutputAnalyzer(pb.start());
out.shouldHaveExitValue(0);
out.shouldNotContain("CodeHeap 'non-nmethods'");
out.shouldNotContain("CodeHeap 'profiled nmethods'");
out.shouldNotContain("CodeHeap 'non-profiled nmethods'");
out.shouldContain("UseLargePages=1, UseTransparentHugePages=0");
out.shouldMatch("CodeCache: min=1[gG] max=1[gG] base=[^ ]+ size=1[gG] page_size=1[gG]");
}
public static void main(String[] args) throws Exception {
final boolean largePages = WHITE_BOX.getBooleanVMFlag("UseLargePages");
final long largePageSize = WHITE_BOX.getVMLargePageSize();
if (largePages && (largePageSize == 1024 * 1024 * 1024)) {
ProcessBuilder pb = ProcessTools.createLimitedTestJavaProcessBuilder(
"-XX:+UseLargePages",
"-XX:+SegmentedCodeCache",
"-XX:InitialCodeCacheSize=2g",
"-XX:ReservedCodeCacheSize=2g",
"-XX:LargePageSizeInBytes=1g",
"-Xlog:pagesize=info",
"-version");
OutputAnalyzer out = new OutputAnalyzer(pb.start());
out.shouldMatch("Code cache size too small for \\S* pages\\. Reverting to smaller page size \\((\\S*)\\)\\.");
out.shouldHaveExitValue(0);
// Parse page sizes to find next biggest page
String sizes = out.firstMatch("Usable page sizes:([^.]+)", 1);
List<Long> sizeList = Arrays.stream(sizes.trim().split("\\s*,\\s*")).map(CheckLargePages::parseMemoryString).sorted().toList();
final int smallerPageSizeIndex = sizeList.indexOf(largePageSize) - 1;
Asserts.assertGreaterThanOrEqual(smallerPageSizeIndex, 0);
final long smallerPageSize = sizeList.get(smallerPageSizeIndex);
// Retrieve reverted page size from code cache warning
String revertedSizeString = out.firstMatch("Code cache size too small for (\\S*) pages. Reverting to smaller page size \\((\\S*)\\)\\.", 2);
Asserts.assertEquals(parseMemoryString(revertedSizeString), smallerPageSize);
if (isLargePageSizeEqual(LP_1G)) {
testSegmented2GbCodeCacheWith1GbPage();
testDefaultCodeCacheWith1GbLargePages();
testNonSegmented1GbCodeCacheWith1GbLargePages();
} else {
System.out.println("1GB large pages not supported: UseLargePages=" + largePages +
(largePages ? ", largePageSize=" + largePageSize : "") + ". Skipping");
System.out.println("1GB large pages not supported: UseLargePages=" + LARGE_PAGES_ENABLED +
(LARGE_PAGES_ENABLED ? ", largePageSize=" + LARGE_PAGE_SIZE : "") + ". Skipping");
}
}