From 4c7cafe7966b233e03291aeb20fdb38ed74725ff Mon Sep 17 00:00:00 2001 From: Severin Gehwolf Date: Fri, 1 Sep 2023 15:23:09 +0200 Subject: [PATCH] Fixes for -XX:MaxRAM and -XX:MaxDirectMemorySize at runtime --- .../core/jdk/Target_jdk_internal_misc_VM.java | 29 +++++++++++++++++-- 1 file changed, 26 insertions(+), 3 deletions(-) diff --git a/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/jdk/Target_jdk_internal_misc_VM.java b/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/jdk/Target_jdk_internal_misc_VM.java index 8be5a00a7098..4a5849f297cb 100644 --- a/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/jdk/Target_jdk_internal_misc_VM.java +++ b/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/jdk/Target_jdk_internal_misc_VM.java @@ -78,6 +78,12 @@ public static ClassLoader latestUserDefinedLoader0() { public static void initLevel(int newVal) { throw VMError.shouldNotReachHere("This is an alias to the method in the target class, so this code is unreachable"); } + + @Alias // + @SuppressWarnings("unused") + public static int initLevel() { + return -1; // Aliased code. Should not reach here + } } final class DirectMemoryAccessors { @@ -134,14 +140,28 @@ private static synchronized void initialize() { newDirectMemory = STATIC_DIRECT_MEMORY_AMOUNT; // Static value during initialization INIT_COUNT.incrementAndGet(); } else { - VMError.guarantee(INIT_COUNT.get() == 1, "Second cycle needs to have init count 1"); + VMError.guarantee(INIT_COUNT.get() <= 1, "Runtime.maxMemory() invariant"); /* * Once we know PhysicalMemory has been properly initialized we can use - * Runtime.maxMemory() + * Runtime.maxMemory(). Note that we might end up in this branch for code explicitly + * using the JDK cgroups code. At that point PhysicalMemory has likely been + * initialized. */ INIT_COUNT.incrementAndGet(); newDirectMemory = Runtime.getRuntime().maxMemory(); } + } else { + /* + * For explicitly set direct memory we are done + */ + Unsafe.getUnsafe().storeFence(); + directMemory = newDirectMemory; + isInitialized = true; + if (Target_jdk_internal_misc_VM.initLevel() < 1) { + // only the first accessor needs to set this + Target_jdk_internal_misc_VM.initLevel(1); + } + return; } VMError.guarantee(newDirectMemory > 0, "New direct memory should be initialized"); @@ -154,7 +174,10 @@ private static synchronized void initialize() { * MAX_MEMORY field. */ isInitialized = true; - Target_jdk_internal_misc_VM.initLevel(1); + if (Target_jdk_internal_misc_VM.initLevel() < 1) { + // only the first accessor needs to set this + Target_jdk_internal_misc_VM.initLevel(1); + } } } }