Also, document why CTR IV size is now set to 16, so user is noted to set
IV appropriately to full extent (including counter). Basically, it's for
openssh (and alike) to make it copy IV from privilege separated process.
(cherry picked from commit
74d13288e0a664f2615014d441087792eabc5cfa)
gost_grasshopper_cipher_destroy_ctr,
1,
sizeof(gost_grasshopper_cipher_ctx_ctr),
gost_grasshopper_cipher_destroy_ctr,
1,
sizeof(gost_grasshopper_cipher_ctx_ctr),
+ /* IV size is set to match full block, to make it responsibility of
+ * user to assign correct values (IV || 0), and to make naive context
+ * copy possible (for software such as openssh) */
+ 16,
static GRASSHOPPER_INLINE void gost_grasshopper_cipher_destroy_ctr(gost_grasshopper_cipher_ctx* c) {
gost_grasshopper_cipher_ctx_ctr* ctx = (gost_grasshopper_cipher_ctx_ctr*) c;
static GRASSHOPPER_INLINE void gost_grasshopper_cipher_destroy_ctr(gost_grasshopper_cipher_ctx* c) {
gost_grasshopper_cipher_ctx_ctr* ctx = (gost_grasshopper_cipher_ctx_ctr*) c;
- grasshopper_zero128(&ctx->iv_buffer);
grasshopper_zero128(&ctx->partial_buffer);
}
grasshopper_zero128(&ctx->partial_buffer);
}
c->c.type = GRASSHOPPER_CIPHER_CTR;
EVP_CIPHER_CTX_set_num(ctx, 0);
c->c.type = GRASSHOPPER_CIPHER_CTR;
EVP_CIPHER_CTX_set_num(ctx, 0);
- grasshopper_zero128(&c->iv_buffer);
grasshopper_zero128(&c->partial_buffer);
return gost_grasshopper_cipher_init(ctx, key, iv, enc);
grasshopper_zero128(&c->partial_buffer);
return gost_grasshopper_cipher_init(ctx, key, iv, enc);
EVP_CIPHER_CTX_set_num(ctx, n);
size_t blocks = inl / GRASSHOPPER_BLOCK_SIZE;
EVP_CIPHER_CTX_set_num(ctx, n);
size_t blocks = inl / GRASSHOPPER_BLOCK_SIZE;
- memcpy(&c->iv_buffer, iv, 8);
+ grasshopper_w128_t* iv_buffer = (grasshopper_w128_t*) iv;
// full parts
for (i = 0; i < blocks; i++) {
currentInputBlock = (grasshopper_w128_t*) current_in;
currentOutputBlock = (grasshopper_w128_t*) current_out;
// full parts
for (i = 0; i < blocks; i++) {
currentInputBlock = (grasshopper_w128_t*) current_in;
currentOutputBlock = (grasshopper_w128_t*) current_out;
- grasshopper_encrypt_block(&c->c.encrypt_round_keys, &c->iv_buffer, currentOutputBlock, &c->c.buffer);
+ grasshopper_encrypt_block(&c->c.encrypt_round_keys, iv_buffer, currentOutputBlock, &c->c.buffer);
grasshopper_append128(currentOutputBlock, currentInputBlock);
grasshopper_append128(currentOutputBlock, currentInputBlock);
- ctr128_inc(c->iv_buffer.b);
+ ctr128_inc(iv_buffer->b);
current_in += GRASSHOPPER_BLOCK_SIZE;
current_out += GRASSHOPPER_BLOCK_SIZE;
}
current_in += GRASSHOPPER_BLOCK_SIZE;
current_out += GRASSHOPPER_BLOCK_SIZE;
}
if (lasted > 0) {
currentInputBlock = (grasshopper_w128_t*) current_in;
currentOutputBlock = (grasshopper_w128_t*) current_out;
if (lasted > 0) {
currentInputBlock = (grasshopper_w128_t*) current_in;
currentOutputBlock = (grasshopper_w128_t*) current_out;
- grasshopper_encrypt_block(&c->c.encrypt_round_keys, &c->iv_buffer, &c->partial_buffer, &c->c.buffer);
+ grasshopper_encrypt_block(&c->c.encrypt_round_keys, iv_buffer, &c->partial_buffer, &c->c.buffer);
for (i = 0; i < lasted; i++) {
currentOutputBlock->b[i] = c->partial_buffer.b[i] ^ currentInputBlock->b[i];
}
EVP_CIPHER_CTX_set_num(ctx, i);
for (i = 0; i < lasted; i++) {
currentOutputBlock->b[i] = c->partial_buffer.b[i] ^ currentInputBlock->b[i];
}
EVP_CIPHER_CTX_set_num(ctx, i);
- ctr128_inc(c->iv_buffer.b);
+ ctr128_inc(iv_buffer->b);
typedef struct {
gost_grasshopper_cipher_ctx c;
typedef struct {
gost_grasshopper_cipher_ctx c;
- grasshopper_w128_t iv_buffer;
grasshopper_w128_t partial_buffer;
uint64_t counter;
} gost_grasshopper_cipher_ctx_ctr;
grasshopper_w128_t partial_buffer;
uint64_t counter;
} gost_grasshopper_cipher_ctx_ctr;