commit b308d9f801c8c54c84edd0c0a18e0303fedd494d
parent 100f4ff91b5a5b31a84b3999365c3058df6251ea
Author: Brad Conte <brad@bradconte.com>
Date: Sun, 26 Apr 2015 20:14:41 -0700
Add an AES CBC decryption function for completeness.
Diffstat:
| M | aes.c | | | 37 | ++++++++++++++++++++++++++++++------- |
| M | aes_test.c | | | 11 | ++++++++++- |
2 files changed, 40 insertions(+), 8 deletions(-)
diff --git a/aes.c b/aes.c
@@ -233,7 +233,7 @@ void xor_buf(const BYTE in[], BYTE out[], size_t len)
*******************/
int aes_encrypt_cbc(const BYTE in[], size_t in_len, BYTE out[], const WORD key[], int keysize, const BYTE iv[])
{
- BYTE buf_in[AES_BLOCK_SIZE], buf_out[AES_BLOCK_SIZE];
+ BYTE buf_in[AES_BLOCK_SIZE], buf_out[AES_BLOCK_SIZE], iv_buf[AES_BLOCK_SIZE];
int blocks, idx;
if (in_len % AES_BLOCK_SIZE != 0)
@@ -241,13 +241,14 @@ int aes_encrypt_cbc(const BYTE in[], size_t in_len, BYTE out[], const WORD key[]
blocks = in_len / AES_BLOCK_SIZE;
- memcpy(buf_out, iv, AES_BLOCK_SIZE);
+ memcpy(iv_buf, iv, AES_BLOCK_SIZE);
for (idx = 0; idx < blocks; idx++) {
memcpy(buf_in, &in[idx * AES_BLOCK_SIZE], AES_BLOCK_SIZE);
- xor_buf(buf_out, buf_in, AES_BLOCK_SIZE);
+ xor_buf(iv_buf, buf_in, AES_BLOCK_SIZE);
aes_encrypt(buf_in, buf_out, key, keysize);
memcpy(&out[idx * AES_BLOCK_SIZE], buf_out, AES_BLOCK_SIZE);
+ memcpy(iv_buf, buf_out, AES_BLOCK_SIZE);
}
return(TRUE);
@@ -255,7 +256,7 @@ int aes_encrypt_cbc(const BYTE in[], size_t in_len, BYTE out[], const WORD key[]
int aes_encrypt_cbc_mac(const BYTE in[], size_t in_len, BYTE out[], const WORD key[], int keysize, const BYTE iv[])
{
- BYTE buf_in[AES_BLOCK_SIZE], buf_out[AES_BLOCK_SIZE];
+ BYTE buf_in[AES_BLOCK_SIZE], buf_out[AES_BLOCK_SIZE], iv_buf[AES_BLOCK_SIZE];
int blocks, idx;
if (in_len % AES_BLOCK_SIZE != 0)
@@ -263,12 +264,13 @@ int aes_encrypt_cbc_mac(const BYTE in[], size_t in_len, BYTE out[], const WORD k
blocks = in_len / AES_BLOCK_SIZE;
- memcpy(buf_out, iv, AES_BLOCK_SIZE);
+ memcpy(iv_buf, iv, AES_BLOCK_SIZE);
for (idx = 0; idx < blocks; idx++) {
memcpy(buf_in, &in[idx * AES_BLOCK_SIZE], AES_BLOCK_SIZE);
- xor_buf(buf_out, buf_in, AES_BLOCK_SIZE);
+ xor_buf(iv_buf, buf_in, AES_BLOCK_SIZE);
aes_encrypt(buf_in, buf_out, key, keysize);
+ memcpy(iv_buf, buf_out, AES_BLOCK_SIZE);
// Do not output all encrypted blocks.
}
@@ -277,7 +279,28 @@ int aes_encrypt_cbc_mac(const BYTE in[], size_t in_len, BYTE out[], const WORD k
return(TRUE);
}
-// No need for an aes_decrypt_cbc() for just CCM.
+int aes_decrypt_cbc(const BYTE in[], size_t in_len, BYTE out[], const WORD key[], int keysize, const BYTE iv[])
+{
+ BYTE buf_in[AES_BLOCK_SIZE], buf_out[AES_BLOCK_SIZE], iv_buf[AES_BLOCK_SIZE];
+ int blocks, idx;
+
+ if (in_len % AES_BLOCK_SIZE != 0)
+ return(FALSE);
+
+ blocks = in_len / AES_BLOCK_SIZE;
+
+ memcpy(iv_buf, iv, AES_BLOCK_SIZE);
+
+ for (idx = 0; idx < blocks; idx++) {
+ memcpy(buf_in, &in[idx * AES_BLOCK_SIZE], AES_BLOCK_SIZE);
+ aes_decrypt(buf_in, buf_out, key, keysize);
+ xor_buf(iv_buf, buf_out, AES_BLOCK_SIZE);
+ memcpy(&out[idx * AES_BLOCK_SIZE], buf_out, AES_BLOCK_SIZE);
+ memcpy(iv_buf, buf_in, AES_BLOCK_SIZE);
+ }
+
+ return(TRUE);
+}
/*******************
* AES - CTR
diff --git a/aes_test.c b/aes_test.c
@@ -77,7 +77,7 @@ int aes_cbc_test()
BYTE plaintext[1][32] = {
{0x6b,0xc1,0xbe,0xe2,0x2e,0x40,0x9f,0x96,0xe9,0x3d,0x7e,0x11,0x73,0x93,0x17,0x2a,0xae,0x2d,0x8a,0x57,0x1e,0x03,0xac,0x9c,0x9e,0xb7,0x6f,0xac,0x45,0xaf,0x8e,0x51}
};
- BYTE ciphertext[2][32] = {
+ BYTE ciphertext[1][32] = {
{0xf5,0x8c,0x4c,0x04,0xd6,0xe5,0xf1,0xba,0x77,0x9e,0xab,0xfb,0x5f,0x7b,0xfb,0xd6,0x9c,0xfc,0x4e,0x96,0x7e,0xdb,0x80,0x8d,0x67,0x9f,0x77,0x7b,0xc6,0x70,0x2c,0x7d}
};
BYTE iv[1][16] = {
@@ -105,6 +105,15 @@ int aes_cbc_test()
//print_hex(ciphertext[0], 32);
pass = pass && !memcmp(enc_buf, ciphertext[0], 32);
+ aes_decrypt_cbc(ciphertext[0], 32, enc_buf, key_schedule, 256, iv[0]);
+ //printf("\nCiphertext : ");
+ //print_hex(ciphertext[0], 32);
+ //printf("\n-decrypted to: ");
+ //print_hex(enc_buf, 32);
+ //printf("\nPlaintext : ");
+ //print_hex(plaintext[0], 32);
+ pass = pass && !memcmp(enc_buf, plaintext[0], 32);
+
//printf("\n\n");
return(pass);
}