{"record":{"id":"ac3d3dce6f20a2bd","repo":"oracle/graal","slug":"malformed-method-variant-name-s","errorCode":null,"errorMessage":"Malformed method variant name: %s","messagePattern":"Malformed method variant name: (.+?)","errorType":"exception","errorClass":"IllegalArgumentException","httpStatus":null,"severity":"error","filePath":"compiler/src/org.graalvm.profdiff/src/org/graalvm/profdiff/core/Method.java","lineNumber":259,"sourceCode":"     *\n     * For example, if the argument is {@code java.util.HashMap.size%%key()}, this method returns\n     * {@code java.util.HashMap.size()} and {@code key}.\n     *\n     * If the provided method name does not contain a method variant key, {@code null} is returned\n     * in place of the method variant key.\n     *\n     * @param methodVariantName a method variant name\n     * @return the method name and method variant key\n     */\n    public static Pair<String, String> splitMethodVariantName(String methodVariantName) {\n        int separatorBegin = methodVariantName.indexOf(StableMethodNameFormatter.METHOD_VARIANT_KEY_SEPARATOR);\n        if (separatorBegin == -1) {\n            return Pair.create(methodVariantName, null);\n        }\n        int keyBegin = separatorBegin + StableMethodNameFormatter.METHOD_VARIANT_KEY_SEPARATOR.length();\n        int keyEnd = methodVariantName.lastIndexOf('(');\n        if (keyEnd == -1 || keyBegin > keyEnd) {\n            throw new IllegalArgumentException(\"Malformed method variant name: \" + methodVariantName);\n        }\n        String methodName = methodVariantName.substring(0, separatorBegin) + methodVariantName.substring(keyEnd);\n        String methodVariantKey = methodVariantName.substring(keyBegin, keyEnd);\n        return Pair.create(methodName, methodVariantKey);\n    }\n\n    /**\n     * Returns a method name (removing the method variant key) from the given method variant name.\n     *\n     * @param methodVariantName name of a method variant (optionally containing a method variant\n     *            key)\n     * @return method name corresponding to the given method variant\n     */\n    public static String removeMethodVariantKey(String methodVariantName) {\n        return splitMethodVariantName(methodVariantName).getLeft();\n    }\n}\n","sourceCodeStart":241,"sourceCodeEnd":277,"githubUrl":"https://github.com/oracle/graal/blob/a66e9ccd1d7bf2552883939aa0788dfd0e294aab/compiler/src/org.graalvm.profdiff/src/org/graalvm/profdiff/core/Method.java#L241-L277","documentation":"Method.splitMethodVariantName throws IllegalArgumentException when a name contains the '%%' separator but the substring between the separator and the last '(' is empty or the name has no '(' at all — i.e. the 'method%%key(signature)' shape cannot be reconstructed. keyEnd = lastIndexOf('('); if it is missing or precedes keyBegin, the name is malformed.","triggerScenarios":"Calling splitMethodVariantName(\"foo%%\") (separator but no '('), splitMethodVariantName(\"foo%%(\") (empty key, keyBegin > keyEnd when key sits after the last paren position is impossible), or hand-mangled names where the only '(' appears before the '%%'.","commonSituations":"Post-processing or user edits of optimization-log method names that drop the signature; regex-based munging that strips parentheses; logs from tools that emit names not following the stable formatter's shape.","solutions":["Ensure names keep the canonical 'holder%%key(signature)' form before splitting.","Pre-check with a validation regex or contains('(') before calling splitMethodVariantName.","For names without '%%' the method already returns (name, null) — only pass variant-carrying names that also have a signature."],"exampleFix":"// before\nPair<String,String> p = Method.splitMethodVariantName(\"java.util.Foo%%noSig\");\n// after\nPair<String,String> p = Method.splitMethodVariantName(\"java.util.Foo%%v0(int)\");","handlingStrategy":"validation","validationCode":"static boolean isWellFormedVariantName(String n) {\n    int sep = n.indexOf(\"%%\");\n    if (sep == -1) return true;\n    int paren = n.lastIndexOf('(');\n    return paren != -1 && sep + 2 <= paren;\n}","typeGuard":"static boolean isWellFormedVariantName(String n) {\n    int sep = n.indexOf(\"%%\");\n    if (sep == -1) return true;\n    int paren = n.lastIndexOf('(');\n    return paren != -1 && sep + 2 <= paren;\n}","tryCatchPattern":"try {\n    Method.splitMethodVariantName(name);\n} catch (IllegalArgumentException e) {\n    // message contains the malformed name; log it and skip the entry\n}","preventionTips":["Do not strip parentheses when post-processing method names.","Keep the 'holder%%key(signature)' shape intact."],"tags":["profdiff","method-names","validation","api-contract"],"backgroundTag":null,"analyzedSha":"a66e9ccd1d7bf2552883939aa0788dfd0e294aab","analyzedAt":"2026-08-14T13:58:47.161Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}