{"record":{"id":"ccc44ac38918d59a","repo":"skylot/jadx","slug":"consume-wrong-char-sign","errorCode":null,"errorMessage":"Consume wrong char: '{}' != '{}', sign: {}","messagePattern":"Consume wrong char: '(.+?)' != '(.+?)', sign: (.+?)","errorType":"exception","errorClass":"JadxRuntimeException","httpStatus":null,"severity":"error","filePath":"jadx-core/src/main/java/jadx/core/dex/nodes/parser/SignatureParser.java","lineNumber":114,"sourceCode":"\n\tprivate boolean skipUntil(char untilChar) {\n\t\tint startPos = pos;\n\t\twhile (true) {\n\t\t\tif (lookAhead(untilChar)) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t\tchar ch = next();\n\t\t\tif (ch == STOP_CHAR) {\n\t\t\t\tpos = startPos;\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t}\n\n\tprivate void consume(char exp) {\n\t\tchar c = next();\n\t\tif (exp != c) {\n\t\t\tthrow new JadxRuntimeException(\"Consume wrong char: '\" + c + \"' != '\" + exp\n\t\t\t\t\t+ \"', sign: \" + debugString());\n\t\t}\n\t}\n\n\tprivate boolean tryConsume(char exp) {\n\t\tif (lookAhead(exp)) {\n\t\t\tnext();\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t@Nullable\n\tpublic String consumeUntil(char lastChar) {\n\t\tmark();\n\t\treturn skipUntil(lastChar) ? inclusiveSlice() : null;\n\t}\n","sourceCodeStart":96,"sourceCodeEnd":132,"githubUrl":"https://github.com/skylot/jadx/blob/e738a26571d02919f01df40de93bc9a44dee4e18/jadx-core/src/main/java/jadx/core/dex/nodes/parser/SignatureParser.java#L96-L132","documentation":"SignatureParser.consume(char) reads the next character and compares it to an expected delimiter. If they differ it throws with both the actual and expected char plus a debug string of the full signature. This signals a structurally invalid generic signature that does not match the expected JVM signature grammar (e.g. wrong placement of '<', '>', ':', ';').","triggerScenarios":"Parsing a Signature attribute that violates the JVM generic signature grammar — e.g. expecting ';' after a class type but finding '>', or expecting '<' at the start of a type parameter list but finding something else.","commonSituations":"Obfuscators that mangle generic signature strings, hand-crafted/invalid Signature attributes, or a DEX produced by a faulty toolchain. The debugString in the message shows the exact position and surrounding signature.","solutions":["Upgrade JADX.","Examine the full signature string in the error message (debugString) to locate the malformed segment.","Use --no-debug-info or skip signature parsing if a CLI option exists, to get partial output.","Report the signature and the class/member it belongs to upstream."],"exampleFix":null,"handlingStrategy":"try-catch","validationCode":"// Pre-validate a generic signature against a minimal grammar before handing to JADX.\nstatic boolean looksLikeValidSignature(String sig) {\n    if (sig == null || sig.isEmpty()) return false;\n    int depth = 0;\n    for (char c : sig.toCharArray()) {\n        if (c == '<') depth++;\n        else if (c == '>') { if (depth-- == 0) return false; }\n    }\n    return depth == 0;\n}","typeGuard":null,"tryCatchPattern":"try {\n    jadx.load();\n} catch (JadxRuntimeException e) {\n    if (e.getMessage().contains(\"Consume wrong char\")) {\n        log.warn(\"Malformed generic signature attribute; input may be obfuscated\", e);\n    } else throw e;\n}","preventionTips":["Inspect the full signature in the error message's debugString to find the malformed segment.","Use --no-debug-info or signature-skipping options if available for partial output.","Report obfuscation-mangled signatures upstream."],"tags":["signature","generics","malformed-input","obfuscation"],"backgroundTag":null,"analyzedSha":"e738a26571d02919f01df40de93bc9a44dee4e18","analyzedAt":"2026-08-14T00:10:24.238Z","schemaVersion":2},"datasetVersion":"2026-08-14T05:17:29.042Z"}