Linux block layer
 help / color / mirror / Atom feed
From: Baokun Li <libaokun@linux.alibaba.com>
To: linux-ext4@vger.kernel.org
Cc: linux-fscrypt@vger.kernel.org, linux-block@vger.kernel.org,
	linux-fsdevel@vger.kernel.org, linux-xfs@vger.kernel.org,
	ebiggers@kernel.org, jaegeuk@kernel.org, axboe@kernel.dk,
	hch@lst.de, djwong@kernel.org, brauner@kernel.org, tytso@mit.edu,
	berto@igalia.com, adilger.kernel@dilger.ca, jack@suse.cz,
	yi.zhang@huawei.com, ojaswin@linux.ibm.com,
	ritesh.list@gmail.com, stable@vger.kernel.org
Subject: [PATCH 03/13] blk-crypto: reject fallback data unit sizes it can't handle
Date: Mon, 12 Oct 2026 01:09:48 +0800	[thread overview]
Message-ID: <20261011170958.1759230-4-libaokun@linux.alibaba.com> (raw)
In-Reply-To: <20261011170958.1759230-1-libaokun@linux.alibaba.com>

blk-crypto-fallback en/decrypts a data unit that fits in one page:
the encryption and the decryption path both require the data unit
to be contained in a single page-clamped bio_vec.

However, the fallback advertises support for all data unit sizes
(modes_supported[] is 0xFFFFFFFF), and blk_crypto_start_using_key()
never checks the fallback's capabilities, so a key with a larger data
unit size is accepted, and fails with BLK_STS_INVAL on the first I/O:

  EXT4-fs warning (device vdc): ext4_end_bio:360:
	I/O error 19 writing to inode 15 starting block 70136)
  EXT4-fs (vdc): failed to convert unwritten extents to written extents
	-- potential data loss!  (inode 15, error -5)

where error 19 is BLK_STS_INVAL.  Such keys exist on filesystems whose
block size is larger than the page size, because fscrypt uses the block
size as its data unit size by default.

Fix this by advertising only the data unit sizes that the fallback
really supports, and by rejecting keys that the fallback can't handle in
blk_crypto_fallback_start_using_key(), so that the failure happens when
the key is set up instead of during I/O, and before any data is written.

Fixes: 488f6682c832 ("block: blk-crypto-fallback for Inline Encryption")
Cc: stable@vger.kernel.org
Signed-off-by: Baokun Li <libaokun@linux.alibaba.com>
---
 block/blk-crypto-fallback.c | 20 ++++++++++++++++----
 block/blk-crypto-internal.h |  4 ++--
 block/blk-crypto.c          | 14 +++++++-------
 3 files changed, 25 insertions(+), 13 deletions(-)

diff --git a/block/blk-crypto-fallback.c b/block/blk-crypto-fallback.c
index 2a8f40a65158..a75daadba4c8 100644
--- a/block/blk-crypto-fallback.c
+++ b/block/blk-crypto-fallback.c
@@ -83,6 +83,9 @@ static struct workqueue_struct *blk_crypto_wq;
 static mempool_t *blk_crypto_bounce_page_pool;
 static struct bio_set enc_bio_set;
 
+/* Data unit sizes blk-crypto-fallback can en/decrypt. */
+#define BLK_CRYPTO_FALLBACK_DU_MASK	GENMASK(PAGE_SHIFT, SECTOR_SHIFT)
+
 /*
  * This is the key we set when evicting a keyslot. This *should* be the all 0's
  * key, but AES-XTS rejects that key, so we use some random bytes instead.
@@ -561,7 +564,8 @@ static int blk_crypto_fallback_init(void)
 
 	/* All blk-crypto modes have a crypto API fallback. */
 	for (i = 0; i < BLK_ENCRYPTION_MODE_MAX; i++)
