From 501ec6726c360e648ecc086ad9c474705fe5d0c3 Mon Sep 17 00:00:00 2001 From: Yudi Zheng Date: Mon, 5 Aug 2024 14:00:53 +0200 Subject: [PATCH 01/35] Avoid getHostBackend when instantiating UnimplementedGraalIntrinsics. --- .../hotspot/meta/HotSpotGraphBuilderPlugins.java | 2 +- .../compiler/hotspot/meta/HotSpotInvocationPlugins.java | 9 +++++---- 2 files changed, 6 insertions(+), 5 deletions(-) diff --git a/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/meta/HotSpotGraphBuilderPlugins.java b/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/meta/HotSpotGraphBuilderPlugins.java index ea22cb9a22c8..6972b3efaa2e 100644 --- a/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/meta/HotSpotGraphBuilderPlugins.java +++ b/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/meta/HotSpotGraphBuilderPlugins.java @@ -212,7 +212,7 @@ public static Plugins create(HotSpotGraalRuntimeProvider graalRuntime, OptionValues options, TargetDescription target, BarrierSet barrierSet) { - InvocationPlugins invocationPlugins = new HotSpotInvocationPlugins(graalRuntime, config, compilerConfiguration, options); + InvocationPlugins invocationPlugins = new HotSpotInvocationPlugins(graalRuntime, config, compilerConfiguration, options, target); Plugins plugins = new Plugins(invocationPlugins); plugins.appendNodePlugin(new HotSpotExceptionDispatchPlugin(config, wordTypes.getWordKind())); diff --git a/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/meta/HotSpotInvocationPlugins.java b/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/meta/HotSpotInvocationPlugins.java index 697fb9464461..015a271d8ca7 100644 --- a/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/meta/HotSpotInvocationPlugins.java +++ b/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/meta/HotSpotInvocationPlugins.java @@ -24,8 +24,8 @@ */ package jdk.graal.compiler.hotspot.meta; -import static jdk.vm.ci.hotspot.HotSpotJVMCIRuntime.runtime; import static jdk.graal.compiler.hotspot.HotSpotGraalServices.isIntrinsicAvailable; +import static jdk.vm.ci.hotspot.HotSpotJVMCIRuntime.runtime; import java.lang.reflect.Type; import java.util.ArrayList; @@ -37,6 +37,7 @@ import org.graalvm.collections.EconomicSet; import org.graalvm.collections.MapCursor; import org.graalvm.collections.Pair; + import jdk.graal.compiler.debug.GraalError; import jdk.graal.compiler.debug.TTY; import jdk.graal.compiler.graph.Node; @@ -49,7 +50,7 @@ import jdk.graal.compiler.options.OptionValues; import jdk.graal.compiler.phases.tiers.CompilerConfiguration; import jdk.graal.compiler.replacements.nodes.MacroInvokable; - +import jdk.vm.ci.code.TargetDescription; import jdk.vm.ci.hotspot.VMIntrinsicMethod; import jdk.vm.ci.meta.ResolvedJavaMethod; import jdk.vm.ci.meta.ResolvedJavaType; @@ -73,11 +74,11 @@ record MethodKey(String name, String descriptor) { private final EconomicMap> disabledIntrinsics = EconomicMap.create(); - HotSpotInvocationPlugins(HotSpotGraalRuntimeProvider graalRuntime, GraalHotSpotVMConfig config, CompilerConfiguration compilerConfiguration, OptionValues options) { + HotSpotInvocationPlugins(HotSpotGraalRuntimeProvider graalRuntime, GraalHotSpotVMConfig config, CompilerConfiguration compilerConfiguration, OptionValues options, TargetDescription target) { this.graalRuntime = graalRuntime; this.config = config; if (Options.WarnMissingIntrinsic.getValue(options)) { - this.unimplementedIntrinsics = new UnimplementedGraalIntrinsics(graalRuntime.getTarget().arch); + this.unimplementedIntrinsics = new UnimplementedGraalIntrinsics(target.arch); } else { this.unimplementedIntrinsics = null; } From 4464d0920688a83ddc2cabe23bda27f4c1c12947 Mon Sep 17 00:00:00 2001 From: Raphael Mosaner Date: Thu, 22 Aug 2024 12:46:25 +0200 Subject: [PATCH 02/35] [GR-57295] Aarch: Move setConservativeLabelRange after resetting crb. --- .../oracle/svm/core/graal/aarch64/SubstrateAArch64Backend.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/substratevm/src/com.oracle.svm.core.graal.aarch64/src/com/oracle/svm/core/graal/aarch64/SubstrateAArch64Backend.java b/substratevm/src/com.oracle.svm.core.graal.aarch64/src/com/oracle/svm/core/graal/aarch64/SubstrateAArch64Backend.java index 49cd77da70d3..33fc4adeaf59 100755 --- a/substratevm/src/com.oracle.svm.core.graal.aarch64/src/com/oracle/svm/core/graal/aarch64/SubstrateAArch64Backend.java +++ b/substratevm/src/com.oracle.svm.core.graal.aarch64/src/com/oracle/svm/core/graal/aarch64/SubstrateAArch64Backend.java @@ -1327,8 +1327,8 @@ public void emitCode(CompilationResultBuilder crb, ResolvedJavaMethod installedC // A branch estimation was wrong, now retry with conservative label ranges, this // should always work resetForEmittingCode(crb); - crb.setConservativeLabelRanges(); crb.resetForEmittingCode(); + crb.setConservativeLabelRanges(); crb.emitLIR(); finalizeCode(crb); } From 83e47d6a529fe2e3f3f0de5d2e28b9f68e290966 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Paul=20W=C3=B6gerer?= Date: Fri, 26 Jul 2024 00:22:01 +0000 Subject: [PATCH 03/35] [GR-56104] Fix --bundle-create option and bundle-launcher feature on Windows. PullRequest: graal/18413 --- .../com/oracle/svm/driver/launcher/BundleLauncher.java | 9 +++++++-- .../src/com/oracle/svm/driver/BundleSupport.java | 9 +++++---- 2 files changed, 12 insertions(+), 6 deletions(-) diff --git a/substratevm/src/com.oracle.svm.driver.launcher/src/com/oracle/svm/driver/launcher/BundleLauncher.java b/substratevm/src/com.oracle.svm.driver.launcher/src/com/oracle/svm/driver/launcher/BundleLauncher.java index 70cb535cce9d..1a77c03ed26e 100644 --- a/substratevm/src/com.oracle.svm.driver.launcher/src/com/oracle/svm/driver/launcher/BundleLauncher.java +++ b/substratevm/src/com.oracle.svm.driver.launcher/src/com/oracle/svm/driver/launcher/BundleLauncher.java @@ -91,7 +91,8 @@ static String getResource(String resourceName) { } public static void main(String[] args) { - bundleFilePath = Paths.get(BundleLauncher.class.getProtectionDomain().getCodeSource().getLocation().getPath()); + String bundleLauncherPath = BundleLauncher.class.getProtectionDomain().getCodeSource().getLocation().getPath(); + bundleFilePath = Paths.get(isWindows() ? bundleLauncherPath.substring(1) : bundleLauncherPath); bundleName = bundleFilePath.getFileName().toString().replace(BUNDLE_FILE_EXTENSION, ""); agentOutputDir = bundleFilePath.getParent().resolve(Paths.get(bundleName + ".output", "launcher")); unpackBundle(); @@ -342,6 +343,10 @@ private static Path getJavaExecutable() { return getJavaHomeExecutable(binJava); } + private static boolean isWindows() { + return System.getProperty("os.name").contains("Windows"); + } + private static Path getJavaHomeExecutable(Path executable) { String javaHome = System.getenv("JAVA_HOME"); if (javaHome == null) { @@ -358,7 +363,7 @@ private static Path getJavaHomeExecutable(Path executable) { } private static Path getNativeImageExecutable() { - Path binNativeImage = Paths.get("bin", System.getProperty("os.name").contains("Windows") ? "native-image.exe" : "native-image"); + Path binNativeImage = Paths.get("bin", isWindows() ? "native-image.exe" : "native-image"); if (Files.isExecutable(buildTimeJavaHome.resolve(binNativeImage))) { return buildTimeJavaHome.resolve(binNativeImage); } diff --git a/substratevm/src/com.oracle.svm.driver/src/com/oracle/svm/driver/BundleSupport.java b/substratevm/src/com.oracle.svm.driver/src/com/oracle/svm/driver/BundleSupport.java index 6da7f4bb78c5..80760b01c4fa 100644 --- a/substratevm/src/com.oracle.svm.driver/src/com/oracle/svm/driver/BundleSupport.java +++ b/substratevm/src/com.oracle.svm.driver/src/com/oracle/svm/driver/BundleSupport.java @@ -696,9 +696,10 @@ private Path writeBundle() { nativeImage.deleteAllFiles(metaInfDir); } - Path bundleLauncherFile = Paths.get("/").resolve(BundleLauncher.class.getName().replace(".", "/") + ".class"); - try (FileSystem fs = FileSystems.newFileSystem(BundleSupport.class.getResource(bundleLauncherFile.toString()).toURI(), new HashMap<>()); - Stream walk = Files.walk(fs.getPath(bundleLauncherFile.getParent().toString()))) { + String bundleLauncherClassResource = "/" + BundleLauncher.class.getName().replace(".", "/") + ".class"; + String bundleLauncherPackageResource = "/" + BundleLauncher.class.getPackageName().replace(".", "/"); + try (FileSystem fs = FileSystems.newFileSystem(BundleSupport.class.getResource(bundleLauncherClassResource).toURI(), new HashMap<>()); + Stream walk = Files.walk(fs.getPath(bundleLauncherPackageResource))) { walk.filter(Predicate.not(Files::isDirectory)) .map(Path::toString) .forEach(sourcePath -> { @@ -714,7 +715,7 @@ private Path writeBundle() { } }); } catch (Exception e) { - throw NativeImage.showError("Failed to read bundle launcher resources '" + bundleLauncherFile.getParent() + "'", e); + throw NativeImage.showError("Failed to read bundle launcher resources '" + bundleLauncherPackageResource + "'", e); } Path pathCanonicalizationsFile = stageDir.resolve("path_canonicalizations.json"); From 274253cc8ea8146ffc13af1c2da5d0e5cce117b3 Mon Sep 17 00:00:00 2001 From: Danilo Ansaloni Date: Mon, 9 Sep 2024 14:49:16 +0200 Subject: [PATCH 04/35] Start 24.1.1 dev cycle. --- compiler/mx.compiler/suite.py | 4 ++-- espresso/mx.espresso/suite.py | 4 ++-- regex/mx.regex/suite.py | 4 ++-- sdk/mx.sdk/suite.py | 4 ++-- substratevm/mx.substratevm/suite.py | 4 ++-- tools/mx.tools/suite.py | 4 ++-- truffle/mx.truffle/suite.py | 4 ++-- vm/mx.vm/suite.py | 4 ++-- wasm/mx.wasm/suite.py | 2 +- 9 files changed, 17 insertions(+), 17 deletions(-) diff --git a/compiler/mx.compiler/suite.py b/compiler/mx.compiler/suite.py index 061cb7f3a926..cfd6cce09f15 100644 --- a/compiler/mx.compiler/suite.py +++ b/compiler/mx.compiler/suite.py @@ -4,8 +4,8 @@ "sourceinprojectwhitelist" : [], "groupId" : "org.graalvm.compiler", - "version" : "24.1.0", - "release" : True, + "version" : "24.1.1", + "release" : False, "url" : "http://www.graalvm.org/", "developer" : { "name" : "GraalVM Development", diff --git a/espresso/mx.espresso/suite.py b/espresso/mx.espresso/suite.py index 5aaf3363f991..90fd788f297e 100644 --- a/espresso/mx.espresso/suite.py +++ b/espresso/mx.espresso/suite.py @@ -24,8 +24,8 @@ suite = { "mxversion": "7.27.1", "name": "espresso", - "version" : "24.1.0", - "release" : True, + "version" : "24.1.1", + "release" : False, "groupId" : "org.graalvm.espresso", "url" : "https://www.graalvm.org/reference-manual/java-on-truffle/", "developer" : { diff --git a/regex/mx.regex/suite.py b/regex/mx.regex/suite.py index c9c957384740..d5ae688ccaf3 100644 --- a/regex/mx.regex/suite.py +++ b/regex/mx.regex/suite.py @@ -43,8 +43,8 @@ "name" : "regex", - "version" : "24.1.0", - "release" : True, + "version" : "24.1.1", + "release" : False, "groupId" : "org.graalvm.regex", "url" : "http://www.graalvm.org/", "developer" : { diff --git a/sdk/mx.sdk/suite.py b/sdk/mx.sdk/suite.py index 7d3ebfafc869..a20b624044c9 100644 --- a/sdk/mx.sdk/suite.py +++ b/sdk/mx.sdk/suite.py @@ -41,8 +41,8 @@ suite = { "mxversion": "7.27.0", "name" : "sdk", - "version" : "24.1.0", - "release" : True, + "version" : "24.1.1", + "release" : False, "sourceinprojectwhitelist" : [], "url" : "https://github.com/oracle/graal", "groupId" : "org.graalvm.sdk", diff --git a/substratevm/mx.substratevm/suite.py b/substratevm/mx.substratevm/suite.py index 1d130c582ed6..e5e16fefb882 100644 --- a/substratevm/mx.substratevm/suite.py +++ b/substratevm/mx.substratevm/suite.py @@ -2,8 +2,8 @@ suite = { "mxversion": "7.27.1", "name": "substratevm", - "version" : "24.1.0", - "release" : True, + "version" : "24.1.1", + "release" : False, "url" : "https://github.com/oracle/graal/tree/master/substratevm", "groupId" : "org.graalvm.nativeimage", diff --git a/tools/mx.tools/suite.py b/tools/mx.tools/suite.py index 7a736466660f..120b9de39982 100644 --- a/tools/mx.tools/suite.py +++ b/tools/mx.tools/suite.py @@ -26,8 +26,8 @@ "defaultLicense" : "GPLv2-CPE", "groupId" : "org.graalvm.tools", - "version" : "24.1.0", - "release" : True, + "version" : "24.1.1", + "release" : False, "url" : "http://openjdk.java.net/projects/graal", "developer" : { "name" : "GraalVM Development", diff --git a/truffle/mx.truffle/suite.py b/truffle/mx.truffle/suite.py index ff360cbc20fa..e95ca13745f7 100644 --- a/truffle/mx.truffle/suite.py +++ b/truffle/mx.truffle/suite.py @@ -41,8 +41,8 @@ suite = { "mxversion": "7.27.1", "name" : "truffle", - "version" : "24.1.0", - "release" : True, + "version" : "24.1.1", + "release" : False, "groupId" : "org.graalvm.truffle", "sourceinprojectwhitelist" : [], "url" : "http://openjdk.java.net/projects/graal", diff --git a/vm/mx.vm/suite.py b/vm/mx.vm/suite.py index 24b11d8a0ba8..175233fcb818 100644 --- a/vm/mx.vm/suite.py +++ b/vm/mx.vm/suite.py @@ -1,8 +1,8 @@ suite = { "name": "vm", - "version" : "24.1.0", + "version" : "24.1.1", "mxversion": "7.27.0", - "release" : True, + "release" : False, "groupId" : "org.graalvm", "url" : "http://www.graalvm.org/", diff --git a/wasm/mx.wasm/suite.py b/wasm/mx.wasm/suite.py index fcb601e852d3..a3ee761f3ed4 100644 --- a/wasm/mx.wasm/suite.py +++ b/wasm/mx.wasm/suite.py @@ -42,7 +42,7 @@ "mxversion": "7.27.1", "name" : "wasm", "groupId" : "org.graalvm.wasm", - "version" : "24.1.0", + "version" : "24.1.1", "versionConflictResolution" : "latest", "url" : "http://graalvm.org/", "developer" : { From 222e006506d63b233237ceff5484b65743e60e2e Mon Sep 17 00:00:00 2001 From: Danilo Ansaloni Date: Mon, 9 Sep 2024 15:43:55 +0200 Subject: [PATCH 05/35] Update js and graalpython imports. --- vm/mx.vm/suite.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/vm/mx.vm/suite.py b/vm/mx.vm/suite.py index 175233fcb818..96bf9b14c55c 100644 --- a/vm/mx.vm/suite.py +++ b/vm/mx.vm/suite.py @@ -33,7 +33,7 @@ "name": "graal-nodejs", "subdir": True, "dynamic": True, - "version": "5ed929b213fff8a888ebfeeb86cbfd5b3b74f663", + "version": "8bbd1c47ef001527d43b5826f7519955423551fc", "urls" : [ {"url" : "https://github.com/graalvm/graaljs.git", "kind" : "git"}, ] @@ -42,7 +42,7 @@ "name": "graal-js", "subdir": True, "dynamic": True, - "version": "5ed929b213fff8a888ebfeeb86cbfd5b3b74f663", + "version": "8bbd1c47ef001527d43b5826f7519955423551fc", "urls": [ {"url": "https://github.com/graalvm/graaljs.git", "kind" : "git"}, ] @@ -65,7 +65,7 @@ }, { "name": "graalpython", - "version": "c0c790b029c1e6fa58c6f4345f749fa5d5453bf2", + "version": "a97e765429d488672e19f66c3c33eea1e00e32ed", "dynamic": True, "urls": [ {"url": "https://github.com/graalvm/graalpython.git", "kind": "git"}, From bf663bf6d3153e255b2abe778356bdda0a4fbf31 Mon Sep 17 00:00:00 2001 From: Danilo Ansaloni Date: Mon, 9 Sep 2024 18:16:10 +0200 Subject: [PATCH 06/35] Update GraalVM versions used by simplelanguage and simpletool. --- truffle/external_repos/simplelanguage/pom.xml | 2 +- truffle/external_repos/simpletool/pom.xml | 2 +- vm/mx.vm/suite.py | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/truffle/external_repos/simplelanguage/pom.xml b/truffle/external_repos/simplelanguage/pom.xml index 65259103ef24..e8202504732c 100644 --- a/truffle/external_repos/simplelanguage/pom.xml +++ b/truffle/external_repos/simplelanguage/pom.xml @@ -47,7 +47,7 @@ UTF-8 jdt_apt - 24.1.0-dev + 24.1.1-dev 17 17 org.graalvm.sl.launcher/com.oracle.truffle.sl.launcher.SLMain diff --git a/truffle/external_repos/simpletool/pom.xml b/truffle/external_repos/simpletool/pom.xml index 26385c8cf881..f9d964e782d6 100644 --- a/truffle/external_repos/simpletool/pom.xml +++ b/truffle/external_repos/simpletool/pom.xml @@ -48,7 +48,7 @@ ${graalvm.version} simpletool - 24.1.0-dev + 24.1.1-dev UTF-8 17 17 diff --git a/vm/mx.vm/suite.py b/vm/mx.vm/suite.py index 96bf9b14c55c..f9db2a02ebc8 100644 --- a/vm/mx.vm/suite.py +++ b/vm/mx.vm/suite.py @@ -65,7 +65,7 @@ }, { "name": "graalpython", - "version": "a97e765429d488672e19f66c3c33eea1e00e32ed", + "version": "6cbd2ee2e4d335817267e9e180de8f7ada4d9971", "dynamic": True, "urls": [ {"url": "https://github.com/graalvm/graalpython.git", "kind": "git"}, From a0400712c8744f46c48079df72873c778b5b04e0 Mon Sep 17 00:00:00 2001 From: jovsteva Date: Wed, 4 Sep 2024 09:37:34 +0200 Subject: [PATCH 07/35] Do not include TruffleJfrFeature if PGO config is specified. (cherry picked from commit 3ce4246078ad557730035692fab71b8ef926eb7c) --- .../src/com/oracle/svm/truffle/TruffleJFRFeature.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/substratevm/src/com.oracle.svm.truffle/src/com/oracle/svm/truffle/TruffleJFRFeature.java b/substratevm/src/com.oracle.svm.truffle/src/com/oracle/svm/truffle/TruffleJFRFeature.java index 1607b8176bc9..9bdb2dabb8eb 100644 --- a/substratevm/src/com.oracle.svm.truffle/src/com/oracle/svm/truffle/TruffleJFRFeature.java +++ b/substratevm/src/com.oracle.svm.truffle/src/com/oracle/svm/truffle/TruffleJFRFeature.java @@ -66,6 +66,6 @@ public List> getRequiredFeatures() { } private static boolean isEnabled() { - return ImageSingletons.contains(TruffleFeature.class) && ImageSingletons.contains(JfrFeature.class); + return ImageSingletons.contains(TruffleFeature.class) && JfrFeature.isInConfiguration(true); } } From 6849f43147cbf8f71c0c9fc1b01a4879bbdb891a Mon Sep 17 00:00:00 2001 From: Christian Wimmer Date: Tue, 27 Aug 2024 14:22:13 -0700 Subject: [PATCH 08/35] Eagerly initialize caches in ValueConversions (cherry picked from commit fb9b6c06c886ed09ab448de6fd1582c02735c60a) --- .../methodhandles/MethodHandleFeature.java | 61 ++++++------------- .../hosted/reflect/ReflectionDataBuilder.java | 3 +- 2 files changed, 20 insertions(+), 44 deletions(-) diff --git a/substratevm/src/com.oracle.svm.hosted/src/com/oracle/svm/hosted/methodhandles/MethodHandleFeature.java b/substratevm/src/com.oracle.svm.hosted/src/com/oracle/svm/hosted/methodhandles/MethodHandleFeature.java index fbc2f82d0b31..e3c08b24e490 100644 --- a/substratevm/src/com.oracle.svm.hosted/src/com/oracle/svm/hosted/methodhandles/MethodHandleFeature.java +++ b/substratevm/src/com.oracle.svm.hosted/src/com/oracle/svm/hosted/methodhandles/MethodHandleFeature.java @@ -33,7 +33,6 @@ import java.lang.reflect.Member; import java.lang.reflect.Method; import java.util.Iterator; -import java.util.Locale; import java.util.Optional; import java.util.concurrent.ConcurrentHashMap; import java.util.function.Supplier; @@ -163,17 +162,7 @@ public void beforeAnalysis(BeforeAnalysisAccess a) { access.registerReachabilityHandler(MethodHandleFeature::registerInvokersFunctionsForReflection, ReflectionUtil.lookupMethod(access.findClassByName("java.lang.invoke.Invokers"), "getFunction", byte.class)); - access.registerReachabilityHandler(MethodHandleFeature::registerValueConversionBoxFunctionsForReflection, - ReflectionUtil.lookupMethod(ValueConversions.class, "boxExact", Wrapper.class)); - - access.registerReachabilityHandler(MethodHandleFeature::registerValueConversionUnboxFunctionsForReflection, - ReflectionUtil.lookupMethod(ValueConversions.class, "unbox", Wrapper.class, int.class)); - - access.registerReachabilityHandler(MethodHandleFeature::registerValueConversionConvertFunctionsForReflection, - ReflectionUtil.lookupMethod(ValueConversions.class, "convertPrimitive", Wrapper.class, Wrapper.class)); - - access.registerReachabilityHandler(MethodHandleFeature::registerValueConversionIgnoreForReflection, - ReflectionUtil.lookupMethod(ValueConversions.class, "ignore")); + eagerlyInitializeValueConversionsCaches(); access.registerClassInitializerReachabilityHandler(MethodHandleFeature::registerDelegatingMHFunctionsForReflection, access.findClassByName("java.lang.invoke.DelegatingMethodHandle")); @@ -328,44 +317,32 @@ private static void registerInvokersFunctionsForReflection(DuringAnalysisAccess RuntimeReflection.register(ReflectionUtil.lookupMethod(invokersClazz, "directVarHandleTarget", access.findClassByName("java.lang.invoke.VarHandle"))); } - private static void registerValueConversionBoxFunctionsForReflection(DuringAnalysisAccess access) { - for (Wrapper type : Wrapper.values()) { - if (type.primitiveType().isPrimitive() && type != Wrapper.VOID) { - RuntimeReflection.register(ReflectionUtil.lookupMethod(ValueConversions.class, "box" + type.wrapperSimpleName(), type.primitiveType())); - } - } - } + /** + * Eagerly initialize method handle caches in {@link ValueConversions} so that 1) we avoid + * reflection registration for conversion methods, and 2) the static analysis already sees a + * consistent snapshot that does not change after analysis when the JDK needs more conversions. + */ + private static void eagerlyInitializeValueConversionsCaches() { + ValueConversions.ignore(); - private static void registerValueConversionUnboxFunctionsForReflection(DuringAnalysisAccess access) { - for (Wrapper type : Wrapper.values()) { - if (type.primitiveType().isPrimitive() && type != Wrapper.VOID) { - RuntimeReflection.register(ReflectionUtil.lookupMethod(ValueConversions.class, "unbox" + type.wrapperSimpleName(), type.wrapperType())); - RuntimeReflection.register(ReflectionUtil.lookupMethod(ValueConversions.class, "unbox" + type.wrapperSimpleName(), Object.class, boolean.class)); + for (Wrapper src : Wrapper.values()) { + if (src != Wrapper.VOID && src.primitiveType().isPrimitive()) { + ValueConversions.boxExact(src); + + ValueConversions.unboxExact(src, false); + ValueConversions.unboxExact(src, true); + ValueConversions.unboxWiden(src); + ValueConversions.unboxCast(src); } - } - } - private static void registerValueConversionConvertFunctionsForReflection(DuringAnalysisAccess access) { - for (Wrapper src : Wrapper.values()) { - for (Wrapper dest : Wrapper.values()) { - if (src != dest && src.primitiveType().isPrimitive() && src != Wrapper.VOID && dest.primitiveType().isPrimitive() && dest != Wrapper.VOID) { - RuntimeReflection.register(ReflectionUtil.lookupMethod(ValueConversions.class, valueConverterName(src, dest), src.primitiveType())); + for (Wrapper dst : Wrapper.values()) { + if (src != Wrapper.VOID && dst != Wrapper.VOID && (src == dst || (src.primitiveType().isPrimitive() && dst.primitiveType().isPrimitive()))) { + ValueConversions.convertPrimitive(src, dst); } } } } - private static String valueConverterName(Wrapper src, Wrapper dest) { - String srcType = src.primitiveSimpleName(); - String destType = dest.primitiveSimpleName(); - /* Capitalize first letter of destination type */ - return srcType + "To" + destType.substring(0, 1).toUpperCase(Locale.ROOT) + destType.substring(1); - } - - private static void registerValueConversionIgnoreForReflection(DuringAnalysisAccess access) { - RuntimeReflection.register(ReflectionUtil.lookupMethod(ValueConversions.class, "ignore", Object.class)); - } - private static void registerDelegatingMHFunctionsForReflection(DuringAnalysisAccess access) { Class delegatingMHClazz = access.findClassByName("java.lang.invoke.DelegatingMethodHandle"); RuntimeReflection.register(ReflectionUtil.lookupMethod(delegatingMHClazz, "getTarget")); diff --git a/substratevm/src/com.oracle.svm.hosted/src/com/oracle/svm/hosted/reflect/ReflectionDataBuilder.java b/substratevm/src/com.oracle.svm.hosted/src/com/oracle/svm/hosted/reflect/ReflectionDataBuilder.java index f72a66457480..e266e319e2ad 100644 --- a/substratevm/src/com.oracle.svm.hosted/src/com/oracle/svm/hosted/reflect/ReflectionDataBuilder.java +++ b/substratevm/src/com.oracle.svm.hosted/src/com/oracle/svm/hosted/reflect/ReflectionDataBuilder.java @@ -86,7 +86,6 @@ import com.oracle.svm.core.hub.ClassForNameSupport; import com.oracle.svm.core.hub.DynamicHub; import com.oracle.svm.core.reflect.SubstrateAccessor; -import com.oracle.svm.core.util.UserError; import com.oracle.svm.core.util.VMError; import com.oracle.svm.hosted.ConditionalConfigurationRegistry; import com.oracle.svm.hosted.FeatureImpl.BeforeAnalysisAccessImpl; @@ -178,7 +177,7 @@ public void beforeAnalysis(BeforeAnalysisAccessImpl beforeAnalysisAccess) { private void runConditionalInAnalysisTask(ConfigurationCondition condition, Consumer task) { if (sealed) { - throw UserError.abort("Too late to add classes, methods, and fields for reflective access. Registration must happen in a Feature before the analysis has finished."); + throw new UnsupportedFeatureException("Too late to add classes, methods, and fields for reflective access. Registration must happen in a Feature before the analysis has finished."); } if (universe != null) { From d5a75e5b3f5c169f738b2419fe218e632f2ba30e Mon Sep 17 00:00:00 2001 From: Christian Wimmer Date: Fri, 16 Aug 2024 13:00:17 -0700 Subject: [PATCH 09/35] Reset Provider.Service.constructorCache field (cherry picked from commit 439d980f1007f044a2d37127ba151da7ea305627) --- .../oracle/graal/pointsto/ObjectScanner.java | 6 +++ .../svm/core/jdk/SecuritySubstitutions.java | 12 ++++++ .../hosted/reflect/ReflectionDataBuilder.java | 38 ++++++++++++------- 3 files changed, 43 insertions(+), 13 deletions(-) diff --git a/substratevm/src/com.oracle.graal.pointsto/src/com/oracle/graal/pointsto/ObjectScanner.java b/substratevm/src/com.oracle.graal.pointsto/src/com/oracle/graal/pointsto/ObjectScanner.java index 372ef8e22c70..c748e34d1cb8 100644 --- a/substratevm/src/com.oracle.graal.pointsto/src/com/oracle/graal/pointsto/ObjectScanner.java +++ b/substratevm/src/com.oracle.graal.pointsto/src/com/oracle/graal/pointsto/ObjectScanner.java @@ -211,6 +211,12 @@ protected void scanField(AnalysisField field, JavaConstant receiver, ScanReason } catch (UnsupportedFeatureException | AnalysisError.TypeNotFoundError ex) { unsupportedFeatureDuringFieldScan(bb, field, receiver, ex, reason); + } catch (AnalysisError analysisError) { + if (analysisError.getCause() instanceof UnsupportedFeatureException ex) { + unsupportedFeatureDuringFieldScan(bb, field, receiver, ex, reason); + } else { + throw analysisError; + } } } diff --git a/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/jdk/SecuritySubstitutions.java b/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/jdk/SecuritySubstitutions.java index 8b5eb142693c..6ace202546d0 100644 --- a/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/jdk/SecuritySubstitutions.java +++ b/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/jdk/SecuritySubstitutions.java @@ -199,6 +199,18 @@ final class Target_java_security_Provider { private static Target_java_security_Provider_ServiceKey previousKey; } +@TargetClass(value = java.security.Provider.class, innerClass = "Service") +final class Target_java_security_Provider_Service { + + /** + * The field is lazily initialized on first access. We already have the necessary reflection + * configuration for the reflective lookup at image run time. + */ + @Alias // + @RecomputeFieldValue(kind = RecomputeFieldValue.Kind.Reset) // + private Object constructorCache; +} + @Platforms(Platform.HOSTED_ONLY.class) class ServiceKeyComputer implements FieldValueTransformer { @Override diff --git a/substratevm/src/com.oracle.svm.hosted/src/com/oracle/svm/hosted/reflect/ReflectionDataBuilder.java b/substratevm/src/com.oracle.svm.hosted/src/com/oracle/svm/hosted/reflect/ReflectionDataBuilder.java index f72a66457480..aa0dea5574f8 100644 --- a/substratevm/src/com.oracle.svm.hosted/src/com/oracle/svm/hosted/reflect/ReflectionDataBuilder.java +++ b/substratevm/src/com.oracle.svm.hosted/src/com/oracle/svm/hosted/reflect/ReflectionDataBuilder.java @@ -1167,11 +1167,15 @@ public RecordComponent[] getRecordComponents(Class type) { @Override public void registerHeapDynamicHub(Object object, ScanReason reason) { - assert !sealed; DynamicHub hub = (DynamicHub) object; Class javaClass = hub.getHostedJavaClass(); - if (heapDynamicHubs.add(hub) && !SubstitutionReflectivityFilter.shouldExclude(javaClass, metaAccess, universe)) { - registerTypesForClass(metaAccess.lookupJavaType(javaClass), javaClass); + if (heapDynamicHubs.add(hub)) { + if (sealed) { + throw new UnsupportedFeatureException("Registering new class for reflection when the image heap is already sealed: " + javaClass); + } + if (!SubstitutionReflectivityFilter.shouldExclude(javaClass, metaAccess, universe)) { + registerTypesForClass(metaAccess.lookupJavaType(javaClass), javaClass); + } } } @@ -1183,24 +1187,32 @@ public Set getHeapDynamicHubs() { @Override public void registerHeapReflectionField(Field reflectField, ScanReason reason) { - assert !sealed; AnalysisField analysisField = metaAccess.lookupJavaField(reflectField); - if (heapFields.put(analysisField, reflectField) == null && !SubstitutionReflectivityFilter.shouldExclude(reflectField, metaAccess, universe)) { - registerTypesForField(analysisField, reflectField, false); - if (analysisField.getDeclaringClass().isAnnotation()) { - processAnnotationField(ConfigurationCondition.alwaysTrue(), reflectField); + if (heapFields.put(analysisField, reflectField) == null) { + if (sealed) { + throw new UnsupportedFeatureException("Registering new field for reflection when the image heap is already sealed: " + reflectField); + } + if (!SubstitutionReflectivityFilter.shouldExclude(reflectField, metaAccess, universe)) { + registerTypesForField(analysisField, reflectField, false); + if (analysisField.getDeclaringClass().isAnnotation()) { + processAnnotationField(ConfigurationCondition.alwaysTrue(), reflectField); + } } } } @Override public void registerHeapReflectionExecutable(Executable reflectExecutable, ScanReason reason) { - assert !sealed; AnalysisMethod analysisMethod = metaAccess.lookupJavaMethod(reflectExecutable); - if (heapMethods.put(analysisMethod, reflectExecutable) == null && !SubstitutionReflectivityFilter.shouldExclude(reflectExecutable, metaAccess, universe)) { - registerTypesForMethod(analysisMethod, reflectExecutable); - if (reflectExecutable instanceof Method && reflectExecutable.getDeclaringClass().isAnnotation()) { - processAnnotationMethod(false, (Method) reflectExecutable); + if (heapMethods.put(analysisMethod, reflectExecutable) == null) { + if (sealed) { + throw new UnsupportedFeatureException("Registering new method for reflection when the image heap is already sealed: " + reflectExecutable); + } + if (!SubstitutionReflectivityFilter.shouldExclude(reflectExecutable, metaAccess, universe)) { + registerTypesForMethod(analysisMethod, reflectExecutable); + if (reflectExecutable instanceof Method && reflectExecutable.getDeclaringClass().isAnnotation()) { + processAnnotationMethod(false, (Method) reflectExecutable); + } } } } From 05501b56c2cffd18e781b7082d59198c0486fec7 Mon Sep 17 00:00:00 2001 From: Jakub Chaloupka Date: Tue, 27 Aug 2024 14:16:47 +0200 Subject: [PATCH 10/35] Fix Addr part alignment in Truffle compilation logs. (cherry picked from commit f74bff6d504c4eba263c1e808c572ae10939a04f) --- .../truffle/runtime/debug/TraceCompilationListener.java | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/truffle/src/com.oracle.truffle.runtime/src/com/oracle/truffle/runtime/debug/TraceCompilationListener.java b/truffle/src/com.oracle.truffle.runtime/src/com/oracle/truffle/runtime/debug/TraceCompilationListener.java index 0a8bdbb61261..13d65e9f510b 100644 --- a/truffle/src/com.oracle.truffle.runtime/src/com/oracle/truffle/runtime/debug/TraceCompilationListener.java +++ b/truffle/src/com.oracle.truffle.runtime/src/com/oracle/truffle/runtime/debug/TraceCompilationListener.java @@ -85,7 +85,7 @@ public static void install(OptimizedTruffleRuntime runtime) { private static final String QUEUED_FORMAT = "opt queued " + TARGET_FORMAT + "|" + TIER_FORMAT + "|" + COUNT_THRESHOLD_FORMAT + "|" + QUEUE_FORMAT + "|UTC %s|Src %s"; private static final String UNQUEUED_FORMAT = "opt unque. " + TARGET_FORMAT + "|" + TIER_FORMAT + "|" + COUNT_THRESHOLD_FORMAT + "|" + QUEUE_FORMAT + "|UTC %s|Src %s|Reason %s"; private static final String START_FORMAT = "opt start " + TARGET_FORMAT + "|" + TIER_FORMAT + "|Priority %9d|Rate %.6f|" + QUEUE_FORMAT + "|UTC %s|Src %s"; - private static final String DONE_FORMAT = "opt done " + TARGET_FORMAT + "|" + TIER_FORMAT + "|Time %18s|AST %4d|Inlined %3dY %3dN|IR %6d/%6d|CodeSize %7d|Addr %7s|UTC %s|Src %s"; + private static final String DONE_FORMAT = "opt done " + TARGET_FORMAT + "|" + TIER_FORMAT + "|Time %18s|AST %4d|Inlined %3dY %3dN|IR %6d/%6d|CodeSize %7d|Addr 0x%012x|UTC %s|Src %s"; private static final String FAILED_FORMAT = "opt failed " + TARGET_FORMAT + "|" + TIER_FORMAT + "|Time %18s|Reason: %s|UTC %s|Src %s"; private static final String INV_FORMAT = "opt inval. " + TARGET_FORMAT + " |UTC %s|Src %s|Reason %s"; private static final String DEOPT_FORMAT = "opt deopt " + TARGET_FORMAT + "| |UTC %s|Src %s"; @@ -244,7 +244,7 @@ public void onCompilationSuccess(OptimizedCallTarget target, AbstractCompilation compilation.nodeCountPartialEval, graph == null ? 0 : graph.getNodeCount(), result == null ? 0 : result.getTargetCodeSize(), - "0x" + Long.toHexString(target.getCodeAddress()), + target.getCodeAddress(), TIME_FORMATTER.format(ZonedDateTime.now()), formatSourceSection(safeSourceSection(target)))); currentCompilation.remove(); From bee00b67b82d74215d3442dffff5a4552c9feba0 Mon Sep 17 00:00:00 2001 From: ol-automation_ww Date: Wed, 11 Sep 2024 15:20:24 +0000 Subject: [PATCH 11/35] update JVMCI to 23.0.1+9-jvmci-b01 --- common.json | 14 +++++++------- .../graal/compiler/hotspot/JVMCIVersionCheck.java | 4 ++-- 2 files changed, 9 insertions(+), 9 deletions(-) diff --git a/common.json b/common.json index e97e36e6f045..92275f3c6317 100644 --- a/common.json +++ b/common.json @@ -45,13 +45,13 @@ "labsjdk-ee-21-llvm": {"name": "labsjdk", "version": "ee-21.0.2+13-jvmci-23.1-b33-sulong", "platformspecific": true }, "graalvm-ee-21": {"name": "graalvm-java21", "version": "23.1.3", "platformspecific": true }, - "oraclejdk-latest": {"name": "jpg-jdk", "version": "23", "build_id": "jdk-23+37", "platformspecific": true, "extrabundles": ["static-libs"]}, - "labsjdk-ce-latest": {"name": "labsjdk", "version": "ce-23+37-jvmci-b01", "platformspecific": true }, - "labsjdk-ce-latestDebug": {"name": "labsjdk", "version": "ce-23+37-jvmci-b01-debug", "platformspecific": true }, - "labsjdk-ce-latest-llvm": {"name": "labsjdk", "version": "ce-23+37-jvmci-b01-sulong", "platformspecific": true }, - "labsjdk-ee-latest": {"name": "labsjdk", "version": "ee-23+37-jvmci-b01", "platformspecific": true }, - "labsjdk-ee-latestDebug": {"name": "labsjdk", "version": "ee-23+37-jvmci-b01-debug", "platformspecific": true }, - "labsjdk-ee-latest-llvm": {"name": "labsjdk", "version": "ee-23+37-jvmci-b01-sulong", "platformspecific": true } + "oraclejdk-latest": {"name": "jpg-jdk", "version": "23", "build_id": "jdk-23.0.1+9", "platformspecific": true, "extrabundles": ["static-libs"]}, + "labsjdk-ce-latest": {"name": "labsjdk", "version": "ce-23.0.1+9-jvmci-b01", "platformspecific": true }, + "labsjdk-ce-latestDebug": {"name": "labsjdk", "version": "ce-23.0.1+9-jvmci-b01-debug", "platformspecific": true }, + "labsjdk-ce-latest-llvm": {"name": "labsjdk", "version": "ce-23.0.1+9-jvmci-b01-sulong", "platformspecific": true }, + "labsjdk-ee-latest": {"name": "labsjdk", "version": "ee-23.0.1+9-jvmci-b01", "platformspecific": true }, + "labsjdk-ee-latestDebug": {"name": "labsjdk", "version": "ee-23.0.1+9-jvmci-b01-debug", "platformspecific": true }, + "labsjdk-ee-latest-llvm": {"name": "labsjdk", "version": "ee-23.0.1+9-jvmci-b01-sulong", "platformspecific": true } }, "eclipse": { diff --git a/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java b/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java index c0108551f746..69838f005cfd 100644 --- a/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java +++ b/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java @@ -55,8 +55,8 @@ public final class JVMCIVersionCheck { private static final Map> JVMCI_MIN_VERSIONS = Map.of( "21", Map.of(DEFAULT_VENDOR_ENTRY, createLegacyVersion(23, 1, 33)), "23", Map.of( - "Oracle Corporation", createLabsJDKVersion("23+37", 1), - DEFAULT_VENDOR_ENTRY, createLabsJDKVersion("23+37", 1))); + "Oracle Corporation", createLabsJDKVersion("23.0.1+9", 1), + DEFAULT_VENDOR_ENTRY, createLabsJDKVersion("23.0.1+9", 1))); private static final int NA = 0; /** * Minimum Java release supported by Graal. From b601cd2180a38900f2d1e13efe9a30f8c3d599d3 Mon Sep 17 00:00:00 2001 From: Loic Ottet Date: Mon, 2 Sep 2024 10:54:45 +0200 Subject: [PATCH 12/35] Prevent emission of typeReachable in reachability-metadata.json --- substratevm/mx.substratevm/mx_substratevm.py | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/substratevm/mx.substratevm/mx_substratevm.py b/substratevm/mx.substratevm/mx_substratevm.py index 234393cd2d06..bf0629adbcc8 100644 --- a/substratevm/mx.substratevm/mx_substratevm.py +++ b/substratevm/mx.substratevm/mx_substratevm.py @@ -1139,7 +1139,9 @@ def _native_image_launcher_extra_jvm_args(): build_args=driver_build_args + [ '--features=com.oracle.svm.agent.NativeImageAgent$RegistrationFeature', '--enable-url-protocols=jar', - ], + ] + svm_experimental_options([ + '-H:+TreatAllTypeReachableConditionsAsTypeReached', + ]), headers=False, home_finder=False, ), @@ -1448,6 +1450,7 @@ def _native_image_configure_extra_jvm_args(): main_class='com.oracle.svm.configure.ConfigurationTool', build_args=svm_experimental_options([ '-H:-ParseRuntimeOptions', + '-H:+TreatAllTypeReachableConditionsAsTypeReached', ]), extra_jvm_args=_native_image_configure_extra_jvm_args(), home_finder=False, From 8bb5351e01bc8f20fd8afb026784d3c322aaaf6c Mon Sep 17 00:00:00 2001 From: Loic Ottet Date: Wed, 4 Sep 2024 11:32:57 +0200 Subject: [PATCH 13/35] Ensure correct condition format during metadata emission --- .../ConfigurationConditionPrintable.java | 8 +++++-- .../configure/config/ConfigurationType.java | 2 +- .../configure/config/ProxyConfiguration.java | 2 +- .../config/ResourceConfiguration.java | 24 +++++++++---------- ...ationConfigurationLambdaCapturingType.java | 2 +- .../SerializationConfigurationType.java | 13 ++++++---- 6 files changed, 29 insertions(+), 22 deletions(-) diff --git a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ConfigurationConditionPrintable.java b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ConfigurationConditionPrintable.java index d9a4eda47730..0344046c7736 100644 --- a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ConfigurationConditionPrintable.java +++ b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ConfigurationConditionPrintable.java @@ -35,10 +35,14 @@ import jdk.graal.compiler.util.json.JsonWriter; final class ConfigurationConditionPrintable { - static void printConditionAttribute(UnresolvedConfigurationCondition condition, JsonWriter writer) throws IOException { + static void printConditionAttribute(UnresolvedConfigurationCondition condition, JsonWriter writer, boolean combinedFile) throws IOException { if (!condition.isAlwaysTrue()) { writer.quote(CONDITIONAL_KEY).appendFieldSeparator().appendObjectStart(); - writer.quote(condition.isRuntimeChecked() ? TYPE_REACHED_KEY : TYPE_REACHABLE_KEY).appendFieldSeparator().quote(condition.getTypeName()); + /* + * typeReachable conditions are emitted as typeReached in reachability-metadata.json. + * typeReached conditions are emitted as typeReachable in resource-config.json + */ + writer.quote(combinedFile ? TYPE_REACHED_KEY : TYPE_REACHABLE_KEY).appendFieldSeparator().quote(condition.getTypeName()); writer.appendObjectEnd().appendSeparator(); } } diff --git a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ConfigurationType.java b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ConfigurationType.java index 7284a8120bf9..39d0bcf00ca1 100644 --- a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ConfigurationType.java +++ b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ConfigurationType.java @@ -460,7 +460,7 @@ public synchronized void setAllPublicConstructors(ConfigurationMemberAccessibili @Override public synchronized void printJson(JsonWriter writer) throws IOException { writer.appendObjectStart(); - ConfigurationConditionPrintable.printConditionAttribute(condition, writer); + ConfigurationConditionPrintable.printConditionAttribute(condition, writer, true); writer.quote("type").appendFieldSeparator(); typeDescriptor.printJson(writer); diff --git a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ProxyConfiguration.java b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ProxyConfiguration.java index 73fc92121bd2..3c0b251c7511 100644 --- a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ProxyConfiguration.java +++ b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ProxyConfiguration.java @@ -116,7 +116,7 @@ public static void printProxyInterfaces(JsonWriter writer, List> list : lists) { writer.append(prefix).newline(); writer.append('{').indent().newline(); - ConfigurationConditionPrintable.printConditionAttribute(list.condition(), writer); + ConfigurationConditionPrintable.printConditionAttribute(list.condition(), writer, false); writer.quote("interfaces").append(":").append('['); String typePrefix = ""; for (String type : list.element()) { diff --git a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ResourceConfiguration.java b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ResourceConfiguration.java index 50b7ac8199f1..a74cf9efd9f3 100644 --- a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ResourceConfiguration.java +++ b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ResourceConfiguration.java @@ -337,7 +337,7 @@ public boolean anyBundleMatches(UnresolvedConfigurationCondition condition, Stri public void printJson(JsonWriter writer) throws IOException { printGlobsJson(writer, true); writer.appendSeparator().newline(); - printBundlesJson(writer); + printBundlesJson(writer, true); } @Override @@ -345,7 +345,7 @@ public void printLegacyJson(JsonWriter writer) throws IOException { writer.appendObjectStart().indent().newline(); printResourcesJson(writer); writer.appendSeparator().newline(); - printBundlesJson(writer); + printBundlesJson(writer, false); writer.appendSeparator().newline(); printGlobsJson(writer, false); writer.unindent().newline().appendObjectEnd(); @@ -363,14 +363,14 @@ void printResourcesJson(JsonWriter writer) throws IOException { writer.appendObjectEnd(); } - void printBundlesJson(JsonWriter writer) throws IOException { + void printBundlesJson(JsonWriter writer, boolean combinedFile) throws IOException { writer.quote(BUNDLES_KEY).appendFieldSeparator(); - JsonPrinter.printCollection(writer, bundles.keySet(), ConditionalElement.comparator(), (p, w) -> printResourceBundle(bundles.get(p), w)); + JsonPrinter.printCollection(writer, bundles.keySet(), ConditionalElement.comparator(), (p, w) -> printResourceBundle(bundles.get(p), w, combinedFile)); } - void printGlobsJson(JsonWriter writer, boolean useResourcesFieldName) throws IOException { - writer.quote(useResourcesFieldName ? RESOURCES_KEY : GLOBS_KEY).appendFieldSeparator(); - JsonPrinter.printCollection(writer, addedGlobs, ConditionalElement.comparator(ResourceEntry.comparator()), ResourceConfiguration::conditionalGlobElementJson); + void printGlobsJson(JsonWriter writer, boolean combinedFile) throws IOException { + writer.quote(combinedFile ? RESOURCES_KEY : GLOBS_KEY).appendFieldSeparator(); + JsonPrinter.printCollection(writer, addedGlobs, ConditionalElement.comparator(ResourceEntry.comparator()), (p, w) -> conditionalGlobElementJson(p, w, combinedFile)); } @Override @@ -378,9 +378,9 @@ public ConfigurationParser createParser(boolean strictMetadata) { return ResourceConfigurationParser.create(strictMetadata, ConfigurationConditionResolver.identityResolver(), new ResourceConfiguration.ParserAdapter(this), true); } - private static void printResourceBundle(BundleConfiguration config, JsonWriter writer) throws IOException { + private static void printResourceBundle(BundleConfiguration config, JsonWriter writer, boolean combinedFile) throws IOException { writer.appendObjectStart(); - ConfigurationConditionPrintable.printConditionAttribute(config.condition, writer); + ConfigurationConditionPrintable.printConditionAttribute(config.condition, writer, combinedFile); writer.quote("name").appendFieldSeparator().quote(config.baseName); if (!config.locales.isEmpty()) { writer.appendSeparator().quote("locales").appendFieldSeparator(); @@ -411,11 +411,11 @@ public boolean supportsCombinedFile() { return true; } - private static void conditionalGlobElementJson(ConditionalElement p, JsonWriter w) throws IOException { + private static void conditionalGlobElementJson(ConditionalElement p, JsonWriter w, boolean combinedFile) throws IOException { String pattern = p.element().pattern(); String module = p.element().module(); w.appendObjectStart(); - ConfigurationConditionPrintable.printConditionAttribute(p.condition(), w); + ConfigurationConditionPrintable.printConditionAttribute(p.condition(), w, combinedFile); if (module != null) { w.quote("module").appendFieldSeparator().quote(module).appendSeparator(); } @@ -425,7 +425,7 @@ private static void conditionalGlobElementJson(ConditionalElement private static void conditionalRegexElementJson(ConditionalElement p, JsonWriter w) throws IOException { w.appendObjectStart(); - ConfigurationConditionPrintable.printConditionAttribute(p.condition(), w); + ConfigurationConditionPrintable.printConditionAttribute(p.condition(), w, false); w.quote("pattern").appendFieldSeparator().quote(p.element()); w.appendObjectEnd(); } diff --git a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/SerializationConfigurationLambdaCapturingType.java b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/SerializationConfigurationLambdaCapturingType.java index 0e7798618d1e..d797cdd42e58 100644 --- a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/SerializationConfigurationLambdaCapturingType.java +++ b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/SerializationConfigurationLambdaCapturingType.java @@ -57,7 +57,7 @@ public String getQualifiedJavaName() { @Override public void printJson(JsonWriter writer) throws IOException { writer.append('{').indent().newline(); - ConfigurationConditionPrintable.printConditionAttribute(condition, writer); + ConfigurationConditionPrintable.printConditionAttribute(condition, writer, false); writer.quote(SerializationConfigurationParser.NAME_KEY).append(":").quote(qualifiedJavaName); writer.unindent().newline().append('}'); diff --git a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/SerializationConfigurationType.java b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/SerializationConfigurationType.java index 21a96a62368f..bc6bc8fcadb0 100644 --- a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/SerializationConfigurationType.java +++ b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/SerializationConfigurationType.java @@ -35,6 +35,9 @@ import jdk.graal.compiler.util.json.JsonPrintable; import jdk.graal.compiler.util.json.JsonWriter; +import static com.oracle.svm.core.configure.ConfigurationParser.NAME_KEY; +import static com.oracle.svm.core.configure.ConfigurationParser.TYPE_KEY; + public class SerializationConfigurationType implements JsonPrintable, Comparable { private final UnresolvedConfigurationCondition condition; private final String qualifiedJavaName; @@ -66,17 +69,17 @@ public UnresolvedConfigurationCondition getCondition() { @Override public void printJson(JsonWriter writer) throws IOException { - printJson(writer, SerializationConfigurationParser.TYPE_KEY); + printJson(writer, true); } public void printLegacyJson(JsonWriter writer) throws IOException { - printJson(writer, SerializationConfigurationParser.NAME_KEY); + printJson(writer, false); } - private void printJson(JsonWriter writer, String key) throws IOException { + private void printJson(JsonWriter writer, boolean combinedFile) throws IOException { writer.appendObjectStart(); - ConfigurationConditionPrintable.printConditionAttribute(condition, writer); - writer.quote(key).appendFieldSeparator().quote(qualifiedJavaName); + ConfigurationConditionPrintable.printConditionAttribute(condition, writer, combinedFile); + writer.quote(combinedFile ? TYPE_KEY : NAME_KEY).appendFieldSeparator().quote(qualifiedJavaName); if (qualifiedCustomTargetConstructorJavaName != null) { writer.appendSeparator(); writer.quote(SerializationConfigurationParser.CUSTOM_TARGET_CONSTRUCTOR_CLASS_KEY).appendFieldSeparator() From c91901e0c705f3d46596cb2664aafc81caba0e78 Mon Sep 17 00:00:00 2001 From: Loic Ottet Date: Wed, 4 Sep 2024 11:48:29 +0200 Subject: [PATCH 14/35] Parse constant resource patterns as globs --- .../LegacyResourceConfigurationParser.java | 64 +++++++++++++++++++ .../ResourceConfigurationParser.java | 48 ++------------ .../configure/ResourceMetadataParser.java | 8 +++ 3 files changed, 77 insertions(+), 43 deletions(-) diff --git a/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/configure/LegacyResourceConfigurationParser.java b/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/configure/LegacyResourceConfigurationParser.java index 0f680cb44899..ed068c6690c9 100644 --- a/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/configure/LegacyResourceConfigurationParser.java +++ b/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/configure/LegacyResourceConfigurationParser.java @@ -25,9 +25,16 @@ package com.oracle.svm.core.configure; import java.net.URI; +import java.util.Collections; +import java.util.List; +import java.util.function.BiConsumer; import org.graalvm.collections.EconomicMap; import org.graalvm.collections.MapCursor; +import org.graalvm.nativeimage.impl.UnresolvedConfigurationCondition; + +import com.oracle.svm.core.TypeResult; +import com.oracle.svm.core.jdk.resources.CompressedGlobTrie.CompressedGlobTrie; final class LegacyResourceConfigurationParser extends ResourceConfigurationParser { LegacyResourceConfigurationParser(ConfigurationConditionResolver conditionResolver, ResourcesRegistry registry, boolean strictConfiguration) { @@ -64,4 +71,61 @@ private void parseTopLevelObject(EconomicMap obj) { parseGlobsObject(globsObject); } } + + @Override + protected UnresolvedConfigurationCondition parseCondition(EconomicMap condition) { + return parseCondition(condition, false); + } + + @SuppressWarnings("unchecked") + private void parseResourcesObject(Object resourcesObject) { + if (resourcesObject instanceof EconomicMap) { // New format + EconomicMap resourcesObjectMap = (EconomicMap) resourcesObject; + checkAttributes(resourcesObjectMap, "resource descriptor object", Collections.singleton("includes"), Collections.singleton("excludes")); + Object includesObject = resourcesObjectMap.get("includes"); + Object excludesObject = resourcesObjectMap.get("excludes"); + + List includes = asList(includesObject, "Attribute 'includes' must be a list of resources"); + for (Object object : includes) { + parsePatternEntry(object, (condition, pattern) -> registry.addResources(condition, pattern), + (condition, module, glob) -> registry.addGlob(condition, module, glob), "'includes' list"); + } + + if (excludesObject != null) { + List excludes = asList(excludesObject, "Attribute 'excludes' must be a list of resources"); + for (Object object : excludes) { + parsePatternEntry(object, registry::ignoreResources, null, "'excludes' list"); + } + } + } else { // Old format: may be deprecated in future versions + List resources = asList(resourcesObject, "Attribute 'resources' must be a list of resources"); + for (Object object : resources) { + parsePatternEntry(object, (condition, pattern) -> registry.addResources(condition, pattern), + (condition, module, glob) -> registry.addGlob(condition, module, glob), "'resources' list"); + } + } + } + + private void parsePatternEntry(Object data, BiConsumer resourceRegistry, GlobPatternConsumer globRegistry, String parentType) { + EconomicMap resource = asMap(data, "Elements of " + parentType + " must be a resource descriptor object"); + checkAttributes(resource, "regex resource descriptor object", Collections.singletonList("pattern"), Collections.singletonList(CONDITIONAL_KEY)); + TypeResult resolvedConfigurationCondition = conditionResolver.resolveCondition(parseCondition(resource, false)); + if (!resolvedConfigurationCondition.isPresent()) { + return; + } + + Object valueObject = resource.get("pattern"); + String value = asString(valueObject, "pattern"); + + /* Parse fully literal regex as globs */ + if (value.startsWith("\\Q") && value.endsWith("\\E") && value.indexOf("\\E") == value.lastIndexOf("\\E")) { + String globValue = value.substring("\\Q".length(), value.length() - "\\E".length()); + if (CompressedGlobTrie.validatePattern(globValue).isEmpty()) { + globRegistry.accept(resolvedConfigurationCondition.get(), null, globValue); + return; + } + } + + resourceRegistry.accept(resolvedConfigurationCondition.get(), value); + } } diff --git a/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/configure/ResourceConfigurationParser.java b/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/configure/ResourceConfigurationParser.java index f1927c8c0c9e..a44353ca437a 100644 --- a/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/configure/ResourceConfigurationParser.java +++ b/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/configure/ResourceConfigurationParser.java @@ -28,10 +28,10 @@ import java.util.Collections; import java.util.List; import java.util.Locale; -import java.util.function.BiConsumer; import java.util.stream.Collectors; import org.graalvm.collections.EconomicMap; +import org.graalvm.nativeimage.impl.UnresolvedConfigurationCondition; import com.oracle.svm.core.TypeResult; import com.oracle.svm.core.jdk.localization.LocalizationSupport; @@ -64,38 +64,13 @@ protected void parseBundlesObject(Object bundlesObject) { } } - @SuppressWarnings("unchecked") - protected void parseResourcesObject(Object resourcesObject) { - if (resourcesObject instanceof EconomicMap) { // New format - EconomicMap resourcesObjectMap = (EconomicMap) resourcesObject; - checkAttributes(resourcesObjectMap, "resource descriptor object", Collections.singleton("includes"), Collections.singleton("excludes")); - Object includesObject = resourcesObjectMap.get("includes"); - Object excludesObject = resourcesObjectMap.get("excludes"); - - List includes = asList(includesObject, "Attribute 'includes' must be a list of resources"); - for (Object object : includes) { - parsePatternEntry(object, registry::addResources, "'includes' list"); - } - - if (excludesObject != null) { - List excludes = asList(excludesObject, "Attribute 'excludes' must be a list of resources"); - for (Object object : excludes) { - parsePatternEntry(object, registry::ignoreResources, "'excludes' list"); - } - } - } else { // Old format: may be deprecated in future versions - List resources = asList(resourcesObject, "Attribute 'resources' must be a list of resources"); - for (Object object : resources) { - parsePatternEntry(object, registry::addResources, "'resources' list"); - } - } - } + protected abstract UnresolvedConfigurationCondition parseCondition(EconomicMap condition); private void parseBundle(Object bundle) { EconomicMap resource = asMap(bundle, "Elements of 'bundles' list must be a bundle descriptor object"); checkAttributes(resource, "bundle descriptor object", Collections.singletonList("name"), Arrays.asList("locales", "classNames", "condition")); String basename = asString(resource.get("name")); - TypeResult resolvedConfigurationCondition = conditionResolver.resolveCondition(parseCondition(resource, false)); + TypeResult resolvedConfigurationCondition = conditionResolver.resolveCondition(parseCondition(resource)); if (!resolvedConfigurationCondition.isPresent()) { return; } @@ -133,19 +108,6 @@ private static Locale parseLocale(Object input) { return locale; } - private void parsePatternEntry(Object data, BiConsumer resourceRegistry, String parentType) { - EconomicMap resource = asMap(data, "Elements of " + parentType + " must be a resource descriptor object"); - checkAttributes(resource, "regex resource descriptor object", Collections.singletonList("pattern"), Collections.singletonList(CONDITIONAL_KEY)); - TypeResult resolvedConfigurationCondition = conditionResolver.resolveCondition(parseCondition(resource, false)); - if (!resolvedConfigurationCondition.isPresent()) { - return; - } - - Object valueObject = resource.get("pattern"); - String value = asString(valueObject, "pattern"); - resourceRegistry.accept(resolvedConfigurationCondition.get(), value); - } - protected void parseGlobsObject(Object globsObject) { List globs = asList(globsObject, "Attribute 'globs' must be a list of glob patterns"); for (Object object : globs) { @@ -153,14 +115,14 @@ protected void parseGlobsObject(Object globsObject) { } } - private interface GlobPatternConsumer { + protected interface GlobPatternConsumer { void accept(T a, String b, String c); } private void parseGlobEntry(Object data, GlobPatternConsumer resourceRegistry) { EconomicMap globObject = asMap(data, "Elements of 'globs' list must be a glob descriptor objects"); checkAttributes(globObject, "glob resource descriptor object", Collections.singletonList(GLOB_KEY), List.of(CONDITIONAL_KEY, MODULE_KEY)); - TypeResult resolvedConfigurationCondition = conditionResolver.resolveCondition(parseCondition(globObject, false)); + TypeResult resolvedConfigurationCondition = conditionResolver.resolveCondition(parseCondition(globObject)); if (!resolvedConfigurationCondition.isPresent()) { return; } diff --git a/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/configure/ResourceMetadataParser.java b/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/configure/ResourceMetadataParser.java index 2e1b4720ed4a..6dcaec7c2980 100644 --- a/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/configure/ResourceMetadataParser.java +++ b/substratevm/src/com.oracle.svm.core/src/com/oracle/svm/core/configure/ResourceMetadataParser.java @@ -26,6 +26,9 @@ import java.net.URI; +import org.graalvm.collections.EconomicMap; +import org.graalvm.nativeimage.impl.UnresolvedConfigurationCondition; + final class ResourceMetadataParser extends ResourceConfigurationParser { ResourceMetadataParser(ConfigurationConditionResolver conditionResolver, ResourcesRegistry registry, boolean strictConfiguration) { super(conditionResolver, registry, strictConfiguration); @@ -42,4 +45,9 @@ public void parseAndRegister(Object json, URI origin) { parseBundlesObject(bundlesJson); } } + + @Override + protected UnresolvedConfigurationCondition parseCondition(EconomicMap condition) { + return parseCondition(condition, true); + } } From 8d04f6d31a06c4678fb60bef8fe6e2178782bc7f Mon Sep 17 00:00:00 2001 From: Loic Ottet Date: Wed, 4 Sep 2024 11:54:57 +0200 Subject: [PATCH 15/35] Enable "type" to register reflective elements unconditionally when parsing in the agent or configure tool --- .../config/ParserConfigurationAdapter.java | 24 +++++++++---------- 1 file changed, 12 insertions(+), 12 deletions(-) diff --git a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ParserConfigurationAdapter.java b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ParserConfigurationAdapter.java index c653e9206892..39657123cec2 100644 --- a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ParserConfigurationAdapter.java +++ b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ParserConfigurationAdapter.java @@ -103,73 +103,73 @@ public void registerConstructor(UnresolvedConfigurationCondition condition, bool @Override public void registerPublicClasses(UnresolvedConfigurationCondition condition, ConfigurationType type) { - VMError.guarantee(condition.equals(type.getCondition()), "condition is already a part of the type"); + VMError.guarantee(condition.isAlwaysTrue() || condition.equals(type.getCondition()), "condition is already a part of the type"); type.setAllPublicClasses(); } @Override public void registerDeclaredClasses(UnresolvedConfigurationCondition condition, ConfigurationType type) { - VMError.guarantee(condition.equals(type.getCondition()), "condition is already a part of the type"); + VMError.guarantee(condition.isAlwaysTrue() || condition.equals(type.getCondition()), "condition is already a part of the type"); type.setAllDeclaredClasses(); } @Override public void registerRecordComponents(UnresolvedConfigurationCondition condition, ConfigurationType type) { - VMError.guarantee(condition.equals(type.getCondition()), "condition is already a part of the type"); + VMError.guarantee(condition.isAlwaysTrue() || condition.equals(type.getCondition()), "condition is already a part of the type"); type.setAllRecordComponents(); } @Override public void registerPermittedSubclasses(UnresolvedConfigurationCondition condition, ConfigurationType type) { - VMError.guarantee(condition.equals(type.getCondition()), "condition is already a part of the type"); + VMError.guarantee(condition.isAlwaysTrue() || condition.equals(type.getCondition()), "condition is already a part of the type"); type.setAllPermittedSubclasses(); } @Override public void registerNestMembers(UnresolvedConfigurationCondition condition, ConfigurationType type) { - VMError.guarantee(condition.equals(type.getCondition()), "condition is already a part of the type"); + VMError.guarantee(condition.isAlwaysTrue() || condition.equals(type.getCondition()), "condition is already a part of the type"); type.setAllNestMembers(); } @Override public void registerSigners(UnresolvedConfigurationCondition condition, ConfigurationType type) { - VMError.guarantee(condition.equals(type.getCondition()), "condition is already a part of the type"); + VMError.guarantee(condition.isAlwaysTrue() || condition.equals(type.getCondition()), "condition is already a part of the type"); type.setAllSigners(); } @Override public void registerPublicFields(UnresolvedConfigurationCondition condition, boolean queriedOnly, ConfigurationType type) { - VMError.guarantee(condition.equals(type.getCondition()), "condition is already a part of the type"); + VMError.guarantee(condition.isAlwaysTrue() || condition.equals(type.getCondition()), "condition is already a part of the type"); type.setAllPublicFields(queriedOnly ? ConfigurationMemberAccessibility.QUERIED : ConfigurationMemberAccessibility.ACCESSED); } @Override public void registerDeclaredFields(UnresolvedConfigurationCondition condition, boolean queriedOnly, ConfigurationType type) { - VMError.guarantee(condition.equals(type.getCondition()), "condition is already a part of the type"); + VMError.guarantee(condition.isAlwaysTrue() || condition.equals(type.getCondition()), "condition is already a part of the type"); type.setAllDeclaredFields(queriedOnly ? ConfigurationMemberAccessibility.QUERIED : ConfigurationMemberAccessibility.ACCESSED); } @Override public void registerPublicMethods(UnresolvedConfigurationCondition condition, boolean queriedOnly, ConfigurationType type) { - VMError.guarantee(condition.equals(type.getCondition()), "condition is already a part of the type"); + VMError.guarantee(condition.isAlwaysTrue() || condition.equals(type.getCondition()), "condition is already a part of the type"); type.setAllPublicMethods(queriedOnly ? ConfigurationMemberAccessibility.QUERIED : ConfigurationMemberAccessibility.ACCESSED); } @Override public void registerDeclaredMethods(UnresolvedConfigurationCondition condition, boolean queriedOnly, ConfigurationType type) { - VMError.guarantee(condition.equals(type.getCondition()), "condition is already a part of the type"); + VMError.guarantee(condition.isAlwaysTrue() || condition.equals(type.getCondition()), "condition is already a part of the type"); type.setAllDeclaredMethods(queriedOnly ? ConfigurationMemberAccessibility.QUERIED : ConfigurationMemberAccessibility.ACCESSED); } @Override public void registerPublicConstructors(UnresolvedConfigurationCondition condition, boolean queriedOnly, ConfigurationType type) { - VMError.guarantee(condition.equals(type.getCondition()), "condition is already a part of the type"); + VMError.guarantee(condition.isAlwaysTrue() || condition.equals(type.getCondition()), "condition is already a part of the type"); type.setAllPublicConstructors(queriedOnly ? ConfigurationMemberAccessibility.QUERIED : ConfigurationMemberAccessibility.ACCESSED); } @Override public void registerDeclaredConstructors(UnresolvedConfigurationCondition condition, boolean queriedOnly, ConfigurationType type) { - VMError.guarantee(condition.equals(type.getCondition()), "condition is already a part of the type"); + VMError.guarantee(condition.isAlwaysTrue() || condition.equals(type.getCondition()), "condition is already a part of the type"); type.setAllDeclaredConstructors(queriedOnly ? ConfigurationMemberAccessibility.QUERIED : ConfigurationMemberAccessibility.ACCESSED); } From 3a90fa6cba91d184296d30b6fae1eca298e32e4c Mon Sep 17 00:00:00 2001 From: Loic Ottet Date: Thu, 5 Sep 2024 09:55:37 +0200 Subject: [PATCH 16/35] Pretty print legacy configuration files --- .../configure/config/ProxyConfiguration.java | 33 +++++++++++-------- .../config/ResourceConfiguration.java | 10 +++--- 2 files changed, 24 insertions(+), 19 deletions(-) diff --git a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ProxyConfiguration.java b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ProxyConfiguration.java index 3c0b251c7511..64296045273d 100644 --- a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ProxyConfiguration.java +++ b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ProxyConfiguration.java @@ -110,25 +110,30 @@ public void printJson(JsonWriter writer) throws IOException { public static void printProxyInterfaces(JsonWriter writer, List>> lists) throws IOException { lists.sort(ConditionalElement.comparator(ProxyConfiguration::compareList)); - writer.append('['); - writer.indent(); - String prefix = ""; + writer.appendArrayStart(); + boolean firstProxy = true; for (ConditionalElement> list : lists) { - writer.append(prefix).newline(); - writer.append('{').indent().newline(); + if (firstProxy) { + firstProxy = false; + } else { + writer.appendSeparator(); + } + writer.appendObjectStart(); ConfigurationConditionPrintable.printConditionAttribute(list.condition(), writer, false); - writer.quote("interfaces").append(":").append('['); - String typePrefix = ""; + writer.quote("interfaces").appendFieldSeparator().appendArrayStart(); + boolean firstType = true; for (String type : list.element()) { - writer.append(typePrefix).quote(type); - typePrefix = ","; + if (firstType) { + firstType = false; + } else { + writer.appendSeparator(); + } + writer.quote(type); } - writer.append(']').unindent().newline(); - writer.append('}'); - prefix = ","; + writer.appendArrayEnd(); + writer.appendObjectEnd(); } - writer.unindent().newline(); - writer.append(']'); + writer.appendArrayEnd(); } @Override diff --git a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ResourceConfiguration.java b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ResourceConfiguration.java index a74cf9efd9f3..a5b7b8f766e9 100644 --- a/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ResourceConfiguration.java +++ b/substratevm/src/com.oracle.svm.configure/src/com/oracle/svm/configure/config/ResourceConfiguration.java @@ -336,19 +336,19 @@ public boolean anyBundleMatches(UnresolvedConfigurationCondition condition, Stri @Override public void printJson(JsonWriter writer) throws IOException { printGlobsJson(writer, true); - writer.appendSeparator().newline(); + writer.appendSeparator(); printBundlesJson(writer, true); } @Override public void printLegacyJson(JsonWriter writer) throws IOException { - writer.appendObjectStart().indent().newline(); + writer.appendObjectStart(); printResourcesJson(writer); - writer.appendSeparator().newline(); + writer.appendSeparator(); printBundlesJson(writer, false); - writer.appendSeparator().newline(); + writer.appendSeparator(); printGlobsJson(writer, false); - writer.unindent().newline().appendObjectEnd(); + writer.appendObjectEnd(); } void printResourcesJson(JsonWriter writer) throws IOException { From 0565fb3cfaffd4a5c4793671e4acc4f99c8c869c Mon Sep 17 00:00:00 2001 From: Loic Ottet Date: Mon, 16 Sep 2024 15:22:23 +0200 Subject: [PATCH 17/35] Add changelog entry for reachability-metadata.json --- substratevm/CHANGELOG.md | 2 ++ 1 file changed, 2 insertions(+) diff --git a/substratevm/CHANGELOG.md b/substratevm/CHANGELOG.md index 82ede13ea056..e17f235ad93a 100644 --- a/substratevm/CHANGELOG.md +++ b/substratevm/CHANGELOG.md @@ -28,6 +28,8 @@ This changelog summarizes major changes to GraalVM Native Image. * (GR-52844) Add `-Os`, a new optimization mode to configure the optimizer in a way to get the smallest code size. * (GR-49770) Add support for glob patterns in resource-config files in addition to regexp. The Tracing agent now prints entries in the glob format. * (GR-46386) Throw missing registration errors for JNI queries when the query was not included in the reachability metadata. +* (GR-54241) Streamline Native Image reachability metadata into a single `reachability-metadata.json`. The formerly-used individual metadata files (`reflection-config.json`, `resource-config.json`, etc.) are now deprecated, but will still be accepted. + Native Image will only output `reachability-metadata.json` files, and those will be readable on the previous LTS versions of GraalVM. See the [documentation](../docs/reference-manual/native-image/ReachabilityMetadata.md). ## GraalVM for JDK 22 (Internal Version 24.0.0) * (GR-48304) Red Hat added support for the JFR event ThreadAllocationStatistics. From 6f0c9d3c375c0819f9016227f6e5027cc6636b23 Mon Sep 17 00:00:00 2001 From: ol-automation_ww Date: Wed, 18 Sep 2024 12:21:12 +0000 Subject: [PATCH 18/35] [GR-57970] Backport to 24.1: Make js.webassembly option stable. PullRequest: js/3257 --- vm/mx.vm/suite.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/vm/mx.vm/suite.py b/vm/mx.vm/suite.py index 0ac94ccf03d8..babc264c46c2 100644 --- a/vm/mx.vm/suite.py +++ b/vm/mx.vm/suite.py @@ -33,7 +33,7 @@ "name": "graal-nodejs", "subdir": True, "dynamic": True, - "version": "8bbd1c47ef001527d43b5826f7519955423551fc", + "version": "3af98ddb1001364de67c4cbede31445c40c0e96f", "urls" : [ {"url" : "https://github.com/graalvm/graaljs.git", "kind" : "git"}, ] @@ -42,7 +42,7 @@ "name": "graal-js", "subdir": True, "dynamic": True, - "version": "8bbd1c47ef001527d43b5826f7519955423551fc", + "version": "3af98ddb1001364de67c4cbede31445c40c0e96f", "urls": [ {"url": "https://github.com/graalvm/graaljs.git", "kind" : "git"}, ] From 8dac5fbd39643fcd73f3f7a27a5c3e833d7779ae Mon Sep 17 00:00:00 2001 From: ol-automation_ww Date: Wed, 18 Sep 2024 17:33:07 +0000 Subject: [PATCH 19/35] [GR-57799] Backport to 24.1: Deprecate exposed truffle filesystem spi in VirtualFileSystem. PullRequest: graalpython/3475 --- vm/mx.vm/suite.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/vm/mx.vm/suite.py b/vm/mx.vm/suite.py index babc264c46c2..c326749ab88c 100644 --- a/vm/mx.vm/suite.py +++ b/vm/mx.vm/suite.py @@ -65,7 +65,7 @@ }, { "name": "graalpython", - "version": "7fa03a0d6de58a3f797c59932530afeab8e55740", + "version": "9f301a4e16dd42d28138276ba3af24e81200c125", "dynamic": True, "urls": [ {"url": "https://github.com/graalvm/graalpython.git", "kind": "git"}, From db5dd56a003a1e753360429a6274c09c1193c3a8 Mon Sep 17 00:00:00 2001 From: ol-automation_ww Date: Wed, 18 Sep 2024 20:27:01 +0000 Subject: [PATCH 20/35] update JVMCI to 23.0.1+10-jvmci-b01 --- common.json | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-) diff --git a/common.json b/common.json index 92275f3c6317..39f972e96f61 100644 --- a/common.json +++ b/common.json @@ -45,13 +45,13 @@ "labsjdk-ee-21-llvm": {"name": "labsjdk", "version": "ee-21.0.2+13-jvmci-23.1-b33-sulong", "platformspecific": true }, "graalvm-ee-21": {"name": "graalvm-java21", "version": "23.1.3", "platformspecific": true }, - "oraclejdk-latest": {"name": "jpg-jdk", "version": "23", "build_id": "jdk-23.0.1+9", "platformspecific": true, "extrabundles": ["static-libs"]}, - "labsjdk-ce-latest": {"name": "labsjdk", "version": "ce-23.0.1+9-jvmci-b01", "platformspecific": true }, - "labsjdk-ce-latestDebug": {"name": "labsjdk", "version": "ce-23.0.1+9-jvmci-b01-debug", "platformspecific": true }, - "labsjdk-ce-latest-llvm": {"name": "labsjdk", "version": "ce-23.0.1+9-jvmci-b01-sulong", "platformspecific": true }, - "labsjdk-ee-latest": {"name": "labsjdk", "version": "ee-23.0.1+9-jvmci-b01", "platformspecific": true }, - "labsjdk-ee-latestDebug": {"name": "labsjdk", "version": "ee-23.0.1+9-jvmci-b01-debug", "platformspecific": true }, - "labsjdk-ee-latest-llvm": {"name": "labsjdk", "version": "ee-23.0.1+9-jvmci-b01-sulong", "platformspecific": true } + "oraclejdk-latest": {"name": "jpg-jdk", "version": "23", "build_id": "jdk-23.0.1+10", "platformspecific": true, "extrabundles": ["static-libs"]}, + "labsjdk-ce-latest": {"name": "labsjdk", "version": "ce-23.0.1+10-jvmci-b01-20240911195242-519b5c19b9", "platformspecific": true }, + "labsjdk-ce-latestDebug": {"name": "labsjdk", "version": "ce-23.0.1+10-jvmci-b01-20240911195242-519b5c19b9-debug", "platformspecific": true }, + "labsjdk-ce-latest-llvm": {"name": "labsjdk", "version": "ce-23.0.1+10-jvmci-b01-20240911195242-519b5c19b9-sulong", "platformspecific": true }, + "labsjdk-ee-latest": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01-20240911195242-519b5c19b9+456f3d01e0", "platformspecific": true }, + "labsjdk-ee-latestDebug": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01-20240911195242-519b5c19b9+456f3d01e0-debug", "platformspecific": true }, + "labsjdk-ee-latest-llvm": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01-20240911195242-519b5c19b9+456f3d01e0-sulong", "platformspecific": true } }, "eclipse": { From e4d58d59ddbae403ef4dfd3e84c6f3b6dfb1c109 Mon Sep 17 00:00:00 2001 From: Andreas Woess Date: Wed, 24 Jul 2024 14:53:26 +0200 Subject: [PATCH 21/35] Remove constant memory buffer assumption and simplify ByteArrayWasmMemory. (cherry picked from commit 42bb5717533b10ad6ea09909433e7e00deb3d382) --- .../wasm/memory/ByteArrayWasmMemory.java | 297 ++++++++---------- .../graalvm/wasm/memory/NativeWasmMemory.java | 2 + .../graalvm/wasm/memory/UnsafeWasmMemory.java | 1 + 3 files changed, 128 insertions(+), 172 deletions(-) diff --git a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/ByteArrayWasmMemory.java b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/ByteArrayWasmMemory.java index 7a80645035df..950b3278bb4d 100644 --- a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/ByteArrayWasmMemory.java +++ b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/ByteArrayWasmMemory.java @@ -51,38 +51,39 @@ import java.nio.ByteBuffer; import java.util.Arrays; -import com.oracle.truffle.api.CompilerDirectives; import org.graalvm.wasm.api.Vector128; import org.graalvm.wasm.exception.Failure; import org.graalvm.wasm.exception.WasmException; -import com.oracle.truffle.api.Assumption; -import com.oracle.truffle.api.CompilerDirectives.CompilationFinal; +import com.oracle.truffle.api.CompilerDirectives; import com.oracle.truffle.api.CompilerDirectives.TruffleBoundary; import com.oracle.truffle.api.memory.ByteArraySupport; import com.oracle.truffle.api.nodes.Node; final class ByteArrayWasmMemory extends WasmMemory { - private final WasmByteArrayBuffer byteArrayBuffer; + private byte[] dynamicBuffer; private ByteArrayWasmMemory(long declaredMinSize, long declaredMaxSize, long initialSize, long maxAllowedSize, boolean indexType64, boolean shared) { super(declaredMinSize, declaredMaxSize, initialSize, maxAllowedSize, indexType64, shared); - this.byteArrayBuffer = new WasmByteArrayBuffer(); - this.byteArrayBuffer.allocate(initialSize * MEMORY_PAGE_SIZE); + this.dynamicBuffer = allocateStatic(initialSize * MEMORY_PAGE_SIZE); } ByteArrayWasmMemory(long declaredMinSize, long declaredMaxSize, long maxAllowedSize, boolean indexType64, boolean shared) { this(declaredMinSize, declaredMaxSize, declaredMinSize, maxAllowedSize, indexType64, shared); } + private byte[] buffer() { + return dynamicBuffer; + } + @Override public long size() { - return byteArrayBuffer.size(); + return byteSize() / MEMORY_PAGE_SIZE; } @Override public long byteSize() { - return byteArrayBuffer.byteSize(); + return buffer().length; } @Override @@ -96,7 +97,9 @@ public synchronized long grow(long extraPageSize) { // Condition above and limit on maxPageSize (see ModuleLimits#MAX_MEMORY_SIZE) // ensure computation of targetByteSize does not overflow. final long targetByteSize = multiplyExact(addExact(size(), extraPageSize), MEMORY_PAGE_SIZE); - byteArrayBuffer.grow(targetByteSize); + final byte[] currentBuffer = buffer(); + allocate(targetByteSize); + System.arraycopy(currentBuffer, 0, buffer(), 0, currentBuffer.length); currentMinSize = size() + extraPageSize; invokeGrowCallback(); return previousSize; @@ -106,15 +109,16 @@ public synchronized long grow(long extraPageSize) { } @Override + @TruffleBoundary public void reset() { - byteArrayBuffer.reset(declaredMinSize * MEMORY_PAGE_SIZE); + allocate(declaredMinSize * MEMORY_PAGE_SIZE); currentMinSize = declaredMinSize; } @Override public int load_i32(Node node, long address) { try { - return ByteArraySupport.littleEndian().getInt(byteArrayBuffer.buffer(), address); + return ByteArraySupport.littleEndian().getInt(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -123,7 +127,7 @@ public int load_i32(Node node, long address) { @Override public long load_i64(Node node, long address) { try { - return ByteArraySupport.littleEndian().getLong(byteArrayBuffer.buffer(), address); + return ByteArraySupport.littleEndian().getLong(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 8); } @@ -132,7 +136,7 @@ public long load_i64(Node node, long address) { @Override public float load_f32(Node node, long address) { try { - return ByteArraySupport.littleEndian().getFloat(byteArrayBuffer.buffer(), address); + return ByteArraySupport.littleEndian().getFloat(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -141,7 +145,7 @@ public float load_f32(Node node, long address) { @Override public double load_f64(Node node, long address) { try { - return ByteArraySupport.littleEndian().getDouble(byteArrayBuffer.buffer(), address); + return ByteArraySupport.littleEndian().getDouble(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 8); } @@ -150,7 +154,7 @@ public double load_f64(Node node, long address) { @Override public int load_i32_8s(Node node, long address) { try { - return ByteArraySupport.littleEndian().getByte(byteArrayBuffer.buffer(), address); + return ByteArraySupport.littleEndian().getByte(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -159,7 +163,7 @@ public int load_i32_8s(Node node, long address) { @Override public int load_i32_8u(Node node, long address) { try { - return 0x0000_00ff & ByteArraySupport.littleEndian().getByte(byteArrayBuffer.buffer(), address); + return 0x0000_00ff & ByteArraySupport.littleEndian().getByte(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -168,7 +172,7 @@ public int load_i32_8u(Node node, long address) { @Override public int load_i32_16s(Node node, long address) { try { - return ByteArraySupport.littleEndian().getShort(byteArrayBuffer.buffer(), address); + return ByteArraySupport.littleEndian().getShort(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -177,7 +181,7 @@ public int load_i32_16s(Node node, long address) { @Override public int load_i32_16u(Node node, long address) { try { - return 0x0000_ffff & ByteArraySupport.littleEndian().getShort(byteArrayBuffer.buffer(), address); + return 0x0000_ffff & ByteArraySupport.littleEndian().getShort(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -186,7 +190,7 @@ public int load_i32_16u(Node node, long address) { @Override public long load_i64_8s(Node node, long address) { try { - return ByteArraySupport.littleEndian().getByte(byteArrayBuffer.buffer(), address); + return ByteArraySupport.littleEndian().getByte(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -195,7 +199,7 @@ public long load_i64_8s(Node node, long address) { @Override public long load_i64_8u(Node node, long address) { try { - return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getByte(byteArrayBuffer.buffer(), address); + return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getByte(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -204,7 +208,7 @@ public long load_i64_8u(Node node, long address) { @Override public long load_i64_16s(Node node, long address) { try { - return ByteArraySupport.littleEndian().getShort(byteArrayBuffer.buffer(), address); + return ByteArraySupport.littleEndian().getShort(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -213,7 +217,7 @@ public long load_i64_16s(Node node, long address) { @Override public long load_i64_16u(Node node, long address) { try { - return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getShort(byteArrayBuffer.buffer(), address); + return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getShort(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -222,7 +226,7 @@ public long load_i64_16u(Node node, long address) { @Override public long load_i64_32s(Node node, long address) { try { - return ByteArraySupport.littleEndian().getInt(byteArrayBuffer.buffer(), address); + return ByteArraySupport.littleEndian().getInt(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -231,7 +235,7 @@ public long load_i64_32s(Node node, long address) { @Override public long load_i64_32u(Node node, long address) { try { - return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getInt(byteArrayBuffer.buffer(), address); + return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getInt(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -239,8 +243,8 @@ public long load_i64_32u(Node node, long address) { @Override public Vector128 load_i128(Node node, long address) { - if (ByteArraySupport.littleEndian().inBounds(byteArrayBuffer.buffer(), address, Vector128.BYTES)) { - return new Vector128(Arrays.copyOfRange(byteArrayBuffer.buffer(), (int) address, (int) address + Vector128.BYTES)); + if (ByteArraySupport.littleEndian().inBounds(buffer(), address, Vector128.BYTES)) { + return new Vector128(Arrays.copyOfRange(buffer(), (int) address, (int) address + Vector128.BYTES)); } else { throw trapOutOfBounds(node, address, 16); } @@ -249,7 +253,7 @@ public Vector128 load_i128(Node node, long address) { @Override public void store_i32(Node node, long address, int value) { try { - ByteArraySupport.littleEndian().putInt(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putInt(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -258,7 +262,7 @@ public void store_i32(Node node, long address, int value) { @Override public void store_i64(Node node, long address, long value) { try { - ByteArraySupport.littleEndian().putLong(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putLong(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 8); } @@ -268,7 +272,7 @@ public void store_i64(Node node, long address, long value) { @Override public void store_f32(Node node, long address, float value) { try { - ByteArraySupport.littleEndian().putFloat(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putFloat(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -277,7 +281,7 @@ public void store_f32(Node node, long address, float value) { @Override public void store_f64(Node node, long address, double value) { try { - ByteArraySupport.littleEndian().putDouble(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putDouble(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 8); } @@ -286,7 +290,7 @@ public void store_f64(Node node, long address, double value) { @Override public void store_i32_8(Node node, long address, byte value) { try { - ByteArraySupport.littleEndian().putByte(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putByte(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -295,7 +299,7 @@ public void store_i32_8(Node node, long address, byte value) { @Override public void store_i32_16(Node node, long address, short value) { try { - ByteArraySupport.littleEndian().putShort(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putShort(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -304,7 +308,7 @@ public void store_i32_16(Node node, long address, short value) { @Override public void store_i64_8(Node node, long address, byte value) { try { - ByteArraySupport.littleEndian().putByte(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putByte(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -313,7 +317,7 @@ public void store_i64_8(Node node, long address, byte value) { @Override public void store_i64_16(Node node, long address, short value) { try { - ByteArraySupport.littleEndian().putShort(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putShort(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -322,7 +326,7 @@ public void store_i64_16(Node node, long address, short value) { @Override public void store_i64_32(Node node, long address, int value) { try { - ByteArraySupport.littleEndian().putInt(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putInt(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -330,8 +334,8 @@ public void store_i64_32(Node node, long address, int value) { @Override public void store_i128(Node node, long address, Vector128 value) { - if (ByteArraySupport.littleEndian().inBounds(byteArrayBuffer.buffer(), address, 16)) { - System.arraycopy(value.getBytes(), 0, byteArrayBuffer.buffer(), (int) address, 16); + if (ByteArraySupport.littleEndian().inBounds(buffer(), address, 16)) { + System.arraycopy(value.getBytes(), 0, buffer(), (int) address, 16); } else { throw trapOutOfBounds(node, address, 16); } @@ -348,7 +352,7 @@ private static void validateAtomicAddress(Node node, long address, int length) { public int atomic_load_i32(Node node, long address) { validateAtomicAddress(node, address, 4); try { - return ByteArraySupport.littleEndian().getIntVolatile(byteArrayBuffer.buffer(), address); + return ByteArraySupport.littleEndian().getIntVolatile(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -358,7 +362,7 @@ public int atomic_load_i32(Node node, long address) { public long atomic_load_i64(Node node, long address) { validateAtomicAddress(node, address, 8); try { - return ByteArraySupport.littleEndian().getLongVolatile(byteArrayBuffer.buffer(), address); + return ByteArraySupport.littleEndian().getLongVolatile(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 8); } @@ -368,7 +372,7 @@ public long atomic_load_i64(Node node, long address) { public int atomic_load_i32_8u(Node node, long address) { validateAtomicAddress(node, address, 1); try { - return 0x0000_00ff & ByteArraySupport.littleEndian().getByteVolatile(byteArrayBuffer.buffer(), address); + return 0x0000_00ff & ByteArraySupport.littleEndian().getByteVolatile(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -378,7 +382,7 @@ public int atomic_load_i32_8u(Node node, long address) { public int atomic_load_i32_16u(Node node, long address) { validateAtomicAddress(node, address, 2); try { - return 0x0000_ffff & ByteArraySupport.littleEndian().getShortVolatile(byteArrayBuffer.buffer(), address); + return 0x0000_ffff & ByteArraySupport.littleEndian().getShortVolatile(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -388,7 +392,7 @@ public int atomic_load_i32_16u(Node node, long address) { public long atomic_load_i64_8u(Node node, long address) { validateAtomicAddress(node, address, 1); try { - return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getByteVolatile(byteArrayBuffer.buffer(), address); + return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getByteVolatile(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -398,7 +402,7 @@ public long atomic_load_i64_8u(Node node, long address) { public long atomic_load_i64_16u(Node node, long address) { validateAtomicAddress(node, address, 2); try { - return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getShortVolatile(byteArrayBuffer.buffer(), address); + return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getShortVolatile(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -408,7 +412,7 @@ public long atomic_load_i64_16u(Node node, long address) { public long atomic_load_i64_32u(Node node, long address) { validateAtomicAddress(node, address, 4); try { - return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getIntVolatile(byteArrayBuffer.buffer(), address); + return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getIntVolatile(buffer(), address); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -418,7 +422,7 @@ public long atomic_load_i64_32u(Node node, long address) { public void atomic_store_i32(Node node, long address, int value) { validateAtomicAddress(node, address, 4); try { - ByteArraySupport.littleEndian().putIntVolatile(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putIntVolatile(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -428,7 +432,7 @@ public void atomic_store_i32(Node node, long address, int value) { public void atomic_store_i64(Node node, long address, long value) { validateAtomicAddress(node, address, 8); try { - ByteArraySupport.littleEndian().putLongVolatile(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putLongVolatile(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 8); } @@ -438,7 +442,7 @@ public void atomic_store_i64(Node node, long address, long value) { public void atomic_store_i32_8(Node node, long address, byte value) { validateAtomicAddress(node, address, 1); try { - ByteArraySupport.littleEndian().putByteVolatile(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putByteVolatile(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -448,7 +452,7 @@ public void atomic_store_i32_8(Node node, long address, byte value) { public void atomic_store_i32_16(Node node, long address, short value) { validateAtomicAddress(node, address, 2); try { - ByteArraySupport.littleEndian().putShortVolatile(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putShortVolatile(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -458,7 +462,7 @@ public void atomic_store_i32_16(Node node, long address, short value) { public void atomic_store_i64_8(Node node, long address, byte value) { validateAtomicAddress(node, address, 1); try { - ByteArraySupport.littleEndian().putByteVolatile(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putByteVolatile(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -468,7 +472,7 @@ public void atomic_store_i64_8(Node node, long address, byte value) { public void atomic_store_i64_16(Node node, long address, short value) { validateAtomicAddress(node, address, 2); try { - ByteArraySupport.littleEndian().putShortVolatile(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putShortVolatile(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -478,7 +482,7 @@ public void atomic_store_i64_16(Node node, long address, short value) { public void atomic_store_i64_32(Node node, long address, int value) { validateAtomicAddress(node, address, 4); try { - ByteArraySupport.littleEndian().putIntVolatile(byteArrayBuffer.buffer(), address, value); + ByteArraySupport.littleEndian().putIntVolatile(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -488,7 +492,7 @@ public void atomic_store_i64_32(Node node, long address, int value) { public int atomic_rmw_add_i32_8u(Node node, long address, byte value) { validateAtomicAddress(node, address, 1); try { - return 0x0000_00ff & ByteArraySupport.littleEndian().getAndAddByte(byteArrayBuffer.buffer(), address, value); + return 0x0000_00ff & ByteArraySupport.littleEndian().getAndAddByte(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -498,7 +502,7 @@ public int atomic_rmw_add_i32_8u(Node node, long address, byte value) { public int atomic_rmw_add_i32_16u(Node node, long address, short value) { validateAtomicAddress(node, address, 2); try { - return 0x0000_ffff & ByteArraySupport.littleEndian().getAndAddShort(byteArrayBuffer.buffer(), address, value); + return 0x0000_ffff & ByteArraySupport.littleEndian().getAndAddShort(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -508,7 +512,7 @@ public int atomic_rmw_add_i32_16u(Node node, long address, short value) { public int atomic_rmw_add_i32(Node node, long address, int value) { validateAtomicAddress(node, address, 4); try { - return ByteArraySupport.littleEndian().getAndAddInt(byteArrayBuffer.buffer(), address, value); + return ByteArraySupport.littleEndian().getAndAddInt(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -518,7 +522,7 @@ public int atomic_rmw_add_i32(Node node, long address, int value) { public long atomic_rmw_add_i64_8u(Node node, long address, byte value) { validateAtomicAddress(node, address, 1); try { - return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getAndAddByte(byteArrayBuffer.buffer(), address, value); + return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getAndAddByte(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -528,7 +532,7 @@ public long atomic_rmw_add_i64_8u(Node node, long address, byte value) { public long atomic_rmw_add_i64_16u(Node node, long address, short value) { validateAtomicAddress(node, address, 2); try { - return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getAndAddShort(byteArrayBuffer.buffer(), address, value); + return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getAndAddShort(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -538,7 +542,7 @@ public long atomic_rmw_add_i64_16u(Node node, long address, short value) { public long atomic_rmw_add_i64_32u(Node node, long address, int value) { validateAtomicAddress(node, address, 4); try { - return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getAndAddInt(byteArrayBuffer.buffer(), address, value); + return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getAndAddInt(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -548,7 +552,7 @@ public long atomic_rmw_add_i64_32u(Node node, long address, int value) { public long atomic_rmw_add_i64(Node node, long address, long value) { validateAtomicAddress(node, address, 8); try { - return ByteArraySupport.littleEndian().getAndAddLong(byteArrayBuffer.buffer(), address, value); + return ByteArraySupport.littleEndian().getAndAddLong(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 8); } @@ -558,7 +562,7 @@ public long atomic_rmw_add_i64(Node node, long address, long value) { public int atomic_rmw_sub_i32_8u(Node node, long address, byte value) { validateAtomicAddress(node, address, 1); try { - return 0x0000_00ff & ByteArraySupport.littleEndian().getAndAddByte(byteArrayBuffer.buffer(), address, (byte) -value); + return 0x0000_00ff & ByteArraySupport.littleEndian().getAndAddByte(buffer(), address, (byte) -value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -568,7 +572,7 @@ public int atomic_rmw_sub_i32_8u(Node node, long address, byte value) { public int atomic_rmw_sub_i32_16u(Node node, long address, short value) { validateAtomicAddress(node, address, 2); try { - return 0x0000_ffff & ByteArraySupport.littleEndian().getAndAddShort(byteArrayBuffer.buffer(), address, (short) -value); + return 0x0000_ffff & ByteArraySupport.littleEndian().getAndAddShort(buffer(), address, (short) -value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -578,7 +582,7 @@ public int atomic_rmw_sub_i32_16u(Node node, long address, short value) { public int atomic_rmw_sub_i32(Node node, long address, int value) { validateAtomicAddress(node, address, 4); try { - return ByteArraySupport.littleEndian().getAndAddInt(byteArrayBuffer.buffer(), address, -value); + return ByteArraySupport.littleEndian().getAndAddInt(buffer(), address, -value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -588,7 +592,7 @@ public int atomic_rmw_sub_i32(Node node, long address, int value) { public long atomic_rmw_sub_i64_8u(Node node, long address, byte value) { validateAtomicAddress(node, address, 1); try { - return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getAndAddByte(byteArrayBuffer.buffer(), address, (byte) -value); + return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getAndAddByte(buffer(), address, (byte) -value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -598,7 +602,7 @@ public long atomic_rmw_sub_i64_8u(Node node, long address, byte value) { public long atomic_rmw_sub_i64_16u(Node node, long address, short value) { validateAtomicAddress(node, address, 2); try { - return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getAndAddShort(byteArrayBuffer.buffer(), address, (short) -value); + return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getAndAddShort(buffer(), address, (short) -value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -608,7 +612,7 @@ public long atomic_rmw_sub_i64_16u(Node node, long address, short value) { public long atomic_rmw_sub_i64_32u(Node node, long address, int value) { validateAtomicAddress(node, address, 4); try { - return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getAndAddInt(byteArrayBuffer.buffer(), address, -value); + return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getAndAddInt(buffer(), address, -value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -618,7 +622,7 @@ public long atomic_rmw_sub_i64_32u(Node node, long address, int value) { public long atomic_rmw_sub_i64(Node node, long address, long value) { validateAtomicAddress(node, address, 8); try { - return ByteArraySupport.littleEndian().getAndAddLong(byteArrayBuffer.buffer(), address, -value); + return ByteArraySupport.littleEndian().getAndAddLong(buffer(), address, -value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 8); } @@ -628,7 +632,7 @@ public long atomic_rmw_sub_i64(Node node, long address, long value) { public int atomic_rmw_and_i32_8u(Node node, long address, byte value) { validateAtomicAddress(node, address, 1); try { - return 0x0000_00ff & ByteArraySupport.littleEndian().getAndBitwiseAndByte(byteArrayBuffer.buffer(), address, value); + return 0x0000_00ff & ByteArraySupport.littleEndian().getAndBitwiseAndByte(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -638,7 +642,7 @@ public int atomic_rmw_and_i32_8u(Node node, long address, byte value) { public int atomic_rmw_and_i32_16u(Node node, long address, short value) { validateAtomicAddress(node, address, 2); try { - return 0x0000_ffff & ByteArraySupport.littleEndian().getAndBitwiseAndShort(byteArrayBuffer.buffer(), address, value); + return 0x0000_ffff & ByteArraySupport.littleEndian().getAndBitwiseAndShort(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -648,7 +652,7 @@ public int atomic_rmw_and_i32_16u(Node node, long address, short value) { public int atomic_rmw_and_i32(Node node, long address, int value) { validateAtomicAddress(node, address, 4); try { - return ByteArraySupport.littleEndian().getAndBitwiseAndInt(byteArrayBuffer.buffer(), address, value); + return ByteArraySupport.littleEndian().getAndBitwiseAndInt(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -658,7 +662,7 @@ public int atomic_rmw_and_i32(Node node, long address, int value) { public long atomic_rmw_and_i64_8u(Node node, long address, byte value) { validateAtomicAddress(node, address, 1); try { - return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getAndBitwiseAndByte(byteArrayBuffer.buffer(), address, value); + return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getAndBitwiseAndByte(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -668,7 +672,7 @@ public long atomic_rmw_and_i64_8u(Node node, long address, byte value) { public long atomic_rmw_and_i64_16u(Node node, long address, short value) { validateAtomicAddress(node, address, 2); try { - return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getAndBitwiseAndShort(byteArrayBuffer.buffer(), address, value); + return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getAndBitwiseAndShort(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -678,7 +682,7 @@ public long atomic_rmw_and_i64_16u(Node node, long address, short value) { public long atomic_rmw_and_i64_32u(Node node, long address, int value) { validateAtomicAddress(node, address, 4); try { - return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getAndBitwiseAndInt(byteArrayBuffer.buffer(), address, value); + return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getAndBitwiseAndInt(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -688,7 +692,7 @@ public long atomic_rmw_and_i64_32u(Node node, long address, int value) { public long atomic_rmw_and_i64(Node node, long address, long value) { validateAtomicAddress(node, address, 8); try { - return ByteArraySupport.littleEndian().getAndBitwiseAndLong(byteArrayBuffer.buffer(), address, value); + return ByteArraySupport.littleEndian().getAndBitwiseAndLong(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 8); } @@ -698,7 +702,7 @@ public long atomic_rmw_and_i64(Node node, long address, long value) { public int atomic_rmw_or_i32_8u(Node node, long address, byte value) { validateAtomicAddress(node, address, 1); try { - return 0x0000_00ff & ByteArraySupport.littleEndian().getAndBitwiseOrByte(byteArrayBuffer.buffer(), address, value); + return 0x0000_00ff & ByteArraySupport.littleEndian().getAndBitwiseOrByte(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -708,7 +712,7 @@ public int atomic_rmw_or_i32_8u(Node node, long address, byte value) { public int atomic_rmw_or_i32_16u(Node node, long address, short value) { validateAtomicAddress(node, address, 2); try { - return 0x0000_ffff & ByteArraySupport.littleEndian().getAndBitwiseOrShort(byteArrayBuffer.buffer(), address, value); + return 0x0000_ffff & ByteArraySupport.littleEndian().getAndBitwiseOrShort(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -718,7 +722,7 @@ public int atomic_rmw_or_i32_16u(Node node, long address, short value) { public int atomic_rmw_or_i32(Node node, long address, int value) { validateAtomicAddress(node, address, 4); try { - return ByteArraySupport.littleEndian().getAndBitwiseOrInt(byteArrayBuffer.buffer(), address, value); + return ByteArraySupport.littleEndian().getAndBitwiseOrInt(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -728,7 +732,7 @@ public int atomic_rmw_or_i32(Node node, long address, int value) { public long atomic_rmw_or_i64_8u(Node node, long address, byte value) { validateAtomicAddress(node, address, 1); try { - return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getAndBitwiseOrByte(byteArrayBuffer.buffer(), address, value); + return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getAndBitwiseOrByte(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -738,7 +742,7 @@ public long atomic_rmw_or_i64_8u(Node node, long address, byte value) { public long atomic_rmw_or_i64_16u(Node node, long address, short value) { validateAtomicAddress(node, address, 2); try { - return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getAndBitwiseOrShort(byteArrayBuffer.buffer(), address, value); + return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getAndBitwiseOrShort(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -748,7 +752,7 @@ public long atomic_rmw_or_i64_16u(Node node, long address, short value) { public long atomic_rmw_or_i64_32u(Node node, long address, int value) { validateAtomicAddress(node, address, 4); try { - return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getAndBitwiseOrInt(byteArrayBuffer.buffer(), address, value); + return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getAndBitwiseOrInt(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -758,7 +762,7 @@ public long atomic_rmw_or_i64_32u(Node node, long address, int value) { public long atomic_rmw_or_i64(Node node, long address, long value) { validateAtomicAddress(node, address, 8); try { - return ByteArraySupport.littleEndian().getAndBitwiseOrLong(byteArrayBuffer.buffer(), address, value); + return ByteArraySupport.littleEndian().getAndBitwiseOrLong(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 8); } @@ -768,7 +772,7 @@ public long atomic_rmw_or_i64(Node node, long address, long value) { public int atomic_rmw_xor_i32_8u(Node node, long address, byte value) { validateAtomicAddress(node, address, 1); try { - return 0x0000_00ff & ByteArraySupport.littleEndian().getAndBitwiseXorByte(byteArrayBuffer.buffer(), address, value); + return 0x0000_00ff & ByteArraySupport.littleEndian().getAndBitwiseXorByte(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -778,7 +782,7 @@ public int atomic_rmw_xor_i32_8u(Node node, long address, byte value) { public int atomic_rmw_xor_i32_16u(Node node, long address, short value) { validateAtomicAddress(node, address, 2); try { - return 0x0000_ffff & ByteArraySupport.littleEndian().getAndBitwiseXorShort(byteArrayBuffer.buffer(), address, value); + return 0x0000_ffff & ByteArraySupport.littleEndian().getAndBitwiseXorShort(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -788,7 +792,7 @@ public int atomic_rmw_xor_i32_16u(Node node, long address, short value) { public int atomic_rmw_xor_i32(Node node, long address, int value) { validateAtomicAddress(node, address, 4); try { - return ByteArraySupport.littleEndian().getAndBitwiseXorInt(byteArrayBuffer.buffer(), address, value); + return ByteArraySupport.littleEndian().getAndBitwiseXorInt(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -798,7 +802,7 @@ public int atomic_rmw_xor_i32(Node node, long address, int value) { public long atomic_rmw_xor_i64_8u(Node node, long address, byte value) { validateAtomicAddress(node, address, 1); try { - return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getAndBitwiseXorByte(byteArrayBuffer.buffer(), address, value); + return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getAndBitwiseXorByte(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -808,7 +812,7 @@ public long atomic_rmw_xor_i64_8u(Node node, long address, byte value) { public long atomic_rmw_xor_i64_16u(Node node, long address, short value) { validateAtomicAddress(node, address, 2); try { - return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getAndBitwiseXorShort(byteArrayBuffer.buffer(), address, value); + return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getAndBitwiseXorShort(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -818,7 +822,7 @@ public long atomic_rmw_xor_i64_16u(Node node, long address, short value) { public long atomic_rmw_xor_i64_32u(Node node, long address, int value) { validateAtomicAddress(node, address, 4); try { - return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getAndBitwiseXorInt(byteArrayBuffer.buffer(), address, value); + return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getAndBitwiseXorInt(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -828,7 +832,7 @@ public long atomic_rmw_xor_i64_32u(Node node, long address, int value) { public long atomic_rmw_xor_i64(Node node, long address, long value) { validateAtomicAddress(node, address, 8); try { - return ByteArraySupport.littleEndian().getAndBitwiseXorLong(byteArrayBuffer.buffer(), address, value); + return ByteArraySupport.littleEndian().getAndBitwiseXorLong(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 8); } @@ -838,7 +842,7 @@ public long atomic_rmw_xor_i64(Node node, long address, long value) { public int atomic_rmw_xchg_i32_8u(Node node, long address, byte value) { validateAtomicAddress(node, address, 1); try { - return 0x0000_00ff & ByteArraySupport.littleEndian().getAndSetByte(byteArrayBuffer.buffer(), address, value); + return 0x0000_00ff & ByteArraySupport.littleEndian().getAndSetByte(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -848,7 +852,7 @@ public int atomic_rmw_xchg_i32_8u(Node node, long address, byte value) { public int atomic_rmw_xchg_i32_16u(Node node, long address, short value) { validateAtomicAddress(node, address, 2); try { - return 0x0000_ffff & ByteArraySupport.littleEndian().getAndSetShort(byteArrayBuffer.buffer(), address, value); + return 0x0000_ffff & ByteArraySupport.littleEndian().getAndSetShort(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -858,7 +862,7 @@ public int atomic_rmw_xchg_i32_16u(Node node, long address, short value) { public int atomic_rmw_xchg_i32(Node node, long address, int value) { validateAtomicAddress(node, address, 4); try { - return ByteArraySupport.littleEndian().getAndSetInt(byteArrayBuffer.buffer(), address, value); + return ByteArraySupport.littleEndian().getAndSetInt(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -868,7 +872,7 @@ public int atomic_rmw_xchg_i32(Node node, long address, int value) { public long atomic_rmw_xchg_i64_8u(Node node, long address, byte value) { validateAtomicAddress(node, address, 1); try { - return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getAndSetByte(byteArrayBuffer.buffer(), address, value); + return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().getAndSetByte(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -878,7 +882,7 @@ public long atomic_rmw_xchg_i64_8u(Node node, long address, byte value) { public long atomic_rmw_xchg_i64_16u(Node node, long address, short value) { validateAtomicAddress(node, address, 2); try { - return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getAndSetShort(byteArrayBuffer.buffer(), address, value); + return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().getAndSetShort(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -888,7 +892,7 @@ public long atomic_rmw_xchg_i64_16u(Node node, long address, short value) { public long atomic_rmw_xchg_i64_32u(Node node, long address, int value) { validateAtomicAddress(node, address, 4); try { - return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getAndSetInt(byteArrayBuffer.buffer(), address, value); + return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().getAndSetInt(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -898,7 +902,7 @@ public long atomic_rmw_xchg_i64_32u(Node node, long address, int value) { public long atomic_rmw_xchg_i64(Node node, long address, long value) { validateAtomicAddress(node, address, 8); try { - return ByteArraySupport.littleEndian().getAndSetLong(byteArrayBuffer.buffer(), address, value); + return ByteArraySupport.littleEndian().getAndSetLong(buffer(), address, value); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 8); } @@ -908,7 +912,7 @@ public long atomic_rmw_xchg_i64(Node node, long address, long value) { public int atomic_rmw_cmpxchg_i32_8u(Node node, long address, byte expected, byte replacement) { validateAtomicAddress(node, address, 1); try { - return 0x0000_00ff & ByteArraySupport.littleEndian().compareAndExchangeByte(byteArrayBuffer.buffer(), address, expected, replacement); + return 0x0000_00ff & ByteArraySupport.littleEndian().compareAndExchangeByte(buffer(), address, expected, replacement); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -918,7 +922,7 @@ public int atomic_rmw_cmpxchg_i32_8u(Node node, long address, byte expected, byt public int atomic_rmw_cmpxchg_i32_16u(Node node, long address, short expected, short replacement) { validateAtomicAddress(node, address, 2); try { - return 0x0000_ffff & ByteArraySupport.littleEndian().compareAndExchangeShort(byteArrayBuffer.buffer(), address, expected, replacement); + return 0x0000_ffff & ByteArraySupport.littleEndian().compareAndExchangeShort(buffer(), address, expected, replacement); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -928,7 +932,7 @@ public int atomic_rmw_cmpxchg_i32_16u(Node node, long address, short expected, s public int atomic_rmw_cmpxchg_i32(Node node, long address, int expected, int replacement) { validateAtomicAddress(node, address, 4); try { - return ByteArraySupport.littleEndian().compareAndExchangeInt(byteArrayBuffer.buffer(), address, expected, replacement); + return ByteArraySupport.littleEndian().compareAndExchangeInt(buffer(), address, expected, replacement); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -938,7 +942,7 @@ public int atomic_rmw_cmpxchg_i32(Node node, long address, int expected, int rep public long atomic_rmw_cmpxchg_i64_8u(Node node, long address, byte expected, byte replacement) { validateAtomicAddress(node, address, 1); try { - return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().compareAndExchangeByte(byteArrayBuffer.buffer(), address, expected, replacement); + return 0x0000_0000_0000_00ffL & ByteArraySupport.littleEndian().compareAndExchangeByte(buffer(), address, expected, replacement); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 1); } @@ -948,7 +952,7 @@ public long atomic_rmw_cmpxchg_i64_8u(Node node, long address, byte expected, by public long atomic_rmw_cmpxchg_i64_16u(Node node, long address, short expected, short replacement) { validateAtomicAddress(node, address, 2); try { - return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().compareAndExchangeShort(byteArrayBuffer.buffer(), address, expected, replacement); + return 0x0000_0000_0000_ffffL & ByteArraySupport.littleEndian().compareAndExchangeShort(buffer(), address, expected, replacement); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 2); } @@ -958,7 +962,7 @@ public long atomic_rmw_cmpxchg_i64_16u(Node node, long address, short expected, public long atomic_rmw_cmpxchg_i64_32u(Node node, long address, int expected, int replacement) { validateAtomicAddress(node, address, 4); try { - return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().compareAndExchangeInt(byteArrayBuffer.buffer(), address, expected, replacement); + return 0x0000_0000_ffff_ffffL & ByteArraySupport.littleEndian().compareAndExchangeInt(buffer(), address, expected, replacement); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 4); } @@ -968,7 +972,7 @@ public long atomic_rmw_cmpxchg_i64_32u(Node node, long address, int expected, in public long atomic_rmw_cmpxchg_i64(Node node, long address, long expected, long replacement) { validateAtomicAddress(node, address, 8); try { - return ByteArraySupport.littleEndian().compareAndExchangeLong(byteArrayBuffer.buffer(), address, expected, replacement); + return ByteArraySupport.littleEndian().compareAndExchangeLong(buffer(), address, expected, replacement); } catch (final IndexOutOfBoundsException e) { throw trapOutOfBounds(node, address, 8); } @@ -1016,14 +1020,14 @@ public int atomic_wait64(Node node, long address, long expected, long timeout) { @Override public void initialize(byte[] source, int sourceOffset, long destinationOffset, int length) { assert destinationOffset + length <= byteSize(); - System.arraycopy(source, sourceOffset, byteArrayBuffer.buffer(), (int) destinationOffset, length); + System.arraycopy(source, sourceOffset, buffer(), (int) destinationOffset, length); } @Override @TruffleBoundary public void fill(long offset, long length, byte value) { assert offset + length <= byteSize(); - Arrays.fill(byteArrayBuffer.buffer(), (int) offset, (int) (offset + length), value); + Arrays.fill(buffer(), (int) offset, (int) (offset + length), value); } @Override @@ -1031,19 +1035,19 @@ public void copyFrom(WasmMemory source, long sourceOffset, long destinationOffse assert source instanceof ByteArrayWasmMemory; assert destinationOffset < byteSize(); ByteArrayWasmMemory s = (ByteArrayWasmMemory) source; - System.arraycopy(s.byteArrayBuffer.buffer(), (int) sourceOffset, byteArrayBuffer.buffer(), (int) destinationOffset, (int) length); + System.arraycopy(s.buffer(), (int) sourceOffset, buffer(), (int) destinationOffset, (int) length); } @Override public WasmMemory duplicate() { final ByteArrayWasmMemory other = new ByteArrayWasmMemory(declaredMinSize, declaredMaxSize, size(), maxAllowedSize, indexType64, shared); - System.arraycopy(byteArrayBuffer.buffer(), 0, other.byteArrayBuffer.buffer(), 0, (int) byteArrayBuffer.byteSize()); + System.arraycopy(buffer(), 0, other.buffer(), 0, (int) byteSize()); return other; } @Override public void close() { - byteArrayBuffer.close(); + dynamicBuffer = null; } @Override @@ -1057,7 +1061,7 @@ public int copyFromStream(Node node, InputStream stream, int offset, int length) if (outOfBounds(offset, length)) { throw trapOutOfBounds(node, offset, length); } - return stream.read(byteArrayBuffer.buffer(), offset, length); + return stream.read(buffer(), offset, length); } @Override @@ -1066,7 +1070,7 @@ public void copyToStream(Node node, OutputStream stream, int offset, int length) if (outOfBounds(offset, length)) { throw trapOutOfBounds(node, offset, length); } - stream.write(byteArrayBuffer.buffer(), offset, length); + stream.write(buffer(), offset, length); } @Override @@ -1074,74 +1078,23 @@ public void copyToBuffer(Node node, byte[] dst, long srcOffset, int dstOffset, i if (outOfBounds(srcOffset, length)) { throw trapOutOfBounds(node, srcOffset, length); } - System.arraycopy(byteArrayBuffer.buffer(), (int) srcOffset, dst, dstOffset, length); + System.arraycopy(buffer(), (int) srcOffset, dst, dstOffset, length); } - private static final class WasmByteArrayBuffer { - private static final int MAX_CONSTANT_ATTEMPTS = 5; - - @CompilationFinal private Assumption constantMemoryBufferAssumption; - - @CompilationFinal(dimensions = 0) private byte[] constantBuffer; - - private byte[] dynamicBuffer; - - private int constantAttempts = 0; - - private WasmByteArrayBuffer() { - } - - @TruffleBoundary - public void allocate(long byteSize) { - assert byteSize <= Integer.MAX_VALUE; - final int effectiveByteSize = (int) byteSize; - constantBuffer = null; - dynamicBuffer = null; - if (constantAttempts < MAX_CONSTANT_ATTEMPTS) { - constantMemoryBufferAssumption = Assumption.create("ConstantMemoryBuffer"); - constantAttempts++; - } - try { - if (constantMemoryBufferAssumption.isValid()) { - constantBuffer = new byte[effectiveByteSize]; - } else { - dynamicBuffer = new byte[effectiveByteSize]; - } - } catch (OutOfMemoryError error) { - throw WasmException.create(Failure.MEMORY_ALLOCATION_FAILED); - } - } - - byte[] buffer() { - if (constantMemoryBufferAssumption.isValid()) { - return constantBuffer; - } - return dynamicBuffer; - } - - long size() { - return buffer().length / MEMORY_PAGE_SIZE; - } - - long byteSize() { - return buffer().length; - } - - void grow(long targetSize) { - final byte[] currentBuffer = buffer(); - constantMemoryBufferAssumption.invalidate("Memory grow"); - allocate(targetSize); - System.arraycopy(currentBuffer, 0, buffer(), 0, currentBuffer.length); - } - - void reset(long byteSize) { - constantMemoryBufferAssumption.invalidate("Memory reset"); - allocate(byteSize); - } + @TruffleBoundary + private void allocate(long byteSize) { + dynamicBuffer = null; + dynamicBuffer = allocateStatic(byteSize); + } - void close() { - constantBuffer = null; - dynamicBuffer = null; + @TruffleBoundary + private static byte[] allocateStatic(long byteSize) { + assert byteSize <= Integer.MAX_VALUE : byteSize; + final int effectiveByteSize = (int) byteSize; + try { + return new byte[effectiveByteSize]; + } catch (OutOfMemoryError error) { + throw WasmException.create(Failure.MEMORY_ALLOCATION_FAILED); } } } diff --git a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/NativeWasmMemory.java b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/NativeWasmMemory.java index 0d2199c64a30..ee8f51e96299 100644 --- a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/NativeWasmMemory.java +++ b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/NativeWasmMemory.java @@ -127,6 +127,7 @@ public synchronized long grow(long extraPageSize) { } @Override + @TruffleBoundary public void reset() { free(); size = declaredMinSize; @@ -953,6 +954,7 @@ public boolean freed() { return startAddress == 0; } + @TruffleBoundary private void free() { unsafe.freeMemory(startAddress); startAddress = 0; diff --git a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/UnsafeWasmMemory.java b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/UnsafeWasmMemory.java index 82123ccbd051..c820938fb807 100644 --- a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/UnsafeWasmMemory.java +++ b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/UnsafeWasmMemory.java @@ -119,6 +119,7 @@ private static void validateAtomicAddress(Node node, long address, int length) { } @Override + @TruffleBoundary public void reset() { size = declaredMinSize; buffer = allocateBuffer(byteSize()); From 1f57c96ca63590fb94d09e939f411f9d53d48369 Mon Sep 17 00:00:00 2001 From: Andreas Woess Date: Thu, 25 Jul 2024 17:35:41 +0200 Subject: [PATCH 22/35] Check that memory 0 size >= initial size at the start of a wasm function. This allows hoisting bounds checks for memory accesses that are guaranteed to stay within the initial bounds. (cherry picked from commit 7b622f63a306665c9d482155a94886aac27aa35e) --- .../org.graalvm.wasm/src/org/graalvm/wasm/SymbolTable.java | 4 ++-- .../src/org/graalvm/wasm/memory/WasmMemory.java | 7 +++++++ .../src/org/graalvm/wasm/nodes/WasmFunctionNode.java | 6 +++--- 3 files changed, 12 insertions(+), 5 deletions(-) diff --git a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/SymbolTable.java b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/SymbolTable.java index 296b9f7d0efa..a9258baaed9a 100644 --- a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/SymbolTable.java +++ b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/SymbolTable.java @@ -179,12 +179,12 @@ public TableInfo(int initialSize, int maximumSize, byte elemType) { public static class MemoryInfo { /** - * Lower bound on memory size. + * Lower bound on memory size (in pages of 64 kiB). */ public final long initialSize; /** - * Upper bound on memory size. + * Upper bound on memory size (in pages of 64 kiB). *

* Note: this is the upper bound defined by the module. A memory instance might * have a lower internal max allowed size in practice. diff --git a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/WasmMemory.java b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/WasmMemory.java index dd8cc63464fc..d4bced208bd4 100644 --- a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/WasmMemory.java +++ b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/memory/WasmMemory.java @@ -838,6 +838,13 @@ protected boolean outOfBounds(long offset, long length) { return length < 0 || offset < 0 || offset > getBufferSize() - length; } + public final WasmMemory checkSize(long initialSize) { + if (byteSize() < initialSize * Sizes.MEMORY_PAGE_SIZE) { + throw CompilerDirectives.shouldNotReachHere("Memory size must not be less than initial size"); + } + return this; + } + /** * Copy data from an input stream into memory. * diff --git a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/nodes/WasmFunctionNode.java b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/nodes/WasmFunctionNode.java index af0cf6d98f0d..0f0f85736d5d 100644 --- a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/nodes/WasmFunctionNode.java +++ b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/nodes/WasmFunctionNode.java @@ -183,8 +183,8 @@ void updateBytecode(byte[] bytecode, int bytecodeStartOffset, int bytecodeEndOff this.notifyFunction = notifyFunction; } - private WasmMemory memory(WasmInstance instance) { - return memory(instance, 0); + private WasmMemory memory0(WasmInstance instance) { + return memory(instance, 0).checkSize(module.memoryInitialSize(0)); } private WasmMemory memory(WasmInstance instance, int index) { @@ -270,7 +270,7 @@ public Object executeBodyFromOffset(WasmContext context, WasmInstance instance, int line = startLine; // Note: The module may not have any memories. - final WasmMemory zeroMemory = module.memoryCount() == 0 ? null : memory(instance); + final WasmMemory zeroMemory = module.memoryCount() == 0 ? null : memory0(instance); check(bytecode.length, (1 << 31) - 1); From d9e04204d4fc7fa3e3d83946847e2211766c52da Mon Sep 17 00:00:00 2001 From: Andreas Woess Date: Fri, 26 Jul 2024 15:53:05 +0200 Subject: [PATCH 23/35] Only perform initial memory 0 bounds check if the wasm function uses memory 0. (cherry picked from commit e3377572e554cba58141397948d710e6a6886101) --- .../src/org/graalvm/wasm/BinaryParser.java | 2 +- .../src/org/graalvm/wasm/WasmCodeEntry.java | 10 ++- .../org/graalvm/wasm/WasmInstantiator.java | 2 +- .../graalvm/wasm/nodes/WasmFunctionNode.java | 2 +- .../wasm/parser/bytecode/BytecodeParser.java | 3 +- .../org/graalvm/wasm/parser/ir/CodeEntry.java | 8 ++- .../wasm/parser/validation/ParserState.java | 70 +++++++++++-------- 7 files changed, 62 insertions(+), 35 deletions(-) diff --git a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/BinaryParser.java b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/BinaryParser.java index 4b3cfdf1146a..8cad2f83c2dd 100644 --- a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/BinaryParser.java +++ b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/BinaryParser.java @@ -1033,7 +1033,7 @@ private CodeEntry readFunction(int functionIndex, byte[] locals, byte[] resultTy // Do not override the code entry offset when rereading the function. module.setCodeEntryOffset(codeEntryIndex, bytecodeEndOffset); } - return new CodeEntry(functionIndex, state.maxStackSize(), locals, resultTypes, callNodes, bytecodeStartOffset, bytecodeEndOffset); + return new CodeEntry(functionIndex, state.maxStackSize(), locals, resultTypes, callNodes, bytecodeStartOffset, bytecodeEndOffset, state.usesMemoryZero()); } private void readNumericInstructions(ParserState state, int opcode) { diff --git a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/WasmCodeEntry.java b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/WasmCodeEntry.java index c50d10d03275..3c9dcf85854c 100644 --- a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/WasmCodeEntry.java +++ b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/WasmCodeEntry.java @@ -1,5 +1,5 @@ /* - * Copyright (c) 2019, 2022, Oracle and/or its affiliates. All rights reserved. + * Copyright (c) 2019, 2024, Oracle and/or its affiliates. All rights reserved. * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER. * * The Universal Permissive License (UPL), Version 1.0 @@ -52,14 +52,16 @@ public final class WasmCodeEntry { private final BranchProfile errorBranch = BranchProfile.create(); private final int numLocals; private final int resultCount; + private final boolean usesMemoryZero; - public WasmCodeEntry(WasmFunction function, byte[] bytecode, byte[] localTypes, byte[] resultTypes) { + public WasmCodeEntry(WasmFunction function, byte[] bytecode, byte[] localTypes, byte[] resultTypes, boolean usesMemoryZero) { this.function = function; this.bytecode = bytecode; this.localTypes = localTypes; this.numLocals = localTypes.length; this.resultTypes = resultTypes; this.resultCount = resultTypes.length; + this.usesMemoryZero = usesMemoryZero; } public WasmFunction function() { @@ -94,6 +96,10 @@ public void errorBranch() { errorBranch.enter(); } + public boolean usesMemoryZero() { + return usesMemoryZero; + } + @Override public String toString() { return "wasm-code-entry:" + functionIndex(); diff --git a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/WasmInstantiator.java b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/WasmInstantiator.java index 505c50e8f2c5..ad1b3ae9a35e 100644 --- a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/WasmInstantiator.java +++ b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/WasmInstantiator.java @@ -495,7 +495,7 @@ private CallTarget instantiateCodeEntry(WasmContext context, WasmModule module, assert context.language().isMultiContext(); return cachedTarget; } - final WasmCodeEntry wasmCodeEntry = new WasmCodeEntry(function, module.bytecode(), codeEntry.localTypes(), codeEntry.resultTypes()); + final WasmCodeEntry wasmCodeEntry = new WasmCodeEntry(function, module.bytecode(), codeEntry.localTypes(), codeEntry.resultTypes(), codeEntry.usesMemoryZero()); final FrameDescriptor frameDescriptor = createFrameDescriptor(codeEntry.localTypes(), codeEntry.maxStackSize()); final WasmInstrumentableFunctionNode functionNode = instantiateFunctionNode(module, instance, wasmCodeEntry, codeEntry); final WasmRootNode rootNode; diff --git a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/nodes/WasmFunctionNode.java b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/nodes/WasmFunctionNode.java index 0f0f85736d5d..649bf788fe14 100644 --- a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/nodes/WasmFunctionNode.java +++ b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/nodes/WasmFunctionNode.java @@ -270,7 +270,7 @@ public Object executeBodyFromOffset(WasmContext context, WasmInstance instance, int line = startLine; // Note: The module may not have any memories. - final WasmMemory zeroMemory = module.memoryCount() == 0 ? null : memory0(instance); + final WasmMemory zeroMemory = !codeEntry.usesMemoryZero() ? null : memory0(instance); check(bytecode.length, (1 << 31) - 1); diff --git a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/parser/bytecode/BytecodeParser.java b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/parser/bytecode/BytecodeParser.java index 22c4052c2de3..9d6df0ec3a24 100644 --- a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/parser/bytecode/BytecodeParser.java +++ b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/parser/bytecode/BytecodeParser.java @@ -424,7 +424,8 @@ public static CodeEntry readCodeEntry(WasmModule module, byte[] bytecode, int co results = Bytecode.EMPTY_BYTES; } List callNodes = readCallNodes(bytecode, codeEntryOffset - length, codeEntryOffset); - return new CodeEntry(functionIndex, maxStackSize, locals, results, callNodes, codeEntryOffset - length, codeEntryOffset); + boolean usesMemoryZero = module.memoryCount() != 0; + return new CodeEntry(functionIndex, maxStackSize, locals, results, callNodes, codeEntryOffset - length, codeEntryOffset, usesMemoryZero); } /** diff --git a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/parser/ir/CodeEntry.java b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/parser/ir/CodeEntry.java index 3903e9c4328c..a3248b3c2fc7 100644 --- a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/parser/ir/CodeEntry.java +++ b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/parser/ir/CodeEntry.java @@ -54,8 +54,9 @@ public final class CodeEntry { private final List callNodes; private final int bytecodeStartOffset; private final int bytecodeEndOffset; + private final boolean usesMemoryZero; - public CodeEntry(int functionIndex, int maxStackSize, byte[] localTypes, byte[] resultTypes, List callNodes, int startOffset, int endOffset) { + public CodeEntry(int functionIndex, int maxStackSize, byte[] localTypes, byte[] resultTypes, List callNodes, int startOffset, int endOffset, boolean usesMemoryZero) { this.functionIndex = functionIndex; this.maxStackSize = maxStackSize; this.localTypes = localTypes; @@ -63,6 +64,7 @@ public CodeEntry(int functionIndex, int maxStackSize, byte[] localTypes, byte[] this.callNodes = callNodes; this.bytecodeStartOffset = startOffset; this.bytecodeEndOffset = endOffset; + this.usesMemoryZero = usesMemoryZero; } public int maxStackSize() { @@ -92,4 +94,8 @@ public int bytecodeStartOffset() { public int bytecodeEndOffset() { return bytecodeEndOffset; } + + public boolean usesMemoryZero() { + return usesMemoryZero; + } } diff --git a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/parser/validation/ParserState.java b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/parser/validation/ParserState.java index 3dab12c42e2a..6c0b58559e8f 100644 --- a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/parser/validation/ParserState.java +++ b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/parser/validation/ParserState.java @@ -65,6 +65,7 @@ public class ParserState { private final RuntimeBytecodeGen bytecode; private int maxStackSize; + private boolean usesMemoryZero; public ParserState(RuntimeBytecodeGen bytecode) { this.valueStack = new ByteArrayList(); @@ -76,7 +77,7 @@ public ParserState(RuntimeBytecodeGen bytecode) { /** * Pops a value from the stack if possible. Throws an error on stack underflow. - * + * * @param expectedValueType The expectedValueType used for error generation. * @return The top of the stack or -1. */ @@ -101,7 +102,7 @@ private byte popInternal(byte expectedValueType) { * are returned. If the number of values on the stack is greater or equal to the number of * expectedValueTypes, the values equal to the number of expectedValueTypes is popped from the * stack. - * + * * @param expectedValueTypes Value types expected on the stack. * @return The maximum of available stack values smaller than the length of expectedValueTypes. */ @@ -117,7 +118,7 @@ private byte[] popAvailableUnchecked(byte[] expectedValueTypes) { /** * Pops the maximum available values from the current stack frame. - * + * * @return The maximum of available stack values. */ private byte[] popAvailableUnchecked() { @@ -133,7 +134,7 @@ private byte[] popAvailableUnchecked() { /** * Checks if two sets of value types are equivalent. - * + * * @param expectedTypes The expected value types. * @param actualTypes The actual value types. * @return True if both are equivalent. @@ -155,7 +156,7 @@ private boolean isTypeMismatch(byte[] expectedTypes, byte[] actualTypes) { /** * Pushes a value type onto the stack. - * + * * @param valueType The value type that should be added. */ public void push(byte valueType) { @@ -165,7 +166,7 @@ public void push(byte valueType) { /** * Pushes all provided value types onto the stack. - * + * * @param valueTypes The value types that should be added. */ public void pushAll(byte[] valueTypes) { @@ -176,7 +177,7 @@ public void pushAll(byte[] valueTypes) { /** * Pops the topmost value type from the stack. Throws an error if the stack is empty. - * + * * @return The value type on top of the stack or -1. * @throws WasmException If the stack is empty. */ @@ -186,7 +187,7 @@ public byte pop() { /** * Pops the topmost value type from the stack and checks if it is equivalent to the given value. - * + * * @param expectedValueType The expected value type. * @return The value type on top of the stack. * @throws WasmException If the stack is empty or the value types do not match. @@ -220,7 +221,7 @@ public void popReferenceTypeChecked() { /** * Pops the topmost value types from the stack and checks if they are equivalent to the given * set of value types. - * + * * @param expectedValueTypes The expected value types. * @return The value types on top of the stack. * @throws WasmException If the stack is empty or the value types do not match. @@ -335,7 +336,7 @@ public void addConditionalBranch(int branchLabel) { /** * Performs the necessary branch checks and adds the unconditional branch information to the * extra data array. - * + * * @param branchLabel The target label. */ public void addUnconditionalBranch(int branchLabel) { @@ -349,7 +350,7 @@ public void addUnconditionalBranch(int branchLabel) { /** * Performs the necessary branch checks and adds the branch table information to the extra data * array. - * + * * @param branchLabels The target labels. */ public void addBranchTable(int[] branchLabels) { @@ -371,7 +372,7 @@ public void addBranchTable(int[] branchLabels) { /** * Performs the necessary checks for a function return. - * + * * @param multiValue If multiple return values are supported. */ public void addReturn(boolean multiValue) { @@ -386,7 +387,7 @@ public void addReturn(boolean multiValue) { /** * Adds the index of an indirect call node to the extra data array. - * + * * @param nodeIndex The index of the indirect call. */ public void addIndirectCall(int nodeIndex, int typeIndex, int tableIndex) { @@ -395,7 +396,7 @@ public void addIndirectCall(int nodeIndex, int typeIndex, int tableIndex) { /** * Adds the index of a direct call node to the extra data array. - * + * * @param nodeIndex The index of the direct call. */ public void addCall(int nodeIndex, int functionIndex) { @@ -425,7 +426,7 @@ public void addVectorFlag() { /** * Adds the given instruction and an i32 immediate value to the bytecode. - * + * * @param instruction The instruction * @param value The immediate value */ @@ -435,7 +436,7 @@ public void addInstruction(int instruction, int value) { /** * Adds the given instruction and an i64 immediate value to the bytecode. - * + * * @param instruction The instruction * @param value The immediate value */ @@ -455,7 +456,7 @@ public void addInstruction(int instruction, Vector128 value) { /** * Adds the given instruction and two i32 immediate values to the bytecode. - * + * * @param instruction The instruction * @param value1 The first immediate value * @param value2 The second immediate value @@ -468,7 +469,7 @@ public void addInstruction(int instruction, int value1, int value2) { * Adds the i8 or i32 version of the given instruction to the bytecode based on the given * immediate value. If the value fits into a signed i8 value, the i8 instruction and an i8 value * are added. Otherwise, the i32 instruction and an i32 value are added. - * + * * @param instruction The i8 version of the instruction * @param value The immediate value. */ @@ -480,7 +481,7 @@ public void addSignedInstruction(int instruction, int value) { * Adds the i8 or i64 version of the given instruction to the bytecode based on the given * immediate value. If the value fits into a signed i8 value, the i8 instruction and an i8 value * are added. Otherwise, the i64 instruction and i64 value are added. - * + * * @param instruction The i8 version of the instruction * @param value The immediate value */ @@ -492,7 +493,7 @@ public void addSignedInstruction(int instruction, long value) { * Adds the u8 or i32 version of the given instruction to the bytecode based on the given * immediate value. If the value fits into a u8 value, the u8 instruction and a u8 value are * added. Otherwise, the i32 instruction and an i32 value are added. - * + * * @param instruction The u8 version of the instruction * @param value The immediate value */ @@ -502,13 +503,14 @@ public void addUnsignedInstruction(int instruction, int value) { /** * Adds a memory instruction based on the given values and index type. - * + * * @param baseInstruction The base version of the memory instruction * @param memoryIndex The index of the memory being accessed * @param value The immediate value * @param indexType64 If the index type is 64 bit. */ public void addMemoryInstruction(int baseInstruction, int memoryIndex, long value, boolean indexType64) { + markMemoryUsed(memoryIndex); bytecode.addMemoryInstruction(baseInstruction, baseInstruction + 1, baseInstruction + 2, memoryIndex, value, indexType64); } @@ -522,6 +524,7 @@ public void addMemoryInstruction(int baseInstruction, int memoryIndex, long valu * @param indexType64 If the index type is 64 bit. */ public void addExtendedMemoryInstruction(int instruction, int memoryIndex, long value, boolean indexType64) { + markMemoryUsed(memoryIndex); bytecode.addExtendedMemoryInstruction(instruction, memoryIndex, value, indexType64); } @@ -535,13 +538,14 @@ public void addExtendedMemoryInstruction(int instruction, int memoryIndex, long * @param laneIndex The lane index */ public void addVectorMemoryLaneInstruction(int instruction, int memoryIndex, long value, boolean indexType64, byte laneIndex) { + markMemoryUsed(memoryIndex); bytecode.addExtendedMemoryInstruction(instruction, memoryIndex, value, indexType64); bytecode.add(laneIndex); } /** * Adds a lane-indexed vector instruction (extract_lane or replace_lane). - * + * * @param instruction The vector instruction * @param laneIndex The lane index */ @@ -554,7 +558,7 @@ public void addVectorLaneInstruction(int instruction, byte laneIndex) { * Finishes the current control frame and removes it from the control frame stack. * * @param multiValue If multiple return values are supported. - * + * * @throws WasmException If the number of return value types do not match with the remaining * stack or the number of return values is greater than 1. */ @@ -576,7 +580,7 @@ public void exit(boolean multiValue) { /** * Checks that the expected return types are actually on the value stack. - * + * * @param frame The frame that is exited. * @param resultTypes The expected return types of the frame. */ @@ -627,7 +631,7 @@ private void checkResultTypes(ControlFrame frame) { /** * Checks if the given parameter value types do match the current value types on the stack. - * + * * @param paramTypes The expected value types. * @throws WasmException If the parameter value types and the vale types on the stack do not * match. @@ -645,7 +649,7 @@ public void checkParamTypes(byte[] paramTypes) { /** * Checks if the given label is a valid jump target. - * + * * @param label The label which to jump to. * @throws WasmException If the label is out or reach. */ @@ -657,7 +661,7 @@ public void checkLabelExists(int label) { /** * Checks if the value types of two different labels match. - * + * * @param expectedTypes The expected value types. * @param actualTypes The value types that should be checked. * @throws WasmException If the provided sets of value types do not match. @@ -670,7 +674,7 @@ public void checkLabelTypes(byte[] expectedTypes, byte[] actualTypes) { /** * Checks if the given function type is within range. - * + * * @param typeIndex The function type. * @param max The number of available function types. * @throws WasmException If the given function type is greater or equal to the given maximum. @@ -701,4 +705,14 @@ public int valueStackSize() { public int maxStackSize() { return maxStackSize; } + + private void markMemoryUsed(int memoryIndex) { + if (memoryIndex == 0) { + usesMemoryZero = true; + } + } + + public boolean usesMemoryZero() { + return usesMemoryZero; + } } From 030948477da886ff4259c292eaadc944e968be13 Mon Sep 17 00:00:00 2001 From: Andreas Woess Date: Fri, 26 Jul 2024 18:39:12 +0200 Subject: [PATCH 24/35] Work around for nullary benchmarkTeardownEach() in photon benchmark. (cherry picked from commit 03b8dfcd69b757fd0128bb56535837c8955d4216) --- .../benchmark/WasmBenchmarkSuiteBase.java | 29 +++++++++++++++++-- 1 file changed, 26 insertions(+), 3 deletions(-) diff --git a/wasm/src/org.graalvm.wasm.benchmark/src/org/graalvm/wasm/benchmark/WasmBenchmarkSuiteBase.java b/wasm/src/org.graalvm.wasm.benchmark/src/org/graalvm/wasm/benchmark/WasmBenchmarkSuiteBase.java index 0a078cfb97cd..6caf376a8b9a 100644 --- a/wasm/src/org.graalvm.wasm.benchmark/src/org/graalvm/wasm/benchmark/WasmBenchmarkSuiteBase.java +++ b/wasm/src/org.graalvm.wasm.benchmark/src/org/graalvm/wasm/benchmark/WasmBenchmarkSuiteBase.java @@ -48,8 +48,8 @@ import java.util.Objects; import org.graalvm.polyglot.Context; +import org.graalvm.polyglot.PolyglotAccess; import org.graalvm.polyglot.Value; -import org.graalvm.wasm.WasmContextOptions; import org.graalvm.wasm.WasmLanguage; import org.graalvm.wasm.utils.WasmBinaryTools; import org.graalvm.wasm.utils.cases.WasmCase; @@ -71,6 +71,7 @@ public abstract static class WasmBenchmarkState { private Value benchmarkTeardownEach; private Value benchmarkRun; private Value result; + private int benchmarkTeardownEachArgs = 1; /** * Benchmarks must not be validated via their standard out, unlike tests. @@ -97,6 +98,8 @@ public void setup() throws IOException, InterruptedException { } } }); + // Export "WebAssembly" binding. + contextBuilder.allowPolyglotAccess(PolyglotAccess.ALL); context = contextBuilder.build(); var sources = benchmarkCase.getSources(EnumSet.noneOf(WasmBinaryTools.WabtOption.class)); @@ -112,6 +115,18 @@ public void setup() throws IOException, InterruptedException { throw new RuntimeException(String.format("No benchmarkRun method in %s.", benchmarkCase.name())); } + // Workaround for photon benchmark's nullary benchmarkTeardownEach(). + Value api = context.getPolyglotBindings().getMember("WebAssembly"); + if (api != null) { + Value funcType = api.getMember("func_type"); + if (funcType != null) { + Value signature = funcType.execute(benchmarkTeardownEach); + if (signature.asString().contains("()")) { + benchmarkTeardownEachArgs = 0; + } + } + } + if (benchmarkSetupOnce != null) { benchmarkSetupOnce.execute(); } @@ -141,12 +156,20 @@ public void setupInvocation() { // is that they can handle VM-state side-effects. // We may support benchmark-specific teardown actions in the future (at the invocation // level). - benchmarkSetupEach.execute(); + if (benchmarkSetupEach != null) { + benchmarkSetupEach.execute(); + } } @TearDown(Level.Invocation) public void teardownInvocation() { - benchmarkTeardownEach.execute(0); + if (benchmarkTeardownEach != null) { + if (benchmarkTeardownEachArgs == 0) { + benchmarkTeardownEach.execute(); + } else { + benchmarkTeardownEach.execute(0); + } + } } public void run() { From 51b5e48e15a64fed4a82cdcf62d742c4d1374513 Mon Sep 17 00:00:00 2001 From: Andreas Woess Date: Fri, 26 Jul 2024 23:59:34 +0200 Subject: [PATCH 25/35] Fix TraceTransferToInterpreter in WasmFunctionNode.profileCondition. (cherry picked from commit 66c83744b3edc6a4b2488f93704727e5f3f3aa0f) --- .../org/graalvm/wasm/nodes/WasmFunctionNode.java | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-) diff --git a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/nodes/WasmFunctionNode.java b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/nodes/WasmFunctionNode.java index 649bf788fe14..beccbbab99ec 100644 --- a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/nodes/WasmFunctionNode.java +++ b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/nodes/WasmFunctionNode.java @@ -4642,31 +4642,31 @@ private static boolean profileCondition(byte[] data, final int profileOffset, bo int f = rawPeekU8(data, profileOffset + 1); boolean val = condition; if (val) { + if (t == 0) { + CompilerDirectives.transferToInterpreterAndInvalidate(); + } if (!CompilerDirectives.inInterpreter()) { - if (t == 0) { - CompilerDirectives.transferToInterpreterAndInvalidate(); - } if (f == 0) { // Make this branch fold during PE val = true; } } else { if (t < MAX_PROFILE_VALUE) { - data[profileOffset]++; + data[profileOffset] = (byte) (t + 1); } } } else { + if (f == 0) { + CompilerDirectives.transferToInterpreterAndInvalidate(); + } if (!CompilerDirectives.inInterpreter()) { - if (f == 0) { - CompilerDirectives.transferToInterpreterAndInvalidate(); - } if (t == 0) { // Make this branch fold during PE val = false; } } else { if (f < MAX_PROFILE_VALUE) { - data[profileOffset + 1]++; + data[profileOffset + 1] = (byte) (f + 1); } } } From 40d8fbe102d9825197a48ee2b7867c6ab8e5411f Mon Sep 17 00:00:00 2001 From: Andreas Woess Date: Wed, 31 Jul 2024 18:41:31 +0200 Subject: [PATCH 26/35] Try to read WebAssembly.Module bytes via Buffer Interop. (cherry picked from commit a6fa57bc4d9fc68631d3dcfff6330b43c03ce9e3) --- .../src/org/graalvm/wasm/api/WebAssembly.java | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) diff --git a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/api/WebAssembly.java b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/api/WebAssembly.java index 3bd50851883e..8ea8fd84fe20 100644 --- a/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/api/WebAssembly.java +++ b/wasm/src/org.graalvm.wasm/src/org/graalvm/wasm/api/WebAssembly.java @@ -297,8 +297,15 @@ private static void checkArgumentCount(Object[] args, int requiredCount) { private static byte[] toBytes(Object source) { InteropLibrary interop = InteropLibrary.getUncached(source); - if (interop.hasArrayElements(source)) { - try { + try { + if (interop.hasBufferElements(source)) { + long size = interop.getBufferSize(source); + if (size == (int) size) { + byte[] bytes = new byte[(int) size]; + interop.readBuffer(source, 0, bytes, 0, (int) size); + return bytes; + } + } else if (interop.hasArrayElements(source)) { long size = interop.getArraySize(source); if (size == (int) size) { byte[] bytes = new byte[(int) size]; @@ -312,9 +319,9 @@ private static byte[] toBytes(Object source) { } return bytes; } - } catch (InteropException iex) { - throw cannotConvertToBytesError(iex); } + } catch (InteropException iex) { + throw cannotConvertToBytesError(iex); } throw cannotConvertToBytesError(null); } From 06883bc7e6fed5b04b7d951688420c155b5ab687 Mon Sep 17 00:00:00 2001 From: Marouane El Hallaoui Date: Thu, 19 Sep 2024 10:06:14 +0100 Subject: [PATCH 27/35] support different JDK version between CE and EE for labsjdk-latest --- common.json | 6 +++--- compiler/ci/ci_common/gate.jsonnet | 2 +- .../src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java | 2 +- 3 files changed, 5 insertions(+), 5 deletions(-) diff --git a/common.json b/common.json index 39f972e96f61..92a849a861b7 100644 --- a/common.json +++ b/common.json @@ -46,9 +46,9 @@ "graalvm-ee-21": {"name": "graalvm-java21", "version": "23.1.3", "platformspecific": true }, "oraclejdk-latest": {"name": "jpg-jdk", "version": "23", "build_id": "jdk-23.0.1+10", "platformspecific": true, "extrabundles": ["static-libs"]}, - "labsjdk-ce-latest": {"name": "labsjdk", "version": "ce-23.0.1+10-jvmci-b01-20240911195242-519b5c19b9", "platformspecific": true }, - "labsjdk-ce-latestDebug": {"name": "labsjdk", "version": "ce-23.0.1+10-jvmci-b01-20240911195242-519b5c19b9-debug", "platformspecific": true }, - "labsjdk-ce-latest-llvm": {"name": "labsjdk", "version": "ce-23.0.1+10-jvmci-b01-20240911195242-519b5c19b9-sulong", "platformspecific": true }, + "labsjdk-ce-latest": {"name": "labsjdk", "version": "ce-23+37-jvmci-b01", "platformspecific": true }, + "labsjdk-ce-latestDebug": {"name": "labsjdk", "version": "ce-23+37-jvmci-b01-debug", "platformspecific": true }, + "labsjdk-ce-latest-llvm": {"name": "labsjdk", "version": "ce-23+37-jvmci-b01-sulong", "platformspecific": true }, "labsjdk-ee-latest": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01-20240911195242-519b5c19b9+456f3d01e0", "platformspecific": true }, "labsjdk-ee-latestDebug": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01-20240911195242-519b5c19b9+456f3d01e0-debug", "platformspecific": true }, "labsjdk-ee-latest-llvm": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01-20240911195242-519b5c19b9+456f3d01e0-sulong", "platformspecific": true } diff --git a/compiler/ci/ci_common/gate.jsonnet b/compiler/ci/ci_common/gate.jsonnet index ed32a080ba00..c39a65bcdb78 100644 --- a/compiler/ci/ci_common/gate.jsonnet +++ b/compiler/ci/ci_common/gate.jsonnet @@ -487,7 +487,7 @@ local jdk_latest_version_check_builds = [self.make_build(self.jdk_latest, "linux-amd64", "build", extra_tasks={build:: s.base("build"),}).build + galahad.exclude { environment+: { # Run the strict JVMCI version check, i.e., that JVMCIVersionCheck.JVMCI_MIN_VERSION matches the versions in common.json. - JVMCI_VERSION_CHECK: "strict", + JVMCI_VERSION_CHECK: "ignore", }, }], diff --git a/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java b/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java index 69838f005cfd..5f5d522d656b 100644 --- a/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java +++ b/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java @@ -56,7 +56,7 @@ public final class JVMCIVersionCheck { "21", Map.of(DEFAULT_VENDOR_ENTRY, createLegacyVersion(23, 1, 33)), "23", Map.of( "Oracle Corporation", createLabsJDKVersion("23.0.1+9", 1), - DEFAULT_VENDOR_ENTRY, createLabsJDKVersion("23.0.1+9", 1))); + DEFAULT_VENDOR_ENTRY, createLabsJDKVersion("23+37", 1))); private static final int NA = 0; /** * Minimum Java release supported by Graal. From a75a4bbd3fc2b0a2e1d27de1c7f775a1dfd68093 Mon Sep 17 00:00:00 2001 From: Marouane El Hallaoui Date: Thu, 19 Sep 2024 13:26:08 +0100 Subject: [PATCH 28/35] deploy snapshots --- common.json | 6 +++--- .../src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/common.json b/common.json index 92a849a861b7..ea67d7b2fdc8 100644 --- a/common.json +++ b/common.json @@ -49,9 +49,9 @@ "labsjdk-ce-latest": {"name": "labsjdk", "version": "ce-23+37-jvmci-b01", "platformspecific": true }, "labsjdk-ce-latestDebug": {"name": "labsjdk", "version": "ce-23+37-jvmci-b01-debug", "platformspecific": true }, "labsjdk-ce-latest-llvm": {"name": "labsjdk", "version": "ce-23+37-jvmci-b01-sulong", "platformspecific": true }, - "labsjdk-ee-latest": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01-20240911195242-519b5c19b9+456f3d01e0", "platformspecific": true }, - "labsjdk-ee-latestDebug": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01-20240911195242-519b5c19b9+456f3d01e0-debug", "platformspecific": true }, - "labsjdk-ee-latest-llvm": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01-20240911195242-519b5c19b9+456f3d01e0-sulong", "platformspecific": true } + "labsjdk-ee-latest": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01", "platformspecific": true }, + "labsjdk-ee-latestDebug": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01-debug", "platformspecific": true }, + "labsjdk-ee-latest-llvm": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01-sulong", "platformspecific": true } }, "eclipse": { diff --git a/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java b/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java index 5f5d522d656b..0587b2d0c8d2 100644 --- a/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java +++ b/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java @@ -55,7 +55,7 @@ public final class JVMCIVersionCheck { private static final Map> JVMCI_MIN_VERSIONS = Map.of( "21", Map.of(DEFAULT_VENDOR_ENTRY, createLegacyVersion(23, 1, 33)), "23", Map.of( - "Oracle Corporation", createLabsJDKVersion("23.0.1+9", 1), + "Oracle Corporation", createLabsJDKVersion("23.0.1+10", 1), DEFAULT_VENDOR_ENTRY, createLabsJDKVersion("23+37", 1))); private static final int NA = 0; /** From 7fadceaeb61a2bab83de0b3e0ee1f661b214dc7f Mon Sep 17 00:00:00 2001 From: Marouane El Hallaoui Date: Thu, 26 Sep 2024 11:14:31 +0100 Subject: [PATCH 29/35] update JVMCI CE to 23.0.1+10-jvmci-b01 --- common.json | 6 +++--- .../src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java | 2 +- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/common.json b/common.json index ea67d7b2fdc8..8229dcc485ba 100644 --- a/common.json +++ b/common.json @@ -46,9 +46,9 @@ "graalvm-ee-21": {"name": "graalvm-java21", "version": "23.1.3", "platformspecific": true }, "oraclejdk-latest": {"name": "jpg-jdk", "version": "23", "build_id": "jdk-23.0.1+10", "platformspecific": true, "extrabundles": ["static-libs"]}, - "labsjdk-ce-latest": {"name": "labsjdk", "version": "ce-23+37-jvmci-b01", "platformspecific": true }, - "labsjdk-ce-latestDebug": {"name": "labsjdk", "version": "ce-23+37-jvmci-b01-debug", "platformspecific": true }, - "labsjdk-ce-latest-llvm": {"name": "labsjdk", "version": "ce-23+37-jvmci-b01-sulong", "platformspecific": true }, + "labsjdk-ce-latest": {"name": "labsjdk", "version": "ce-23.0.1+10-jvmci-b01", "platformspecific": true }, + "labsjdk-ce-latestDebug": {"name": "labsjdk", "version": "ce-23.0.1+10-jvmci-b01-debug", "platformspecific": true }, + "labsjdk-ce-latest-llvm": {"name": "labsjdk", "version": "ce-23.0.1+10-jvmci-b01-sulong", "platformspecific": true }, "labsjdk-ee-latest": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01", "platformspecific": true }, "labsjdk-ee-latestDebug": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01-debug", "platformspecific": true }, "labsjdk-ee-latest-llvm": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01-sulong", "platformspecific": true } diff --git a/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java b/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java index 0587b2d0c8d2..e7c2db349166 100644 --- a/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java +++ b/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java @@ -56,7 +56,7 @@ public final class JVMCIVersionCheck { "21", Map.of(DEFAULT_VENDOR_ENTRY, createLegacyVersion(23, 1, 33)), "23", Map.of( "Oracle Corporation", createLabsJDKVersion("23.0.1+10", 1), - DEFAULT_VENDOR_ENTRY, createLabsJDKVersion("23+37", 1))); + DEFAULT_VENDOR_ENTRY, createLabsJDKVersion("23.0.1+10", 1))); private static final int NA = 0; /** * Minimum Java release supported by Graal. From a8318eb0bfe6340731e0f58437a31e3a8c6fc64a Mon Sep 17 00:00:00 2001 From: Marouane El Hallaoui Date: Thu, 26 Sep 2024 11:15:41 +0100 Subject: [PATCH 30/35] revert : support different JDK version between CE and EE for labsjdk-latest --- compiler/ci/ci_common/gate.jsonnet | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/compiler/ci/ci_common/gate.jsonnet b/compiler/ci/ci_common/gate.jsonnet index c39a65bcdb78..ed32a080ba00 100644 --- a/compiler/ci/ci_common/gate.jsonnet +++ b/compiler/ci/ci_common/gate.jsonnet @@ -487,7 +487,7 @@ local jdk_latest_version_check_builds = [self.make_build(self.jdk_latest, "linux-amd64", "build", extra_tasks={build:: s.base("build"),}).build + galahad.exclude { environment+: { # Run the strict JVMCI version check, i.e., that JVMCIVersionCheck.JVMCI_MIN_VERSION matches the versions in common.json. - JVMCI_VERSION_CHECK: "ignore", + JVMCI_VERSION_CHECK: "strict", }, }], From d759153c017c3f29220f623115a2f10505e03e50 Mon Sep 17 00:00:00 2001 From: Danilo Ansaloni Date: Thu, 26 Sep 2024 14:50:10 +0200 Subject: [PATCH 31/35] Update mx import. --- common.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/common.json b/common.json index ea67d7b2fdc8..989f34d6baae 100644 --- a/common.json +++ b/common.json @@ -4,7 +4,7 @@ "Jsonnet files should not include this file directly but use ci/common.jsonnet instead." ], - "mx_version": "7.27.5", + "mx_version": "7.27.5.1", "COMMENT.jdks": "When adding or removing JDKs keep in sync with JDKs in ci/common.jsonnet", "jdks": { From d0e195814a481842df28e06f06a3e66df88a69a2 Mon Sep 17 00:00:00 2001 From: ol-automation_ww Date: Fri, 27 Sep 2024 17:40:08 +0000 Subject: [PATCH 32/35] [GR-57721] Backport to 24.1: Create Gradle plugin with similar features as our Maven plugin. PullRequest: graalpython/3476 --- vm/mx.vm/suite.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/vm/mx.vm/suite.py b/vm/mx.vm/suite.py index c326749ab88c..472809418f06 100644 --- a/vm/mx.vm/suite.py +++ b/vm/mx.vm/suite.py @@ -65,7 +65,7 @@ }, { "name": "graalpython", - "version": "9f301a4e16dd42d28138276ba3af24e81200c125", + "version": "9f8c823b41d79e1da43bf78000ce790ac657e5d6", "dynamic": True, "urls": [ {"url": "https://github.com/graalvm/graalpython.git", "kind": "git"}, From 8dc96da6ff8060b70f14fc662a22a211f9685654 Mon Sep 17 00:00:00 2001 From: Marouane El Hallaoui Date: Tue, 1 Oct 2024 16:16:37 +0100 Subject: [PATCH 33/35] labsjdk respin : adopt jdk-23.0.1+11 --- common.json | 14 +++++++------- .../graal/compiler/hotspot/JVMCIVersionCheck.java | 4 ++-- 2 files changed, 9 insertions(+), 9 deletions(-) diff --git a/common.json b/common.json index 8229dcc485ba..53b0d29ae1e3 100644 --- a/common.json +++ b/common.json @@ -45,13 +45,13 @@ "labsjdk-ee-21-llvm": {"name": "labsjdk", "version": "ee-21.0.2+13-jvmci-23.1-b33-sulong", "platformspecific": true }, "graalvm-ee-21": {"name": "graalvm-java21", "version": "23.1.3", "platformspecific": true }, - "oraclejdk-latest": {"name": "jpg-jdk", "version": "23", "build_id": "jdk-23.0.1+10", "platformspecific": true, "extrabundles": ["static-libs"]}, - "labsjdk-ce-latest": {"name": "labsjdk", "version": "ce-23.0.1+10-jvmci-b01", "platformspecific": true }, - "labsjdk-ce-latestDebug": {"name": "labsjdk", "version": "ce-23.0.1+10-jvmci-b01-debug", "platformspecific": true }, - "labsjdk-ce-latest-llvm": {"name": "labsjdk", "version": "ce-23.0.1+10-jvmci-b01-sulong", "platformspecific": true }, - "labsjdk-ee-latest": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01", "platformspecific": true }, - "labsjdk-ee-latestDebug": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01-debug", "platformspecific": true }, - "labsjdk-ee-latest-llvm": {"name": "labsjdk", "version": "ee-23.0.1+10-jvmci-b01-sulong", "platformspecific": true } + "oraclejdk-latest": {"name": "jpg-jdk", "version": "23", "build_id": "jdk-23.0.1+11", "platformspecific": true, "extrabundles": ["static-libs"]}, + "labsjdk-ce-latest": {"name": "labsjdk", "version": "ce-23.0.1+11-jvmci-b01", "platformspecific": true }, + "labsjdk-ce-latestDebug": {"name": "labsjdk", "version": "ce-23.0.1+11-jvmci-b01-debug", "platformspecific": true }, + "labsjdk-ce-latest-llvm": {"name": "labsjdk", "version": "ce-23.0.1+11-jvmci-b01-sulong", "platformspecific": true }, + "labsjdk-ee-latest": {"name": "labsjdk", "version": "ee-23.0.1+11-jvmci-b01", "platformspecific": true }, + "labsjdk-ee-latestDebug": {"name": "labsjdk", "version": "ee-23.0.1+11-jvmci-b01-debug", "platformspecific": true }, + "labsjdk-ee-latest-llvm": {"name": "labsjdk", "version": "ee-23.0.1+11-jvmci-b01-sulong", "platformspecific": true } }, "eclipse": { diff --git a/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java b/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java index e7c2db349166..6781458475a9 100644 --- a/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java +++ b/compiler/src/jdk.graal.compiler/src/jdk/graal/compiler/hotspot/JVMCIVersionCheck.java @@ -55,8 +55,8 @@ public final class JVMCIVersionCheck { private static final Map> JVMCI_MIN_VERSIONS = Map.of( "21", Map.of(DEFAULT_VENDOR_ENTRY, createLegacyVersion(23, 1, 33)), "23", Map.of( - "Oracle Corporation", createLabsJDKVersion("23.0.1+10", 1), - DEFAULT_VENDOR_ENTRY, createLabsJDKVersion("23.0.1+10", 1))); + "Oracle Corporation", createLabsJDKVersion("23.0.1+11", 1), + DEFAULT_VENDOR_ENTRY, createLabsJDKVersion("23.0.1+11", 1))); private static final int NA = 0; /** * Minimum Java release supported by Graal. From 9dabc6283868a2c513f7f0bc7c15888555cf4de1 Mon Sep 17 00:00:00 2001 From: ol-automation_ww Date: Thu, 3 Oct 2024 08:42:07 +0000 Subject: [PATCH 34/35] [GR-57975] Backport to 24.1: Update bouncycastle dependency PullRequest: graalpython/3474 --- vm/mx.vm/suite.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/vm/mx.vm/suite.py b/vm/mx.vm/suite.py index 472809418f06..2b9a16c30c5d 100644 --- a/vm/mx.vm/suite.py +++ b/vm/mx.vm/suite.py @@ -65,7 +65,7 @@ }, { "name": "graalpython", - "version": "9f8c823b41d79e1da43bf78000ce790ac657e5d6", + "version": "facfb86f6c17a97986300619626538966fbf1ae6", "dynamic": True, "urls": [ {"url": "https://github.com/graalvm/graalpython.git", "kind": "git"}, From 4d9a08f482271b778fb72171d80e3970c034924f Mon Sep 17 00:00:00 2001 From: Marouane El Hallaoui Date: Fri, 4 Oct 2024 13:54:23 +0100 Subject: [PATCH 35/35] Release GraalVM 24.1.1. --- compiler/mx.compiler/suite.py | 2 +- espresso/mx.espresso/suite.py | 2 +- regex/mx.regex/suite.py | 2 +- sdk/mx.sdk/suite.py | 2 +- substratevm/mx.substratevm/suite.py | 2 +- tools/mx.tools/suite.py | 2 +- truffle/mx.truffle/suite.py | 2 +- vm/mx.vm/suite.py | 8 ++++---- 8 files changed, 11 insertions(+), 11 deletions(-) diff --git a/compiler/mx.compiler/suite.py b/compiler/mx.compiler/suite.py index cfd6cce09f15..8f341b61673e 100644 --- a/compiler/mx.compiler/suite.py +++ b/compiler/mx.compiler/suite.py @@ -5,7 +5,7 @@ "groupId" : "org.graalvm.compiler", "version" : "24.1.1", - "release" : False, + "release" : True, "url" : "http://www.graalvm.org/", "developer" : { "name" : "GraalVM Development", diff --git a/espresso/mx.espresso/suite.py b/espresso/mx.espresso/suite.py index 90fd788f297e..9db519180700 100644 --- a/espresso/mx.espresso/suite.py +++ b/espresso/mx.espresso/suite.py @@ -25,7 +25,7 @@ "mxversion": "7.27.1", "name": "espresso", "version" : "24.1.1", - "release" : False, + "release" : True, "groupId" : "org.graalvm.espresso", "url" : "https://www.graalvm.org/reference-manual/java-on-truffle/", "developer" : { diff --git a/regex/mx.regex/suite.py b/regex/mx.regex/suite.py index d5ae688ccaf3..615f7bee4833 100644 --- a/regex/mx.regex/suite.py +++ b/regex/mx.regex/suite.py @@ -44,7 +44,7 @@ "name" : "regex", "version" : "24.1.1", - "release" : False, + "release" : True, "groupId" : "org.graalvm.regex", "url" : "http://www.graalvm.org/", "developer" : { diff --git a/sdk/mx.sdk/suite.py b/sdk/mx.sdk/suite.py index a20b624044c9..c5a3871fe72d 100644 --- a/sdk/mx.sdk/suite.py +++ b/sdk/mx.sdk/suite.py @@ -42,7 +42,7 @@ "mxversion": "7.27.0", "name" : "sdk", "version" : "24.1.1", - "release" : False, + "release" : True, "sourceinprojectwhitelist" : [], "url" : "https://github.com/oracle/graal", "groupId" : "org.graalvm.sdk", diff --git a/substratevm/mx.substratevm/suite.py b/substratevm/mx.substratevm/suite.py index e5e16fefb882..9f966197fd9b 100644 --- a/substratevm/mx.substratevm/suite.py +++ b/substratevm/mx.substratevm/suite.py @@ -3,7 +3,7 @@ "mxversion": "7.27.1", "name": "substratevm", "version" : "24.1.1", - "release" : False, + "release" : True, "url" : "https://github.com/oracle/graal/tree/master/substratevm", "groupId" : "org.graalvm.nativeimage", diff --git a/tools/mx.tools/suite.py b/tools/mx.tools/suite.py index 120b9de39982..7b4beebeef5a 100644 --- a/tools/mx.tools/suite.py +++ b/tools/mx.tools/suite.py @@ -27,7 +27,7 @@ "groupId" : "org.graalvm.tools", "version" : "24.1.1", - "release" : False, + "release" : True, "url" : "http://openjdk.java.net/projects/graal", "developer" : { "name" : "GraalVM Development", diff --git a/truffle/mx.truffle/suite.py b/truffle/mx.truffle/suite.py index e95ca13745f7..02d010a8fc37 100644 --- a/truffle/mx.truffle/suite.py +++ b/truffle/mx.truffle/suite.py @@ -42,7 +42,7 @@ "mxversion": "7.27.1", "name" : "truffle", "version" : "24.1.1", - "release" : False, + "release" : True, "groupId" : "org.graalvm.truffle", "sourceinprojectwhitelist" : [], "url" : "http://openjdk.java.net/projects/graal", diff --git a/vm/mx.vm/suite.py b/vm/mx.vm/suite.py index 2b9a16c30c5d..9e667fa76099 100644 --- a/vm/mx.vm/suite.py +++ b/vm/mx.vm/suite.py @@ -2,7 +2,7 @@ "name": "vm", "version" : "24.1.1", "mxversion": "7.27.0", - "release" : False, + "release" : True, "groupId" : "org.graalvm", "url" : "http://www.graalvm.org/", @@ -33,7 +33,7 @@ "name": "graal-nodejs", "subdir": True, "dynamic": True, - "version": "3af98ddb1001364de67c4cbede31445c40c0e96f", + "version": "2e808370bb8c82ecef81700afd890864f75ef9a1", "urls" : [ {"url" : "https://github.com/graalvm/graaljs.git", "kind" : "git"}, ] @@ -42,7 +42,7 @@ "name": "graal-js", "subdir": True, "dynamic": True, - "version": "3af98ddb1001364de67c4cbede31445c40c0e96f", + "version": "2e808370bb8c82ecef81700afd890864f75ef9a1", "urls": [ {"url": "https://github.com/graalvm/graaljs.git", "kind" : "git"}, ] @@ -65,7 +65,7 @@ }, { "name": "graalpython", - "version": "facfb86f6c17a97986300619626538966fbf1ae6", + "version": "a5d4b186761583a006ed3cfc6f0887c6306bc696", "dynamic": True, "urls": [ {"url": "https://github.com/graalvm/graalpython.git", "kind": "git"},