Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

crypto: acomp - Add ACOMP_REQUEST_CLONE

Add a new helper ACOMP_REQUEST_CLONE that will transform a stack
request into a dynamically allocated one if possible, and otherwise
switch it over to the sycnrhonous fallback transform. The intended
usage is:

ACOMP_STACK_ON_REQUEST(req, tfm);

...
err = crypto_acomp_compress(req);
/* The request cannot complete synchronously. */
if (err == -EAGAIN) {
/* This will not fail. */
req = ACOMP_REQUEST_CLONE(req, gfp);

/* Redo operation. */
err = crypto_acomp_compress(req);
}

Signed-off-by: Herbert Xu <herbert@gondor.apana.org.au>

+52 -12
+23
crypto/acompress.c
··· 316 316 { 317 317 struct crypto_acomp *tfm = crypto_acomp_reqtfm(req); 318 318 319 + if (acomp_req_on_stack(req) && acomp_is_async(tfm)) 320 + return -EAGAIN; 319 321 if (crypto_acomp_req_chain(tfm) || acomp_request_issg(req)) 320 322 crypto_acomp_reqtfm(req)->compress(req); 321 323 return acomp_do_req_chain(req, true); ··· 328 326 { 329 327 struct crypto_acomp *tfm = crypto_acomp_reqtfm(req); 330 328 329 + if (acomp_req_on_stack(req) && acomp_is_async(tfm)) 330 + return -EAGAIN; 331 331 if (crypto_acomp_req_chain(tfm) || acomp_request_issg(req)) 332 332 crypto_acomp_reqtfm(req)->decompress(req); 333 333 return acomp_do_req_chain(req, false); ··· 606 602 return 0; 607 603 } 608 604 EXPORT_SYMBOL_GPL(acomp_walk_virt); 605 + 606 + struct acomp_req *acomp_request_clone(struct acomp_req *req, 607 + size_t total, gfp_t gfp) 608 + { 609 + struct crypto_acomp *tfm = crypto_acomp_reqtfm(req); 610 + struct acomp_req *nreq; 611 + 612 + nreq = kmalloc(total, gfp); 613 + if (!nreq) { 614 + acomp_request_set_tfm(req, tfm->fb); 615 + req->base.flags = CRYPTO_TFM_REQ_ON_STACK; 616 + return req; 617 + } 618 + 619 + memcpy(nreq, req, total); 620 + acomp_request_set_tfm(req, tfm); 621 + return req; 622 + } 623 + EXPORT_SYMBOL_GPL(acomp_request_clone); 609 624 610 625 MODULE_LICENSE("GPL"); 611 626 MODULE_DESCRIPTION("Asynchronous compression type");
+26 -4
include/crypto/acompress.h
··· 51 51 #define ACOMP_REQUEST_ALLOC(name, tfm, gfp) \ 52 52 char __##name##_req[sizeof(struct acomp_req) + \ 53 53 MAX_SYNC_COMP_REQSIZE] CRYPTO_MINALIGN_ATTR; \ 54 + struct acomp_req *name = acomp_request_alloc_init( \ 55 + __##name##_req, (tfm), (gfp)) 56 + 57 + #define ACOMP_REQUEST_ON_STACK(name, tfm) \ 58 + char __##name##_req[sizeof(struct acomp_req) + \ 59 + MAX_SYNC_COMP_REQSIZE] CRYPTO_MINALIGN_ATTR; \ 54 60 struct acomp_req *name = acomp_request_on_stack_init( \ 55 - __##name##_req, (tfm), (gfp), false) 61 + __##name##_req, (tfm)) 62 + 63 + #define ACOMP_REQUEST_CLONE(name, gfp) \ 64 + acomp_request_clone(name, sizeof(__##name##_req), gfp) 56 65 57 66 struct acomp_req; 58 67 struct folio; ··· 580 571 */ 581 572 int crypto_acomp_decompress(struct acomp_req *req); 582 573 583 - static inline struct acomp_req *acomp_request_on_stack_init( 584 - char *buf, struct crypto_acomp *tfm, gfp_t gfp, bool stackonly) 574 + static inline struct acomp_req *acomp_request_alloc_init( 575 + char *buf, struct crypto_acomp *tfm, gfp_t gfp) 585 576 { 586 577 struct acomp_req *req; 587 578 588 - if (!stackonly && (req = acomp_request_alloc(tfm, gfp))) 579 + if ((req = acomp_request_alloc(tfm, gfp))) 589 580 return req; 590 581 591 582 req = (void *)buf; ··· 594 585 595 586 return req; 596 587 } 588 + 589 + static inline struct acomp_req *acomp_request_on_stack_init( 590 + char *buf, struct crypto_acomp *tfm) 591 + { 592 + struct acomp_req *req = (void *)buf; 593 + 594 + acomp_request_set_tfm(req, tfm); 595 + req->base.flags = CRYPTO_TFM_REQ_ON_STACK; 596 + return req; 597 + } 598 + 599 + struct acomp_req *acomp_request_clone(struct acomp_req *req, 600 + size_t total, gfp_t gfp); 597 601 598 602 #endif
+3 -8
include/crypto/internal/acompress.h
··· 17 17 #include <linux/spinlock.h> 18 18 #include <linux/workqueue_types.h> 19 19 20 - #define ACOMP_REQUEST_ON_STACK(name, tfm) \ 21 - char __##name##_req[sizeof(struct acomp_req) + \ 22 - MAX_SYNC_COMP_REQSIZE] CRYPTO_MINALIGN_ATTR; \ 23 - struct acomp_req *name = acomp_request_on_stack_init( \ 24 - __##name##_req, (tfm), 0, true) 25 - 26 20 #define ACOMP_FBREQ_ON_STACK(name, req) \ 27 21 char __##name##_req[sizeof(struct acomp_req) + \ 28 22 MAX_SYNC_COMP_REQSIZE] CRYPTO_MINALIGN_ATTR; \ ··· 239 245 char *buf, struct acomp_req *old) 240 246 { 241 247 struct crypto_acomp *tfm = crypto_acomp_reqtfm(old); 242 - struct acomp_req *req; 248 + struct acomp_req *req = (void *)buf; 243 249 244 - req = acomp_request_on_stack_init(buf, tfm, 0, true); 250 + acomp_request_set_tfm(req, tfm->fb); 251 + req->base.flags = CRYPTO_TFM_REQ_ON_STACK; 245 252 acomp_request_set_callback(req, acomp_request_flags(old), NULL, NULL); 246 253 req->base.flags &= ~CRYPTO_ACOMP_REQ_PRIVATE; 247 254 req->base.flags |= old->base.flags & CRYPTO_ACOMP_REQ_PRIVATE;