6

I am trying to encrypt a string as follows

public class AES256Cipher {
static byte[] ivBytes = new byte[]{0x49, 0x76, 0x61, 0x6e, 0x20, 0x4d, 0x65, 0x64, 0x76, 0x65, 0x64, 0x65, 0x76};
static String EncryptionKey = "abc123";

public static byte[] encrypt(String plainText)
        throws java.io.UnsupportedEncodingException,
        NoSuchAlgorithmException,
        NoSuchPaddingException,
        InvalidKeyException,
        InvalidAlgorithmParameterException,
        IllegalBlockSizeException,
        BadPaddingException {
    byte[] keyBytes = EncryptionKey.getBytes("UTF-8");

    AlgorithmParameterSpec ivSpec = new IvParameterSpec(ivBytes);
    SecretKeySpec newKey = new SecretKeySpec(keyBytes, "AES");
    Cipher cipher = null;
    cipher = Cipher.getInstance("AES/CBC/PKCS5Padding");
    cipher.init(Cipher.ENCRYPT_MODE, newKey, ivSpec);
    byte[] cipherData = cipher.doFinal(plainText.getBytes("UTF-8"));
    Log.e("cipher", Base64.encodeToString(cipherData, Base64.DEFAULT));
    return cipher.doFinal(plainText.getBytes("UTF-8"));
}
}

I am getting this exception

java.security.InvalidKeyException: Unsupported key size: 6 bytes
at com.android.org.conscrypt.OpenSSLCipher$EVP_CIPHER$AES.checkSupportedKeySize(OpenSSLCipher.java:686)
at com.android.org.conscrypt.OpenSSLCipher.checkAndSetEncodedKey(OpenSSLCipher.java:442)
at com.android.org.conscrypt.OpenSSLCipher.engineInit(OpenSSLCipher.java:272)
at javax.crypto.Cipher.tryTransformWithProvider(Cipher.java:608)
at javax.crypto.Cipher.tryCombinations(Cipher.java:532)
at javax.crypto.Cipher.getSpi(Cipher.java:437)
at javax.crypto.Cipher.init(Cipher.java:909)
at javax.crypto.Cipher.init(Cipher.java:859)
at com.vfirst.util.netwrok.AES256Cipher.encrypt(AES256Cipher.java:36)
at com.vfirst.LoginActivity.onCreate(LoginActivity.java:61)
at android.app.Activity.performCreate(Activity.java:6321)

String to encrypt

AES256Cipher.encrypt("12345");
WISHY
  • 11,067
  • 25
  • 105
  • 197

3 Answers3

22

AES only supports key sizes of 16, 24 or 32 bytes... So you have to change your EncryptionKey.

SecureRandom random = new SecureRandom();
byte[] EncryptionKey = new byte[16];
random.nextBytes(EncryptionKey);

You can use above code sample.

Alper Özaslan
  • 271
  • 2
  • 12
8

AES allows 128, 192 and 256 bit of key length. In other words 16, 24 or 32 byte.

Sunil Kanzar
  • 1,244
  • 1
  • 9
  • 21
4

If you want to use a password you should derive an AES key from your password instead of trying to use the password directly as a key.

The simplest way would be to hash the password using SHA-256 and use the hashed password as AES key.

The common way (preferred) is to use PBKDF2 e.g. with HMAC-SHA1 that generates an AES key (128/192 or 256 bit) from an password:

byte[] salt = new byte[8];
random.nextBytes(salt);
KeySpec spec = new PBEKeySpec(EncryptionKey.toCharArray(), salt, 65536, 128);
SecretKeyFactory f = SecretKeyFactory.getInstance("PBKDF2WithHmacSHA1");
byte[] keyBytes = f.generateSecret(spec).getEncoded();

Note that you have to store the random salt if you want to generate later the same key from the password.

JMax
  • 1,134
  • 1
  • 11
  • 20