mirror of
https://git.kernel.org/pub/scm/linux/kernel/git/chenhuacai/linux-loongson
synced 2025-08-27 15:36:48 +00:00
crypto: acomp - Remove request chaining
Request chaining requires the user to do too much book keeping. Remove it from acomp. Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>
This commit is contained in:
parent
78e2846aa4
commit
64929fe8c0
@ -177,7 +177,6 @@ static void acomp_save_req(struct acomp_req *req, crypto_completion_t cplt)
|
|||||||
state->data = req->base.data;
|
state->data = req->base.data;
|
||||||
req->base.complete = cplt;
|
req->base.complete = cplt;
|
||||||
req->base.data = state;
|
req->base.data = state;
|
||||||
state->req0 = req;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
static void acomp_restore_req(struct acomp_req *req)
|
static void acomp_restore_req(struct acomp_req *req)
|
||||||
@ -188,23 +187,20 @@ static void acomp_restore_req(struct acomp_req *req)
|
|||||||
req->base.data = state->data;
|
req->base.data = state->data;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void acomp_reqchain_virt(struct acomp_req_chain *state, int err)
|
static void acomp_reqchain_virt(struct acomp_req *req)
|
||||||
{
|
{
|
||||||
struct acomp_req *req = state->cur;
|
struct acomp_req_chain *state = &req->chain;
|
||||||
unsigned int slen = req->slen;
|
unsigned int slen = req->slen;
|
||||||
unsigned int dlen = req->dlen;
|
unsigned int dlen = req->dlen;
|
||||||
|
|
||||||
req->base.err = err;
|
|
||||||
state = &req->chain;
|
|
||||||
|
|
||||||
if (state->flags & CRYPTO_ACOMP_REQ_SRC_VIRT)
|
if (state->flags & CRYPTO_ACOMP_REQ_SRC_VIRT)
|
||||||
acomp_request_set_src_dma(req, state->src, slen);
|
acomp_request_set_src_dma(req, state->src, slen);
|
||||||
else if (state->flags & CRYPTO_ACOMP_REQ_SRC_FOLIO)
|
else if (state->flags & CRYPTO_ACOMP_REQ_SRC_FOLIO)
|
||||||
acomp_request_set_src_folio(req, state->sfolio, state->soff, slen);
|
acomp_request_set_src_folio(req, state->sfolio, req->soff, slen);
|
||||||
if (state->flags & CRYPTO_ACOMP_REQ_DST_VIRT)
|
if (state->flags & CRYPTO_ACOMP_REQ_DST_VIRT)
|
||||||
acomp_request_set_dst_dma(req, state->dst, dlen);
|
acomp_request_set_dst_dma(req, state->dst, dlen);
|
||||||
else if (state->flags & CRYPTO_ACOMP_REQ_DST_FOLIO)
|
else if (state->flags & CRYPTO_ACOMP_REQ_DST_FOLIO)
|
||||||
acomp_request_set_dst_folio(req, state->dfolio, state->doff, dlen);
|
acomp_request_set_dst_folio(req, state->dfolio, req->doff, dlen);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void acomp_virt_to_sg(struct acomp_req *req)
|
static void acomp_virt_to_sg(struct acomp_req *req)
|
||||||
@ -229,7 +225,6 @@ static void acomp_virt_to_sg(struct acomp_req *req)
|
|||||||
size_t off = req->soff;
|
size_t off = req->soff;
|
||||||
|
|
||||||
state->sfolio = folio;
|
state->sfolio = folio;
|
||||||
state->soff = off;
|
|
||||||
sg_init_table(&state->ssg, 1);
|
sg_init_table(&state->ssg, 1);
|
||||||
sg_set_page(&state->ssg, folio_page(folio, off / PAGE_SIZE),
|
sg_set_page(&state->ssg, folio_page(folio, off / PAGE_SIZE),
|
||||||
slen, off % PAGE_SIZE);
|
slen, off % PAGE_SIZE);
|
||||||
@ -249,7 +244,6 @@ static void acomp_virt_to_sg(struct acomp_req *req)
|
|||||||
size_t off = req->doff;
|
size_t off = req->doff;
|
||||||
|
|
||||||
state->dfolio = folio;
|
state->dfolio = folio;
|
||||||
state->doff = off;
|
|
||||||
sg_init_table(&state->dsg, 1);
|
sg_init_table(&state->dsg, 1);
|
||||||
sg_set_page(&state->dsg, folio_page(folio, off / PAGE_SIZE),
|
sg_set_page(&state->dsg, folio_page(folio, off / PAGE_SIZE),
|
||||||
dlen, off % PAGE_SIZE);
|
dlen, off % PAGE_SIZE);
|
||||||
@ -257,8 +251,7 @@ static void acomp_virt_to_sg(struct acomp_req *req)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
static int acomp_do_nondma(struct acomp_req_chain *state,
|
static int acomp_do_nondma(struct acomp_req *req, bool comp)
|
||||||
struct acomp_req *req)
|
|
||||||
{
|
{
|
||||||
u32 keep = CRYPTO_ACOMP_REQ_SRC_VIRT |
|
u32 keep = CRYPTO_ACOMP_REQ_SRC_VIRT |
|
||||||
CRYPTO_ACOMP_REQ_SRC_NONDMA |
|
CRYPTO_ACOMP_REQ_SRC_NONDMA |
|
||||||
@ -275,7 +268,7 @@ static int acomp_do_nondma(struct acomp_req_chain *state,
|
|||||||
fbreq->slen = req->slen;
|
fbreq->slen = req->slen;
|
||||||
fbreq->dlen = req->dlen;
|
fbreq->dlen = req->dlen;
|
||||||
|
|
||||||
if (state->op == crypto_acomp_reqtfm(req)->compress)
|
if (comp)
|
||||||
err = crypto_acomp_compress(fbreq);
|
err = crypto_acomp_compress(fbreq);
|
||||||
else
|
else
|
||||||
err = crypto_acomp_decompress(fbreq);
|
err = crypto_acomp_decompress(fbreq);
|
||||||
@ -284,114 +277,70 @@ static int acomp_do_nondma(struct acomp_req_chain *state,
|
|||||||
return err;
|
return err;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int acomp_do_one_req(struct acomp_req_chain *state,
|
static int acomp_do_one_req(struct acomp_req *req, bool comp)
|
||||||
struct acomp_req *req)
|
|
||||||
{
|
{
|
||||||
state->cur = req;
|
|
||||||
|
|
||||||
if (acomp_request_isnondma(req))
|
if (acomp_request_isnondma(req))
|
||||||
return acomp_do_nondma(state, req);
|
return acomp_do_nondma(req, comp);
|
||||||
|
|
||||||
acomp_virt_to_sg(req);
|
acomp_virt_to_sg(req);
|
||||||
return state->op(req);
|
return comp ? crypto_acomp_reqtfm(req)->compress(req) :
|
||||||
|
crypto_acomp_reqtfm(req)->decompress(req);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int acomp_reqchain_finish(struct acomp_req *req0, int err, u32 mask)
|
static int acomp_reqchain_finish(struct acomp_req *req, int err)
|
||||||
{
|
{
|
||||||
struct acomp_req_chain *state = req0->base.data;
|
acomp_reqchain_virt(req);
|
||||||
struct acomp_req *req = state->cur;
|
acomp_restore_req(req);
|
||||||
struct acomp_req *n;
|
|
||||||
|
|
||||||
acomp_reqchain_virt(state, err);
|
|
||||||
|
|
||||||
if (req != req0)
|
|
||||||
list_add_tail(&req->base.list, &req0->base.list);
|
|
||||||
|
|
||||||
list_for_each_entry_safe(req, n, &state->head, base.list) {
|
|
||||||
list_del_init(&req->base.list);
|
|
||||||
|
|
||||||
req->base.flags &= mask;
|
|
||||||
req->base.complete = acomp_reqchain_done;
|
|
||||||
req->base.data = state;
|
|
||||||
|
|
||||||
err = acomp_do_one_req(state, req);
|
|
||||||
|
|
||||||
if (err == -EINPROGRESS) {
|
|
||||||
if (!list_empty(&state->head))
|
|
||||||
err = -EBUSY;
|
|
||||||
goto out;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (err == -EBUSY)
|
|
||||||
goto out;
|
|
||||||
|
|
||||||
acomp_reqchain_virt(state, err);
|
|
||||||
list_add_tail(&req->base.list, &req0->base.list);
|
|
||||||
}
|
|
||||||
|
|
||||||
acomp_restore_req(req0);
|
|
||||||
|
|
||||||
out:
|
|
||||||
return err;
|
return err;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void acomp_reqchain_done(void *data, int err)
|
static void acomp_reqchain_done(void *data, int err)
|
||||||
{
|
{
|
||||||
struct acomp_req_chain *state = data;
|
struct acomp_req *req = data;
|
||||||
crypto_completion_t compl = state->compl;
|
crypto_completion_t compl;
|
||||||
|
|
||||||
data = state->data;
|
compl = req->chain.compl;
|
||||||
|
data = req->chain.data;
|
||||||
|
|
||||||
if (err == -EINPROGRESS) {
|
if (err == -EINPROGRESS)
|
||||||
if (!list_empty(&state->head))
|
|
||||||
return;
|
|
||||||
goto notify;
|
goto notify;
|
||||||
}
|
|
||||||
|
|
||||||
err = acomp_reqchain_finish(state->req0, err,
|
err = acomp_reqchain_finish(req, err);
|
||||||
CRYPTO_TFM_REQ_MAY_BACKLOG);
|
|
||||||
if (err == -EBUSY)
|
|
||||||
return;
|
|
||||||
|
|
||||||
notify:
|
notify:
|
||||||
compl(data, err);
|
compl(data, err);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int acomp_do_req_chain(struct acomp_req *req,
|
static int acomp_do_req_chain(struct acomp_req *req, bool comp)
|
||||||
int (*op)(struct acomp_req *req))
|
|
||||||
{
|
{
|
||||||
struct crypto_acomp *tfm = crypto_acomp_reqtfm(req);
|
|
||||||
struct acomp_req_chain *state;
|
|
||||||
int err;
|
int err;
|
||||||
|
|
||||||
if (crypto_acomp_req_chain(tfm) ||
|
|
||||||
(!acomp_request_chained(req) && acomp_request_issg(req)))
|
|
||||||
return op(req);
|
|
||||||
|
|
||||||
acomp_save_req(req, acomp_reqchain_done);
|
acomp_save_req(req, acomp_reqchain_done);
|
||||||
state = req->base.data;
|
|
||||||
|
|
||||||
state->op = op;
|
err = acomp_do_one_req(req, comp);
|
||||||
state->src = NULL;
|
|
||||||
INIT_LIST_HEAD(&state->head);
|
|
||||||
list_splice_init(&req->base.list, &state->head);
|
|
||||||
|
|
||||||
err = acomp_do_one_req(state, req);
|
|
||||||
if (err == -EBUSY || err == -EINPROGRESS)
|
if (err == -EBUSY || err == -EINPROGRESS)
|
||||||
return -EBUSY;
|
return err;
|
||||||
|
|
||||||
return acomp_reqchain_finish(req, err, ~0);
|
return acomp_reqchain_finish(req, err);
|
||||||
}
|
}
|
||||||
|
|
||||||
int crypto_acomp_compress(struct acomp_req *req)
|
int crypto_acomp_compress(struct acomp_req *req)
|
||||||
{
|
{
|
||||||
return acomp_do_req_chain(req, crypto_acomp_reqtfm(req)->compress);
|
struct crypto_acomp *tfm = crypto_acomp_reqtfm(req);
|
||||||
|
|
||||||
|
if (crypto_acomp_req_chain(tfm) || acomp_request_issg(req))
|
||||||
|
crypto_acomp_reqtfm(req)->compress(req);
|
||||||
|
return acomp_do_req_chain(req, true);
|
||||||
}
|
}
|
||||||
EXPORT_SYMBOL_GPL(crypto_acomp_compress);
|
EXPORT_SYMBOL_GPL(crypto_acomp_compress);
|
||||||
|
|
||||||
int crypto_acomp_decompress(struct acomp_req *req)
|
int crypto_acomp_decompress(struct acomp_req *req)
|
||||||
{
|
{
|
||||||
return acomp_do_req_chain(req, crypto_acomp_reqtfm(req)->decompress);
|
struct crypto_acomp *tfm = crypto_acomp_reqtfm(req);
|
||||||
|
|
||||||
|
if (crypto_acomp_req_chain(tfm) || acomp_request_issg(req))
|
||||||
|
crypto_acomp_reqtfm(req)->decompress(req);
|
||||||
|
return acomp_do_req_chain(req, false);
|
||||||
}
|
}
|
||||||
EXPORT_SYMBOL_GPL(crypto_acomp_decompress);
|
EXPORT_SYMBOL_GPL(crypto_acomp_decompress);
|
||||||
|
|
||||||
|
@ -284,28 +284,14 @@ static int scomp_acomp_comp_decomp(struct acomp_req *req, int dir)
|
|||||||
return ret;
|
return ret;
|
||||||
}
|
}
|
||||||
|
|
||||||
static int scomp_acomp_chain(struct acomp_req *req, int dir)
|
|
||||||
{
|
|
||||||
struct acomp_req *r2;
|
|
||||||
int err;
|
|
||||||
|
|
||||||
err = scomp_acomp_comp_decomp(req, dir);
|
|
||||||
req->base.err = err;
|
|
||||||
|
|
||||||
list_for_each_entry(r2, &req->base.list, base.list)
|
|
||||||
r2->base.err = scomp_acomp_comp_decomp(r2, dir);
|
|
||||||
|
|
||||||
return err;
|
|
||||||
}
|
|
||||||
|
|
||||||
static int scomp_acomp_compress(struct acomp_req *req)
|
static int scomp_acomp_compress(struct acomp_req *req)
|
||||||
{
|
{
|
||||||
return scomp_acomp_chain(req, 1);
|
return scomp_acomp_comp_decomp(req, 1);
|
||||||
}
|
}
|
||||||
|
|
||||||
static int scomp_acomp_decompress(struct acomp_req *req)
|
static int scomp_acomp_decompress(struct acomp_req *req)
|
||||||
{
|
{
|
||||||
return scomp_acomp_chain(req, 0);
|
return scomp_acomp_comp_decomp(req, 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void crypto_exit_scomp_ops_async(struct crypto_tfm *tfm)
|
static void crypto_exit_scomp_ops_async(struct crypto_tfm *tfm)
|
||||||
|
@ -52,10 +52,6 @@ struct acomp_req;
|
|||||||
struct folio;
|
struct folio;
|
||||||
|
|
||||||
struct acomp_req_chain {
|
struct acomp_req_chain {
|
||||||
struct list_head head;
|
|
||||||
struct acomp_req *req0;
|
|
||||||
struct acomp_req *cur;
|
|
||||||
int (*op)(struct acomp_req *req);
|
|
||||||
crypto_completion_t compl;
|
crypto_completion_t compl;
|
||||||
void *data;
|
void *data;
|
||||||
struct scatterlist ssg;
|
struct scatterlist ssg;
|
||||||
@ -68,8 +64,6 @@ struct acomp_req_chain {
|
|||||||
u8 *dst;
|
u8 *dst;
|
||||||
struct folio *dfolio;
|
struct folio *dfolio;
|
||||||
};
|
};
|
||||||
size_t soff;
|
|
||||||
size_t doff;
|
|
||||||
u32 flags;
|
u32 flags;
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -343,8 +337,6 @@ static inline void acomp_request_set_callback(struct acomp_req *req,
|
|||||||
req->base.data = data;
|
req->base.data = data;
|
||||||
req->base.flags &= keep;
|
req->base.flags &= keep;
|
||||||
req->base.flags |= flgs & ~keep;
|
req->base.flags |= flgs & ~keep;
|
||||||
|
|
||||||
crypto_reqchain_init(&req->base);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -552,12 +544,6 @@ static inline void acomp_request_set_dst_folio(struct acomp_req *req,
|
|||||||
req->base.flags |= CRYPTO_ACOMP_REQ_DST_FOLIO;
|
req->base.flags |= CRYPTO_ACOMP_REQ_DST_FOLIO;
|
||||||
}
|
}
|
||||||
|
|
||||||
static inline void acomp_request_chain(struct acomp_req *req,
|
|
||||||
struct acomp_req *head)
|
|
||||||
{
|
|
||||||
crypto_request_chain(&req->base, &head->base);
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* crypto_acomp_compress() -- Invoke asynchronous compress operation
|
* crypto_acomp_compress() -- Invoke asynchronous compress operation
|
||||||
*
|
*
|
||||||
|
@ -151,11 +151,6 @@ void crypto_unregister_acomp(struct acomp_alg *alg);
|
|||||||
int crypto_register_acomps(struct acomp_alg *algs, int count);
|
int crypto_register_acomps(struct acomp_alg *algs, int count);
|
||||||
void crypto_unregister_acomps(struct acomp_alg *algs, int count);
|
void crypto_unregister_acomps(struct acomp_alg *algs, int count);
|
||||||
|
|
||||||
static inline bool acomp_request_chained(struct acomp_req *req)
|
|
||||||
{
|
|
||||||
return crypto_request_chained(&req->base);
|
|
||||||
}
|
|
||||||
|
|
||||||
static inline bool acomp_request_issg(struct acomp_req *req)
|
static inline bool acomp_request_issg(struct acomp_req *req)
|
||||||
{
|
{
|
||||||
return !(req->base.flags & (CRYPTO_ACOMP_REQ_SRC_VIRT |
|
return !(req->base.flags & (CRYPTO_ACOMP_REQ_SRC_VIRT |
|
||||||
|
Loading…
Reference in New Issue
Block a user