2017-11-24 17:00:34 +03:00
// SPDX-License-Identifier: GPL-2.0+
2008-03-06 14:52:00 +03:00
/*
* Cryptographic API .
*
2008-03-06 14:53:50 +03:00
* s390 implementation of the SHA512 and SHA38 Secure Hash Algorithm .
2008-03-06 14:52:00 +03:00
*
* Copyright IBM Corp . 2007
* Author ( s ) : Jan Glauber ( jang @ de . ibm . com )
*/
2009-01-18 12:33:33 +03:00
# include <crypto/internal/hash.h>
2009-07-22 08:29:41 +04:00
# include <crypto/sha.h>
# include <linux/errno.h>
2008-03-06 14:52:00 +03:00
# include <linux/init.h>
2009-07-22 08:29:41 +04:00
# include <linux/kernel.h>
2008-03-06 14:52:00 +03:00
# include <linux/module.h>
2015-02-19 19:34:07 +03:00
# include <linux/cpufeature.h>
2016-03-17 17:22:12 +03:00
# include <asm/cpacf.h>
2008-03-06 14:52:00 +03:00
# include "sha.h"
2009-01-18 12:33:33 +03:00
static int sha512_init ( struct shash_desc * desc )
2008-03-06 14:52:00 +03:00
{
2009-01-18 12:33:33 +03:00
struct s390_sha_ctx * ctx = shash_desc_ctx ( desc ) ;
2008-03-06 14:52:00 +03:00
* ( __u64 * ) & ctx - > state [ 0 ] = 0x6a09e667f3bcc908ULL ;
* ( __u64 * ) & ctx - > state [ 2 ] = 0xbb67ae8584caa73bULL ;
* ( __u64 * ) & ctx - > state [ 4 ] = 0x3c6ef372fe94f82bULL ;
* ( __u64 * ) & ctx - > state [ 6 ] = 0xa54ff53a5f1d36f1ULL ;
* ( __u64 * ) & ctx - > state [ 8 ] = 0x510e527fade682d1ULL ;
* ( __u64 * ) & ctx - > state [ 10 ] = 0x9b05688c2b3e6c1fULL ;
* ( __u64 * ) & ctx - > state [ 12 ] = 0x1f83d9abfb41bd6bULL ;
* ( __u64 * ) & ctx - > state [ 14 ] = 0x5be0cd19137e2179ULL ;
ctx - > count = 0 ;
2016-03-17 17:22:12 +03:00
ctx - > func = CPACF_KIMD_SHA_512 ;
2009-01-18 12:33:33 +03:00
return 0 ;
2008-03-06 14:52:00 +03:00
}
2009-07-22 08:29:41 +04:00
static int sha512_export ( struct shash_desc * desc , void * out )
{
struct s390_sha_ctx * sctx = shash_desc_ctx ( desc ) ;
struct sha512_state * octx = out ;
octx - > count [ 0 ] = sctx - > count ;
octx - > count [ 1 ] = 0 ;
memcpy ( octx - > state , sctx - > state , sizeof ( octx - > state ) ) ;
memcpy ( octx - > buf , sctx - > buf , sizeof ( octx - > buf ) ) ;
return 0 ;
}
2009-09-05 10:27:35 +04:00
static int sha512_import ( struct shash_desc * desc , const void * in )
2009-07-22 08:29:41 +04:00
{
struct s390_sha_ctx * sctx = shash_desc_ctx ( desc ) ;
2009-09-05 10:27:35 +04:00
const struct sha512_state * ictx = in ;
2009-07-22 08:29:41 +04:00
if ( unlikely ( ictx - > count [ 1 ] ) )
return - ERANGE ;
sctx - > count = ictx - > count [ 0 ] ;
memcpy ( sctx - > state , ictx - > state , sizeof ( ictx - > state ) ) ;
memcpy ( sctx - > buf , ictx - > buf , sizeof ( ictx - > buf ) ) ;
2016-03-17 17:22:12 +03:00
sctx - > func = CPACF_KIMD_SHA_512 ;
2009-07-22 08:29:41 +04:00
return 0 ;
}
2009-01-18 12:33:33 +03:00
static struct shash_alg sha512_alg = {
. digestsize = SHA512_DIGEST_SIZE ,
. init = sha512_init ,
. update = s390_sha_update ,
. final = s390_sha_final ,
2009-07-22 08:29:41 +04:00
. export = sha512_export ,
. import = sha512_import ,
2009-01-18 12:33:33 +03:00
. descsize = sizeof ( struct s390_sha_ctx ) ,
2009-07-22 08:29:41 +04:00
. statesize = sizeof ( struct sha512_state ) ,
2009-01-18 12:33:33 +03:00
. base = {
. cra_name = " sha512 " ,
. cra_driver_name = " sha512-s390 " ,
2016-03-17 17:22:12 +03:00
. cra_priority = 300 ,
2009-01-18 12:33:33 +03:00
. cra_flags = CRYPTO_ALG_TYPE_SHASH ,
. cra_blocksize = SHA512_BLOCK_SIZE ,
. cra_module = THIS_MODULE ,
}
2008-03-06 14:52:00 +03:00
} ;
2014-11-21 04:05:53 +03:00
MODULE_ALIAS_CRYPTO ( " sha512 " ) ;
2008-03-06 14:53:50 +03:00
2009-01-18 12:33:33 +03:00
static int sha384_init ( struct shash_desc * desc )
2008-03-06 14:53:50 +03:00
{
2009-01-18 12:33:33 +03:00
struct s390_sha_ctx * ctx = shash_desc_ctx ( desc ) ;
2008-03-06 14:53:50 +03:00
* ( __u64 * ) & ctx - > state [ 0 ] = 0xcbbb9d5dc1059ed8ULL ;
* ( __u64 * ) & ctx - > state [ 2 ] = 0x629a292a367cd507ULL ;
* ( __u64 * ) & ctx - > state [ 4 ] = 0x9159015a3070dd17ULL ;
* ( __u64 * ) & ctx - > state [ 6 ] = 0x152fecd8f70e5939ULL ;
* ( __u64 * ) & ctx - > state [ 8 ] = 0x67332667ffc00b31ULL ;
* ( __u64 * ) & ctx - > state [ 10 ] = 0x8eb44a8768581511ULL ;
* ( __u64 * ) & ctx - > state [ 12 ] = 0xdb0c2e0d64f98fa7ULL ;
* ( __u64 * ) & ctx - > state [ 14 ] = 0x47b5481dbefa4fa4ULL ;
ctx - > count = 0 ;
2016-03-17 17:22:12 +03:00
ctx - > func = CPACF_KIMD_SHA_512 ;
2009-01-18 12:33:33 +03:00
return 0 ;
2008-03-06 14:53:50 +03:00
}
2009-01-18 12:33:33 +03:00
static struct shash_alg sha384_alg = {
. digestsize = SHA384_DIGEST_SIZE ,
. init = sha384_init ,
. update = s390_sha_update ,
. final = s390_sha_final ,
2009-07-22 08:29:41 +04:00
. export = sha512_export ,
. import = sha512_import ,
2009-01-18 12:33:33 +03:00
. descsize = sizeof ( struct s390_sha_ctx ) ,
2009-07-22 08:29:41 +04:00
. statesize = sizeof ( struct sha512_state ) ,
2009-01-18 12:33:33 +03:00
. base = {
. cra_name = " sha384 " ,
. cra_driver_name = " sha384-s390 " ,
2016-03-17 17:22:12 +03:00
. cra_priority = 300 ,
2009-01-18 12:33:33 +03:00
. cra_flags = CRYPTO_ALG_TYPE_SHASH ,
2009-03-21 16:12:19 +03:00
. cra_blocksize = SHA384_BLOCK_SIZE ,
2009-01-18 12:33:33 +03:00
. cra_ctxsize = sizeof ( struct s390_sha_ctx ) ,
. cra_module = THIS_MODULE ,
}
2008-03-06 14:53:50 +03:00
} ;
2014-11-21 04:05:53 +03:00
MODULE_ALIAS_CRYPTO ( " sha384 " ) ;
2008-03-06 14:53:50 +03:00
2008-03-06 14:52:00 +03:00
static int __init init ( void )
{
2008-03-06 14:53:50 +03:00
int ret ;
2016-08-18 13:59:46 +03:00
if ( ! cpacf_query_func ( CPACF_KIMD , CPACF_KIMD_SHA_512 ) )
2008-03-06 14:52:00 +03:00
return - EOPNOTSUPP ;
2009-01-18 12:33:33 +03:00
if ( ( ret = crypto_register_shash ( & sha512_alg ) ) < 0 )
2008-03-06 14:53:50 +03:00
goto out ;
2009-01-18 12:33:33 +03:00
if ( ( ret = crypto_register_shash ( & sha384_alg ) ) < 0 )
crypto_unregister_shash ( & sha512_alg ) ;
2008-03-06 14:53:50 +03:00
out :
return ret ;
2008-03-06 14:52:00 +03:00
}
static void __exit fini ( void )
{
2009-01-18 12:33:33 +03:00
crypto_unregister_shash ( & sha512_alg ) ;
crypto_unregister_shash ( & sha384_alg ) ;
2008-03-06 14:52:00 +03:00
}
2015-02-19 19:34:07 +03:00
module_cpu_feature_match ( MSA , init ) ;
2008-03-06 14:52:00 +03:00
module_exit ( fini ) ;
MODULE_LICENSE ( " GPL " ) ;
2008-03-06 14:53:50 +03:00
MODULE_DESCRIPTION ( " SHA512 and SHA-384 Secure Hash Algorithm " ) ;