Describe the Issue
Ristretto can infer a phi stamp whose inputs contain one AOT SubstrateType and one runtime-loaded RistrettoType. AbstractObjectStamp.meetTypes calls findLeastCommonAncestor across those two type universes. Because RistrettoType inherits SubstrateType.findLeastCommonAncestor, the mixed pair passes that method's outer SubstrateType cast, then fails when virtual dispatch reaches RistrettoType.isAssignableFrom, which requires its argument to already be a RistrettoType.
The runtime compilation is abandoned and the method remains interpreted. A minimal Maven project triggers this deterministically during Maven startup: 5 of 221–227 compilations failed in repeated runs (about 2%). Maven output remains correct and may still exit 0, but stderr reports a systemic compiler failure.
Using the latest version of GraalVM can resolve many issues.
GraalVM Version
java version "25.0.4.1" 2026-08-18 LTS
Oracle GraalVM 25.3.4.1-dev+0.1 (build 25.0.4.1+0-LTS-jvmci-25.3-b21)
Substrate VM Oracle GraalVM 25.3.4.1-dev+0.1 (serial gc, compressed references)
Also reproduced previously with Oracle GraalVM 25.2.4+7.1 on linux-amd64.
Operating System and Version
macOS 26.5 (Darwin 25.5.0), arm64. Also reproduced on Linux 6.6 / WSL2, amd64.
Troubleshooting Confirmation
Run Command
With a Crema/Ristretto image installed as JAVA_HOME:
JAVA_HOME=/path/to/runtime MAVEN_OPTS=-Djdk.graal.CompilationFailureAction=Print mvn clean
Expected Behavior
Runtime compilation should normalize type metadata into one universe before computing a least common ancestor, and the Sisu method should compile successfully.
Actual Behavior
Compilation of org.eclipse.sisu.inject.InjectorBindings.isAssignableFrom(TypeLiteral, Binding) throws ClassCastException; the compilation is discarded and repeated attempts trip SystemicCompilationFailureRate.
Steps to Reproduce
Create this pom.xml in an empty directory:
<project xmlns="http://maven.apache.org/POM/4.0.0">
<modelVersion>4.0.0</modelVersion>
<groupId>demo</groupId>
<artifactId>demo</artifactId>
<version>1.0</version>
</project>
Then run Maven 3.9.x with a -H:+RuntimeClassLoading -H:+GraalJITCompileAtRuntime native-image runtime as JAVA_HOME:
mkdir -p target/classes
touch target/classes/marker
JAVA_HOME=/path/to/runtime \
MAVEN_OPTS=-Djdk.graal.CompilationFailureAction=Print \
mvn clean
The failure occurs during Maven/Sisu startup. The pom.xml has no dependencies and the build goal itself is not material.
Additional Context
Current master makes the incompatible assumptions visible:
// SubstrateType.java:302-318
public ResolvedJavaType findLeastCommonAncestor(ResolvedJavaType otherType) {
...
SubstrateType t1 = this; // RistrettoType
SubstrateType t2 = (SubstrateType) otherType; // plain SubstrateType; succeeds
while (true) {
if (t1.isAssignableFrom(t2)) { // virtual dispatch
// RistrettoType.java:117-122
public boolean isAssignableFrom(ResolvedJavaType other) {
assert other instanceof RistrettoType : Assertions.errorMessage("Must already be wrapped", this, other);
RistrettoType rTypeOther = (RistrettoType) other; // ClassCastException
return this.interpreterType.isAssignableFrom(rTypeOther.interpreterType);
}
With assertions enabled, the same path should fail earlier with the clearer Must already be wrapped assertion. In a product image it reaches the cast.
Possible normalization points include RistrettoType.isAssignableFrom, SubstrateType.findLeastCommonAncestor, or the stamp producer that permits an AOT/runtime mixed phi. I am not asserting which layer should own the fix, only that findLeastCommonAncestor currently dispatches a plain SubstrateType into an override whose stated invariant forbids it.
Run-Time Log Output and Error Messages
Compilation of org.eclipse.sisu.inject.InjectorBindings.isAssignableFrom(TypeLiteral, Binding) failed:
java.lang.ClassCastException: com.oracle.svm.graal.meta.SubstrateType cannot be cast to
com.oracle.svm.interpreter.ristretto.meta.RistrettoType
at org.graalvm.nativeimage.builder/com.oracle.svm.interpreter.ristretto.meta.RistrettoType.isAssignableFrom(RistrettoType.java:120)
at org.graalvm.nativeimage.builder/com.oracle.svm.graal.meta.SubstrateType.findLeastCommonAncestor(SubstrateType.java:310)
at jdk.graal.compiler/jdk.graal.compiler.core.common.type.AbstractObjectStamp.meetTypes(AbstractObjectStamp.java:316)
at jdk.graal.compiler/jdk.graal.compiler.core.common.type.AbstractObjectStamp.meet(AbstractObjectStamp.java:181)
at jdk.graal.compiler/jdk.graal.compiler.nodes.type.StampTool.meetOrNull(StampTool.java:69)
at jdk.graal.compiler/jdk.graal.compiler.nodes.ValuePhiNode.inferStamp(ValuePhiNode.java:92)
at jdk.graal.compiler/jdk.graal.compiler.phases.common.CanonicalizerPhase.tryInferStamp(CanonicalizerPhase.java:888)
...
at org.graalvm.nativeimage.builder/com.oracle.svm.interpreter.ristretto.RistrettoUtils.compileAndInstallForPublication(RistrettoUtils.java:365)
Describe the Issue
Ristretto can infer a phi stamp whose inputs contain one AOT
SubstrateTypeand one runtime-loadedRistrettoType.AbstractObjectStamp.meetTypescallsfindLeastCommonAncestoracross those two type universes. BecauseRistrettoTypeinheritsSubstrateType.findLeastCommonAncestor, the mixed pair passes that method's outerSubstrateTypecast, then fails when virtual dispatch reachesRistrettoType.isAssignableFrom, which requires its argument to already be aRistrettoType.The runtime compilation is abandoned and the method remains interpreted. A minimal Maven project triggers this deterministically during Maven startup: 5 of 221–227 compilations failed in repeated runs (about 2%). Maven output remains correct and may still exit 0, but stderr reports a systemic compiler failure.
Using the latest version of GraalVM can resolve many issues.
8f1ea8c43038.GraalVM Version
Also reproduced previously with Oracle GraalVM
25.2.4+7.1on linux-amd64.Operating System and Version
macOS 26.5 (Darwin 25.5.0), arm64. Also reproduced on Linux 6.6 / WSL2, amd64.
Troubleshooting Confirmation
Run Command
With a Crema/Ristretto image installed as
JAVA_HOME:Expected Behavior
Runtime compilation should normalize type metadata into one universe before computing a least common ancestor, and the Sisu method should compile successfully.
Actual Behavior
Compilation of
org.eclipse.sisu.inject.InjectorBindings.isAssignableFrom(TypeLiteral, Binding)throwsClassCastException; the compilation is discarded and repeated attempts tripSystemicCompilationFailureRate.Steps to Reproduce
Create this
pom.xmlin an empty directory:Then run Maven 3.9.x with a
-H:+RuntimeClassLoading -H:+GraalJITCompileAtRuntimenative-image runtime asJAVA_HOME:The failure occurs during Maven/Sisu startup. The
pom.xmlhas no dependencies and the build goal itself is not material.Additional Context
Current master makes the incompatible assumptions visible:
With assertions enabled, the same path should fail earlier with the clearer
Must already be wrappedassertion. In a product image it reaches the cast.Possible normalization points include
RistrettoType.isAssignableFrom,SubstrateType.findLeastCommonAncestor, or the stamp producer that permits an AOT/runtime mixed phi. I am not asserting which layer should own the fix, only thatfindLeastCommonAncestorcurrently dispatches a plainSubstrateTypeinto an override whose stated invariant forbids it.Run-Time Log Output and Error Messages