Issue
I've created this two extensions in Kotlin to Encrypt/Decrypt strings:
fun String.encrypt(seed : String): String {
val keyGenerator = KeyGenerator.getInstance("AES")
val secureRandom = SecureRandom.getInstance("SHA1PRNG")
secureRandom.setSeed(seed.toByteArray())
keyGenerator.init(128, secureRandom)
val skey = keyGenerator.generateKey()
val rawKey : ByteArray = skey.encoded
val skeySpec = SecretKeySpec(rawKey, "AES")
val cipher = Cipher.getInstance("AES/CBC/PKCS5Padding")
cipher.init(Cipher.ENCRYPT_MODE, skeySpec)
val byteArray = cipher.doFinal(this.toByteArray())
return byteArray.toString()
}
fun String.decrypt(seed : String): String {
val keyGenerator = KeyGenerator.getInstance("AES")
val secureRandom = SecureRandom.getInstance("SHA1PRNG")
secureRandom.setSeed(seed.toByteArray())
keyGenerator.init(128, secureRandom)
val skey = keyGenerator.generateKey()
val rawKey : ByteArray = skey.encoded
val skeySpec = SecretKeySpec(rawKey, "AES")
val cipher = Cipher.getInstance("AES/CBC/PKCS5Padding")
cipher.init(Cipher.DECRYPT_MODE, skeySpec)
val byteArray = cipher.doFinal(this.toByteArray())
return byteArray.toString()
}
for some reason I'm getting the following exception:
javax.crypto.IllegalBlockSizeException: last block incomplete in decryption
What I'm doing wrong?
Solution
To encode your ciphertext use base 64 or hexadecimals. The Java API contains a Base64 class, so you're probably best off using that.
byte[]#toString
doesn't do what you expect it to do; it simply returns a representation of the byte array reference, not the contents of the byte array.
Besides that:
- don't use SecureRandom to derive a key, try and lookup PBKDF2;
- explicitly use a mode of operation such as
"AES/GCM/NoPadding"
; - use a unique IV, and a random IV if you decide to use CBC (usually insecure);
- don't use
toByteArray
without explicitly selecting a character encoding for the message.
Answered By - Maarten Bodewes
0 comments:
Post a Comment
Note: Only a member of this blog may post a comment.