diff options
-rw-r--r-- | arch/s390/crypto/des_s390.c | 217 |
1 files changed, 210 insertions, 7 deletions
diff --git a/arch/s390/crypto/des_s390.c b/arch/s390/crypto/des_s390.c index f090c3c2745b..e3c37aa0a199 100644 --- a/arch/s390/crypto/des_s390.c +++ b/arch/s390/crypto/des_s390.c @@ -57,18 +57,79 @@ static int des_setkey(void *ctx, const u8 *key, unsigned int keylen, return ret; } -static void des_encrypt(void *ctx, u8 *dst, const u8 *src) +static void des_encrypt(void *ctx, u8 *out, const u8 *in) { struct crypt_s390_des_ctx *dctx = ctx; - crypt_s390_km(KM_DEA_ENCRYPT, dctx->key, dst, src, DES_BLOCK_SIZE); + crypt_s390_km(KM_DEA_ENCRYPT, dctx->key, out, in, DES_BLOCK_SIZE); } -static void des_decrypt(void *ctx, u8 *dst, const u8 *src) +static void des_decrypt(void *ctx, u8 *out, const u8 *in) { struct crypt_s390_des_ctx *dctx = ctx; - crypt_s390_km(KM_DEA_DECRYPT, dctx->key, dst, src, DES_BLOCK_SIZE); + crypt_s390_km(KM_DEA_DECRYPT, dctx->key, out, in, DES_BLOCK_SIZE); +} + +static unsigned int des_encrypt_ecb(const struct cipher_desc *desc, u8 *out, + const u8 *in, unsigned int nbytes) +{ + struct crypt_s390_des_ctx *sctx = crypto_tfm_ctx(desc->tfm); + int ret; + + /* only use complete blocks */ + nbytes &= ~(DES_BLOCK_SIZE - 1); + ret = crypt_s390_km(KM_DEA_ENCRYPT, sctx->key, out, in, nbytes); + BUG_ON((ret < 0) || (ret != nbytes)); + + return nbytes; +} + +static unsigned int des_decrypt_ecb(const struct cipher_desc *desc, u8 *out, + const u8 *in, unsigned int nbytes) +{ + struct crypt_s390_des_ctx *sctx = crypto_tfm_ctx(desc->tfm); + int ret; + + /* only use complete blocks */ + nbytes &= ~(DES_BLOCK_SIZE - 1); + ret = crypt_s390_km(KM_DEA_DECRYPT, sctx->key, out, in, nbytes); + BUG_ON((ret < 0) || (ret != nbytes)); + + return nbytes; +} + +static unsigned int des_encrypt_cbc(const struct cipher_desc *desc, u8 *out, + const u8 *in, unsigned int nbytes) +{ + struct crypt_s390_des_ctx *sctx = crypto_tfm_ctx(desc->tfm); + int ret; + + /* only use complete blocks */ + nbytes &= ~(DES_BLOCK_SIZE - 1); + + memcpy(sctx->iv, desc->info, DES_BLOCK_SIZE); + ret = crypt_s390_kmc(KMC_DEA_ENCRYPT, &sctx->iv, out, in, nbytes); + BUG_ON((ret < 0) || (ret != nbytes)); + + memcpy(desc->info, sctx->iv, DES_BLOCK_SIZE); + return nbytes; +} + +static unsigned int des_decrypt_cbc(const struct cipher_desc *desc, u8 *out, + const u8 *in, unsigned int nbytes) +{ + struct crypt_s390_des_ctx *sctx = crypto_tfm_ctx(desc->tfm); + int ret; + + /* only use complete blocks */ + nbytes &= ~(DES_BLOCK_SIZE - 1); + + memcpy(&sctx->iv, desc->info, DES_BLOCK_SIZE); + ret = crypt_s390_kmc(KMC_DEA_DECRYPT, &sctx->iv, out, in, nbytes); + BUG_ON((ret < 0) || (ret != nbytes)); + + return nbytes; } static struct crypto_alg des_alg = { @@ -84,7 +145,11 @@ static struct crypto_alg des_alg = { .cia_max_keysize = DES_KEY_SIZE, .cia_setkey = des_setkey, .cia_encrypt = des_encrypt, - .cia_decrypt = des_decrypt + .cia_decrypt = des_decrypt, + .cia_encrypt_ecb = des_encrypt_ecb, + .cia_decrypt_ecb = des_decrypt_ecb, + .cia_encrypt_cbc = des_encrypt_cbc, + .cia_decrypt_cbc = des_decrypt_cbc, } } }; @@ -137,6 +202,71 @@ static void des3_128_decrypt(void *ctx, u8 *dst, const u8 *src) DES3_128_BLOCK_SIZE); } +static unsigned int des3_128_encrypt_ecb(const struct cipher_desc *desc, + u8 *out, const u8 *in, + unsigned int nbytes) +{ + struct crypt_s390_des3_128_ctx *sctx = crypto_tfm_ctx(desc->tfm); + int ret; + + /* only use complete blocks */ + nbytes &= ~(DES3_128_BLOCK_SIZE - 1); + ret = crypt_s390_km(KM_TDEA_128_ENCRYPT, sctx->key, out, in, nbytes); + BUG_ON((ret < 0) || (ret != nbytes)); + + return nbytes; +} + +static unsigned int des3_128_decrypt_ecb(const struct cipher_desc *desc, + u8 *out, const u8 *in, + unsigned int nbytes) +{ + struct crypt_s390_des3_128_ctx *sctx = crypto_tfm_ctx(desc->tfm); + int ret; + + /* only use complete blocks */ + nbytes &= ~(DES3_128_BLOCK_SIZE - 1); + ret = crypt_s390_km(KM_TDEA_128_DECRYPT, sctx->key, out, in, nbytes); + BUG_ON((ret < 0) || (ret != nbytes)); + + return nbytes; +} + +static unsigned int des3_128_encrypt_cbc(const struct cipher_desc *desc, + u8 *out, const u8 *in, + unsigned int nbytes) +{ + struct crypt_s390_des3_128_ctx *sctx = crypto_tfm_ctx(desc->tfm); + int ret; + + /* only use complete blocks */ + nbytes &= ~(DES3_128_BLOCK_SIZE - 1); + + memcpy(sctx->iv, desc->info, DES3_128_BLOCK_SIZE); + ret = crypt_s390_kmc(KMC_TDEA_128_ENCRYPT, &sctx->iv, out, in, nbytes); + BUG_ON((ret < 0) || (ret != nbytes)); + + memcpy(desc->info, sctx->iv, DES3_128_BLOCK_SIZE); + return nbytes; +} + +static unsigned int des3_128_decrypt_cbc(const struct cipher_desc *desc, + u8 *out, const u8 *in, + unsigned int nbytes) +{ + struct crypt_s390_des3_128_ctx *sctx = crypto_tfm_ctx(desc->tfm); + int ret; + + /* only use complete blocks */ + nbytes &= ~(DES3_128_BLOCK_SIZE - 1); + + memcpy(&sctx->iv, desc->info, DES3_128_BLOCK_SIZE); + ret = crypt_s390_kmc(KMC_TDEA_128_DECRYPT, &sctx->iv, out, in, nbytes); + BUG_ON((ret < 0) || (ret != nbytes)); + + return nbytes; +} + static struct crypto_alg des3_128_alg = { .cra_name = "des3_ede128", .cra_flags = CRYPTO_ALG_TYPE_CIPHER, @@ -150,7 +280,11 @@ static struct crypto_alg des3_128_alg = { .cia_max_keysize = DES3_128_KEY_SIZE, .cia_setkey = des3_128_setkey, .cia_encrypt = des3_128_encrypt, - .cia_decrypt = des3_128_decrypt + .cia_decrypt = des3_128_decrypt, + .cia_encrypt_ecb = des3_128_encrypt_ecb, + .cia_decrypt_ecb = des3_128_decrypt_ecb, + .cia_encrypt_cbc = des3_128_encrypt_cbc, + .cia_decrypt_cbc = des3_128_decrypt_cbc, } } }; @@ -207,6 +341,71 @@ static void des3_192_decrypt(void *ctx, u8 *dst, const u8 *src) DES3_192_BLOCK_SIZE); } +static unsigned int des3_192_encrypt_ecb(const struct cipher_desc *desc, + u8 *out, const u8 *in, + unsigned int nbytes) +{ + struct crypt_s390_des3_192_ctx *sctx = crypto_tfm_ctx(desc->tfm); + int ret; + + /* only use complete blocks */ + nbytes &= ~(DES3_192_BLOCK_SIZE - 1); + ret = crypt_s390_km(KM_TDEA_192_ENCRYPT, sctx->key, out, in, nbytes); + BUG_ON((ret < 0) || (ret != nbytes)); + + return nbytes; +} + +static unsigned int des3_192_decrypt_ecb(const struct cipher_desc *desc, + u8 *out, const u8 *in, + unsigned int nbytes) +{ + struct crypt_s390_des3_192_ctx *sctx = crypto_tfm_ctx(desc->tfm); + int ret; + + /* only use complete blocks */ + nbytes &= ~(DES3_192_BLOCK_SIZE - 1); + ret = crypt_s390_km(KM_TDEA_192_DECRYPT, sctx->key, out, in, nbytes); + BUG_ON((ret < 0) || (ret != nbytes)); + + return nbytes; +} + +static unsigned int des3_192_encrypt_cbc(const struct cipher_desc *desc, + u8 *out, const u8 *in, + unsigned int nbytes) +{ + struct crypt_s390_des3_192_ctx *sctx = crypto_tfm_ctx(desc->tfm); + int ret; + + /* only use complete blocks */ + nbytes &= ~(DES3_192_BLOCK_SIZE - 1); + + memcpy(sctx->iv, desc->info, DES3_192_BLOCK_SIZE); + ret = crypt_s390_kmc(KMC_TDEA_192_ENCRYPT, &sctx->iv, out, in, nbytes); + BUG_ON((ret < 0) || (ret != nbytes)); + + memcpy(desc->info, sctx->iv, DES3_192_BLOCK_SIZE); + return nbytes; +} + +static unsigned int des3_192_decrypt_cbc(const struct cipher_desc *desc, + u8 *out, const u8 *in, + unsigned int nbytes) +{ + struct crypt_s390_des3_192_ctx *sctx = crypto_tfm_ctx(desc->tfm); + int ret; + + /* only use complete blocks */ + nbytes &= ~(DES3_192_BLOCK_SIZE - 1); + + memcpy(&sctx->iv, desc->info, DES3_192_BLOCK_SIZE); + ret = crypt_s390_kmc(KMC_TDEA_192_DECRYPT, &sctx->iv, out, in, nbytes); + BUG_ON((ret < 0) || (ret != nbytes)); + + return nbytes; +} + static struct crypto_alg des3_192_alg = { .cra_name = "des3_ede", .cra_flags = CRYPTO_ALG_TYPE_CIPHER, @@ -220,7 +419,11 @@ static struct crypto_alg des3_192_alg = { .cia_max_keysize = DES3_192_KEY_SIZE, .cia_setkey = des3_192_setkey, .cia_encrypt = des3_192_encrypt, - .cia_decrypt = des3_192_decrypt + .cia_decrypt = des3_192_decrypt, + .cia_encrypt_ecb = des3_192_encrypt_ecb, + .cia_decrypt_ecb = des3_192_decrypt_ecb, + .cia_encrypt_cbc = des3_192_encrypt_cbc, + .cia_decrypt_cbc = des3_192_decrypt_cbc, } } }; |