From 71ffd1dc5234f522a7647dd30ca8fc9eefe8da1b Mon Sep 17 00:00:00 2001 From: Eric Biggers Date: Wed, 9 Jul 2025 23:07:48 -0700 Subject: [PATCH] fscrypt: Don't use asynchronous CryptoAPI algorithms Now that fscrypt's incomplete support for non-inline crypto engines has been removed, and none of the CPU-based algorithms have the CRYPTO_ALG_ASYNC flag set anymore, there is no need to accommodate asynchronous algorithms. Therefore, explicitly allocate only synchronous algorithms. Then, remove the code that handled waiting for asynchronous en/decryption operations to complete. This commit should *not* be backported to kernels that lack commit 0ba6ec5b2972 ("crypto: x86/aes - stop using the SIMD helper"), as then it would disable the use of the optimized AES code on x86. Link: https://lore.kernel.org/r/20250710060754.637098-2-ebiggers@kernel.org Signed-off-by: Eric Biggers --- fs/crypto/crypto.c | 7 +++---- fs/crypto/fname.c | 18 ++++++++---------- fs/crypto/fscrypt_private.h | 5 +++-- fs/crypto/keysetup_v1.c | 9 ++++----- 4 files changed, 18 insertions(+), 21 deletions(-) diff --git a/fs/crypto/crypto.c b/fs/crypto/crypto.c index ddf6991d46da2..43d1658e07cec 100644 --- a/fs/crypto/crypto.c +++ b/fs/crypto/crypto.c @@ -115,7 +115,6 @@ int fscrypt_crypt_data_unit(const struct fscrypt_inode_info *ci, { union fscrypt_iv iv; struct skcipher_request *req = NULL; - DECLARE_CRYPTO_WAIT(wait); struct scatterlist dst, src; struct crypto_skcipher *tfm = ci->ci_enc_key.tfm; int res = 0; @@ -133,7 +132,7 @@ int fscrypt_crypt_data_unit(const struct fscrypt_inode_info *ci, skcipher_request_set_callback( req, CRYPTO_TFM_REQ_MAY_BACKLOG | CRYPTO_TFM_REQ_MAY_SLEEP, - crypto_req_done, &wait); + NULL, NULL); sg_init_table(&dst, 1); sg_set_page(&dst, dest_page, len, offs); @@ -141,9 +140,9 @@ int fscrypt_crypt_data_unit(const struct fscrypt_inode_info *ci, sg_set_page(&src, src_page, len, offs); skcipher_request_set_crypt(req, &src, &dst, len, &iv); if (rw == FS_DECRYPT) - res = crypto_wait_req(crypto_skcipher_decrypt(req), &wait); + res = crypto_skcipher_decrypt(req); else - res = crypto_wait_req(crypto_skcipher_encrypt(req), &wait); + res = crypto_skcipher_encrypt(req); skcipher_request_free(req); if (res) { fscrypt_err(ci->ci_inode, diff --git a/fs/crypto/fname.c b/fs/crypto/fname.c index fb01dde0f2e55..17edc24ccd42f 100644 --- a/fs/crypto/fname.c +++ b/fs/crypto/fname.c @@ -95,7 +95,6 @@ int fscrypt_fname_encrypt(const struct inode *inode, const struct qstr *iname, u8 *out, unsigned int olen) { struct skcipher_request *req = NULL; - DECLARE_CRYPTO_WAIT(wait); const struct fscrypt_inode_info *ci = inode->i_crypt_info; struct crypto_skcipher *tfm = ci->ci_enc_key.tfm; union fscrypt_iv iv; @@ -118,14 +117,14 @@ int fscrypt_fname_encrypt(const struct inode *inode, const struct qstr *iname, req = skcipher_request_alloc(tfm, GFP_NOFS); if (!req) return -ENOMEM; - skcipher_request_set_callback(req, - CRYPTO_TFM_REQ_MAY_BACKLOG | CRYPTO_TFM_REQ_MAY_SLEEP, - crypto_req_done, &wait); + skcipher_request_set_callback( + req, CRYPTO_TFM_REQ_MAY_BACKLOG | CRYPTO_TFM_REQ_MAY_SLEEP, + NULL, NULL); sg_init_one(&sg, out, olen); skcipher_request_set_crypt(req, &sg, &sg, olen, &iv); /* Do the encryption */ - res = crypto_wait_req(crypto_skcipher_encrypt(req), &wait); + res = crypto_skcipher_encrypt(req); skcipher_request_free(req); if (res < 0) { fscrypt_err(inode, "Filename encryption failed: %d", res); @@ -151,7 +150,6 @@ static int fname_decrypt(const struct inode *inode, struct fscrypt_str *oname) { struct skcipher_request *req = NULL; - DECLARE_CRYPTO_WAIT(wait); struct scatterlist src_sg, dst_sg; const struct fscrypt_inode_info *ci = inode->i_crypt_info; struct crypto_skcipher *tfm = ci->ci_enc_key.tfm; @@ -162,9 +160,9 @@ static int fname_decrypt(const struct inode *inode, req = skcipher_request_alloc(tfm, GFP_NOFS); if (!req) return -ENOMEM; - skcipher_request_set_callback(req, - CRYPTO_TFM_REQ_MAY_BACKLOG | CRYPTO_TFM_REQ_MAY_SLEEP, - crypto_req_done, &wait); + skcipher_request_set_callback( + req, CRYPTO_TFM_REQ_MAY_BACKLOG | CRYPTO_TFM_REQ_MAY_SLEEP, + NULL, NULL); /* Initialize IV */ fscrypt_generate_iv(&iv, 0, ci); @@ -173,7 +171,7 @@ static int fname_decrypt(const struct inode *inode, sg_init_one(&src_sg, iname->name, iname->len); sg_init_one(&dst_sg, oname->name, oname->len); skcipher_request_set_crypt(req, &src_sg, &dst_sg, iname->len, &iv); - res = crypto_wait_req(crypto_skcipher_decrypt(req), &wait); + res = crypto_skcipher_decrypt(req); skcipher_request_free(req); if (res < 0) { fscrypt_err(inode, "Filename decryption failed: %d", res); diff --git a/fs/crypto/fscrypt_private.h b/fs/crypto/fscrypt_private.h index 6e7164530a1e2..06fa8f2b2d081 100644 --- a/fs/crypto/fscrypt_private.h +++ b/fs/crypto/fscrypt_private.h @@ -59,8 +59,9 @@ * Note that fscrypt also supports inline crypto engines. Those don't use the * Crypto API and work much better than the old-style (non-inline) engines. */ -#define FSCRYPT_CRYPTOAPI_MASK \ - (CRYPTO_ALG_ALLOCATES_MEMORY | CRYPTO_ALG_KERN_DRIVER_ONLY) +#define FSCRYPT_CRYPTOAPI_MASK \ + (CRYPTO_ALG_ASYNC | CRYPTO_ALG_ALLOCATES_MEMORY | \ + CRYPTO_ALG_KERN_DRIVER_ONLY) #define FSCRYPT_CONTEXT_V1 1 #define FSCRYPT_CONTEXT_V2 2 diff --git a/fs/crypto/keysetup_v1.c b/fs/crypto/keysetup_v1.c index 158ceae8a5bce..3fdf174384f3d 100644 --- a/fs/crypto/keysetup_v1.c +++ b/fs/crypto/keysetup_v1.c @@ -50,7 +50,6 @@ static int derive_key_aes(const u8 *master_key, { int res = 0; struct skcipher_request *req = NULL; - DECLARE_CRYPTO_WAIT(wait); struct scatterlist src_sg, dst_sg; struct crypto_skcipher *tfm = crypto_alloc_skcipher("ecb(aes)", 0, FSCRYPT_CRYPTOAPI_MASK); @@ -66,9 +65,9 @@ static int derive_key_aes(const u8 *master_key, res = -ENOMEM; goto out; } - skcipher_request_set_callback(req, - CRYPTO_TFM_REQ_MAY_BACKLOG | CRYPTO_TFM_REQ_MAY_SLEEP, - crypto_req_done, &wait); + skcipher_request_set_callback( + req, CRYPTO_TFM_REQ_MAY_BACKLOG | CRYPTO_TFM_REQ_MAY_SLEEP, + NULL, NULL); res = crypto_skcipher_setkey(tfm, nonce, FSCRYPT_FILE_NONCE_SIZE); if (res < 0) goto out; @@ -77,7 +76,7 @@ static int derive_key_aes(const u8 *master_key, sg_init_one(&dst_sg, derived_key, derived_keysize); skcipher_request_set_crypt(req, &src_sg, &dst_sg, derived_keysize, NULL); - res = crypto_wait_req(crypto_skcipher_encrypt(req), &wait); + res = crypto_skcipher_encrypt(req); out: skcipher_request_free(req); crypto_free_skcipher(tfm); -- 2.51.0