Merge branch 'linus' of git://git.kernel.org/pub/scm/linux/kernel/git/herbert/crypto-2.6

Pull crypto updates from Herbert Xu:
 "API:
   - Add support for allocating transforms on a specific NUMA Node
   - Introduce the flag CRYPTO_ALG_ALLOCATES_MEMORY for storage users

  Algorithms:
   - Drop PMULL based ghash on arm64
   - Fixes for building with clang on x86
   - Add sha256 helper that does the digest in one go
   - Add SP800-56A rev 3 validation checks to dh

  Drivers:
   - Permit users to specify NUMA node in hisilicon/zip
   - Add support for i.MX6 in imx-rngc
   - Add sa2ul crypto driver
   - Add BA431 hwrng driver
   - Add Ingenic JZ4780 and X1000 hwrng driver
   - Spread IRQ affinity in inside-secure and marvell/cesa"

* 'linus' of git://git.kernel.org/pub/scm/linux/kernel/git/herbert/crypto-2.6: (157 commits)
  crypto: sa2ul - Fix inconsistent IS_ERR and PTR_ERR
  hwrng: core - remove redundant initialization of variable ret
  crypto: x86/curve25519 - Remove unused carry variables
  crypto: ingenic - Add hardware RNG for Ingenic JZ4780 and X1000
  dt-bindings: RNG: Add Ingenic RNG bindings.
  crypto: caam/qi2 - add module alias
  crypto: caam - add more RNG hw error codes
  crypto: caam/jr - remove incorrect reference to caam_jr_register()
  crypto: caam - silence .setkey in case of bad key length
  crypto: caam/qi2 - create ahash shared descriptors only once
  crypto: caam/qi2 - fix error reporting for caam_hash_alloc
  crypto: caam - remove deadcode on 32-bit platforms
  crypto: ccp - use generic power management
  crypto: xts - Replace memcpy() invocation with simple assignment
  crypto: marvell/cesa - irq balance
  crypto: inside-secure - irq balance
  crypto: ecc - SP800-56A rev 3 local public key validation
  crypto: dh - SP800-56A rev 3 local public key validation
  crypto: dh - check validity of Z before export
  lib/mpi: Add mpi_sub_ui()
  ...
This commit is contained in:
Linus Torvalds
2020-08-03 10:40:14 -07:00
257 changed files with 6651 additions and 5500 deletions

View File

@@ -17,64 +17,69 @@
#include <linux/notifier.h>
static struct crypto_shash __rcu *crct10dif_tfm;
static struct static_key crct10dif_fallback __read_mostly;
static DEFINE_STATIC_KEY_TRUE(crct10dif_fallback);
static DEFINE_MUTEX(crc_t10dif_mutex);
static struct work_struct crct10dif_rehash_work;
static int crc_t10dif_rehash(struct notifier_block *self, unsigned long val, void *data)
static int crc_t10dif_notify(struct notifier_block *self, unsigned long val, void *data)
{
struct crypto_alg *alg = data;
struct crypto_shash *new, *old;
if (val != CRYPTO_MSG_ALG_LOADED ||
static_key_false(&crct10dif_fallback) ||
strncmp(alg->cra_name, CRC_T10DIF_STRING, strlen(CRC_T10DIF_STRING)))
return 0;
strcmp(alg->cra_name, CRC_T10DIF_STRING))
return NOTIFY_DONE;
schedule_work(&crct10dif_rehash_work);
return NOTIFY_OK;
}
static void crc_t10dif_rehash(struct work_struct *work)
{
struct crypto_shash *new, *old;
mutex_lock(&crc_t10dif_mutex);
old = rcu_dereference_protected(crct10dif_tfm,
lockdep_is_held(&crc_t10dif_mutex));
if (!old) {
mutex_unlock(&crc_t10dif_mutex);
return 0;
}
new = crypto_alloc_shash("crct10dif", 0, 0);
new = crypto_alloc_shash(CRC_T10DIF_STRING, 0, 0);
if (IS_ERR(new)) {
mutex_unlock(&crc_t10dif_mutex);
return 0;
return;
}
rcu_assign_pointer(crct10dif_tfm, new);
mutex_unlock(&crc_t10dif_mutex);
synchronize_rcu();
crypto_free_shash(old);
return 0;
if (old) {
synchronize_rcu();
crypto_free_shash(old);
} else {
static_branch_disable(&crct10dif_fallback);
}
}
static struct notifier_block crc_t10dif_nb = {
.notifier_call = crc_t10dif_rehash,
.notifier_call = crc_t10dif_notify,
};
__u16 crc_t10dif_update(__u16 crc, const unsigned char *buffer, size_t len)
{
struct {
struct shash_desc shash;
char ctx[2];
__u16 crc;
} desc;
int err;
if (static_key_false(&crct10dif_fallback))
if (static_branch_unlikely(&crct10dif_fallback))
return crc_t10dif_generic(crc, buffer, len);
rcu_read_lock();
desc.shash.tfm = rcu_dereference(crct10dif_tfm);
*(__u16 *)desc.ctx = crc;
desc.crc = crc;
err = crypto_shash_update(&desc.shash, buffer, len);
rcu_read_unlock();
BUG_ON(err);
return *(__u16 *)desc.ctx;
return desc.crc;
}
EXPORT_SYMBOL(crc_t10dif_update);
@@ -86,19 +91,17 @@ EXPORT_SYMBOL(crc_t10dif);
static int __init crc_t10dif_mod_init(void)
{
INIT_WORK(&crct10dif_rehash_work, crc_t10dif_rehash);
crypto_register_notifier(&crc_t10dif_nb);
crct10dif_tfm = crypto_alloc_shash("crct10dif", 0, 0);
if (IS_ERR(crct10dif_tfm)) {
static_key_slow_inc(&crct10dif_fallback);
crct10dif_tfm = NULL;
}
crc_t10dif_rehash(&crct10dif_rehash_work);
return 0;
}
static void __exit crc_t10dif_mod_fini(void)
{
crypto_unregister_notifier(&crc_t10dif_nb);
crypto_free_shash(crct10dif_tfm);
cancel_work_sync(&crct10dif_rehash_work);
crypto_free_shash(rcu_dereference_protected(crct10dif_tfm, 1));
}
module_init(crc_t10dif_mod_init);
@@ -106,15 +109,23 @@ module_exit(crc_t10dif_mod_fini);
static int crc_t10dif_transform_show(char *buffer, const struct kernel_param *kp)
{
if (static_key_false(&crct10dif_fallback))
struct crypto_shash *tfm;
int len;
if (static_branch_unlikely(&crct10dif_fallback))
return sprintf(buffer, "fallback\n");
return sprintf(buffer, "%s\n",
crypto_tfm_alg_driver_name(crypto_shash_tfm(crct10dif_tfm)));
rcu_read_lock();
tfm = rcu_dereference(crct10dif_tfm);
len = snprintf(buffer, PAGE_SIZE, "%s\n",
crypto_shash_driver_name(tfm));
rcu_read_unlock();
return len;
}
module_param_call(transform, NULL, crc_t10dif_transform_show, NULL, 0644);
module_param_call(transform, NULL, crc_t10dif_transform_show, NULL, 0444);
MODULE_DESCRIPTION("T10 DIF CRC calculation");
MODULE_DESCRIPTION("T10 DIF CRC calculation (library API)");
MODULE_LICENSE("GPL");
MODULE_SOFTDEP("pre: crct10dif");

