secretstream: set the initial counter to 1

Avoids using the first block for two different purposes, and will be more
consistent with the AES-based version.

This breaks backwards compatibility, but better do it now that most distro are
still shipping < 1.0.14, that no applications seem to be already using that new
API, and that there will be an update to the library major due to the aes128ctr
removal.
This commit is contained in:
Frank Denis 2017-10-01 10:08:04 +02:00
parent 3659d342af
commit 2542367c2d
2 changed files with 14 additions and 5 deletions

View File

@ -23,6 +23,15 @@
static const unsigned char _pad0[16] = { 0 }; static const unsigned char _pad0[16] = { 0 };
static inline void
_crypto_secretstream_xchacha20poly1305_counter_reset
(crypto_secretstream_xchacha20poly1305_state *state)
{
memset(STATE_COUNTER(state), 0,
crypto_secretstream_xchacha20poly1305_COUNTERBYTES);
STATE_COUNTER(state)[0] = 1;
}
void void
crypto_secretstream_xchacha20poly1305_keygen crypto_secretstream_xchacha20poly1305_keygen
(unsigned char k[crypto_secretstream_xchacha20poly1305_KEYBYTES]) (unsigned char k[crypto_secretstream_xchacha20poly1305_KEYBYTES])
@ -47,7 +56,7 @@ crypto_secretstream_xchacha20poly1305_init_push
randombytes_buf(out, crypto_secretstream_xchacha20poly1305_HEADERBYTES); randombytes_buf(out, crypto_secretstream_xchacha20poly1305_HEADERBYTES);
crypto_core_hchacha20(state->k, out, k, NULL); crypto_core_hchacha20(state->k, out, k, NULL);
memset(STATE_COUNTER(state), 0, crypto_secretstream_xchacha20poly1305_COUNTERBYTES); _crypto_secretstream_xchacha20poly1305_counter_reset(state);
memcpy(STATE_INONCE(state), out + crypto_core_hchacha20_INPUTBYTES, memcpy(STATE_INONCE(state), out + crypto_core_hchacha20_INPUTBYTES,
crypto_secretstream_xchacha20poly1305_INONCEBYTES); crypto_secretstream_xchacha20poly1305_INONCEBYTES);
memset(state->_pad, 0, sizeof state->_pad); memset(state->_pad, 0, sizeof state->_pad);
@ -62,7 +71,7 @@ crypto_secretstream_xchacha20poly1305_init_pull
const unsigned char k[crypto_secretstream_xchacha20poly1305_KEYBYTES]) const unsigned char k[crypto_secretstream_xchacha20poly1305_KEYBYTES])
{ {
crypto_core_hchacha20(state->k, in, k, NULL); crypto_core_hchacha20(state->k, in, k, NULL);
memset(STATE_COUNTER(state), 0, crypto_secretstream_xchacha20poly1305_COUNTERBYTES); _crypto_secretstream_xchacha20poly1305_counter_reset(state);
memcpy(STATE_INONCE(state), in + crypto_core_hchacha20_INPUTBYTES, memcpy(STATE_INONCE(state), in + crypto_core_hchacha20_INPUTBYTES,
crypto_secretstream_xchacha20poly1305_INONCEBYTES); crypto_secretstream_xchacha20poly1305_INONCEBYTES);
memset(state->_pad, 0, sizeof state->_pad); memset(state->_pad, 0, sizeof state->_pad);
@ -95,8 +104,7 @@ crypto_secretstream_xchacha20poly1305_rekey
STATE_INONCE(state)[i] = STATE_INONCE(state)[i] =
new_key_and_inonce[crypto_stream_chacha20_ietf_KEYBYTES + i]; new_key_and_inonce[crypto_stream_chacha20_ietf_KEYBYTES + i];
} }
memset(STATE_COUNTER(state), 0, _crypto_secretstream_xchacha20poly1305_counter_reset(state);
crypto_secretstream_xchacha20poly1305_COUNTERBYTES);
} }
int int

View File

@ -219,7 +219,8 @@ main(void)
assert(memcmp(state_copy.k, state->k, sizeof state->k) != 0); assert(memcmp(state_copy.k, state->k, sizeof state->k) != 0);
assert(memcmp(state_copy.nonce, state->nonce, sizeof state->nonce) != 0); assert(memcmp(state_copy.nonce, state->nonce, sizeof state->nonce) != 0);
assert(sodium_is_zero(state->nonce, 4U)); assert(state->nonce[0] == 1U);
assert(sodium_is_zero(state->nonce + 1, 3U));
ret = crypto_secretstream_xchacha20poly1305_init_pull(state, header, k); ret = crypto_secretstream_xchacha20poly1305_init_pull(state, header, k);
assert(ret == 0); assert(ret == 0);