Back to home page

OSCL-LXR

 
 

    


0001 // SPDX-License-Identifier: GPL-2.0+
0002 /*
0003  * Cryptographic API.
0004  *
0005  * s390 implementation of the SHA512 and SHA384 Secure Hash Algorithm.
0006  *
0007  * Copyright IBM Corp. 2019
0008  * Author(s): Joerg Schmidbauer (jschmidb@de.ibm.com)
0009  */
0010 #include <crypto/internal/hash.h>
0011 #include <linux/init.h>
0012 #include <linux/module.h>
0013 #include <linux/cpufeature.h>
0014 #include <crypto/sha3.h>
0015 #include <asm/cpacf.h>
0016 
0017 #include "sha.h"
0018 
0019 static int sha3_512_init(struct shash_desc *desc)
0020 {
0021     struct s390_sha_ctx *sctx = shash_desc_ctx(desc);
0022 
0023     memset(sctx->state, 0, sizeof(sctx->state));
0024     sctx->count = 0;
0025     sctx->func = CPACF_KIMD_SHA3_512;
0026 
0027     return 0;
0028 }
0029 
0030 static int sha3_512_export(struct shash_desc *desc, void *out)
0031 {
0032     struct s390_sha_ctx *sctx = shash_desc_ctx(desc);
0033     struct sha3_state *octx = out;
0034 
0035     octx->rsiz = sctx->count;
0036     octx->rsizw = sctx->count >> 32;
0037 
0038     memcpy(octx->st, sctx->state, sizeof(octx->st));
0039     memcpy(octx->buf, sctx->buf, sizeof(octx->buf));
0040 
0041     return 0;
0042 }
0043 
0044 static int sha3_512_import(struct shash_desc *desc, const void *in)
0045 {
0046     struct s390_sha_ctx *sctx = shash_desc_ctx(desc);
0047     const struct sha3_state *ictx = in;
0048 
0049     if (unlikely(ictx->rsizw))
0050         return -ERANGE;
0051     sctx->count = ictx->rsiz;
0052 
0053     memcpy(sctx->state, ictx->st, sizeof(ictx->st));
0054     memcpy(sctx->buf, ictx->buf, sizeof(ictx->buf));
0055     sctx->func = CPACF_KIMD_SHA3_512;
0056 
0057     return 0;
0058 }
0059 
0060 static int sha3_384_import(struct shash_desc *desc, const void *in)
0061 {
0062     struct s390_sha_ctx *sctx = shash_desc_ctx(desc);
0063     const struct sha3_state *ictx = in;
0064 
0065     if (unlikely(ictx->rsizw))
0066         return -ERANGE;
0067     sctx->count = ictx->rsiz;
0068 
0069     memcpy(sctx->state, ictx->st, sizeof(ictx->st));
0070     memcpy(sctx->buf, ictx->buf, sizeof(ictx->buf));
0071     sctx->func = CPACF_KIMD_SHA3_384;
0072 
0073     return 0;
0074 }
0075 
0076 static struct shash_alg sha3_512_alg = {
0077     .digestsize =   SHA3_512_DIGEST_SIZE,
0078     .init       =   sha3_512_init,
0079     .update     =   s390_sha_update,
0080     .final      =   s390_sha_final,
0081     .export     =   sha3_512_export,
0082     .import     =   sha3_512_import,
0083     .descsize   =   sizeof(struct s390_sha_ctx),
0084     .statesize  =   sizeof(struct sha3_state),
0085     .base       =   {
0086         .cra_name    =  "sha3-512",
0087         .cra_driver_name =  "sha3-512-s390",
0088         .cra_priority    =  300,
0089         .cra_blocksize   =  SHA3_512_BLOCK_SIZE,
0090         .cra_module  =  THIS_MODULE,
0091     }
0092 };
0093 
0094 MODULE_ALIAS_CRYPTO("sha3-512");
0095 
0096 static int sha3_384_init(struct shash_desc *desc)
0097 {
0098     struct s390_sha_ctx *sctx = shash_desc_ctx(desc);
0099 
0100     memset(sctx->state, 0, sizeof(sctx->state));
0101     sctx->count = 0;
0102     sctx->func = CPACF_KIMD_SHA3_384;
0103 
0104     return 0;
0105 }
0106 
0107 static struct shash_alg sha3_384_alg = {
0108     .digestsize =   SHA3_384_DIGEST_SIZE,
0109     .init       =   sha3_384_init,
0110     .update     =   s390_sha_update,
0111     .final      =   s390_sha_final,
0112     .export     =   sha3_512_export, /* same as for 512 */
0113     .import     =   sha3_384_import, /* function code different! */
0114     .descsize   =   sizeof(struct s390_sha_ctx),
0115     .statesize  =   sizeof(struct sha3_state),
0116     .base       =   {
0117         .cra_name    =  "sha3-384",
0118         .cra_driver_name =  "sha3-384-s390",
0119         .cra_priority    =  300,
0120         .cra_blocksize   =  SHA3_384_BLOCK_SIZE,
0121         .cra_ctxsize     =  sizeof(struct s390_sha_ctx),
0122         .cra_module  =  THIS_MODULE,
0123     }
0124 };
0125 
0126 MODULE_ALIAS_CRYPTO("sha3-384");
0127 
0128 static int __init init(void)
0129 {
0130     int ret;
0131 
0132     if (!cpacf_query_func(CPACF_KIMD, CPACF_KIMD_SHA3_512))
0133         return -ENODEV;
0134     ret = crypto_register_shash(&sha3_512_alg);
0135     if (ret < 0)
0136         goto out;
0137     ret = crypto_register_shash(&sha3_384_alg);
0138     if (ret < 0)
0139         crypto_unregister_shash(&sha3_512_alg);
0140 out:
0141     return ret;
0142 }
0143 
0144 static void __exit fini(void)
0145 {
0146     crypto_unregister_shash(&sha3_512_alg);
0147     crypto_unregister_shash(&sha3_384_alg);
0148 }
0149 
0150 module_cpu_feature_match(S390_CPU_FEATURE_MSA, init);
0151 module_exit(fini);
0152 
0153 MODULE_LICENSE("GPL");
0154 MODULE_DESCRIPTION("SHA3-512 and SHA3-384 Secure Hash Algorithm");