add openssl chacha20 support

This commit is contained in:
sehraf 2017-05-05 18:50:40 +02:00
parent 96b4a1b2d8
commit 7371fdc432

View File

@ -363,7 +363,7 @@ static void print(const chacha20_state& s)
}
#endif
void chacha20_encrypt(uint8_t key[32], uint32_t block_counter, uint8_t nonce[12], uint8_t *data, uint32_t size)
void chacha20_encrypt_rs(uint8_t key[32], uint32_t block_counter, uint8_t nonce[12], uint8_t *data, uint32_t size)
{
for(uint32_t i=0;i<size/64 + 1;++i)
{
@ -386,6 +386,50 @@ void chacha20_encrypt(uint8_t key[32], uint32_t block_counter, uint8_t nonce[12]
}
}
#if OPENSSL_VERSION_NUMBER >= 0x010100000L
void chacha20_encrypt_openssl(uint8_t key[32], uint32_t block_counter, uint8_t nonce[12], uint8_t *data, uint32_t size)
{
EVP_CIPHER_CTX *ctx;
int len;
int tmp_len;
uint8_t tmp[size];
uint8_t iv[16];
// create iv with nonce and block counter
memcpy(iv, &block_counter, 4);
memcpy(iv + 4, nonce, 12);
/* Create and initialise the context */
if(!(ctx = EVP_CIPHER_CTX_new())) return;
/* Initialise the encryption operation. IMPORTANT - ensure you use a key
* and IV size appropriate for your cipher
* In this example we are using 256 bit AES (i.e. a 256 bit key). The
* IV size for *most* modes is the same as the block size. For AES this
* is 128 bits */
if(1 != EVP_EncryptInit_ex(ctx, EVP_chacha20(), NULL, key, iv)) goto out;
/* Provide the message to be encrypted, and obtain the encrypted output.
* EVP_EncryptUpdate can be called multiple times if necessary
*/
if(1 != EVP_EncryptUpdate(ctx, tmp, &len, data, size)) goto out;
tmp_len = len;
/* Finalise the encryption. Further ciphertext bytes may be written at
* this stage.
*/
if(1 != EVP_EncryptFinal_ex(ctx, tmp + len, &len)) goto out;
tmp_len += len;
memcpy(data, tmp, tmp_len);
out:
/* Clean up */
EVP_CIPHER_CTX_free(ctx);
}
#endif
struct poly1305_state
{
uint256_32 r ;
@ -499,7 +543,7 @@ bool AEAD_chacha20_poly1305_rs(uint8_t key[32], uint8_t nonce[12],uint8_t *data,
if(encrypt)
{
chacha20_encrypt(key,1,nonce,data,data_size);
chacha20_encrypt_rs(key,1,nonce,data,data_size);
poly1305_state pls ;
@ -527,12 +571,13 @@ bool AEAD_chacha20_poly1305_rs(uint8_t key[32], uint8_t nonce[12],uint8_t *data,
// decrypt
chacha20_encrypt(key,1,nonce,data,data_size);
chacha20_encrypt_rs(key,1,nonce,data,data_size);
return constant_time_memory_compare(tag,computed_tag,16) ;
}
}
#if OPENSSL_VERSION_NUMBER >= 0x010100000L
#define errorOut {ret = false; goto out;}
bool AEAD_chacha20_poly1305_openssl(uint8_t key[32], uint8_t nonce[12], uint8_t *data, uint32_t data_size, uint8_t *aad, uint32_t aad_size, uint8_t tag[16], bool encrypt_or_decrypt)
@ -614,6 +659,7 @@ out:
}
#undef errorOut
#endif
bool AEAD_chacha20_sha256(uint8_t key[32], uint8_t nonce[12],uint8_t *data,uint32_t data_size,uint8_t *aad,uint32_t aad_size,uint8_t tag[16],bool encrypt)
{
@ -621,7 +667,11 @@ bool AEAD_chacha20_sha256(uint8_t key[32], uint8_t nonce[12],uint8_t *data,uint3
if(encrypt)
{
chacha20_encrypt(key,1,nonce,data,data_size);
#if OPENSSL_VERSION_NUMBER < 0x10100000L
chacha20_encrypt_rs(key,1,nonce,data,data_size);
#else
chacha20_encrypt_openssl(key, 1, nonce, data, data_size);
#endif
uint8_t computed_tag[EVP_MAX_MD_SIZE];
unsigned int md_size ;
@ -683,7 +733,11 @@ bool AEAD_chacha20_sha256(uint8_t key[32], uint8_t nonce[12],uint8_t *data,uint3
// decrypt
chacha20_encrypt(key,1,nonce,data,data_size);
#if OPENSSL_VERSION_NUMBER < 0x10100000L
chacha20_encrypt_rs(key,1,nonce,data,data_size);
#else
chacha20_encrypt_openssl(key, 1, nonce, data, data_size);
#endif
return constant_time_memory_compare(tag,computed_tag,16) ;
}
@ -763,7 +817,7 @@ bool perform_tests()
0x74, 0x2e
};
chacha20_encrypt(key,1,nounce2,plaintext,7*16+2) ;
chacha20_encrypt_rs(key,1,nounce2,plaintext,7*16+2) ;
#ifdef DEBUG_CHACHA20
fprintf(stdout,"CipherText: \n") ;
@ -1332,7 +1386,7 @@ bool perform_tests()
{
RsScopeTimer s("AEAD1") ;
chacha20_encrypt(key, 1, nonce, ten_megabyte_data,SIZE) ;
chacha20_encrypt_rs(key, 1, nonce, ten_megabyte_data,SIZE) ;
std::cerr << " Chacha20 encryption speed : " << SIZE / (1024.0*1024.0) / s.duration() << " MB/s" << std::endl;
}
@ -1342,12 +1396,14 @@ bool perform_tests()
std::cerr << " AEAD/poly1305 own encryption speed : " << SIZE / (1024.0*1024.0) / s.duration() << " MB/s" << std::endl;
}
#if OPENSSL_VERSION_NUMBER >= 0x010100000L
{
RsScopeTimer s("AEAD3") ;
AEAD_chacha20_poly1305_openssl(key,nonce,ten_megabyte_data,SIZE,aad,12,received_tag,true) ;
std::cerr << " AEAD/poly1305 openssl encryption speed: " << SIZE / (1024.0*1024.0) / s.duration() << " MB/s" << std::endl;
}
#endif
{
RsScopeTimer s("AEAD4") ;
AEAD_chacha20_sha256(key,nonce,ten_megabyte_data,SIZE,aad,12,received_tag,true) ;