^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 1) // SPDX-License-Identifier: GPL-2.0+
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 2) /*
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 3) * Cryptographic API.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 4) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 5) * s390 implementation of the SHA512 and SHA38 Secure Hash Algorithm.
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 6) *
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 7) * Copyright IBM Corp. 2007
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 8) * Author(s): Jan Glauber (jang@de.ibm.com)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 9) */
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 10) #include <crypto/internal/hash.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 11) #include <crypto/sha.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 12) #include <linux/errno.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 13) #include <linux/init.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 14) #include <linux/kernel.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 15) #include <linux/module.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 16) #include <linux/cpufeature.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 17) #include <asm/cpacf.h>
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 18)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 19) #include "sha.h"
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 20)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 21) static int sha512_init(struct shash_desc *desc)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 22) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 23) struct s390_sha_ctx *ctx = shash_desc_ctx(desc);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 24)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 25) *(__u64 *)&ctx->state[0] = 0x6a09e667f3bcc908ULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 26) *(__u64 *)&ctx->state[2] = 0xbb67ae8584caa73bULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 27) *(__u64 *)&ctx->state[4] = 0x3c6ef372fe94f82bULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 28) *(__u64 *)&ctx->state[6] = 0xa54ff53a5f1d36f1ULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 29) *(__u64 *)&ctx->state[8] = 0x510e527fade682d1ULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 30) *(__u64 *)&ctx->state[10] = 0x9b05688c2b3e6c1fULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 31) *(__u64 *)&ctx->state[12] = 0x1f83d9abfb41bd6bULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 32) *(__u64 *)&ctx->state[14] = 0x5be0cd19137e2179ULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 33) ctx->count = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 34) ctx->func = CPACF_KIMD_SHA_512;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 35)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 36) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 37) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 38)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 39) static int sha512_export(struct shash_desc *desc, void *out)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 40) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 41) struct s390_sha_ctx *sctx = shash_desc_ctx(desc);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 42) struct sha512_state *octx = out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 43)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 44) octx->count[0] = sctx->count;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 45) octx->count[1] = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 46) memcpy(octx->state, sctx->state, sizeof(octx->state));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 47) memcpy(octx->buf, sctx->buf, sizeof(octx->buf));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 48) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 49) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 50)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 51) static int sha512_import(struct shash_desc *desc, const void *in)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 52) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 53) struct s390_sha_ctx *sctx = shash_desc_ctx(desc);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 54) const struct sha512_state *ictx = in;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 55)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 56) if (unlikely(ictx->count[1]))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 57) return -ERANGE;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 58) sctx->count = ictx->count[0];
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 59)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 60) memcpy(sctx->state, ictx->state, sizeof(ictx->state));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 61) memcpy(sctx->buf, ictx->buf, sizeof(ictx->buf));
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 62) sctx->func = CPACF_KIMD_SHA_512;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 63) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 64) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 65)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 66) static struct shash_alg sha512_alg = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 67) .digestsize = SHA512_DIGEST_SIZE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 68) .init = sha512_init,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 69) .update = s390_sha_update,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 70) .final = s390_sha_final,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 71) .export = sha512_export,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 72) .import = sha512_import,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 73) .descsize = sizeof(struct s390_sha_ctx),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 74) .statesize = sizeof(struct sha512_state),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 75) .base = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 76) .cra_name = "sha512",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 77) .cra_driver_name= "sha512-s390",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 78) .cra_priority = 300,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 79) .cra_blocksize = SHA512_BLOCK_SIZE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 80) .cra_module = THIS_MODULE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 81) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 82) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 83)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 84) MODULE_ALIAS_CRYPTO("sha512");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 85)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 86) static int sha384_init(struct shash_desc *desc)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 87) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 88) struct s390_sha_ctx *ctx = shash_desc_ctx(desc);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 89)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 90) *(__u64 *)&ctx->state[0] = 0xcbbb9d5dc1059ed8ULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 91) *(__u64 *)&ctx->state[2] = 0x629a292a367cd507ULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 92) *(__u64 *)&ctx->state[4] = 0x9159015a3070dd17ULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 93) *(__u64 *)&ctx->state[6] = 0x152fecd8f70e5939ULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 94) *(__u64 *)&ctx->state[8] = 0x67332667ffc00b31ULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 95) *(__u64 *)&ctx->state[10] = 0x8eb44a8768581511ULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 96) *(__u64 *)&ctx->state[12] = 0xdb0c2e0d64f98fa7ULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 97) *(__u64 *)&ctx->state[14] = 0x47b5481dbefa4fa4ULL;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 98) ctx->count = 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 99) ctx->func = CPACF_KIMD_SHA_512;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 100)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 101) return 0;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 102) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 103)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 104) static struct shash_alg sha384_alg = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 105) .digestsize = SHA384_DIGEST_SIZE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 106) .init = sha384_init,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 107) .update = s390_sha_update,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 108) .final = s390_sha_final,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 109) .export = sha512_export,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 110) .import = sha512_import,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 111) .descsize = sizeof(struct s390_sha_ctx),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 112) .statesize = sizeof(struct sha512_state),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 113) .base = {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 114) .cra_name = "sha384",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 115) .cra_driver_name= "sha384-s390",
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 116) .cra_priority = 300,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 117) .cra_blocksize = SHA384_BLOCK_SIZE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 118) .cra_ctxsize = sizeof(struct s390_sha_ctx),
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 119) .cra_module = THIS_MODULE,
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 120) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 121) };
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 122)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 123) MODULE_ALIAS_CRYPTO("sha384");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 124)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 125) static int __init init(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 126) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 127) int ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 128)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 129) if (!cpacf_query_func(CPACF_KIMD, CPACF_KIMD_SHA_512))
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 130) return -ENODEV;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 131) if ((ret = crypto_register_shash(&sha512_alg)) < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 132) goto out;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 133) if ((ret = crypto_register_shash(&sha384_alg)) < 0)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 134) crypto_unregister_shash(&sha512_alg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 135) out:
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 136) return ret;
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 137) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 138)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 139) static void __exit fini(void)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 140) {
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 141) crypto_unregister_shash(&sha512_alg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 142) crypto_unregister_shash(&sha384_alg);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 143) }
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 144)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 145) module_cpu_feature_match(MSA, init);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 146) module_exit(fini);
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 147)
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 148) MODULE_LICENSE("GPL");
^8f3ce5b39 (kx 2023-10-28 12:00:06 +0300 149) MODULE_DESCRIPTION("SHA512 and SHA-384 Secure Hash Algorithm");