Skip to content
Snippets Groups Projects
  1. Nov 20, 2018
    • Eric Biggers's avatar
      crypto: chacha - add XChaCha12 support · aa762409
      Eric Biggers authored
      Now that the generic implementation of ChaCha20 has been refactored to
      allow varying the number of rounds, add support for XChaCha12, which is
      the XSalsa construction applied to ChaCha12.  ChaCha12 is one of the
      three ciphers specified by the original ChaCha paper
      (https://cr.yp.to/chacha/chacha-20080128.pdf
      
      : "ChaCha, a variant of
      Salsa20"), alongside ChaCha8 and ChaCha20.  ChaCha12 is faster than
      ChaCha20 but has a lower, but still large, security margin.
      
      We need XChaCha12 support so that it can be used in the Adiantum
      encryption mode, which enables disk/file encryption on low-end mobile
      devices where AES-XTS is too slow as the CPUs lack AES instructions.
      
      We'd prefer XChaCha20 (the more popular variant), but it's too slow on
      some of our target devices, so at least in some cases we do need the
      XChaCha12-based version.  In more detail, the problem is that Adiantum
      is still much slower than we're happy with, and encryption still has a
      quite noticeable effect on the feel of low-end devices.  Users and
      vendors push back hard against encryption that degrades the user
      experience, which always risks encryption being disabled entirely.  So
      we need to choose the fastest option that gives us a solid margin of
      security, and here that's XChaCha12.  The best known attack on ChaCha
      breaks only 7 rounds and has 2^235 time complexity, so ChaCha12's
      security margin is still better than AES-256's.  Much has been learned
      about cryptanalysis of ARX ciphers since Salsa20 was originally designed
      in 2005, and it now seems we can be comfortable with a smaller number of
      rounds.  The eSTREAM project also suggests the 12-round version of
      Salsa20 as providing the best balance among the different variants:
      combining very good performance with a "comfortable margin of security".
      
      Note that it would be trivial to add vanilla ChaCha12 in addition to
      XChaCha12.  However, it's unneeded for now and therefore is omitted.
      
      As discussed in the patch that introduced XChaCha20 support, I
      considered splitting the code into separate chacha-common, chacha20,
      xchacha20, and xchacha12 modules, so that these algorithms could be
      enabled/disabled independently.  However, since nearly all the code is
      shared anyway, I ultimately decided there would have been little benefit
      to the added complexity.
      
      Reviewed-by: default avatarArd Biesheuvel <ard.biesheuvel@linaro.org>
      Acked-by: default avatarMartin Willi <martin@strongswan.org>
      Signed-off-by: default avatarEric Biggers <ebiggers@google.com>
      Signed-off-by: default avatarHerbert Xu <herbert@gondor.apana.org.au>
      aa762409
    • Eric Biggers's avatar
      crypto: chacha20-generic - refactor to allow varying number of rounds · 1ca1b917
      Eric Biggers authored
      
      In preparation for adding XChaCha12 support, rename/refactor
      chacha20-generic to support different numbers of rounds.  The
      justification for needing XChaCha12 support is explained in more detail
      in the patch "crypto: chacha - add XChaCha12 support".
      
      The only difference between ChaCha{8,12,20} are the number of rounds
      itself; all other parts of the algorithm are the same.  Therefore,
      remove the "20" from all definitions, structures, functions, files, etc.
      that will be shared by all ChaCha versions.
      
      Also make ->setkey() store the round count in the chacha_ctx (previously
      chacha20_ctx).  The generic code then passes the round count through to
      chacha_block().  There will be a ->setkey() function for each explicitly
      allowed round count; the encrypt/decrypt functions will be the same.  I
      decided not to do it the opposite way (same ->setkey() function for all
      round counts, with different encrypt/decrypt functions) because that
      would have required more boilerplate code in architecture-specific
      implementations of ChaCha and XChaCha.
      
      Reviewed-by: default avatarArd Biesheuvel <ard.biesheuvel@linaro.org>
      Acked-by: default avatarMartin Willi <martin@strongswan.org>
      Signed-off-by: default avatarEric Biggers <ebiggers@google.com>
      Signed-off-by: default avatarHerbert Xu <herbert@gondor.apana.org.au>
      1ca1b917
    • Eric Biggers's avatar
      crypto: chacha20-generic - add HChaCha20 library function · dd333449
      Eric Biggers authored
      Refactor the unkeyed permutation part of chacha20_block() into its own
      function, then add hchacha20_block() which is the ChaCha equivalent of
      HSalsa20 and is an intermediate step towards XChaCha20 (see
      https://cr.yp.to/snuffle/xsalsa-20081128.pdf
      
      ).  HChaCha20 skips the
      final addition of the initial state, and outputs only certain words of
      the state.  It should not be used for streaming directly.
      
      Reviewed-by: default avatarArd Biesheuvel <ard.biesheuvel@linaro.org>
      Acked-by: default avatarMartin Willi <martin@strongswan.org>
      Signed-off-by: default avatarEric Biggers <ebiggers@google.com>
      Signed-off-by: default avatarHerbert Xu <herbert@gondor.apana.org.au>
      dd333449
  2. Sep 21, 2018
    • Eric Biggers's avatar
      crypto: chacha20 - Fix chacha20_block() keystream alignment (again) · a5e9f557
      Eric Biggers authored
      
      In commit 9f480fae ("crypto: chacha20 - Fix keystream alignment for
      chacha20_block()"), I had missed that chacha20_block() can be called
      directly on the buffer passed to get_random_bytes(), which can have any
      alignment.  So, while my commit didn't break anything, 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 need not be aligned.
      This is simpler, and on many CPUs it's the same speed.
      
      But, I kept the 'tmp' buffers in extract_crng_user() and
      _get_random_bytes() 4-byte aligned, since that alignment is actually
      needed for _crng_backtrack_protect() too.
      
      Reported-by: default avatarStephan Müller <smueller@chronox.de>
      Cc: Theodore Ts'o <tytso@mit.edu>
      Signed-off-by: default avatarEric Biggers <ebiggers@google.com>
      Signed-off-by: default avatarHerbert Xu <herbert@gondor.apana.org.au>
      a5e9f557
  3. Jan 12, 2018
  4. Nov 29, 2017
    • Eric Biggers's avatar
      crypto: chacha20 - Fix keystream alignment for chacha20_block() · 9f480fae
      Eric Biggers authored
      
      When chacha20_block() outputs the keystream block, it uses 'u32' stores
      directly.  However, the callers (crypto/chacha20_generic.c and
      drivers/char/random.c) declare the keystream buffer as a 'u8' array,
      which is not guaranteed to have the needed alignment.
      
      Fix it by having both callers declare the keystream as a 'u32' array.
      For now this is preferable to switching over to the unaligned access
      macros because chacha20_block() is only being used in cases where we can
      easily control the alignment (stack buffers).
      
      Signed-off-by: default avatarEric Biggers <ebiggers@google.com>
      Signed-off-by: default avatarHerbert Xu <herbert@gondor.apana.org.au>
      9f480fae
  5. Jul 03, 2016
Loading