View File

@@ -21,8 +21,6 @@
#define CHACHA_KEY_WORDS (CHACHA_KEY_SIZE / sizeof(u32))
bool __init chacha20poly1305_selftest(void);
static void chacha_load_key(u32 *k, const u8 *in)
{
k[0] = get_unaligned_le32(in);

View File

@@ -280,4 +280,14 @@ void sha224_final(struct sha256_state *sctx, u8 *out)
}
EXPORT_SYMBOL(sha224_final);
void sha256(const u8 *data, unsigned int len, u8 *out)
{
struct sha256_state sctx;
sha256_init(&sctx);
sha256_update(&sctx, data, len);
sha256_final(&sctx, out);
}
EXPORT_SYMBOL(sha256);
MODULE_LICENSE("GPL");

View File

@@ -16,6 +16,7 @@ mpi-y = \
mpicoder.o \
mpi-bit.o \
mpi-cmp.o \
mpi-sub-ui.o \
mpih-cmp.o \
mpih-div.o \
mpih-mul.o \

78
lib/mpi/mpi-sub-ui.c Normal file
View File

@@ -0,0 +1,78 @@
// SPDX-License-Identifier: GPL-2.0-or-later
/* mpi-sub-ui.c - Subtract an unsigned integer from an MPI.
*
* Copyright 1991, 1993, 1994, 1996, 1999-2002, 2004, 2012, 2013, 2015
* Free Software Foundation, Inc.
*
* This file was based on the GNU MP Library source file:
* https://gmplib.org/repo/gmp-6.2/file/510b83519d1c/mpz/aors_ui.h
*
* The GNU MP Library is free software; you can redistribute it and/or modify
* it under the terms of either:
*
* * the GNU Lesser General Public License as published by the Free
* Software Foundation; either version 3 of the License, or (at your
* option) any later version.
*
* or
*
* * the GNU General Public License as published by the Free Software
* Foundation; either version 2 of the License, or (at your option) any
* later version.
*
* or both in parallel, as here.
*
* The GNU MP Library is distributed in the hope that it will be useful, but
* WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
* or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
* for more details.
*
* You should have received copies of the GNU General Public License and the
* GNU Lesser General Public License along with the GNU MP Library. If not,
* see https://www.gnu.org/licenses/.
*/
#include "mpi-internal.h"
int mpi_sub_ui(MPI w, MPI u, unsigned long vval)
{
if (u->nlimbs == 0) {
if (mpi_resize(w, 1) < 0)
return -ENOMEM;
w->d[0] = vval;
w->nlimbs = (vval != 0);
w->sign = (vval != 0);
return 0;
}
/* If not space for W (and possible carry), increase space. */
if (mpi_resize(w, u->nlimbs + 1))
return -ENOMEM;
if (u->sign) {
mpi_limb_t cy;
cy = mpihelp_add_1(w->d, u->d, u->nlimbs, (mpi_limb_t) vval);
w->d[u->nlimbs] = cy;
w->nlimbs = u->nlimbs + cy;
w->sign = 1;
} else {
/* The signs are different. Need exact comparison to determine
* which operand to subtract from which.
*/
if (u->nlimbs == 1 && u->d[0] < vval) {
w->d[0] = vval - u->d[0];
w->nlimbs = 1;
w->sign = 1;
} else {
mpihelp_sub_1(w->d, u->d, u->nlimbs, (mpi_limb_t) vval);
/* Size can decrease with at most one limb. */
w->nlimbs = (u->nlimbs - (w->d[u->nlimbs - 1] == 0));
w->sign = 0;
}
}
mpi_normalize(w);
return 0;
}
EXPORT_SYMBOL_GPL(mpi_sub_ui);