diff options
-rw-r--r-- | drivers/crypto/nx/nx-aes-cbc.c | 56 |
1 files changed, 33 insertions, 23 deletions
diff --git a/drivers/crypto/nx/nx-aes-cbc.c b/drivers/crypto/nx/nx-aes-cbc.c index a9e76c6c37d8..cc00b52306ba 100644 --- a/drivers/crypto/nx/nx-aes-cbc.c +++ b/drivers/crypto/nx/nx-aes-cbc.c | |||
@@ -71,39 +71,49 @@ static int cbc_aes_nx_crypt(struct blkcipher_desc *desc, | |||
71 | struct nx_crypto_ctx *nx_ctx = crypto_blkcipher_ctx(desc->tfm); | 71 | struct nx_crypto_ctx *nx_ctx = crypto_blkcipher_ctx(desc->tfm); |
72 | struct nx_csbcpb *csbcpb = nx_ctx->csbcpb; | 72 | struct nx_csbcpb *csbcpb = nx_ctx->csbcpb; |
73 | unsigned long irq_flags; | 73 | unsigned long irq_flags; |
74 | unsigned int processed = 0, to_process; | ||
75 | u32 max_sg_len; | ||
74 | int rc; | 76 | int rc; |
75 | 77 | ||
76 | spin_lock_irqsave(&nx_ctx->lock, irq_flags); | 78 | spin_lock_irqsave(&nx_ctx->lock, irq_flags); |
77 | 79 | ||
78 | if (nbytes > nx_ctx->ap->databytelen) { | 80 | max_sg_len = min_t(u32, nx_driver.of.max_sg_len/sizeof(struct nx_sg), |
79 | rc = -EINVAL; | 81 | nx_ctx->ap->sglen); |
80 | goto out; | ||
81 | } | ||
82 | 82 | ||
83 | if (enc) | 83 | if (enc) |
84 | NX_CPB_FDM(csbcpb) |= NX_FDM_ENDE_ENCRYPT; | 84 | NX_CPB_FDM(csbcpb) |= NX_FDM_ENDE_ENCRYPT; |
85 | else | 85 | else |
86 | NX_CPB_FDM(csbcpb) &= ~NX_FDM_ENDE_ENCRYPT; | 86 | NX_CPB_FDM(csbcpb) &= ~NX_FDM_ENDE_ENCRYPT; |
87 | 87 | ||
88 | rc = nx_build_sg_lists(nx_ctx, desc, dst, src, nbytes, 0, | 88 | do { |
89 | csbcpb->cpb.aes_cbc.iv); | 89 | to_process = min_t(u64, nbytes - processed, |
90 | if (rc) | 90 | nx_ctx->ap->databytelen); |
91 | goto out; | 91 | to_process = min_t(u64, to_process, |
92 | 92 | NX_PAGE_SIZE * (max_sg_len - 1)); | |
93 | if (!nx_ctx->op.inlen || !nx_ctx->op.outlen) { | 93 | to_process = to_process & ~(AES_BLOCK_SIZE - 1); |
94 | rc = -EINVAL; | 94 | |
95 | goto out; | 95 | rc = nx_build_sg_lists(nx_ctx, desc, dst, src, to_process, |
96 | } | 96 | processed, csbcpb->cpb.aes_cbc.iv); |
97 | 97 | if (rc) | |
98 | rc = nx_hcall_sync(nx_ctx, &nx_ctx->op, | 98 | goto out; |
99 | desc->flags & CRYPTO_TFM_REQ_MAY_SLEEP); | 99 | |
100 | if (rc) | 100 | if (!nx_ctx->op.inlen || !nx_ctx->op.outlen) { |
101 | goto out; | 101 | rc = -EINVAL; |
102 | 102 | goto out; | |
103 | memcpy(desc->info, csbcpb->cpb.aes_cbc.cv, AES_BLOCK_SIZE); | 103 | } |
104 | atomic_inc(&(nx_ctx->stats->aes_ops)); | 104 | |
105 | atomic64_add(csbcpb->csb.processed_byte_count, | 105 | rc = nx_hcall_sync(nx_ctx, &nx_ctx->op, |
106 | &(nx_ctx->stats->aes_bytes)); | 106 | desc->flags & CRYPTO_TFM_REQ_MAY_SLEEP); |
107 | if (rc) | ||
108 | goto out; | ||
109 | |||
110 | memcpy(desc->info, csbcpb->cpb.aes_cbc.cv, AES_BLOCK_SIZE); | ||
111 | atomic_inc(&(nx_ctx->stats->aes_ops)); | ||
112 | atomic64_add(csbcpb->csb.processed_byte_count, | ||
113 | &(nx_ctx->stats->aes_bytes)); | ||
114 | |||
115 | processed += to_process; | ||
116 | } while (processed < nbytes); | ||
107 | out: | 117 | out: |
108 | spin_unlock_irqrestore(&nx_ctx->lock, irq_flags); | 118 | spin_unlock_irqrestore(&nx_ctx->lock, irq_flags); |
109 | return rc; | 119 | return rc; |