oracle/graal · error · IllegalArgumentException

unknown primitive or void type character:

Error message

unknown primitive or void type character: 

What it means

Thrown by APHotSpotSignature while resolving a single type-signature character to a javax.lang.model TypeKind during annotation processing. The signature grammar only accepts the JVM primitive/void characters 'Z','C','F','D','B','S','I','J','V' at this position; any other character means the signature string being parsed is not a valid JVM method/type descriptor. This class is used by the Graal annotation processor to parse @MethodSubstitution/@NodeIntrinsic style signatures, so the exception indicates a malformed signature literal in processor input.

Source

Thrown at compiler/src/jdk.graal.compiler.processor/src/jdk/graal/compiler/replacements/processor/APHotSpotSignature.java:181

                return TypeKind.BOOLEAN;
            case 'C':
                return TypeKind.CHAR;
            case 'F':
                return TypeKind.FLOAT;
            case 'D':
                return TypeKind.DOUBLE;
            case 'B':
                return TypeKind.BYTE;
            case 'S':
                return TypeKind.SHORT;
            case 'I':
                return TypeKind.INT;
            case 'J':
                return TypeKind.LONG;
            case 'V':
                return TypeKind.VOID;
        }
        throw new IllegalArgumentException("unknown primitive or void type character: " + ch);
    }

    public TypeMirror getReturnType(ProcessingEnvironment env) {
        if (returnTypeCache == null) {
            if (returnType == null) {
                throw new RuntimeException("Invalid return type.");
            }
            returnTypeCache = lookupType(env, returnType);
        }
        return returnTypeCache;
    }

    @Override
    public String toString() {
        return "Signature<" + originalString + ">";
    }
}

View on GitHub (pinned to a66e9ccd1d)

Solutions

  1. Correct the signature string to be a valid JVM descriptor: parentheses-wrapped parameter descriptors followed by exactly one return descriptor (e.g. "(ILjava/lang/String;)J").
  2. Use fully qualified slash-separated names for reference types ('Ljava/lang/Object;') and '[' prefixes for arrays; do not use '.', '<', or source-type names.
  3. If the signature is derived, print the string being parsed at the construction site and compare it against javap output for the target method.
  4. Add a unit test that constructs APHotSpotSignature for every substitution signature to catch typos at build time.

Example fix

// before
@MethodSubstitution(value = "append", signature = "(ljava/lang/String;)i")
// after
@MethodSubstitution(value = "append", signature = "(Ljava/lang/String;)I")
Defensive patterns

Strategy: validation

Validate before calling

private static final String PRIM = "ZCFDBSIJV";
static boolean isValidPrimitiveChar(char ch) { return PRIM.indexOf(ch) >= 0; }
// validate whole descriptor before parsing:
static boolean isValidDescriptor(String sig) {
    return sig.matches("\\((\\[*(Z|C|F|D|B|S|I|J|L[^;]+;))*\\)(\\[*(Z|C|F|D|B|S|I|J|V|L[^;]+;))");
}

Try / catch

try { sig.lookupType(env); } catch (IllegalArgumentException e) { messager.printMessage(Diagnostic.Kind.ERROR, "bad signature '" + sig + "': " + e.getMessage(), element); }

Prevention

When it happens

Trigger: A method signature string like "(Ljava/lang/Object;)X" or "hello" is handed to the APHotSpotSignature constructor; lookupType later calls the primitive-switch and falls through on 'X', 'L' at the wrong position, '[' , lowercase letters, or any non-descriptor character. Only the eight primitive chars plus 'V' reach this switch, so any Object/array return in a spot expecting a primitive char, or a typo in a signature annotation attribute, triggers it.

Common situations: Hand-writing a signature in a replacements annotation (e.g. @MethodSubstitution(isStatic = ..., signature = ...)), typo'ing the return descriptor ("I" vs "i", "V" vs "void"), or pasting a partial descriptor that omits the leading '(' or the return character. Also occurs after refactoring a substituted method's signature without updating the annotation string.

Related errors


AI-assisted analysis of oracle/graal@a66e9ccd1d (2026-08-14). Data as JSON: /api/errors/3f6c5416994e9c41. Report an issue: GitHub.