Commit 64929fe8 authored by Herbert Xu's avatar Herbert Xu
Browse files

crypto: acomp - Remove request chaining



Request chaining requires the user to do too much book keeping.
Remove it from acomp.

Signed-off-by: default avatarHerbert Xu <herbert@gondor.apana.org.au>
parent 78e2846a
Loading
Loading
Loading
Loading
+33 −84
Original line number Diff line number Diff line
@@ -177,7 +177,6 @@ static void acomp_save_req(struct acomp_req *req, crypto_completion_t cplt)
	state->data = req->base.data;
	req->base.complete = cplt;
	req->base.data = state;
	state->req0 = 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;
}

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 dlen = req->dlen;

	req->base.err = err;
	state = &req->chain;

	if (state->flags & CRYPTO_ACOMP_REQ_SRC_VIRT)
		acomp_request_set_src_dma(req, state->src, slen);
	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)
		acomp_request_set_dst_dma(req, state->dst, dlen);
	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)
@@ -229,7 +225,6 @@ static void acomp_virt_to_sg(struct acomp_req *req)
		size_t off = req->soff;

		state->sfolio = folio;
		state->soff = off;
		sg_init_table(&state->ssg, 1);
		sg_set_page(&state->ssg, folio_page(folio, 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;

		state->dfolio = folio;
		state->doff = off;
		sg_init_table(&state->dsg, 1);
		sg_set_page(&state->dsg, folio_page(folio, 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,
			   struct acomp_req *req)
static int acomp_do_nondma(struct acomp_req *req, bool comp)
{
	u32 keep = CRYPTO_ACOMP_REQ_SRC_VIRT |
		   CRYPTO_ACOMP_REQ_SRC_NONDMA |
@@ -275,7 +268,7 @@ static int acomp_do_nondma(struct acomp_req_chain *state,
	fbreq->slen = req->slen;
	fbreq->dlen = req->dlen;

	if (state->op == crypto_acomp_reqtfm(req)->compress)
	if (comp)
		err = crypto_acomp_compress(fbreq);
	else
		err = crypto_acomp_decompress(fbreq);
@@ -284,114 +277,70 @@ static int acomp_do_nondma(struct acomp_req_chain *state,
	return err;
}

static int acomp_do_one_req(struct acomp_req_chain *state,
			    struct acomp_req *req)
static int acomp_do_one_req(struct acomp_req *req, bool comp)
{
	state->cur = req;

	if (acomp_request_isnondma(req))
		return acomp_do_nondma(state, req);
		return acomp_do_nondma(req, comp);

	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;
	struct acomp_req *req = state->cur;
	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:
	acomp_reqchain_virt(req);
	acomp_restore_req(req);
	return err;
}

static void acomp_reqchain_done(void *data, int err)
{
	struct acomp_req_chain *state = data;
	crypto_completion_t compl = state->compl;
	struct acomp_req *req = data;
	crypto_completion_t compl;

	data = state->data;
	compl = req->chain.compl;
	data = req->chain.data;

	if (err == -EINPROGRESS) {
		if (!list_empty(&state->head))
			return;
	if (err == -EINPROGRESS)
		goto notify;
	}

	err = acomp_reqchain_finish(state->req0, err,
				    CRYPTO_TFM_REQ_MAY_BACKLOG);
	if (err == -EBUSY)
		return;
	err = acomp_reqchain_finish(req, err);

notify:
	compl(data, err);
}

static int acomp_do_req_chain(struct acomp_req *req,
			      int (*op)(struct acomp_req *req))
static int acomp_do_req_chain(struct acomp_req *req, bool comp)
{
	struct crypto_acomp *tfm = crypto_acomp_reqtfm(req);
	struct acomp_req_chain *state;
	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);
	state = req->base.data;

	state->op = op;
	state->src = NULL;
	INIT_LIST_HEAD(&state->head);
	list_splice_init(&req->base.list, &state->head);

	err = acomp_do_one_req(state, req);
	err = acomp_do_one_req(req, comp);
	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)
{
	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);

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);

+2 −16
Original line number Diff line number Diff line
@@ -284,28 +284,14 @@ static int scomp_acomp_comp_decomp(struct acomp_req *req, int dir)
	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)
{
	return scomp_acomp_chain(req, 1);
	return scomp_acomp_comp_decomp(req, 1);
}

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)
+0 −14
Original line number Diff line number Diff line
@@ -52,10 +52,6 @@ struct acomp_req;
struct folio;

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;
	void *data;
	struct scatterlist ssg;
@@ -68,8 +64,6 @@ struct acomp_req_chain {
		u8 *dst;
		struct folio *dfolio;
	};
	size_t soff;
	size_t doff;
	u32 flags;
};

@@ -343,8 +337,6 @@ static inline void acomp_request_set_callback(struct acomp_req *req,
	req->base.data = data;
	req->base.flags &= 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;
}

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
 *
+0 −5
Original line number Diff line number Diff line
@@ -151,11 +151,6 @@ void crypto_unregister_acomp(struct acomp_alg *alg);
int crypto_register_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)
{
	return !(req->base.flags & (CRYPTO_ACOMP_REQ_SRC_VIRT |