AES / GCM — Encryption & Decryption using Kotlin
What is the Advanced Encryption Standard or AES?
The Advanced Encryption Standard, or AES, is a symmetric block cipher chosen by the U.S. government to protect classified information and is implemented in software and hardware throughout the world to encrypt sensitive data.
How does AES encryption work?
AES comprises three block ciphers: AES-128, AES-192, and AES-256. Each cipher encrypts and decrypts data in blocks of 128 bits using cryptographic keys of 128-, 192- and 256-bits, respectively.
This is my another post after AES/ECB encryption & decryption
In my previous story, I shared AES encryption & decryption using ECB mode and now I will share AES encryption & decryption using GCM mode. Check this out for more information: link
ECB: Electronic Code Book (ECB) is a mode of operation for a block cipher, with the characteristic that each possible block of plaintext has a defined corresponding ciphertext value and vice versa. In other words, the same plaintext value will always result in the same ciphertext value.
GCM: AES with Galois/Counter Mode (GCM) is a mode of operation which provides both authenticated encryption (confidentiality and authentication) and the ability to check the integrity and authentication of additional authenticated data (AAD) that is sent in the clear.
Getting started
I have prepared this tutorial using Intellij IDEA and Kotlin programming language. To start with, you can create a new project using Kotlin or you can just create a Kotlin class in your current project.
Library Dependency
I have used BouncyCastle dependency for this project. You can find maven/gradle dependency e.g:
Maven: bouncycastle:bcprov-jdk16:136
Encryptor
fun encrypt(strToEncrypt: String, secret_key: String): String? {
Security.addProvider(BouncyCastleProvider())
val keyBytes: ByteArray
try {
keyBytes = secret_key.toByteArray(charset("UTF8"))
val secretkey = SecretKeySpec(keyBytes, "AES")
val input = strToEncrypt.toByteArray(charset("UTF8"))
synchronized(Cipher::class.java) {
val cipher = Cipher.getInstance("AES/GCM/NoPadding", "BC")
cipher.init(Cipher.ENCRYPT_MODE, secretkey)
val cipherText = ByteArray(cipher.getOutputSize(input.size))
var ctLength = cipher.update(
input, 0, input.size,
cipherText, 0
)
ctLength += cipher.doFinal(cipherText, ctLength)
return String(
Base64.encode(cipherText)
)
}
} catch (uee: UnsupportedEncodingException) {
uee.printStackTrace()
} catch (ibse: IllegalBlockSizeException) {
ibse.printStackTrace()
} catch (bpe: BadPaddingException) {
bpe.printStackTrace()
} catch (ike: InvalidKeyException) {
ike.printStackTrace()
} catch (nspe: NoSuchPaddingException) {
nspe.printStackTrace()
} catch (nsae: NoSuchAlgorithmException) {
nsae.printStackTrace()
} catch (e: ShortBufferException) {
e.printStackTrace()
}
return null
}
Decryptor
fun decryptWithAES(key: String, strToDecrypt: String?): String? {
Security.addProvider(BouncyCastleProvider())
val keyBytes: ByteArray
try {
keyBytes = key.toByteArray(charset("UTF8"))
val secretkey = SecretKeySpec(keyBytes, "AES")
val input = org.bouncycastle.util.encoders.Base64
.decode(strToDecrypt?.trim { it <= ' ' }?.toByteArray(charset("UTF8")))
synchronized(Cipher::class.java) {
val cipher = Cipher.getInstance("AES/GCM/NoPadding", "BC")
cipher.init(Cipher.DECRYPT_MODE, secretkey)
val plainText = ByteArray(cipher.getOutputSize(input.size))
var ptLength = cipher.update(input, 0, input.size, plainText, 0)
ptLength += cipher.doFinal(plainText, ptLength)
val decryptedString = String(plainText)
return decryptedString.trim { it <= ' ' }
}
} catch (uee: UnsupportedEncodingException) {
uee.printStackTrace()
} catch (ibse: IllegalBlockSizeException) {
ibse.printStackTrace()
} catch (bpe: BadPaddingException) {
bpe.printStackTrace()
} catch (ike: InvalidKeyException) {
ike.printStackTrace()
} catch (nspe: NoSuchPaddingException) {
nspe.printStackTrace()
} catch (nsae: NoSuchAlgorithmException) {
nsae.printStackTrace()
} catch (e: ShortBufferException) {
e.printStackTrace()
}
return null
}
Secret Key example
val secretKey: String = “662ede816988e58fb6d057d9d85605e0”
Enjoy and hit clap 👏 few times.. and below is my Github project sample.