diff options
author | iphydf <iphydf@users.noreply.github.com> | 2016-12-16 03:00:55 +0000 |
---|---|---|
committer | iphydf <iphydf@users.noreply.github.com> | 2017-12-29 23:24:54 +0000 |
commit | d26f0eb3bcdd622cc8adae98974a27d7487fc6cb (patch) | |
tree | 5643926efde516051ee9fe9efa9e6f9b04ea0548 /toxencryptsave/toxencryptsave.c | |
parent | 2c8fb05f6e1631403053ef8648d5860e0ec15cc3 (diff) |
Change toxencryptsave API to never overwrite pass keys.
Diffstat (limited to 'toxencryptsave/toxencryptsave.c')
-rw-r--r-- | toxencryptsave/toxencryptsave.c | 47 |
1 files changed, 27 insertions, 20 deletions
diff --git a/toxencryptsave/toxencryptsave.c b/toxencryptsave/toxencryptsave.c index 5640e82f..b7360b56 100644 --- a/toxencryptsave/toxencryptsave.c +++ b/toxencryptsave/toxencryptsave.c | |||
@@ -71,11 +71,6 @@ struct Tox_Pass_Key { | |||
71 | uint8_t key[TOX_PASS_KEY_LENGTH]; | 71 | uint8_t key[TOX_PASS_KEY_LENGTH]; |
72 | }; | 72 | }; |
73 | 73 | ||
74 | Tox_Pass_Key *tox_pass_key_new(void) | ||
75 | { | ||
76 | return (Tox_Pass_Key *)malloc(sizeof(Tox_Pass_Key)); | ||
77 | } | ||
78 | |||
79 | void tox_pass_key_free(Tox_Pass_Key *pass_key) | 74 | void tox_pass_key_free(Tox_Pass_Key *pass_key) |
80 | { | 75 | { |
81 | free(pass_key); | 76 | free(pass_key); |
@@ -123,23 +118,23 @@ bool tox_get_salt(const uint8_t *data, uint8_t *salt, TOX_ERR_GET_SALT *error) | |||
123 | * | 118 | * |
124 | * returns true on success | 119 | * returns true on success |
125 | */ | 120 | */ |
126 | bool tox_pass_key_derive(Tox_Pass_Key *out_key, const uint8_t *passphrase, size_t pplength, | 121 | Tox_Pass_Key *tox_pass_key_derive(const uint8_t *passphrase, size_t pplength, |
127 | TOX_ERR_KEY_DERIVATION *error) | 122 | TOX_ERR_KEY_DERIVATION *error) |
128 | { | 123 | { |
129 | uint8_t salt[crypto_pwhash_scryptsalsa208sha256_SALTBYTES]; | 124 | uint8_t salt[crypto_pwhash_scryptsalsa208sha256_SALTBYTES]; |
130 | randombytes(salt, sizeof salt); | 125 | randombytes(salt, sizeof salt); |
131 | return tox_pass_key_derive_with_salt(out_key, passphrase, pplength, salt, error); | 126 | return tox_pass_key_derive_with_salt(passphrase, pplength, salt, error); |
132 | } | 127 | } |
133 | 128 | ||
134 | /* Same as above, except with use the given salt for deterministic key derivation. | 129 | /* Same as above, except with use the given salt for deterministic key derivation. |
135 | * The salt must be TOX_PASS_SALT_LENGTH bytes in length. | 130 | * The salt must be TOX_PASS_SALT_LENGTH bytes in length. |
136 | */ | 131 | */ |
137 | bool tox_pass_key_derive_with_salt(Tox_Pass_Key *out_key, const uint8_t *passphrase, size_t pplength, | 132 | Tox_Pass_Key *tox_pass_key_derive_with_salt(const uint8_t *passphrase, size_t pplength, |
138 | const uint8_t *salt, TOX_ERR_KEY_DERIVATION *error) | 133 | const uint8_t *salt, TOX_ERR_KEY_DERIVATION *error) |
139 | { | 134 | { |
140 | if (!salt || !out_key || (!passphrase && pplength != 0)) { | 135 | if (!salt || (!passphrase && pplength != 0)) { |
141 | SET_ERROR_PARAMETER(error, TOX_ERR_KEY_DERIVATION_NULL); | 136 | SET_ERROR_PARAMETER(error, TOX_ERR_KEY_DERIVATION_NULL); |
142 | return 0; | 137 | return NULL; |
143 | } | 138 | } |
144 | 139 | ||
145 | uint8_t passkey[crypto_hash_sha256_BYTES]; | 140 | uint8_t passkey[crypto_hash_sha256_BYTES]; |
@@ -157,14 +152,22 @@ bool tox_pass_key_derive_with_salt(Tox_Pass_Key *out_key, const uint8_t *passphr | |||
157 | crypto_pwhash_scryptsalsa208sha256_MEMLIMIT_INTERACTIVE) != 0) { | 152 | crypto_pwhash_scryptsalsa208sha256_MEMLIMIT_INTERACTIVE) != 0) { |
158 | /* out of memory most likely */ | 153 | /* out of memory most likely */ |
159 | SET_ERROR_PARAMETER(error, TOX_ERR_KEY_DERIVATION_FAILED); | 154 | SET_ERROR_PARAMETER(error, TOX_ERR_KEY_DERIVATION_FAILED); |
160 | return 0; | 155 | return NULL; |
161 | } | 156 | } |
162 | 157 | ||
163 | sodium_memzero(passkey, crypto_hash_sha256_BYTES); /* wipe plaintext pw */ | 158 | sodium_memzero(passkey, crypto_hash_sha256_BYTES); /* wipe plaintext pw */ |
159 | |||
160 | Tox_Pass_Key *out_key = (Tox_Pass_Key *)malloc(sizeof(Tox_Pass_Key)); | ||
161 | |||
162 | if (!out_key) { | ||
163 | SET_ERROR_PARAMETER(error, TOX_ERR_KEY_DERIVATION_FAILED); | ||
164 | return NULL; | ||
165 | } | ||
166 | |||
164 | memcpy(out_key->salt, salt, crypto_pwhash_scryptsalsa208sha256_SALTBYTES); | 167 | memcpy(out_key->salt, salt, crypto_pwhash_scryptsalsa208sha256_SALTBYTES); |
165 | memcpy(out_key->key, key, CRYPTO_SHARED_KEY_SIZE); | 168 | memcpy(out_key->key, key, CRYPTO_SHARED_KEY_SIZE); |
166 | SET_ERROR_PARAMETER(error, TOX_ERR_KEY_DERIVATION_OK); | 169 | SET_ERROR_PARAMETER(error, TOX_ERR_KEY_DERIVATION_OK); |
167 | return 1; | 170 | return out_key; |
168 | } | 171 | } |
169 | 172 | ||
170 | /* Encrypt arbitrary with a key produced by tox_derive_key_*. The output | 173 | /* Encrypt arbitrary with a key produced by tox_derive_key_*. The output |
@@ -224,10 +227,10 @@ bool tox_pass_key_encrypt(const Tox_Pass_Key *key, const uint8_t *data, size_t d | |||
224 | bool tox_pass_encrypt(const uint8_t *data, size_t data_len, const uint8_t *passphrase, size_t pplength, uint8_t *out, | 227 | bool tox_pass_encrypt(const uint8_t *data, size_t data_len, const uint8_t *passphrase, size_t pplength, uint8_t *out, |
225 | TOX_ERR_ENCRYPTION *error) | 228 | TOX_ERR_ENCRYPTION *error) |
226 | { | 229 | { |
227 | Tox_Pass_Key key; | ||
228 | TOX_ERR_KEY_DERIVATION _error; | 230 | TOX_ERR_KEY_DERIVATION _error; |
231 | Tox_Pass_Key *key = tox_pass_key_derive(passphrase, pplength, &_error); | ||
229 | 232 | ||
230 | if (!tox_pass_key_derive(&key, passphrase, pplength, &_error)) { | 233 | if (!key) { |
231 | if (_error == TOX_ERR_KEY_DERIVATION_NULL) { | 234 | if (_error == TOX_ERR_KEY_DERIVATION_NULL) { |
232 | SET_ERROR_PARAMETER(error, TOX_ERR_ENCRYPTION_NULL); | 235 | SET_ERROR_PARAMETER(error, TOX_ERR_ENCRYPTION_NULL); |
233 | } else if (_error == TOX_ERR_KEY_DERIVATION_FAILED) { | 236 | } else if (_error == TOX_ERR_KEY_DERIVATION_FAILED) { |
@@ -237,7 +240,9 @@ bool tox_pass_encrypt(const uint8_t *data, size_t data_len, const uint8_t *passp | |||
237 | return 0; | 240 | return 0; |
238 | } | 241 | } |
239 | 242 | ||
240 | return tox_pass_key_encrypt(&key, data, data_len, out, error); | 243 | bool result = tox_pass_key_encrypt(key, data, data_len, out, error); |
244 | tox_pass_key_free(key); | ||
245 | return result; | ||
241 | } | 246 | } |
242 | 247 | ||
243 | /* This is the inverse of tox_pass_key_encrypt, also using only keys produced by | 248 | /* This is the inverse of tox_pass_key_encrypt, also using only keys produced by |
@@ -315,15 +320,17 @@ bool tox_pass_decrypt(const uint8_t *data, size_t length, const uint8_t *passphr | |||
315 | memcpy(salt, data + TOX_ENC_SAVE_MAGIC_LENGTH, crypto_pwhash_scryptsalsa208sha256_SALTBYTES); | 320 | memcpy(salt, data + TOX_ENC_SAVE_MAGIC_LENGTH, crypto_pwhash_scryptsalsa208sha256_SALTBYTES); |
316 | 321 | ||
317 | /* derive the key */ | 322 | /* derive the key */ |
318 | Tox_Pass_Key key; | 323 | Tox_Pass_Key *key = tox_pass_key_derive_with_salt(passphrase, pplength, salt, NULL); |
319 | 324 | ||
320 | if (!tox_pass_key_derive_with_salt(&key, passphrase, pplength, salt, NULL)) { | 325 | if (!key) { |
321 | /* out of memory most likely */ | 326 | /* out of memory most likely */ |
322 | SET_ERROR_PARAMETER(error, TOX_ERR_DECRYPTION_KEY_DERIVATION_FAILED); | 327 | SET_ERROR_PARAMETER(error, TOX_ERR_DECRYPTION_KEY_DERIVATION_FAILED); |
323 | return 0; | 328 | return 0; |
324 | } | 329 | } |
325 | 330 | ||
326 | return tox_pass_key_decrypt(&key, data, length, out, error); | 331 | bool result = tox_pass_key_decrypt(key, data, length, out, error); |
332 | tox_pass_key_free(key); | ||
333 | return result; | ||
327 | } | 334 | } |
328 | 335 | ||
329 | /* Determines whether or not the given data is encrypted (by checking the magic number) | 336 | /* Determines whether or not the given data is encrypted (by checking the magic number) |