{"record":{"id":"b4091f63250b27a2","repo":"spring-projects/spring-security","slug":"ivgenerator-key-length-block-size-16","errorCode":null,"errorMessage":"ivGenerator key length != block size 16","messagePattern":"ivGenerator key length != block size 16","errorType":"exception","errorClass":"IllegalArgumentException","httpStatus":null,"severity":"error","filePath":"crypto/src/main/java/org/springframework/security/crypto/encrypt/BouncyCastleAesBytesEncryptor.java","lineNumber":45,"sourceCode":"/**\n * Base class for AES-256 encryption using Bouncy Castle.\n *\n * @author William Tran\n *\n */\nabstract class BouncyCastleAesBytesEncryptor implements BytesEncryptor {\n\n\tfinal KeyParameter secretKey;\n\n\tfinal BytesKeyGenerator ivGenerator;\n\n\tBouncyCastleAesBytesEncryptor(String password, CharSequence salt) {\n\t\tthis(password, salt, KeyGenerators.secureRandom(16));\n\t}\n\n\tBouncyCastleAesBytesEncryptor(String password, CharSequence salt, BytesKeyGenerator ivGenerator) {\n\t\tif (ivGenerator.getKeyLength() != 16) {\n\t\t\tthrow new IllegalArgumentException(\"ivGenerator key length != block size 16\");\n\t\t}\n\t\tthis.ivGenerator = ivGenerator;\n\t\tPBEParametersGenerator keyGenerator = new PKCS5S2ParametersGenerator();\n\t\tbyte[] pkcs12PasswordBytes = PBEParametersGenerator.PKCS5PasswordToUTF8Bytes(password.toCharArray());\n\t\tkeyGenerator.init(pkcs12PasswordBytes, Hex.decode(salt), 1024);\n\t\tthis.secretKey = (KeyParameter) keyGenerator.generateDerivedParameters(256);\n\t}\n\n}\n","sourceCodeStart":27,"sourceCodeEnd":55,"githubUrl":"https://github.com/spring-projects/spring-security/blob/96852e8860138a482cb13d1479573f24ff6443c6/crypto/src/main/java/org/springframework/security/crypto/encrypt/BouncyCastleAesBytesEncryptor.java#L27-L55","documentation":"BouncyCastleAesBytesEncryptor uses a per-message IV equal in length to the AES block size (16 bytes). The constructor validates that the supplied ivGenerator produces exactly 16-byte keys and throws IllegalArgumentException otherwise, since any other IV length breaks CBC/GCM block processing.","triggerScenarios":"new BouncyCastleAesBytesEncryptor(password, salt, ivGenerator) where ivGenerator.getKeyLength() != 16, e.g. KeyGenerators.secureRandom(8), a 32-byte generator, or a custom generator with shared(16)-style fixed but wrong-length keys.","commonSituations":"Reusing an IV generator configured for a different cipher (e.g. 8-byte for DES); misreading 'key length' docs and passing a generator sized for the AES key (32) rather than the block; refactors that share one generator constant across encryptors.","solutions":["Pass KeyGenerators.secureRandom(16) as the ivGenerator.","Verify the generator's getKeyLength() equals 16 before constructing.","Use the two-arg constructor BouncyCastleAesBytesEncryptor(password, salt), which defaults to a correct 16-byte secure random generator."],"exampleFix":"// before\nBytesKeyGenerator ivGen = KeyGenerators.secureRandom(32);\nBytesEncryptor e = new BouncyCastleAesBytesEncryptor(password, salt, ivGen); // throws\n// after\nBytesEncryptor e = new BouncyCastleAesBytesEncryptor(password, salt, KeyGenerators.secureRandom(16));","handlingStrategy":"validation","validationCode":"if (ivGenerator.getKeyLength() != 16) throw new IllegalStateException(\"ivGenerator must produce 16-byte IVs\");","typeGuard":null,"tryCatchPattern":"try { encryptor = new BouncyCastleAesBytesEncryptor(password, salt, ivGen); } catch (IllegalArgumentException e) { encryptor = new BouncyCastleAesBytesEncryptor(password, salt); }","preventionTips":["Always construct IV generators with KeyGenerators.secureRandom(16).","Never reuse a generator instance configured for a different block size across encryptors.","Use the two-argument constructor unless you have a specific reason to supply your own IV generator."],"tags":["encryption","aes","spring-security","invalid-constructor-argument"],"backgroundTag":"invalid-constructor-argument","analyzedSha":"96852e8860138a482cb13d1479573f24ff6443c6","analyzedAt":"2026-09-10T23:25:23.477Z","contentChangedAt":"2026-09-10T23:25:23.477Z","schemaVersion":2},"datasetVersion":"2026-09-14T16:17:12.679Z"}