Hi,

Le jeudi 09 août 2018 à 12:40 -0700, Eric Biggers a écrit :
> From: Eric Biggers <ebigg...@google.com>
> Subject: [PATCH] crypto: chacha20 - Fix keystream alignment for 
> chacha20_block() (again)
> 
> In commit 9f480faec58cd6 ("crypto: chacha20 - Fix keystream alignment
> for chacha20_block()") I had missed that chacha20_block() can end up
> being called on the buffer passed to get_random_bytes(), which can have
> any alignment.  So, while my commit didn't break anything since
> chacha20_block() has actually always had a u32-alignment requirement for
> the output, it didn't fully solve the alignment problems.
> 
> Revert my solution and just update chacha20_block() to use
> put_unaligned_le32(), so the output buffer doesn't have to be aligned.
> 
> This is simpler, and on many CPUs it's the same speed.
> 
> Reported-by: Stephan Müller <smuel...@chronox.de>
> Signed-off-by: Eric Biggers <ebigg...@google.com>
> ---
>  crypto/chacha20_generic.c |  7 ++++---
>  drivers/char/random.c     | 24 ++++++++++++------------
>  include/crypto/chacha20.h |  3 +--
>  lib/chacha20.c            |  6 +++---
>  4 files changed, 20 insertions(+), 20 deletions(-)
> 
> diff --git a/drivers/char/random.c b/drivers/char/random.c
> index bd449ad52442..b8f4345a50f4 100644
> --- a/drivers/char/random.c
> +++ b/drivers/char/random.c
> @@ -433,9 +433,9 @@ static int crng_init_cnt = 0;
>  static unsigned long crng_global_init_time = 0;
>  #define CRNG_INIT_CNT_THRESH (2*CHACHA20_KEY_SIZE)
>  static void _extract_crng(struct crng_state *crng,
> -                       __u32 out[CHACHA20_BLOCK_WORDS]);
> +                       __u8 out[CHACHA20_BLOCK_SIZE]);
>  static void _crng_backtrack_protect(struct crng_state *crng,
> -                                 __u32 tmp[CHACHA20_BLOCK_WORDS], int used);
> +                                 __u8 tmp[CHACHA20_BLOCK_SIZE], int used);
>  static void process_random_ready_list(void);
>  static void _get_random_bytes(void *buf, int nbytes);
>  

[...]

> @@ -994,7 +994,7 @@ static void extract_crng(__u32 out[CHACHA20_BLOCK_WORDS])
>   * enough) to mutate the CRNG key to provide backtracking protection.
>   */
>  static void _crng_backtrack_protect(struct crng_state *crng,
> -                                 __u32 tmp[CHACHA20_BLOCK_WORDS], int used)
> +                                 __u8 tmp[CHACHA20_BLOCK_SIZE], int used)
>  {
>       unsigned long   flags;
>       __u32           *s, *d;
> @@ -1006,14 +1006,14 @@ static void _crng_backtrack_protect(struct crng_state 
> *crng,
>               used = 0;
>       }
>       spin_lock_irqsave(&crng->lock, flags);
> -     s = &tmp[used / sizeof(__u32)];
> +     s = (__u32 *) &tmp[used];

tmp is __8* while s is __u32*, that sounds like an alignment issue ...

>       d = &crng->state[4];
>       for (i=0; i < 8; i++)
>               *d++ ^= *s++;

... when s is dereferenced

>       spin_unlock_irqrestore(&crng->lock, flags);
>  }
>  


Regards.

-- 
Yann Droneaud
OPTEYA


Reply via email to