Stan
Stan

Reputation: 155

Java, error when decoding AES-256

I receive an error while decrypting: (javax.crypto.BadPaddingException: error:06065064:digital envelope routines:EVP_DecryptFinal_ex:bad decrypt)

My code encryption / decryption:

private static byte[] password = null; //  this.password = editText.getBytes();
static final byte[] ivBytes = {'6','g','6','o','d','a','0','u','4','n','w','i','6','9','i','j'};

public static byte[] encrypt(String text) throws Exception {
    byte[] clear = text.getBytes("UTF-8");
    IvParameterSpec ivSpec = new IvParameterSpec(ivBytes);

    KeyGenerator kgen = KeyGenerator.getInstance("AES");
    SecureRandom sr = SecureRandom.getInstance("SHA1PRNG");
    sr.setSeed(password);
    kgen.init(256, sr); // 192 and 256 bits may not be available
    SecretKey skey = kgen.generateKey();
    byte[] key = skey.getEncoded();

    SecretKeySpec skeySpec = new SecretKeySpec(key, "AES");
    Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
    cipher.init(Cipher.ENCRYPT_MODE, skeySpec, ivSpec);
    byte[] encrypted = cipher.doFinal(clear);
    return encrypted;
}

public static String decrypt(byte[] encrypted) throws Exception {
    IvParameterSpec ivSpec = new IvParameterSpec(ivBytes);

    KeyGenerator kgen = KeyGenerator.getInstance("AES");
    SecureRandom sr = SecureRandom.getInstance("SHA1PRNG");
    sr.setSeed(password);
    kgen.init(256, sr); // 192 and 256 bits may not be available
    SecretKey skey = kgen.generateKey();
    byte[] key = skey.getEncoded();

    SecretKeySpec skeySpec = new SecretKeySpec(key, "AES");
    Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
    cipher.init(Cipher.DECRYPT_MODE, skeySpec, ivSpec);
    String decrypted = new String(cipher.doFinal(encrypted));
    return decrypted;
}

I suspect that the bug generateKey.

Upvotes: 3

Views: 5997

Answers (3)

imnitesh
imnitesh

Reputation: 83

Replace the below line:

Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");

with below line:

Cipher cipher = Cipher.getInstance("AES/CBC/PKCS5Padding","BC");

Upvotes: -1

user3392484
user3392484

Reputation: 1919

You're doing two things wrong:

  • Generating a key from a password by using the key to seed a PRNG is a bad idea. Use password-based-encryption instead. Java has an implementation of PKCS#5 that will generate a key from a password.

  • You need to use a new strong-random IV for each encryption:

    • When you encrypt, don't specify an IV in cipher.init(). A new one will be generated for you.
    • encrypt() needs to serialise both the IV (cipher.getIV()) and the ciphertext into a byte array.
    • decrypt(): separate the IV from the ciphertext, build an IvParameterSpec from it and feed into cipher.init() as you currently do.

Upvotes: 2

sergej shafarenka
sergej shafarenka

Reputation: 20426

Your issues is that when you decrypt, you generate a new secret key instead of deriving it from password. Check out this blog post to see how password-based encryption has to be implemented. There are examples of encryption and decryption functions.

Upvotes: 0

Related Questions