* Re: [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing
[not found] <c6dfdac9fc51c94183e51a861eec269185239660.1784787211.git.wqu@suse.com>
@ 2026-07-23 6:48 ` Christian Borntraeger
2026-07-23 6:59 ` Qu Wenruo
2026-07-23 10:38 ` [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing Filipe Manana
2026-07-23 11:31 ` Christoph Hellwig
2 siblings, 1 reply; 9+ messages in thread
From: Christian Borntraeger @ 2026-07-23 6:48 UTC (permalink / raw)
To: Qu Wenruo, linux-btrfs
Am 23.07.26 um 08:13 schrieb Qu Wenruo:
> There is a bug report that a reproducer which doing the following
> workloads in two threads:
>
> - Direct read into memory mapped from page cache
> - Sync the above range
>
> This can lead to dirty folios without fs knowing, this can be a huge
> problem for btrfs, as even on the very basic bs == ps cases without
> large folios, such reproducer can screw up the ordered extent accounting
> already:
>
> ------------[ cut here ]------------
> WARNING: fs/btrfs/ordered-data.c:390 at can_finish_ordered_extent.isra.0+0x56/0x1f0 [btrfs], CPU#1: kworker/u42:0/68
> CPU: 1 UID: 0 PID: 68 Comm: kworker/u42:0 Tainted: G E 7.2.0-rc4-custom+ #415 PREEMPT(full) 74dbeafab12c410178747d5bec9fb200ae56949f
> Hardware name: QEMU Standard PC (Q35 + ICH9, 2009), BIOS unknown 02/02/2022
> Workqueue: btrfs-endio simple_end_io_work [btrfs]
> RIP: 0010:can_finish_ordered_extent.isra.0+0x56/0x1f0 [btrfs]
> Call Trace:
> <TASK>
> btrfs_finish_ordered_extent+0x39/0xd0 [btrfs 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
> end_bbio_data_write+0x1ff/0x280 [btrfs 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
> btrfs_bio_end_io+0x76/0xf0 [btrfs 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
> process_one_work+0x198/0x380
> worker_thread+0x1c8/0x330
> kthread+0xee/0x120
> ret_from_fork+0x28f/0x310
> ret_from_fork_asm+0x11/0x20
> </TASK>
> ---[ end trace 0000000000000000 ]---
> BTRFS critical (device dm-3): bad ordered extent accounting, root=5 ino=257 OE offset=3465216 OE len=2826240 to_dec=319488 left=135168
>
> Unfortunately we have removed cow fixup mechanism, which is to work
> around such dirty folios by re-dirtying them and reserve space for them,
> across several kernel releases, meaning we can not easily revert a
> single commit to bring it back.
> And without doubt, that old cow fixup mechanism is not support larger
> folios.
>
> As a hot fix, disable btrfs direct reads for non-experimental builds for
> now, so this can buy some time before we find out a proper way to address
> this.
>
> Reported-by: Christian Borntraeger <borntraeger@linux.ibm.com>
> Link: https://lore.kernel.org/linux-btrfs/f12f70e5-d84d-4a9f-ac94-693be4c863ac@linux.ibm.com/
> Signed-off-by: Qu Wenruo <wqu@suse.com>
Wow that is a big hammer. Doesnt that break typical usecases (like databases on a file,
qemu/kvm aio+direct image files etc)?
Even worse, this does not fix the other GUP use cases that still exist? So its only
a partial fix. Have you considered to add my RFC patch on top to close another
problem that I can reproduce easily.
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing
2026-07-23 6:48 ` [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing Christian Borntraeger
@ 2026-07-23 6:59 ` Qu Wenruo
2026-07-23 9:45 ` Help needed to address the dirty folio without fs notification delimma (Re: [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing) Qu Wenruo
0 siblings, 1 reply; 9+ messages in thread
From: Qu Wenruo @ 2026-07-23 6:59 UTC (permalink / raw)
To: Christian Borntraeger, linux-btrfs
在 2026/7/23 16:18, Christian Borntraeger 写道:
> Am 23.07.26 um 08:13 schrieb Qu Wenruo:
>> There is a bug report that a reproducer which doing the following
>> workloads in two threads:
>>
>> - Direct read into memory mapped from page cache
>> - Sync the above range
>>
>> This can lead to dirty folios without fs knowing, this can be a huge
>> problem for btrfs, as even on the very basic bs == ps cases without
>> large folios, such reproducer can screw up the ordered extent accounting
>> already:
>>
>> ------------[ cut here ]------------
>> WARNING: fs/btrfs/ordered-data.c:390 at
>> can_finish_ordered_extent.isra.0+0x56/0x1f0 [btrfs], CPU#1: kworker/
>> u42:0/68
>> CPU: 1 UID: 0 PID: 68 Comm: kworker/u42:0 Tainted: G
>> E 7.2.0-rc4-custom+ #415 PREEMPT(full)
>> 74dbeafab12c410178747d5bec9fb200ae56949f
>> Hardware name: QEMU Standard PC (Q35 + ICH9, 2009), BIOS unknown
>> 02/02/2022
>> Workqueue: btrfs-endio simple_end_io_work [btrfs]
>> RIP: 0010:can_finish_ordered_extent.isra.0+0x56/0x1f0 [btrfs]
>> Call Trace:
>> <TASK>
>> btrfs_finish_ordered_extent+0x39/0xd0 [btrfs
>> 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
>> end_bbio_data_write+0x1ff/0x280 [btrfs
>> 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
>> btrfs_bio_end_io+0x76/0xf0 [btrfs
>> 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
>> process_one_work+0x198/0x380
>> worker_thread+0x1c8/0x330
>> kthread+0xee/0x120
>> ret_from_fork+0x28f/0x310
>> ret_from_fork_asm+0x11/0x20
>> </TASK>
>> ---[ end trace 0000000000000000 ]---
>> BTRFS critical (device dm-3): bad ordered extent accounting, root=5
>> ino=257 OE offset=3465216 OE len=2826240 to_dec=319488 left=135168
>>
>> Unfortunately we have removed cow fixup mechanism, which is to work
>> around such dirty folios by re-dirtying them and reserve space for them,
>> across several kernel releases, meaning we can not easily revert a
>> single commit to bring it back.
>> And without doubt, that old cow fixup mechanism is not support larger
>> folios.
>>
>> As a hot fix, disable btrfs direct reads for non-experimental builds for
>> now, so this can buy some time before we find out a proper way to address
>> this.
>>
>> Reported-by: Christian Borntraeger <borntraeger@linux.ibm.com>
>> Link: https://lore.kernel.org/linux-btrfs/f12f70e5-d84d-4a9f-
>> ac94-693be4c863ac@linux.ibm.com/
>> Signed-off-by: Qu Wenruo <wqu@suse.com>
>
>
> Wow that is a big hammer. Doesnt that break typical usecases (like
> databases on a file,
> qemu/kvm aio+direct image files etc)?
It falls back to buffered read, which has a good side effect that if the
reader is also modifying the buffer, it will not cause a csum mismatch
warning.
Although it causes huge performance drop.
>
> Even worse, this does not fix the other GUP use cases that still exist?
> So its only
> a partial fix. Have you considered to add my RFC patch on top to close
> another
> problem that I can reproduce easily.
Because that doesn't fix the problem at all.
It's just masking a corner error.
With or without your RFC, on x86_64 with large folios disable
intentionally, it still triggers the OE accounting problem mentioned in
the commit message.
I believe if you switch an older kernel, or disable large folios
manually (reverting commit 9bce95edb1b4d2802de9273b5170bfcff3090d24),
then you should hit the same warning on s390x, and also fail the
reproducer (error out, not hang though).
Again, dirty folios without fs knowing is the root cause, your RFC is
only avoiding one symptom, all the other problems are still not
addressed, and those problems are not any less serious than the hang.
Thanks,
Qu
^ permalink raw reply [flat|nested] 9+ messages in thread
* Help needed to address the dirty folio without fs notification delimma (Re: [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing)
2026-07-23 6:59 ` Qu Wenruo
@ 2026-07-23 9:45 ` Qu Wenruo
2026-07-23 12:37 ` Matthew Wilcox
0 siblings, 1 reply; 9+ messages in thread
From: Qu Wenruo @ 2026-07-23 9:45 UTC (permalink / raw)
To: Christian Borntraeger, linux-btrfs, Linux Memory Management List,
linux-fsdevel@vger.kernel.org
在 2026/7/23 16:29, Qu Wenruo 写道:
>
>
> 在 2026/7/23 16:18, Christian Borntraeger 写道:
>> Am 23.07.26 um 08:13 schrieb Qu Wenruo:
>>> There is a bug report that a reproducer which doing the following
>>> workloads in two threads:
>>>
>>> - Direct read into memory mapped from page cache
>>> - Sync the above range
>>>
>>> This can lead to dirty folios without fs knowing, this can be a huge
>>> problem for btrfs, as even on the very basic bs == ps cases without
>>> large folios, such reproducer can screw up the ordered extent accounting
>>> already:
>>>
>>> ------------[ cut here ]------------
>>> WARNING: fs/btrfs/ordered-data.c:390 at
>>> can_finish_ordered_extent.isra.0+0x56/0x1f0 [btrfs], CPU#1: kworker/
>>> u42:0/68
>>> CPU: 1 UID: 0 PID: 68 Comm: kworker/u42:0 Tainted: G E 7.2.0-
>>> rc4-custom+ #415 PREEMPT(full) 74dbeafab12c410178747d5bec9fb200ae56949f
>>> Hardware name: QEMU Standard PC (Q35 + ICH9, 2009), BIOS unknown
>>> 02/02/2022
>>> Workqueue: btrfs-endio simple_end_io_work [btrfs]
>>> RIP: 0010:can_finish_ordered_extent.isra.0+0x56/0x1f0 [btrfs]
>>> Call Trace:
>>> <TASK>
>>> btrfs_finish_ordered_extent+0x39/0xd0 [btrfs
>>> 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
>>> end_bbio_data_write+0x1ff/0x280 [btrfs
>>> 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
>>> btrfs_bio_end_io+0x76/0xf0 [btrfs
>>> 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
>>> process_one_work+0x198/0x380
>>> worker_thread+0x1c8/0x330
>>> kthread+0xee/0x120
>>> ret_from_fork+0x28f/0x310
>>> ret_from_fork_asm+0x11/0x20
>>> </TASK>
>>> ---[ end trace 0000000000000000 ]---
>>> BTRFS critical (device dm-3): bad ordered extent accounting, root=5
>>> ino=257 OE offset=3465216 OE len=2826240 to_dec=319488 left=135168
>>>
>>> Unfortunately we have removed cow fixup mechanism, which is to work
>>> around such dirty folios by re-dirtying them and reserve space for them,
>>> across several kernel releases, meaning we can not easily revert a
>>> single commit to bring it back.
>>> And without doubt, that old cow fixup mechanism is not support larger
>>> folios.
>>>
>>> As a hot fix, disable btrfs direct reads for non-experimental builds for
>>> now, so this can buy some time before we find out a proper way to
>>> address
>>> this.
>>>
>>> Reported-by: Christian Borntraeger <borntraeger@linux.ibm.com>
>>> Link: https://lore.kernel.org/linux-btrfs/f12f70e5-d84d-4a9f-
>>> ac94-693be4c863ac@linux.ibm.com/
>>> Signed-off-by: Qu Wenruo <wqu@suse.com>
>>
>>
>> Wow that is a big hammer. Doesnt that break typical usecases (like
>> databases on a file,
>> qemu/kvm aio+direct image files etc)?
>
> It falls back to buffered read, which has a good side effect that if the
> reader is also modifying the buffer, it will not cause a csum mismatch
> warning.
>
> Although it causes huge performance drop.
>
>>
>> Even worse, this does not fix the other GUP use cases that still
>> exist? So its only
>> a partial fix. Have you considered to add my RFC patch on top to close
>> another
>> problem that I can reproduce easily.
BTW, if you really want to get everything fixed for the very basic bs ==
ps cases, you have to go back to v7.0 with CONFIG_BTRFS_EXPERIMENTAL
disabled.
In that kernel we have cow fixup, which is unfortunately removed in
v7.2-rc by commit b2a9f217ad3f ("btrfs: remove the COW fixup mechanism").
With that feature even if the folio is marked dirty without notifying
the fs, we can detect and later re-dirty them and do the proper space
reservation in a workqueue.
But again, that COW fixup mechanism is not well tested (I believed we
shouldn't require it and we never hit any reports about that), and can
not handle large folios or bs < ps cases either.
Furthermore it's not an easy revert in upstream, at least we have a lot
of involved patches that are removing the cow fixup code step by step:
9bce95edb1b4d2802de9273b5170bfcff3090d24 btrfs: move large data folios
out of experimental features
115421e29b845d521e3dc24b67d83e8695f621f6 btrfs: remove folio checked
subpage bitmap tracking
b2a9f217ad3fa8012940744059956b20a3971135 btrfs: remove the COW fixup
mechanism
4927b141877c35b1af4e32c7876cd2e0a0f16196 btrfs: remove folio ordered
flag and subpage bitmap
aea704836e47decbdcac77872385c9a3fb51da42 btrfs: remove
folio_test_ordered() usage
7d97bdca4bcb0e36b2d1251bffac3ff4e4e09c8c btrfs: use dirty flag to check
if an ordered extent needs to be truncated
095be159f3eb4670fab75f795ce9539a381ebd3f btrfs: unify folio dirty flag
clearing
b066155f06eeb4d6d696668cc58b6101adf6c1c2 btrfs: detect dirty blocks
without an ordered extent more reliably
Not to mention there are also quite some conflicts with other changes.
So the assumption of every dirtied page folio is dirtied by either
buffered write or ->page_mkwrite(), is really the core idea of recent
btrfs update and the basis of the subpage support since v5.15.
I do not have any good idea to go forward.
Full revert is hefty and can only handle bs == ps cases, subpage/large
folios are still affected.
Although I can revert the large folio support, that's a pretty cheap one.
The RFC patch from the reporter is not going to address the very basic
bs == ps cases either, just check the OE accounting error message in the
commit message.
Finally I do not have enough mm knowledge to address it from
mm/block/vfs/gup layer either.
So any help/advice on how to address this situation would be very
appreciated.
Thanks,
Qu
>
> Because that doesn't fix the problem at all.
> It's just masking a corner error.
>
> With or without your RFC, on x86_64 with large folios disable
> intentionally, it still triggers the OE accounting problem mentioned in
> the commit message.
>
> I believe if you switch an older kernel, or disable large folios
> manually (reverting commit 9bce95edb1b4d2802de9273b5170bfcff3090d24),
> then you should hit the same warning on s390x, and also fail the
> reproducer (error out, not hang though).
>
>
> Again, dirty folios without fs knowing is the root cause, your RFC is
> only avoiding one symptom, all the other problems are still not
> addressed, and those problems are not any less serious than the hang.
>
> Thanks,
> Qu
>
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing
[not found] <c6dfdac9fc51c94183e51a861eec269185239660.1784787211.git.wqu@suse.com>
2026-07-23 6:48 ` [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing Christian Borntraeger
@ 2026-07-23 10:38 ` Filipe Manana
2026-07-23 11:17 ` Qu Wenruo
2026-07-23 11:31 ` Christoph Hellwig
2 siblings, 1 reply; 9+ messages in thread
From: Filipe Manana @ 2026-07-23 10:38 UTC (permalink / raw)
To: Qu Wenruo; +Cc: linux-btrfs, Christian Borntraeger
On Thu, Jul 23, 2026 at 7:16 AM Qu Wenruo <wqu@suse.com> wrote:
>
> There is a bug report that a reproducer which doing the following
> workloads in two threads:
>
> - Direct read into memory mapped from page cache
> - Sync the above range
>
> This can lead to dirty folios without fs knowing, this can be a huge
Can you please explain where, and why, the folio is dirtied?
How does a direct IO read dirties a folio or a sync_file_range(2) call?
Thanks.
> problem for btrfs, as even on the very basic bs == ps cases without
> large folios, such reproducer can screw up the ordered extent accounting
> already:
>
> ------------[ cut here ]------------
> WARNING: fs/btrfs/ordered-data.c:390 at can_finish_ordered_extent.isra.0+0x56/0x1f0 [btrfs], CPU#1: kworker/u42:0/68
> CPU: 1 UID: 0 PID: 68 Comm: kworker/u42:0 Tainted: G E 7.2.0-rc4-custom+ #415 PREEMPT(full) 74dbeafab12c410178747d5bec9fb200ae56949f
> Hardware name: QEMU Standard PC (Q35 + ICH9, 2009), BIOS unknown 02/02/2022
> Workqueue: btrfs-endio simple_end_io_work [btrfs]
> RIP: 0010:can_finish_ordered_extent.isra.0+0x56/0x1f0 [btrfs]
> Call Trace:
> <TASK>
> btrfs_finish_ordered_extent+0x39/0xd0 [btrfs 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
> end_bbio_data_write+0x1ff/0x280 [btrfs 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
> btrfs_bio_end_io+0x76/0xf0 [btrfs 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
> process_one_work+0x198/0x380
> worker_thread+0x1c8/0x330
> kthread+0xee/0x120
> ret_from_fork+0x28f/0x310
> ret_from_fork_asm+0x11/0x20
> </TASK>
> ---[ end trace 0000000000000000 ]---
> BTRFS critical (device dm-3): bad ordered extent accounting, root=5 ino=257 OE offset=3465216 OE len=2826240 to_dec=319488 left=135168
>
> Unfortunately we have removed cow fixup mechanism, which is to work
> around such dirty folios by re-dirtying them and reserve space for them,
> across several kernel releases, meaning we can not easily revert a
> single commit to bring it back.
> And without doubt, that old cow fixup mechanism is not support larger
> folios.
>
> As a hot fix, disable btrfs direct reads for non-experimental builds for
> now, so this can buy some time before we find out a proper way to address
> this.
>
> Reported-by: Christian Borntraeger <borntraeger@linux.ibm.com>
> Link: https://lore.kernel.org/linux-btrfs/f12f70e5-d84d-4a9f-ac94-693be4c863ac@linux.ibm.com/
> Signed-off-by: Qu Wenruo <wqu@suse.com>
> ---
> Changelog:
> v2:
> - Fallback to buffered IO to avoid failing existing direct IO users
>
> - Allow direct writes
>
> Reason for RFC:
> I'm not 100% sure if disabling direct IOs can fill all the holes.
>
> We still allow mmapping page cache into user spaces, thus I'm not sure
> if this is the only hole.
> ---
> fs/btrfs/direct-io.c | 5 +++++
> 1 file changed, 5 insertions(+)
>
> diff --git a/fs/btrfs/direct-io.c b/fs/btrfs/direct-io.c
> index ed1779ccb4de..32b29a4faaf2 100644
> --- a/fs/btrfs/direct-io.c
> +++ b/fs/btrfs/direct-io.c
> @@ -1093,6 +1093,11 @@ ssize_t btrfs_direct_read(struct kiocb *iocb, struct iov_iter *to)
> if (check_direct_read(inode_to_fs_info(inode), to, iocb->ki_pos))
> return 0;
>
> +#ifndef CONFIG_BTRFS_EXPERIMENTAL
> + /* To avoid dirty folios without fs knowing through */
> + return 0;
> +#endif
> +
> btrfs_inode_lock(BTRFS_I(inode), BTRFS_ILOCK_SHARED);
> again:
> /*
> --
> 2.54.0
>
>
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing
2026-07-23 10:38 ` [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing Filipe Manana
@ 2026-07-23 11:17 ` Qu Wenruo
2026-07-23 11:23 ` Filipe Manana
0 siblings, 1 reply; 9+ messages in thread
From: Qu Wenruo @ 2026-07-23 11:17 UTC (permalink / raw)
To: Filipe Manana, Qu Wenruo; +Cc: linux-btrfs, Christian Borntraeger
在 2026/7/23 20:08, Filipe Manana 写道:
> On Thu, Jul 23, 2026 at 7:16 AM Qu Wenruo <wqu@suse.com> wrote:
>>
>> There is a bug report that a reproducer which doing the following
>> workloads in two threads:
>>
>> - Direct read into memory mapped from page cache
>> - Sync the above range
>>
>> This can lead to dirty folios without fs knowing, this can be a huge
>
> Can you please explain where, and why, the folio is dirtied?
btrfs_check_read_bio()
|- __iomap_dio_bio_end_io() from btrfs_bio_end_io()
|- bio_check_pages_dirty()
|- bio_dirty_fn()
|- bio_release_pages(bio, true)
|- __bio_release_pages(bio, mark_dirty == true)
|- folio_mark_dirty()
At least this is the one from the reproducer.
Thanks,
Qu
>
> How does a direct IO read dirties a folio or a sync_file_range(2) call?
>
> Thanks.
>
>> problem for btrfs, as even on the very basic bs == ps cases without
>> large folios, such reproducer can screw up the ordered extent accounting
>> already:
>>
>> ------------[ cut here ]------------
>> WARNING: fs/btrfs/ordered-data.c:390 at can_finish_ordered_extent.isra.0+0x56/0x1f0 [btrfs], CPU#1: kworker/u42:0/68
>> CPU: 1 UID: 0 PID: 68 Comm: kworker/u42:0 Tainted: G E 7.2.0-rc4-custom+ #415 PREEMPT(full) 74dbeafab12c410178747d5bec9fb200ae56949f
>> Hardware name: QEMU Standard PC (Q35 + ICH9, 2009), BIOS unknown 02/02/2022
>> Workqueue: btrfs-endio simple_end_io_work [btrfs]
>> RIP: 0010:can_finish_ordered_extent.isra.0+0x56/0x1f0 [btrfs]
>> Call Trace:
>> <TASK>
>> btrfs_finish_ordered_extent+0x39/0xd0 [btrfs 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
>> end_bbio_data_write+0x1ff/0x280 [btrfs 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
>> btrfs_bio_end_io+0x76/0xf0 [btrfs 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
>> process_one_work+0x198/0x380
>> worker_thread+0x1c8/0x330
>> kthread+0xee/0x120
>> ret_from_fork+0x28f/0x310
>> ret_from_fork_asm+0x11/0x20
>> </TASK>
>> ---[ end trace 0000000000000000 ]---
>> BTRFS critical (device dm-3): bad ordered extent accounting, root=5 ino=257 OE offset=3465216 OE len=2826240 to_dec=319488 left=135168
>>
>> Unfortunately we have removed cow fixup mechanism, which is to work
>> around such dirty folios by re-dirtying them and reserve space for them,
>> across several kernel releases, meaning we can not easily revert a
>> single commit to bring it back.
>> And without doubt, that old cow fixup mechanism is not support larger
>> folios.
>>
>> As a hot fix, disable btrfs direct reads for non-experimental builds for
>> now, so this can buy some time before we find out a proper way to address
>> this.
>>
>> Reported-by: Christian Borntraeger <borntraeger@linux.ibm.com>
>> Link: https://lore.kernel.org/linux-btrfs/f12f70e5-d84d-4a9f-ac94-693be4c863ac@linux.ibm.com/
>> Signed-off-by: Qu Wenruo <wqu@suse.com>
>> ---
>> Changelog:
>> v2:
>> - Fallback to buffered IO to avoid failing existing direct IO users
>>
>> - Allow direct writes
>>
>> Reason for RFC:
>> I'm not 100% sure if disabling direct IOs can fill all the holes.
>>
>> We still allow mmapping page cache into user spaces, thus I'm not sure
>> if this is the only hole.
>> ---
>> fs/btrfs/direct-io.c | 5 +++++
>> 1 file changed, 5 insertions(+)
>>
>> diff --git a/fs/btrfs/direct-io.c b/fs/btrfs/direct-io.c
>> index ed1779ccb4de..32b29a4faaf2 100644
>> --- a/fs/btrfs/direct-io.c
>> +++ b/fs/btrfs/direct-io.c
>> @@ -1093,6 +1093,11 @@ ssize_t btrfs_direct_read(struct kiocb *iocb, struct iov_iter *to)
>> if (check_direct_read(inode_to_fs_info(inode), to, iocb->ki_pos))
>> return 0;
>>
>> +#ifndef CONFIG_BTRFS_EXPERIMENTAL
>> + /* To avoid dirty folios without fs knowing through */
>> + return 0;
>> +#endif
>> +
>> btrfs_inode_lock(BTRFS_I(inode), BTRFS_ILOCK_SHARED);
>> again:
>> /*
>> --
>> 2.54.0
>>
>>
>
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing
2026-07-23 11:17 ` Qu Wenruo
@ 2026-07-23 11:23 ` Filipe Manana
2026-07-23 11:45 ` Christian Borntraeger
0 siblings, 1 reply; 9+ messages in thread
From: Filipe Manana @ 2026-07-23 11:23 UTC (permalink / raw)
To: Qu Wenruo; +Cc: Qu Wenruo, linux-btrfs, Christian Borntraeger
On Thu, Jul 23, 2026 at 12:17 PM Qu Wenruo <quwenruo.btrfs@gmx.com> wrote:
>
>
>
> 在 2026/7/23 20:08, Filipe Manana 写道:
> > On Thu, Jul 23, 2026 at 7:16 AM Qu Wenruo <wqu@suse.com> wrote:
> >>
> >> There is a bug report that a reproducer which doing the following
> >> workloads in two threads:
> >>
> >> - Direct read into memory mapped from page cache
> >> - Sync the above range
> >>
> >> This can lead to dirty folios without fs knowing, this can be a huge
> >
> > Can you please explain where, and why, the folio is dirtied?
>
>
> btrfs_check_read_bio()
> |- __iomap_dio_bio_end_io() from btrfs_bio_end_io()
> |- bio_check_pages_dirty()
> |- bio_dirty_fn()
> |- bio_release_pages(bio, true)
> |- __bio_release_pages(bio, mark_dirty == true)
> |- folio_mark_dirty()
>
> At least this is the one from the reproducer.
That should be part of the change log, it's not obvious at all.
I also wonder why a direct IO read dirties the folio if it's not
supposed to change file data.
>
> Thanks,
> Qu
>
> >
> > How does a direct IO read dirties a folio or a sync_file_range(2) call?
> >
> > Thanks.
> >
> >> problem for btrfs, as even on the very basic bs == ps cases without
> >> large folios, such reproducer can screw up the ordered extent accounting
> >> already:
> >>
> >> ------------[ cut here ]------------
> >> WARNING: fs/btrfs/ordered-data.c:390 at can_finish_ordered_extent.isra.0+0x56/0x1f0 [btrfs], CPU#1: kworker/u42:0/68
> >> CPU: 1 UID: 0 PID: 68 Comm: kworker/u42:0 Tainted: G E 7.2.0-rc4-custom+ #415 PREEMPT(full) 74dbeafab12c410178747d5bec9fb200ae56949f
> >> Hardware name: QEMU Standard PC (Q35 + ICH9, 2009), BIOS unknown 02/02/2022
> >> Workqueue: btrfs-endio simple_end_io_work [btrfs]
> >> RIP: 0010:can_finish_ordered_extent.isra.0+0x56/0x1f0 [btrfs]
> >> Call Trace:
> >> <TASK>
> >> btrfs_finish_ordered_extent+0x39/0xd0 [btrfs 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
> >> end_bbio_data_write+0x1ff/0x280 [btrfs 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
> >> btrfs_bio_end_io+0x76/0xf0 [btrfs 7d1ffd99bb9696179883f257e5fd838e2d1a0ca3]
> >> process_one_work+0x198/0x380
> >> worker_thread+0x1c8/0x330
> >> kthread+0xee/0x120
> >> ret_from_fork+0x28f/0x310
> >> ret_from_fork_asm+0x11/0x20
> >> </TASK>
> >> ---[ end trace 0000000000000000 ]---
> >> BTRFS critical (device dm-3): bad ordered extent accounting, root=5 ino=257 OE offset=3465216 OE len=2826240 to_dec=319488 left=135168
> >>
> >> Unfortunately we have removed cow fixup mechanism, which is to work
> >> around such dirty folios by re-dirtying them and reserve space for them,
> >> across several kernel releases, meaning we can not easily revert a
> >> single commit to bring it back.
> >> And without doubt, that old cow fixup mechanism is not support larger
> >> folios.
> >>
> >> As a hot fix, disable btrfs direct reads for non-experimental builds for
> >> now, so this can buy some time before we find out a proper way to address
> >> this.
> >>
> >> Reported-by: Christian Borntraeger <borntraeger@linux.ibm.com>
> >> Link: https://lore.kernel.org/linux-btrfs/f12f70e5-d84d-4a9f-ac94-693be4c863ac@linux.ibm.com/
> >> Signed-off-by: Qu Wenruo <wqu@suse.com>
> >> ---
> >> Changelog:
> >> v2:
> >> - Fallback to buffered IO to avoid failing existing direct IO users
> >>
> >> - Allow direct writes
> >>
> >> Reason for RFC:
> >> I'm not 100% sure if disabling direct IOs can fill all the holes.
> >>
> >> We still allow mmapping page cache into user spaces, thus I'm not sure
> >> if this is the only hole.
> >> ---
> >> fs/btrfs/direct-io.c | 5 +++++
> >> 1 file changed, 5 insertions(+)
> >>
> >> diff --git a/fs/btrfs/direct-io.c b/fs/btrfs/direct-io.c
> >> index ed1779ccb4de..32b29a4faaf2 100644
> >> --- a/fs/btrfs/direct-io.c
> >> +++ b/fs/btrfs/direct-io.c
> >> @@ -1093,6 +1093,11 @@ ssize_t btrfs_direct_read(struct kiocb *iocb, struct iov_iter *to)
> >> if (check_direct_read(inode_to_fs_info(inode), to, iocb->ki_pos))
> >> return 0;
> >>
> >> +#ifndef CONFIG_BTRFS_EXPERIMENTAL
> >> + /* To avoid dirty folios without fs knowing through */
> >> + return 0;
> >> +#endif
> >> +
> >> btrfs_inode_lock(BTRFS_I(inode), BTRFS_ILOCK_SHARED);
> >> again:
> >> /*
> >> --
> >> 2.54.0
> >>
> >>
> >
>
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing
[not found] <c6dfdac9fc51c94183e51a861eec269185239660.1784787211.git.wqu@suse.com>
2026-07-23 6:48 ` [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing Christian Borntraeger
2026-07-23 10:38 ` [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing Filipe Manana
@ 2026-07-23 11:31 ` Christoph Hellwig
2 siblings, 0 replies; 9+ messages in thread
From: Christoph Hellwig @ 2026-07-23 11:31 UTC (permalink / raw)
To: Qu Wenruo; +Cc: linux-btrfs, Christian Borntraeger
On Thu, Jul 23, 2026 at 03:43:40PM +0930, Qu Wenruo wrote:
> There is a bug report that a reproducer which doing the following
> workloads in two threads:
>
> - Direct read into memory mapped from page cache
> - Sync the above range
>
> This can lead to dirty folios without fs knowing, this can be a huge
> problem for btrfs, as even on the very basic bs == ps cases without
> large folios, such reproducer can screw up the ordered extent accounting
> already:
Disabling direct I/O on btrfs is not going to help you with that,
as you could still call the direct I/O read operation on another
file system (or a block device, or various other direct I/O like
things) on the btrfs file mapping.
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing
2026-07-23 11:23 ` Filipe Manana
@ 2026-07-23 11:45 ` Christian Borntraeger
0 siblings, 0 replies; 9+ messages in thread
From: Christian Borntraeger @ 2026-07-23 11:45 UTC (permalink / raw)
To: Filipe Manana, Qu Wenruo; +Cc: Qu Wenruo, linux-btrfs
Am 23.07.26 um 13:23 schrieb Filipe Manana:
> On Thu, Jul 23, 2026 at 12:17 PM Qu Wenruo <quwenruo.btrfs@gmx.com> wrote:
>>
>>
>>
>> 在 2026/7/23 20:08, Filipe Manana 写道:
>>> On Thu, Jul 23, 2026 at 7:16 AM Qu Wenruo <wqu@suse.com> wrote:
>>>>
>>>> There is a bug report that a reproducer which doing the following
>>>> workloads in two threads:
>>>>
>>>> - Direct read into memory mapped from page cache
>>>> - Sync the above range
>>>>
>>>> This can lead to dirty folios without fs knowing, this can be a huge
>>>
>>> Can you please explain where, and why, the folio is dirtied?
>>
>>
>> btrfs_check_read_bio()
>> |- __iomap_dio_bio_end_io() from btrfs_bio_end_io()
>> |- bio_check_pages_dirty()
>> |- bio_dirty_fn()
>> |- bio_release_pages(bio, true)
>> |- __bio_release_pages(bio, mark_dirty == true)
>> |- folio_mark_dirty()
>>
>> At least this is the one from the reproducer.
>
> That should be part of the change log, it's not obvious at all.
> I also wonder why a direct IO read dirties the folio if it's not
> supposed to change file data.
>
>>
See also the initial discussion here
https://lore.kernel.org/linux-s390/79b9b1b2-0455-4a7c-85fd-929f4103f198@gmx.com/T/#m31c388aa6bbfb77c689ff95b5a35c4db5fc231c3
In essence any gup+set_page_dirty_lock user can trigger inconsistencies. We found that
as this resulted in lockups and the O_DIRECT use case was just a reproducer that does
not need a kernel module.
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: Help needed to address the dirty folio without fs notification delimma (Re: [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing)
2026-07-23 9:45 ` Help needed to address the dirty folio without fs notification delimma (Re: [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing) Qu Wenruo
@ 2026-07-23 12:37 ` Matthew Wilcox
0 siblings, 0 replies; 9+ messages in thread
From: Matthew Wilcox @ 2026-07-23 12:37 UTC (permalink / raw)
To: Qu Wenruo
Cc: Christian Borntraeger, linux-btrfs, Linux Memory Management List,
linux-fsdevel@vger.kernel.org
On Thu, Jul 23, 2026 at 07:15:40PM +0930, Qu Wenruo wrote:
> With that feature even if the folio is marked dirty without notifying the
> fs, we can detect and later re-dirty them and do the proper space
> reservation in a workqueue.
Oh good, you started another thread for the same problem. I alreaday
told you what the problem is; you're not listening to the ->dirty_folio()
call; you're just passing it straight through to the VFS.
^ permalink raw reply [flat|nested] 9+ messages in thread
end of thread, other threads:[~2026-07-23 12:37 UTC | newest]
Thread overview: 9+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
[not found] <c6dfdac9fc51c94183e51a861eec269185239660.1784787211.git.wqu@suse.com>
2026-07-23 6:48 ` [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing Christian Borntraeger
2026-07-23 6:59 ` Qu Wenruo
2026-07-23 9:45 ` Help needed to address the dirty folio without fs notification delimma (Re: [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing) Qu Wenruo
2026-07-23 12:37 ` Matthew Wilcox
2026-07-23 10:38 ` [PATCH RFC v2] btrfs: disable direct reads to avoid dirty folios without fs knowing Filipe Manana
2026-07-23 11:17 ` Qu Wenruo
2026-07-23 11:23 ` Filipe Manana
2026-07-23 11:45 ` Christian Borntraeger
2026-07-23 11:31 ` Christoph Hellwig
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox