{"record":{"id":"f989733b63ab0a84","repo":"elastic/elasticsearch","slug":"string-is-not-hexadecimal","errorCode":null,"errorMessage":"String [{}] is not hexadecimal","messagePattern":"String \\[(.+?)\\] is not hexadecimal","errorType":"exception","errorClass":"IllegalStateException","httpStatus":null,"severity":"error","filePath":"libs/ssl-config/src/main/java/org/elasticsearch/common/ssl/PemUtils.java","lineNumber":580,"sourceCode":"            }\n            md5.update(tempDigest, 0, 16); // use previous round digest as IV\n        }\n        Arrays.fill(passwordBytes, (byte) 0);\n        return key;\n    }\n\n    /**\n     * Converts a hexadecimal string to a byte array\n     */\n    private static byte[] hexStringToByteArray(String hexString) {\n        int len = hexString.length();\n        if (len % 2 == 0) {\n            byte[] data = new byte[len / 2];\n            for (int i = 0; i < len; i += 2) {\n                final int k = Character.digit(hexString.charAt(i), 16);\n                final int l = Character.digit(hexString.charAt(i + 1), 16);\n                if (k == -1 || l == -1) {\n                    throw new IllegalStateException(\"String [\" + hexString + \"] is not hexadecimal\");\n                }\n                data[i / 2] = (byte) ((k << 4) + l);\n            }\n            return data;\n        } else {\n            throw new IllegalStateException(\n                \"Hexadecimal string [\" + hexString + \"] has odd length and cannot be converted to a byte array\"\n            );\n        }\n    }\n\n    /**\n     * Parses a DER encoded EC key to an {@link ECPrivateKeySpec} using a minimal {@link DerParser}\n     *\n     * @param keyBytes the private key raw bytes\n     * @return {@link ECPrivateKeySpec}\n     * @throws IOException if the DER encoded key can't be parsed\n     */","sourceCodeStart":562,"sourceCodeEnd":598,"githubUrl":"https://github.com/elastic/elasticsearch/blob/db6a809a667c081ca1dc7500389d26975573215f/libs/ssl-config/src/main/java/org/elasticsearch/common/ssl/PemUtils.java#L562-L598","documentation":"Thrown by hexStringToByteArray when at least one character in an even-length input string is not a valid hexadecimal digit (Character.digit returns -1). This is an IllegalStateException (unchecked) and currently surfaces from the IV-parsing path inside getCipherFromParameters, where it is wrapped into the 'DEK-Info IV is invalid' IOException. The message echoes the offending string verbatim.","triggerScenarios":"Passing a DEK-Info IV (or any hex string) that contains non-hex characters such as 'O' instead of '0', 'l' instead of '1', whitespace, or punctuation; a corrupted or hand-edited IV.","commonSituations":"Manual editing of PEM headers; OCR or copy-paste that substituted look-alike characters; a templating system that mangled the hex; locale-specific digit substitutions.","solutions":["Inspect the hex string and replace any non-hex characters (only 0-9 and A-F/a-f are valid).","Regenerate the encrypted key so the IV is fresh and valid: 'openssl rsa -aes256 -in plain.key -out enc.key'.","Add a pre-validation step in your code that rejects non-hex strings before calling the API (see defense section)."],"exampleFix":null,"handlingStrategy":"validation","validationCode":"// Validate a hex string with explicit error reporting\nstatic byte[] requireHex(String s) {\n    if (s.length() % 2 != 0) throw new IllegalArgumentException(\"odd length\");\n    for (int i = 0; i < s.length(); i++) {\n        if (Character.digit(s.charAt(i), 16) == -1) {\n            throw new IllegalArgumentException(\"non-hex char at index \" + i + \" in \" + s);\n        }\n    }\n    return java.util.HexFormat.of().parseHex(s);\n}","typeGuard":null,"tryCatchPattern":"try { PemUtils.readPrivateKey(path, passwordSupplier); }\ncatch (RuntimeException e) { if (e.getMessage().contains(\"is not hexadecimal\")) { /* regenerate key */ } else throw e; }","preventionTips":["Never hand-edit hex IVs.","Regenerate encrypted keys so the IV is fresh and valid.","Pre-validate hex strings before passing them into low-level parsers."],"tags":["ssl","pem","hex","iv","validation"],"backgroundTag":null,"analyzedSha":"db6a809a667c081ca1dc7500389d26975573215f","analyzedAt":"2026-08-12T01:39:14.192Z","schemaVersion":2},"datasetVersion":"2026-08-13T09:17:06.757Z"}