* [PATCH] netfs: Fix UAF in netfs_unbuffered_write() on failed preparation
@ 2026-05-30 1:14 hongao
2026-06-23 10:28 ` Christian Brauner
` (2 more replies)
0 siblings, 3 replies; 9+ messages in thread
From: hongao @ 2026-05-30 1:14 UTC (permalink / raw)
To: David Howells
Cc: Paulo Alcantara, netfs, linux-fsdevel, linux-kernel, hongao,
syzbot+3c74b1f0c372e98efc32
If write subrequest preparation fails, netfs_unbuffered_write() calls
netfs_write_subrequest_terminated() and then reads subreq->error to set
wreq->error.
However, netfs_write_subrequest_terminated() consumes a reference to the
subrequest through netfs_put_subrequest(), so the subrequest may be freed
before netfs_unbuffered_write() reads subreq->error again. This can
trigger a slab-use-after-free.
Save the error locally before terminating the subrequest, and use the
saved value afterwards.
Fixes: a0b4c7a49137 ("netfs: Fix unbuffered/DIO writes to dispatch subrequests in strict sequence")
Reported-by: syzbot+3c74b1f0c372e98efc32@syzkaller.appspotmail.com
Closes: https://syzkaller.appspot.com/bug?extid=3c74b1f0c372e98efc32
Signed-off-by: hongao <hongao@uniontech.com>
---
fs/netfs/direct_write.c | 5 +++--
1 file changed, 3 insertions(+), 2 deletions(-)
diff --git a/fs/netfs/direct_write.c b/fs/netfs/direct_write.c
index 25f8ceb15fad..2d5361702076 100644
--- a/fs/netfs/direct_write.c
+++ b/fs/netfs/direct_write.c
@@ -115,8 +115,9 @@ static int netfs_unbuffered_write(struct netfs_io_request *wreq)
/* Check if (re-)preparation failed. */
if (unlikely(test_bit(NETFS_SREQ_FAILED, &subreq->flags))) {
- netfs_write_subrequest_terminated(subreq, subreq->error);
- wreq->error = subreq->error;
+ ret = subreq->error;
+ wreq->error = ret;
+ netfs_write_subrequest_terminated(subreq, ret);
break;
}
--
2.51.0
^ permalink raw reply related [flat|nested] 9+ messages in thread
* Re: [PATCH] netfs: Fix UAF in netfs_unbuffered_write() on failed preparation
2026-05-30 1:14 [PATCH] netfs: Fix UAF in netfs_unbuffered_write() on failed preparation hongao
@ 2026-06-23 10:28 ` Christian Brauner
2026-06-23 11:52 ` ChenXiaoSong
2026-06-23 14:53 ` David Howells
2 siblings, 0 replies; 9+ messages in thread
From: Christian Brauner @ 2026-06-23 10:28 UTC (permalink / raw)
To: hongao
Cc: David Howells, Paulo Alcantara, netfs, linux-fsdevel,
linux-kernel, syzbot+3c74b1f0c372e98efc32
On 2026-05-30 09:14 +0800, hongao wrote:
> If write subrequest preparation fails, netfs_unbuffered_write() calls
> netfs_write_subrequest_terminated() and then reads subreq->error to set
> wreq->error.
>
> However, netfs_write_subrequest_terminated() consumes a reference to the
> subrequest through netfs_put_subrequest(), so the subrequest may be freed
> before netfs_unbuffered_write() reads subreq->error again. This can
> trigger a slab-use-after-free.
>
> Save the error locally before terminating the subrequest, and use the
> saved value afterwards.
>
> Fixes: a0b4c7a49137 ("netfs: Fix unbuffered/DIO writes to dispatch subrequests in strict sequence")
> Reported-by: syzbot+3c74b1f0c372e98efc32@syzkaller.appspotmail.com
> Closes: https://syzkaller.appspot.com/bug?extid=3c74b1f0c372e98efc32
>
> Signed-off-by: hongao <hongao@uniontech.com>
> ---
David?
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH] netfs: Fix UAF in netfs_unbuffered_write() on failed preparation
2026-05-30 1:14 [PATCH] netfs: Fix UAF in netfs_unbuffered_write() on failed preparation hongao
2026-06-23 10:28 ` Christian Brauner
@ 2026-06-23 11:52 ` ChenXiaoSong
2026-06-23 16:10 ` David Howells
2026-06-23 14:53 ` David Howells
2 siblings, 1 reply; 9+ messages in thread
From: ChenXiaoSong @ 2026-06-23 11:52 UTC (permalink / raw)
To: hongao, David Howells
Cc: Paulo Alcantara, netfs, linux-fsdevel, linux-kernel,
syzbot+3c74b1f0c372e98efc32
Hi hongao and David,
After applying this patch, I can still reproduce the use-after-free issue.
C reproducer: https://syzkaller.appspot.com/text?tag=ReproC&x=171b697e580000
Note that QEMU should be started with the following virtfs option:
-virtfs ...,mount_tag=syz,...
On 5/30/26 09:14, hongao wrote:
> If write subrequest preparation fails, netfs_unbuffered_write() calls
> netfs_write_subrequest_terminated() and then reads subreq->error to set
> wreq->error.
>
> However, netfs_write_subrequest_terminated() consumes a reference to the
> subrequest through netfs_put_subrequest(), so the subrequest may be freed
> before netfs_unbuffered_write() reads subreq->error again. This can
> trigger a slab-use-after-free.
>
> Save the error locally before terminating the subrequest, and use the
> saved value afterwards.
>
> Fixes: a0b4c7a49137 ("netfs: Fix unbuffered/DIO writes to dispatch subrequests in strict sequence")
> Reported-by: syzbot+3c74b1f0c372e98efc32@syzkaller.appspotmail.com
> Closes: https://syzkaller.appspot.com/bug?extid=3c74b1f0c372e98efc32
>
> Signed-off-by: hongao <hongao@uniontech.com>
> ---
> fs/netfs/direct_write.c | 5 +++--
> 1 file changed, 3 insertions(+), 2 deletions(-)
>
> diff --git a/fs/netfs/direct_write.c b/fs/netfs/direct_write.c
> index 25f8ceb15fad..2d5361702076 100644
> --- a/fs/netfs/direct_write.c
> +++ b/fs/netfs/direct_write.c
> @@ -115,8 +115,9 @@ static int netfs_unbuffered_write(struct netfs_io_request *wreq)
>
> /* Check if (re-)preparation failed. */
> if (unlikely(test_bit(NETFS_SREQ_FAILED, &subreq->flags))) {
> - netfs_write_subrequest_terminated(subreq, subreq->error);
> - wreq->error = subreq->error;
> + ret = subreq->error;
> + wreq->error = ret;
> + netfs_write_subrequest_terminated(subreq, ret);
> break;
> }
>
--
ChenXiaoSong <chenxiaosong@chenxiaosong.com>
Chinese Homepage: https://chenxiaosong.com
English Homepage: https://chenxiaosong.com/en
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH] netfs: Fix UAF in netfs_unbuffered_write() on failed preparation
2026-05-30 1:14 [PATCH] netfs: Fix UAF in netfs_unbuffered_write() on failed preparation hongao
2026-06-23 10:28 ` Christian Brauner
2026-06-23 11:52 ` ChenXiaoSong
@ 2026-06-23 14:53 ` David Howells
2 siblings, 0 replies; 9+ messages in thread
From: David Howells @ 2026-06-23 14:53 UTC (permalink / raw)
To: hongao
Cc: dhowells, Paulo Alcantara, netfs, linux-fsdevel, linux-kernel,
syzbot+3c74b1f0c372e98efc32
hongao <hongao@uniontech.com> wrote:
> /* Check if (re-)preparation failed. */
> if (unlikely(test_bit(NETFS_SREQ_FAILED, &subreq->flags))) {
> - netfs_write_subrequest_terminated(subreq, subreq->error);
> - wreq->error = subreq->error;
> + ret = subreq->error;
> + wreq->error = ret;
> + netfs_write_subrequest_terminated(subreq, ret);
> break;
> }
This shouldn't be effective as all netfs_write_subrequest_terminated() will do
is pass control of the subreq struct back to the app thread.
David
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH] netfs: Fix UAF in netfs_unbuffered_write() on failed preparation
2026-06-23 11:52 ` ChenXiaoSong
@ 2026-06-23 16:10 ` David Howells
2026-06-24 1:26 ` ChenXiaoSong
0 siblings, 1 reply; 9+ messages in thread
From: David Howells @ 2026-06-23 16:10 UTC (permalink / raw)
To: ChenXiaoSong
Cc: dhowells, hongao, Paulo Alcantara, netfs, linux-fsdevel,
linux-kernel, syzbot+3c74b1f0c372e98efc32
ChenXiaoSong <chenxiaosong@chenxiaosong.com> wrote:
> After applying this patch, I can still reproduce the use-after-free issue.
Can you get some tracing? I have a suspicion it's a refcount bug.
The following tracepoints would be useful:
echo 1 > /sys/kernel/tracing/events/netfs/netfs_read/enable
echo 1 > /sys/kernel/tracing/events/netfs/netfs_write/enable
echo 1 > /sys/kernel/tracing/events/netfs/netfs_rreq/enable
echo 1 > /sys/kernel/tracing/events/netfs/netfs_sreq/enable
echo 1 > /sys/kernel/tracing/events/netfs/netfs_failure/enable
echo 1 > /sys/kernel/tracing/events/error_report/enable
And if you can capture this, can you compress the resulting trace and send it
to me?
Thanks,
David
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH] netfs: Fix UAF in netfs_unbuffered_write() on failed preparation
2026-06-23 16:10 ` David Howells
@ 2026-06-24 1:26 ` ChenXiaoSong
2026-06-24 7:36 ` David Howells
` (2 more replies)
0 siblings, 3 replies; 9+ messages in thread
From: ChenXiaoSong @ 2026-06-24 1:26 UTC (permalink / raw)
To: David Howells, hongao
Cc: Paulo Alcantara, netfs, linux-fsdevel, linux-kernel,
syzbot+3c74b1f0c372e98efc32, Steve French, Namjae Jeon,
linux-cifs@vger.kernel.org
Hi David and hongao,
Please refer to my blog for the tracing log and reproduction steps:
https://chenxiaosong.com/en/netfs-uaf-in-netfs_unbuffered_write.html (I
will make sure this link is always accessible)
I would appreciate it if you could continue debugging and fixing this
issue. As I have many SMB features to implement and review tasks to do.
On 6/24/26 00:10, David Howells wrote:
> ChenXiaoSong <chenxiaosong@chenxiaosong.com> wrote:
>
>> After applying this patch, I can still reproduce the use-after-free issue.
>
> Can you get some tracing? I have a suspicion it's a refcount bug.
>
> The following tracepoints would be useful:
>
> echo 1 > /sys/kernel/tracing/events/netfs/netfs_read/enable
> echo 1 > /sys/kernel/tracing/events/netfs/netfs_write/enable
> echo 1 > /sys/kernel/tracing/events/netfs/netfs_rreq/enable
> echo 1 > /sys/kernel/tracing/events/netfs/netfs_sreq/enable
> echo 1 > /sys/kernel/tracing/events/netfs/netfs_failure/enable
> echo 1 > /sys/kernel/tracing/events/error_report/enable
>
> And if you can capture this, can you compress the resulting trace and send it
> to me?
>
> Thanks,
> David
>
--
ChenXiaoSong <chenxiaosong@chenxiaosong.com>
Chinese Homepage: https://chenxiaosong.com
English Homepage: https://chenxiaosong.com/en
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH] netfs: Fix UAF in netfs_unbuffered_write() on failed preparation
2026-06-24 1:26 ` ChenXiaoSong
@ 2026-06-24 7:36 ` David Howells
2026-06-24 10:59 ` David Howells
2026-06-24 11:02 ` David Howells
2 siblings, 0 replies; 9+ messages in thread
From: David Howells @ 2026-06-24 7:36 UTC (permalink / raw)
To: ChenXiaoSong
Cc: dhowells, hongao, Paulo Alcantara, netfs, linux-fsdevel,
linux-kernel, syzbot+3c74b1f0c372e98efc32, Steve French,
Namjae Jeon, linux-cifs@vger.kernel.org
This excerpt would seem to show how the problem comes about:
a.out-717 : netfs_sreq: R=00000001[13] UPLD PREP f=000 s=240000 0/0 s=192 e=0
a.out-717 : netfs_sreq: R=00000001[13] UPLD SUBMT f=100 s=240000 0/20000 s=192 e=0
a.out-717 : netfs_sreq: R=00000001[13] UPLD TERM f=310 s=240000 1fac0/20000 s=160 e=0
a.out-717 : netfs_rreq: R=00000001 UW WAKE-Q f=1801
a.out-717 : netfs_rreq: R=00000001 UW DONE-QUIESCE f=1801
a.out-717 : netfs_sreq: R=00000001[13] UPLD RETRY f=210 s=240000 1fac0/20000 s=160 e=-11
a.out-717 : netfs_sreq: R=00000001[13] UPLD SUBMT f=100 s=240000 0/dbfac0 s=192 e=0
a.out-717 : netfs_failure: R=00000001[13] UPLD f=500 s=240000 0/dbfac0 write e=-5
It looks like there are two issues: firstly, why does the upload stop short?
Presumably that's forced by the test. Secondly, I think it has miscalculated
the subreq size in the retry, hence the EIO.
David
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH] netfs: Fix UAF in netfs_unbuffered_write() on failed preparation
2026-06-24 1:26 ` ChenXiaoSong
2026-06-24 7:36 ` David Howells
@ 2026-06-24 10:59 ` David Howells
2026-06-24 11:02 ` David Howells
2 siblings, 0 replies; 9+ messages in thread
From: David Howells @ 2026-06-24 10:59 UTC (permalink / raw)
To: ChenXiaoSong
Cc: dhowells, hongao, Paulo Alcantara, netfs, linux-fsdevel,
linux-kernel, syzbot+3c74b1f0c372e98efc32, Steve French,
Namjae Jeon, linux-cifs@vger.kernel.org
Actually, this shows what happened:
a.out-717 : netfs_sreq: R=00000001[13] UPLD RETRY f=210 s=240000 1fac0/20000 s=160 e=-11
a.out-717 : netfs_sreq: R=00000001[13] UPLD SUBMT f=100 s=240000 0/dbfac0 s=192 e=0
a.out-717 : netfs_failure: R=00000001[13] UPLD f=500 s=240000 0/dbfac0 write e=-5
a.out-717 : netfs_rreq: R=00000001 UW PAUSE f=1801
a.out-717 : netfs_sreq: R=00000001[13] UPLD TERM f=500 s=240000 0/dbfac0 s=192 e=-5
a.out-717 : netfs_rreq: R=00000001 UW WAKE-Q f=1805
a.out-717 : netfs_failure: R=00000001[13] UPLD f=400 s=240000 0/dbfac0 write e=-5
a.out-717 : netfs_rreq: R=00000001 UW PAUSE f=1805
a.out-717 : netfs_sreq: R=00000001[13] UPLD TERM f=400 s=240000 0/dbfac0 s=192 e=-5
a.out-717 : netfs_rreq: R=00000001 UW WAKE-Q f=1805
a.out-717 : netfs_sreq: R=00000001[13] UPLD FREE f=400 s=240000 0/dbfac0 s=192 e=-5
There are two calls to netfs_write_subrequest_terminated(). You can see the
IN_PROGRESS bit has been cleared by the second one (f=500 -> f=400).
David
^ permalink raw reply [flat|nested] 9+ messages in thread
* Re: [PATCH] netfs: Fix UAF in netfs_unbuffered_write() on failed preparation
2026-06-24 1:26 ` ChenXiaoSong
2026-06-24 7:36 ` David Howells
2026-06-24 10:59 ` David Howells
@ 2026-06-24 11:02 ` David Howells
2 siblings, 0 replies; 9+ messages in thread
From: David Howells @ 2026-06-24 11:02 UTC (permalink / raw)
To: ChenXiaoSong
Cc: dhowells, hongao, Paulo Alcantara, netfs, linux-fsdevel,
linux-kernel, syzbot+3c74b1f0c372e98efc32, Steve French,
Namjae Jeon, linux-cifs@vger.kernel.org
I suspect the issue is this bit in netfs_unbuffered_write():
for (;;) {
...
netfs_get_subrequest(subreq, netfs_sreq_trace_get_resubmit);
if (stream->prepare_write) {
stream->prepare_write(subreq);
__set_bit(NETFS_SREQ_IN_PROGRESS, &subreq->flags);
netfs_stat(&netfs_n_wh_retry_write_subreq);
} else {
struct iov_iter source;
netfs_reset_iter(subreq);
source = subreq->io_iter;
netfs_reissue_write(stream, subreq, &source); <----
}
}
This doesn't happen with AFS because it has a ->prepare_write() method. Does
this change fix the problem for you?
diff --git a/fs/netfs/direct_write.c b/fs/netfs/direct_write.c
index 25f8ceb15fad..9f6258da45d6 100644
--- a/fs/netfs/direct_write.c
+++ b/fs/netfs/direct_write.c
@@ -190,12 +190,6 @@ static int netfs_unbuffered_write(struct netfs_io_request *wreq)
stream->prepare_write(subreq);
__set_bit(NETFS_SREQ_IN_PROGRESS, &subreq->flags);
netfs_stat(&netfs_n_wh_retry_write_subreq);
- } else {
- struct iov_iter source;
-
- netfs_reset_iter(subreq);
- source = subreq->io_iter;
- netfs_reissue_write(stream, subreq, &source);
}
}
David
^ permalink raw reply related [flat|nested] 9+ messages in thread
end of thread, other threads:[~2026-06-24 11:03 UTC | newest]
Thread overview: 9+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2026-05-30 1:14 [PATCH] netfs: Fix UAF in netfs_unbuffered_write() on failed preparation hongao
2026-06-23 10:28 ` Christian Brauner
2026-06-23 11:52 ` ChenXiaoSong
2026-06-23 16:10 ` David Howells
2026-06-24 1:26 ` ChenXiaoSong
2026-06-24 7:36 ` David Howells
2026-06-24 10:59 ` David Howells
2026-06-24 11:02 ` David Howells
2026-06-23 14:53 ` David Howells
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox