Skip to content

Commit

Permalink
crypto: omap-aes - Add fallback support
Browse files Browse the repository at this point in the history
As setting up the DMA operations is quite costly, add software fallback
support for requests smaller than 200 bytes. This change gives some 10%
extra performance in ipsec use case.

Signed-off-by: Lokesh Vutla <[email protected]>
[[email protected]: udpated against latest upstream, to use skcipher mainly]
Signed-off-by: Tero Kristo <[email protected]>
Signed-off-by: Herbert Xu <[email protected]>
  • Loading branch information
lokeshvutla authored and herbertx committed Sep 13, 2016
1 parent 164f3ef commit 9fcb191
Show file tree
Hide file tree
Showing 2 changed files with 52 additions and 4 deletions.
3 changes: 3 additions & 0 deletions drivers/crypto/Kconfig
Original file line number Diff line number Diff line change
Expand Up @@ -318,6 +318,9 @@ config CRYPTO_DEV_OMAP_AES
select CRYPTO_AES
select CRYPTO_BLKCIPHER
select CRYPTO_ENGINE
select CRYPTO_CBC
select CRYPTO_ECB
select CRYPTO_CTR
help
OMAP processors have AES module accelerator. Select this if you
want to use the OMAP module for AES algorithms.
Expand Down
53 changes: 49 additions & 4 deletions drivers/crypto/omap-aes.c
Original file line number Diff line number Diff line change
Expand Up @@ -35,8 +35,8 @@
#include <linux/interrupt.h>
#include <crypto/scatterwalk.h>
#include <crypto/aes.h>
#include <crypto/algapi.h>
#include <crypto/engine.h>
#include <crypto/internal/skcipher.h>

#define DST_MAXBURST 4
#define DMA_MIN (DST_MAXBURST * sizeof(u32))
Expand Down Expand Up @@ -106,6 +106,7 @@ struct omap_aes_ctx {
int keylen;
u32 key[AES_KEYSIZE_256 / sizeof(u32)];
unsigned long flags;
struct crypto_skcipher *fallback;
};

struct omap_aes_reqctx {
Expand Down Expand Up @@ -702,11 +703,29 @@ static int omap_aes_crypt(struct ablkcipher_request *req, unsigned long mode)
crypto_ablkcipher_reqtfm(req));
struct omap_aes_reqctx *rctx = ablkcipher_request_ctx(req);
struct omap_aes_dev *dd;
int ret;

pr_debug("nbytes: %d, enc: %d, cbc: %d\n", req->nbytes,
!!(mode & FLAGS_ENCRYPT),
!!(mode & FLAGS_CBC));

if (req->nbytes < 200) {
SKCIPHER_REQUEST_ON_STACK(subreq, ctx->fallback);

skcipher_request_set_tfm(subreq, ctx->fallback);
skcipher_request_set_callback(subreq, req->base.flags, NULL,
NULL);
skcipher_request_set_crypt(subreq, req->src, req->dst,
req->nbytes, req->info);

if (mode & FLAGS_ENCRYPT)
ret = crypto_skcipher_encrypt(subreq);
else
ret = crypto_skcipher_decrypt(subreq);

skcipher_request_zero(subreq);
return ret;
}
dd = omap_aes_find_dev(ctx);
if (!dd)
return -ENODEV;
Expand All @@ -722,6 +741,7 @@ static int omap_aes_setkey(struct crypto_ablkcipher *tfm, const u8 *key,
unsigned int keylen)
{
struct omap_aes_ctx *ctx = crypto_ablkcipher_ctx(tfm);
int ret;

if (keylen != AES_KEYSIZE_128 && keylen != AES_KEYSIZE_192 &&
keylen != AES_KEYSIZE_256)
Expand All @@ -732,6 +752,14 @@ static int omap_aes_setkey(struct crypto_ablkcipher *tfm, const u8 *key,
memcpy(ctx->key, key, keylen);
ctx->keylen = keylen;

crypto_skcipher_clear_flags(ctx->fallback, CRYPTO_TFM_REQ_MASK);
crypto_skcipher_set_flags(ctx->fallback, tfm->base.crt_flags &
CRYPTO_TFM_REQ_MASK);

ret = crypto_skcipher_setkey(ctx->fallback, key, keylen);
if (!ret)
return 0;

return 0;
}

Expand Down Expand Up @@ -767,13 +795,30 @@ static int omap_aes_ctr_decrypt(struct ablkcipher_request *req)

static int omap_aes_cra_init(struct crypto_tfm *tfm)
{
const char *name = crypto_tfm_alg_name(tfm);
const u32 flags = CRYPTO_ALG_ASYNC | CRYPTO_ALG_NEED_FALLBACK;
struct omap_aes_ctx *ctx = crypto_tfm_ctx(tfm);
struct crypto_skcipher *blk;

blk = crypto_alloc_skcipher(name, 0, flags);
if (IS_ERR(blk))
return PTR_ERR(blk);

ctx->fallback = blk;

tfm->crt_ablkcipher.reqsize = sizeof(struct omap_aes_reqctx);

return 0;
}

static void omap_aes_cra_exit(struct crypto_tfm *tfm)
{
struct omap_aes_ctx *ctx = crypto_tfm_ctx(tfm);

if (ctx->fallback)
crypto_free_skcipher(ctx->fallback);

ctx->fallback = NULL;
}

/* ********************** ALGS ************************************ */
Expand All @@ -785,7 +830,7 @@ static struct crypto_alg algs_ecb_cbc[] = {
.cra_priority = 300,
.cra_flags = CRYPTO_ALG_TYPE_ABLKCIPHER |
CRYPTO_ALG_KERN_DRIVER_ONLY |
CRYPTO_ALG_ASYNC,
CRYPTO_ALG_ASYNC | CRYPTO_ALG_NEED_FALLBACK,
.cra_blocksize = AES_BLOCK_SIZE,
.cra_ctxsize = sizeof(struct omap_aes_ctx),
.cra_alignmask = 0,
Expand All @@ -807,7 +852,7 @@ static struct crypto_alg algs_ecb_cbc[] = {
.cra_priority = 300,
.cra_flags = CRYPTO_ALG_TYPE_ABLKCIPHER |
CRYPTO_ALG_KERN_DRIVER_ONLY |
CRYPTO_ALG_ASYNC,
CRYPTO_ALG_ASYNC | CRYPTO_ALG_NEED_FALLBACK,
.cra_blocksize = AES_BLOCK_SIZE,
.cra_ctxsize = sizeof(struct omap_aes_ctx),
.cra_alignmask = 0,
Expand All @@ -833,7 +878,7 @@ static struct crypto_alg algs_ctr[] = {
.cra_priority = 300,
.cra_flags = CRYPTO_ALG_TYPE_ABLKCIPHER |
CRYPTO_ALG_KERN_DRIVER_ONLY |
CRYPTO_ALG_ASYNC,
CRYPTO_ALG_ASYNC | CRYPTO_ALG_NEED_FALLBACK,
.cra_blocksize = AES_BLOCK_SIZE,
.cra_ctxsize = sizeof(struct omap_aes_ctx),
.cra_alignmask = 0,
Expand Down

0 comments on commit 9fcb191

Please sign in to comment.