diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2011-05-21 02:24:14 +0200 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2011-05-21 02:24:14 +0200 |
commit | 052497553e5dedc04c43800820c1d5788201cc71 (patch) | |
tree | 952466fc0f0df2b44b8df6b087c944ddf890f709 /drivers/crypto/picoxcell_crypto.c | |
parent | Fix for buffer overflow in ldm_frag_add not sufficient (diff) | |
parent | crypto: caam - add support for sha512 variants of existing AEAD algorithms (diff) | |
download | linux-052497553e5dedc04c43800820c1d5788201cc71.tar.xz linux-052497553e5dedc04c43800820c1d5788201cc71.zip |
Merge git://git.kernel.org/pub/scm/linux/kernel/git/herbert/crypto-2.6
* git://git.kernel.org/pub/scm/linux/kernel/git/herbert/crypto-2.6: (45 commits)
crypto: caam - add support for sha512 variants of existing AEAD algorithms
crypto: caam - remove unused authkeylen from caam_ctx
crypto: caam - fix decryption shared vs. non-shared key setting
crypto: caam - platform_bus_type migration
crypto: aesni-intel - fix aesni build on i386
crypto: aesni-intel - Merge with fpu.ko
crypto: mv_cesa - make count_sgs() null-pointer proof
crypto: mv_cesa - copy remaining bytes to SRAM only when needed
crypto: mv_cesa - move digest state initialisation to a better place
crypto: mv_cesa - fill inner/outer IV fields only in HMAC case
crypto: mv_cesa - refactor copy_src_to_buf()
crypto: mv_cesa - no need to save digest state after the last chunk
crypto: mv_cesa - print a warning when registration of AES algos fail
crypto: mv_cesa - drop this call to mv_hash_final from mv_hash_finup
crypto: mv_cesa - the descriptor pointer register needs to be set just once
crypto: mv_cesa - use ablkcipher_request_cast instead of the manual container_of
crypto: caam - fix printk recursion for long error texts
crypto: caam - remove unused keylen from session context
hwrng: amd - enable AMD hw rnd driver for Maple PPC boards
hwrng: amd - manage resource allocation
...
Diffstat (limited to 'drivers/crypto/picoxcell_crypto.c')
-rw-r--r-- | drivers/crypto/picoxcell_crypto.c | 64 |
1 files changed, 35 insertions, 29 deletions
diff --git a/drivers/crypto/picoxcell_crypto.c b/drivers/crypto/picoxcell_crypto.c index b092d0a65837..230b5b8cda1f 100644 --- a/drivers/crypto/picoxcell_crypto.c +++ b/drivers/crypto/picoxcell_crypto.c @@ -176,6 +176,8 @@ struct spacc_aead_ctx { u8 salt[AES_BLOCK_SIZE]; }; +static int spacc_ablk_submit(struct spacc_req *req); + static inline struct spacc_alg *to_spacc_alg(struct crypto_alg *alg) { return alg ? container_of(alg, struct spacc_alg, alg) : NULL; @@ -666,6 +668,24 @@ static int spacc_aead_submit(struct spacc_req *req) return -EINPROGRESS; } +static int spacc_req_submit(struct spacc_req *req); + +static void spacc_push(struct spacc_engine *engine) +{ + struct spacc_req *req; + + while (!list_empty(&engine->pending) && + engine->in_flight + 1 <= engine->fifo_sz) { + + ++engine->in_flight; + req = list_first_entry(&engine->pending, struct spacc_req, + list); + list_move_tail(&req->list, &engine->in_progress); + + req->result = spacc_req_submit(req); + } +} + /* * Setup an AEAD request for processing. This will configure the engine, load * the context and then start the packet processing. @@ -698,7 +718,8 @@ static int spacc_aead_setup(struct aead_request *req, u8 *giv, err = -EINPROGRESS; spin_lock_irqsave(&engine->hw_lock, flags); - if (unlikely(spacc_fifo_cmd_full(engine))) { + if (unlikely(spacc_fifo_cmd_full(engine)) || + engine->in_flight + 1 > engine->fifo_sz) { if (!(req->base.flags & CRYPTO_TFM_REQ_MAY_BACKLOG)) { err = -EBUSY; spin_unlock_irqrestore(&engine->hw_lock, flags); @@ -706,9 +727,8 @@ static int spacc_aead_setup(struct aead_request *req, u8 *giv, } list_add_tail(&dev_req->list, &engine->pending); } else { - ++engine->in_flight; - list_add_tail(&dev_req->list, &engine->in_progress); - spacc_aead_submit(dev_req); + list_add_tail(&dev_req->list, &engine->pending); + spacc_push(engine); } spin_unlock_irqrestore(&engine->hw_lock, flags); @@ -1041,7 +1061,8 @@ static int spacc_ablk_setup(struct ablkcipher_request *req, unsigned alg_type, * we either stick it on the end of a pending list if we can backlog, * or bailout with an error if not. */ - if (unlikely(spacc_fifo_cmd_full(engine))) { + if (unlikely(spacc_fifo_cmd_full(engine)) || + engine->in_flight + 1 > engine->fifo_sz) { if (!(req->base.flags & CRYPTO_TFM_REQ_MAY_BACKLOG)) { err = -EBUSY; spin_unlock_irqrestore(&engine->hw_lock, flags); @@ -1049,9 +1070,8 @@ static int spacc_ablk_setup(struct ablkcipher_request *req, unsigned alg_type, } list_add_tail(&dev_req->list, &engine->pending); } else { - ++engine->in_flight; - list_add_tail(&dev_req->list, &engine->in_progress); - spacc_ablk_submit(dev_req); + list_add_tail(&dev_req->list, &engine->pending); + spacc_push(engine); } spin_unlock_irqrestore(&engine->hw_lock, flags); @@ -1139,6 +1159,7 @@ static void spacc_process_done(struct spacc_engine *engine) req = list_first_entry(&engine->in_progress, struct spacc_req, list); list_move_tail(&req->list, &engine->completed); + --engine->in_flight; /* POP the status register. */ writel(~0, engine->regs + SPA_STAT_POP_REG_OFFSET); @@ -1208,36 +1229,21 @@ static void spacc_spacc_complete(unsigned long data) struct spacc_engine *engine = (struct spacc_engine *)data; struct spacc_req *req, *tmp; unsigned long flags; - int num_removed = 0; LIST_HEAD(completed); spin_lock_irqsave(&engine->hw_lock, flags); + list_splice_init(&engine->completed, &completed); + spacc_push(engine); + if (engine->in_flight) + mod_timer(&engine->packet_timeout, jiffies + PACKET_TIMEOUT); + spin_unlock_irqrestore(&engine->hw_lock, flags); list_for_each_entry_safe(req, tmp, &completed, list) { - ++num_removed; req->complete(req); + list_del(&req->list); } - - /* Try and fill the engine back up again. */ - spin_lock_irqsave(&engine->hw_lock, flags); - - engine->in_flight -= num_removed; - - list_for_each_entry_safe(req, tmp, &engine->pending, list) { - if (spacc_fifo_cmd_full(engine)) - break; - - list_move_tail(&req->list, &engine->in_progress); - ++engine->in_flight; - req->result = spacc_req_submit(req); - } - - if (engine->in_flight) - mod_timer(&engine->packet_timeout, jiffies + PACKET_TIMEOUT); - - spin_unlock_irqrestore(&engine->hw_lock, flags); } #ifdef CONFIG_PM |