diff options
author | Nick Mathewson <nickm@torproject.org> | 2007-09-19 15:53:41 +0000 |
---|---|---|
committer | Nick Mathewson <nickm@torproject.org> | 2007-09-19 15:53:41 +0000 |
commit | 5f7950e8744a8c59ede2da56d99d0e878f00d18a (patch) | |
tree | ce5f17a5dbc7fafb4ae03e44c285f627c12ff722 /src/common | |
parent | 7e93139a85b6f912c11d8e26bc512d9330008278 (diff) | |
download | tor-5f7950e8744a8c59ede2da56d99d0e878f00d18a.tar.gz tor-5f7950e8744a8c59ede2da56d99d0e878f00d18a.zip |
r15172@catbus: nickm | 2007-09-19 11:50:02 -0400
New (untested) code to implement AES-with-IV. Currently, IVs are generated randomly. Once tested, should be (almost) a drop-in replacement for the CBC functions.
svn:r11519
Diffstat (limited to 'src/common')
-rw-r--r-- | src/common/crypto.c | 78 | ||||
-rw-r--r-- | src/common/crypto.h | 11 |
2 files changed, 88 insertions, 1 deletions
diff --git a/src/common/crypto.c b/src/common/crypto.c index 0e78c76af7..fb47dc4040 100644 --- a/src/common/crypto.c +++ b/src/common/crypto.c @@ -1074,7 +1074,24 @@ crypto_cipher_set_key(crypto_cipher_env_t *env, const char *key) return -1; memcpy(env->key, key, CIPHER_KEY_LEN); + return 0; +} + +/** DOCDOC */ +void +crypto_cipher_generate_iv(char *iv_out) +{ + /* XXXX020 It's possible we want to get fancier here. */ + crypto_rand(iv_out, CIPHER_IV_LEN); +} +/** DOCDOC */ +int +crypto_cipher_set_iv(crypto_cipher_env_t *env, const char *iv) +{ + tor_assert(env); + tor_assert(iv); + aes_set_iv(env->cipher, iv); return 0; } @@ -1144,8 +1161,67 @@ crypto_cipher_decrypt(crypto_cipher_env_t *env, char *to, return 0; } -#define AES_CIPHER_BLOCK_SIZE 16 +/** Encrypt <b>fromlen</b> bytes (at least 1) from <b>from</b> with the key in + * <b>cipher</b> to the buffer in <b>to</b> of length + * <b>tolen</b>. <b>tolen</b> must be at least <b>fromlen</b> plus + * CIPHER_IV_LEN bytes for the initialization vector. On success, return the + * number of bytes written, on failure, return -1. + * + * This function adjusts the current position of the counter in <b>cipher</b> + * to immediately after the encrypted data. + */ +int +crypto_cipher_encrypt_with_iv(crypto_cipher_env_t *cipher, + char *to, size_t tolen, + const char *from, size_t fromlen) +{ + tor_assert(cipher); + tor_assert(from); + tor_assert(to); + + if (tolen < fromlen + CIPHER_IV_LEN) + return -1; + + crypto_cipher_generate_iv(to); + if (crypto_cipher_set_iv(cipher, to)<0) + return -1; + crypto_cipher_encrypt(cipher, to+CIPHER_IV_LEN, from, fromlen); + crypto_free_cipher_env(cipher); + return fromlen + CIPHER_IV_LEN; +} + +/** Encrypt <b>fromlen</b> bytes (at least 1+CIPHER_IV_LEN) from <b>from</b> + * with the key in <b>cipher</b> to the buffer in <b>to</b> of length + * <b>tolen</b>. <b>tolen</b> must be at least <b>fromlen</b> minus + * CIPHER_IV_LEN bytes for the initialization vector. On success, return the + * number of bytes written, on failure, return -1. + * + * This function adjusts the current position of the counter in <b>cipher</b> + * to immediately after the decrypted data. + */ +int +crypto_cipher_decrypt_with_iv(crypto_cipher_env_t *cipher, + char *to, size_t tolen, + const char *from, size_t fromlen) +{ + tor_assert(cipher); + tor_assert(from); + tor_assert(to); + + if (fromlen < CIPHER_IV_LEN) + return -1; + if (tolen < fromlen - CIPHER_IV_LEN) + return -1; + + if (crypto_cipher_set_iv(cipher, from)<0) + return -1; + crypto_cipher_encrypt(cipher, to, from+CIPHER_IV_LEN, fromlen-CIPHER_IV_LEN); + crypto_free_cipher_env(cipher); + return fromlen - CIPHER_IV_LEN; +} + +#define AES_CIPHER_BLOCK_SIZE 16 #define AES_IV_SIZE 16 /** Encrypt <b>fromlen</b> bytes (at least 1) from <b>from</b> with the diff --git a/src/common/crypto.h b/src/common/crypto.h index 1d1f758fcb..b548978aaa 100644 --- a/src/common/crypto.h +++ b/src/common/crypto.h @@ -21,6 +21,8 @@ #define DIGEST_LEN 20 /** Length of our symmetric cipher's keys. */ #define CIPHER_KEY_LEN 16 +/** Length of our symmetric cipher's IV. */ +#define CIPHER_IV_LEN 16 /** Length of our public keys. */ #define PK_BYTES (1024/8) /** Length of our DH keys. */ @@ -115,6 +117,8 @@ int crypto_pk_check_fingerprint_syntax(const char *s); /* symmetric crypto */ int crypto_cipher_generate_key(crypto_cipher_env_t *env); int crypto_cipher_set_key(crypto_cipher_env_t *env, const char *key); +void crypto_cipher_generate_iv(char *iv_out); +int crypto_cipher_set_iv(crypto_cipher_env_t *env, const char *iv); const char *crypto_cipher_get_key(crypto_cipher_env_t *env); int crypto_cipher_encrypt_init_cipher(crypto_cipher_env_t *env); int crypto_cipher_decrypt_init_cipher(crypto_cipher_env_t *env); @@ -124,6 +128,13 @@ int crypto_cipher_encrypt(crypto_cipher_env_t *env, char *to, int crypto_cipher_decrypt(crypto_cipher_env_t *env, char *to, const char *from, size_t fromlen); +int crypto_cipher_encrypt_with_iv(crypto_cipher_env_t *env, + char *to, size_t tolen, + const char *from, size_t fromlen); +int crypto_cipher_decrypt_with_iv(crypto_cipher_env_t *env, + char *to, size_t tolen, + const char *from, size_t fromlen); + int crypto_cipher_encrypt_cbc(const char *key, char *to, size_t tolen, const char *from, size_t fromlen); int crypto_cipher_decrypt_cbc(const char *key, char *to, size_t tolen, |