oracle/graal · error · IllegalArgumentException
For instance methods, the receiver argument must not represe
Error message
For instance methods, the receiver argument must not represent a null constant
What it means
Thrown by HostVMAccess.invoke when an instance method is invoked with a JavaConstant that itself represents null (JavaConstant.isNull()). The API distinguishes 'no receiver reference' (null) from 'receiver is the null constant' — for instance calls the latter is meaningless because reflection cannot dispatch invoke on a null object.
Source
Thrown at compiler/src/jdk.graal.compiler.hostvmaccess/src/jdk/graal/compiler/hostvmaccess/HostVMAccess.java:147
public boolean owns(ResolvedJavaField value) {
return value.getClass().getModule() == hostImplModule;
}
@Override
public JavaConstant invoke(ResolvedJavaMethod method, JavaConstant receiver, JavaConstant... arguments) {
SnippetReflectionProvider snippetReflection = providers.getSnippetReflection();
Executable executable = snippetReflection.originalMethod(method);
makeAccessible(executable);
boolean isConstructor = executable instanceof Constructor;
Class<?>[] parameterTypes = executable.getParameterTypes();
if (Modifier.isStatic(executable.getModifiers()) || isConstructor) {
if (receiver != null) {
throw new IllegalArgumentException("For static methods or constructor, the receiver argument must be null");
}
} else if (receiver == null) {
throw new NullPointerException("For instance methods, the receiver argument must not be null");
} else if (receiver.isNull()) {
throw new IllegalArgumentException("For instance methods, the receiver argument must not represent a null constant");
}
if (parameterTypes.length != arguments.length) {
throw new IllegalArgumentException("Wrong number of arguments: expected " + parameterTypes.length + " but got " + arguments.length);
}
Signature signature = method.getSignature();
Object[] unboxedArguments = new Object[parameterTypes.length];
for (int i = 0; i < unboxedArguments.length; i++) {
JavaKind parameterKind = signature.getParameterKind(i);
JavaConstant argument = arguments[i];
if (parameterKind.isObject()) {
if (argument.isNull()) {
unboxedArguments[i] = null;
} else {
unboxedArguments[i] = snippetReflection.asObject(parameterTypes[i], argument);
if (unboxedArguments[i] == null) {
throw new IllegalArgumentException(
"Illegal argument type: arguments[" + i + "] of type " + providers.getMetaAccess().lookupJavaType(arguments[i]).toClassName() +
" could not be converted to a " + parameterTypes[i]);View on GitHub (pinned to a66e9ccd1d)
Solutions
- Guard before invoking: if receiver != null && receiver.isNull(), either skip the call, substitute a real object, or let the caller's NPE semantics apply at the guest level
- Use forObject only for non-null objects and pass null only when the method is static/constructor
- If the guest program legitimately calls an instance method on null, raise/propagate the guest NullPointerException instead of invoking the host
Example fix
// before
hostVM.invoke(instanceMethod, snippetReflection.forObject(maybeNull), args); // null constant -> throws
// after
JavaConstant receiver = maybeNull == null ? null : snippetReflection.forObject(maybeNull);
if (receiver != null && receiver.isNull()) {
throw new NullPointerException("receiver is null"); // explicit guest semantics
}
hostVM.invoke(instanceMethod, receiver, args); Defensive patterns
Strategy: type-guard
Validate before calling
if (receiver != null && receiver.isNull()) { /* null receiver constant: do not invoke */ } Type guard
static boolean isNullConstant(JavaConstant c) { return c == null || c.isNull(); } Try / catch
catch (IllegalArgumentException e) { convert to guest NullPointerException if the guest called a method on null } Prevention
- forObject(null) yields the null constant — never forward its result as a receiver
- Distinguish 'no receiver' (null ref) from 'null receiver' (null constant) in call sites
- Fold explicit null checks before building invoke arguments
When it happens
Trigger: Calling invoke(instanceMethod, JavaConstant.NULL_POINTER, args...) or any receiver constant whose isNull() is true, for a non-static executable.
Common situations: Uniform code that wraps possibly-null objects with snippetReflection.forObject(x) — forObject(null) yields the null constant, which is then forwarded as receiver; unfolding a snippet where the receiver was a null-folded constant.
Related errors
- For instance methods, the receiver argument must not be null
- For instance fields, the receiver argument must not be null
- For instance fields, the receiver argument must not represen
- For static methods or constructor, the receiver argument mus
- Wrong number of arguments: expected {} but got {}
AI-assisted analysis of oracle/graal@a66e9ccd1d (2026-08-14).
Data as JSON: /api/errors/11a8b604443a1144.
Report an issue: GitHub.