-		blk_crypto_fallback_profile->modes_supported[i] = 0xFFFFFFFF;
+		blk_crypto_fallback_profile->modes_supported[i] =
+			BLK_CRYPTO_FALLBACK_DU_MASK;
 	blk_crypto_fallback_profile->modes_supported[BLK_ENCRYPTION_MODE_INVALID] = 0;
 
 	blk_crypto_wq = alloc_workqueue("blk_crypto_wq",
@@ -612,16 +616,24 @@ static int blk_crypto_fallback_init(void)
 }
 
 /*
- * Prepare blk-crypto-fallback for the specified crypto mode.
- * Returns -ENOPKG if the needed crypto API support is missing.
+ * Prepare blk-crypto-fallback for the specified crypto configuration.
+ * Returns -EOPNOTSUPP if the fallback can't handle the data unit size of the
+ * configuration, or -ENOPKG if the needed crypto API support is missing.
  */
-int blk_crypto_fallback_start_using_mode(enum blk_crypto_mode_num mode_num)
+int blk_crypto_fallback_start_using_key(const struct blk_crypto_config *cfg)
 {
+	enum blk_crypto_mode_num mode_num = cfg->crypto_mode;
 	const char *cipher_str = blk_crypto_modes[mode_num].cipher_str;
 	struct blk_crypto_fallback_keyslot *slotp;
 	unsigned int i;
 	int err = 0;
 
+	if (!(BLK_CRYPTO_FALLBACK_DU_MASK & cfg->data_unit_size)) {
+		pr_warn_ratelimited("can't handle data unit size %u\n",
+				    cfg->data_unit_size);
+		return -EOPNOTSUPP;
+	}
+
 	/*
 	 * Fast path
 	 * Ensure that updates to blk_crypto_keyslots[i].tfms[mode_num]
diff --git a/block/blk-crypto-internal.h b/block/blk-crypto-internal.h
index 2c7a0446572a..640527ed05eb 100644
--- a/block/blk-crypto-internal.h
+++ b/block/blk-crypto-internal.h
@@ -219,14 +219,14 @@ bool blk_crypto_fallback_bio_prep(struct bio *bio);
 
 #ifdef CONFIG_BLK_INLINE_ENCRYPTION_FALLBACK
 
-int blk_crypto_fallback_start_using_mode(enum blk_crypto_mode_num mode_num);
+int blk_crypto_fallback_start_using_key(const struct blk_crypto_config *cfg);
 
 int blk_crypto_fallback_evict_key(const struct blk_crypto_key *key);
 
 #else /* CONFIG_BLK_INLINE_ENCRYPTION_FALLBACK */
 
 static inline int
-blk_crypto_fallback_start_using_mode(enum blk_crypto_mode_num mode_num)
+blk_crypto_fallback_start_using_key(const struct blk_crypto_config *cfg)
 {
 	pr_warn_once("crypto API fallback is disabled\n");
 	return -ENOPKG;
diff --git a/block/blk-crypto.c b/block/blk-crypto.c
index bc3a9f59574b..5c670c3e65c5 100644
--- a/block/blk-crypto.c
+++ b/block/blk-crypto.c
@@ -392,13 +392,13 @@ bool blk_crypto_config_supported_natively(struct block_device *bdev,
  * @key: A key to use on the device
  *
  * Upper layers must call this function to ensure that either the hardware
- * supports the key's crypto settings, or the crypto API fallback has transforms
- * for the needed mode allocated and ready to go. This function may allocate
- * an skcipher, and *should not* be called from the data path, since that might
- * cause a deadlock
+ * supports the key's crypto settings, or that the crypto API fallback is ready
+ * to handle them. This function may allocate an skcipher, and *should not* be
+ * called from the data path, since that might cause a deadlock
  *
- * Return: 0 on success; -EOPNOTSUPP if the key is wrapped but the hardware does
- *	   not support wrapped keys; -ENOPKG if the key is a raw key but the
+ * Return: 0 on success; -EOPNOTSUPP if the key can't be used on @bdev, e.g. a
+ *	   wrapped key without hardware support or a data unit size that the
+ *	   fallback can't handle; -ENOPKG if the key is a raw key but the
  *	   hardware does not support raw keys and blk-crypto-fallback is either
  *	   disabled or the needed algorithm is disabled in the crypto API; or
  *	   another -errno code if something else went wrong.
@@ -412,7 +412,7 @@ int blk_crypto_start_using_key(struct block_device *bdev,
 		pr_warn_ratelimited("%pg: no support for wrapped keys\n", bdev);
 		return -EOPNOTSUPP;
 	}
-	return blk_crypto_fallback_start_using_mode(key->crypto_cfg.crypto_mode);
+	return blk_crypto_fallback_start_using_key(&key->crypto_cfg);
 }
 EXPORT_SYMBOL_GPL(blk_crypto_start_using_key);
 
-- 
2.43.7


  parent reply	other threads:[~2026-10-11 17:10 UTC|newest]

Thread overview: 16+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2026-10-11 17:09 [PATCH 00/13] block, ext4: allow encryption with a block size larger than the page size Baokun Li
2026-10-11 17:09 ` [PATCH 01/13] ext4: refuse encryption when block size > " Baokun Li
2026-10-11 17:09 ` [PATCH 02/13] ext4: reject encrypted inodes " Baokun Li
2026-10-11 17:09 ` Baokun Li [this message]
     [not found]   ` <sashiko-outbox-167341@kernel.org>
2026-10-12  7:50     ` [PATCH 03/13] blk-crypto: reject fallback data unit sizes it can't handle Baokun Li
2026-10-11 17:09 ` [PATCH 04/13] blk-crypto: decrypt one data unit per crypto request Baokun Li
2026-10-11 17:09 ` [PATCH 05/13] blk-crypto: encrypt " Baokun Li
2026-10-11 17:09 ` [PATCH 06/13] blk-crypto: support data units larger than a page Baokun Li
2026-10-11 17:09 ` [PATCH 07/13] iomap: align the direct I/O bios of encrypted files to the block size Baokun Li
2026-10-11 17:09 ` [PATCH 08/13] block: split encrypted bios at data unit boundaries Baokun Li
2026-10-11 17:09 ` [PATCH 09/13] block: warn about bios that can't be split Baokun Li
2026-10-11 17:09 ` [PATCH 10/13] block: don't require data unit aligned bio_vecs for encrypted bios Baokun Li
     [not found]   ` <sashiko-outbox-167346@kernel.org>
2026-10-12  8:09     ` Baokun Li
2026-10-11 17:09 ` [PATCH 11/13] ext4: allow encryption with a block size larger than the page size Baokun Li
2026-10-11 17:09 ` [PATCH 12/13] ext4: send folios that cover a wraparound to the buffer_head path Baokun Li
2026-10-11 17:09 ` [PATCH 13/13] ext4: allow large folios for encrypted files Baokun Li

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to=20261011170958.1759230-4-libaokun@linux.alibaba.com \
    --to=libaokun@linux.alibaba.com \
    --cc=adilger.kernel@dilger.ca \
    --cc=axboe@kernel.dk \
    --cc=berto@igalia.com \
    --cc=brauner@kernel.org \
    --cc=djwong@kernel.org \
    --cc=ebiggers@kernel.org \
    --cc=hch@lst.de \
    --cc=jack@suse.cz \
    --cc=jaegeuk@kernel.org \
    --cc=linux-block@vger.kernel.org \
    --cc=linux-ext4@vger.kernel.org \
    --cc=linux-fscrypt@vger.kernel.org \
    --cc=linux-fsdevel@vger.kernel.org \
    --cc=linux-xfs@vger.kernel.org \
    --cc=ojaswin@linux.ibm.com \
    --cc=ritesh.list@gmail.com \
    --cc=stable@vger.kernel.org \
    --cc=tytso@mit.edu \
    --cc=yi.zhang@huawei.com \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox