From: Qu Wenruo <wqu@suse.com>
To: linux-btrfs@vger.kernel.org, linux-block@vger.kernel.org
Subject: [PATCH] block: reject zero length in bio_add_page()
Date: Fri, 13 Mar 2026 12:55:55 +1030 [thread overview]
Message-ID: <f3db373bad065ae6251892acd15993f5dd56dfe1.1773368732.git.wqu@suse.com> (raw)
[BUG]
I caused a regression in btrfs where an incorrect check leads to
a bio_add_folio() call with a zero length.
Then btrfs goes through the error handling, including:
- Freeing the folio
- Freeing every folio inside that bio
But that can lead VM_BUG_ON() on the last folio.
[CAUSE]
When calling bio_add_folio()/bio_add_page() with zero length, the folio
can still be added to the bio as long as there is a free bvec slot or
can be merged with previous folio/page.
Then bio_add_page() return @len, which is 0.
Normally this means an addition failure, but this time the folio is
already queued into the folio.
This can easily confuse the caller, as for normal failure cases both the
folio and bio should be cleaned up.
But since the bio has the last folio queued in already, this leads to
double folio freeing.
[FIX]
I do not think anyone should call bio_add_folio()/bio_add_page() with zero
length, but idiots like me can still show up.
So add an extra WARN_ON_ONCE() check for zero length and rejects it
early to avoid double freeing.
Signed-off-by: Qu Wenruo <wqu@suse.com>
---
block/bio.c | 2 ++
1 file changed, 2 insertions(+)
diff --git a/block/bio.c b/block/bio.c
index d80d5d26804e..6048d9382fec 100644
--- a/block/bio.c
+++ b/block/bio.c
@@ -1064,6 +1064,8 @@ int bio_add_page(struct bio *bio, struct page *page,
{
if (WARN_ON_ONCE(bio_flagged(bio, BIO_CLONED)))
return 0;
+ if (WARN_ON_ONCE(len == 0))
+ return 0;
if (bio->bi_iter.bi_size > BIO_MAX_SIZE - len)
return 0;
--
2.53.0
next reply other threads:[~2026-03-13 2:26 UTC|newest]
Thread overview: 3+ messages / expand[flat|nested] mbox.gz Atom feed top
2026-03-13 2:25 Qu Wenruo [this message]
2026-03-16 16:29 ` [PATCH] block: reject zero length in bio_add_page() Christoph Hellwig
2026-03-16 20:44 ` Qu Wenruo
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=f3db373bad065ae6251892acd15993f5dd56dfe1.1773368732.git.wqu@suse.com \
--to=wqu@suse.com \
--cc=linux-block@vger.kernel.org \
--cc=linux-btrfs@vger.kernel.org \
/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