crypto-algorithms.c

Basic implementations of standard cryptography algorithms, like AES and SHA-1
git clone git://git.finwo.net/lib/crypto-algorithms.c
Log | Files | Refs | README

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:
Maes.c | 37++++++++++++++++++++++++++++++-------
Maes_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); }