Since commit 1e7ab6f678 ("anon_inode: rework assertions"),
path_noexec() warns when an anonymous-inode file is mmap'd from a
superblock that has not set SB_I_NOEXEC. dma-buf backs its files this
way and never set the flag, so mmap of any exported buffer trips the
warning on a CONFIG_DEBUG_VFS=y kernel:
WARNING: CPU: 11 PID: 121813 at fs/exec.c:118 path_noexec+0x47/0x50
do_mmap+0x2b5/0x680
vm_mmap_pgoff+0x129/0x210
ksys_mmap_pgoff+0x177/0x240
__x64_sys_mmap+0x33/0x70
init_pseudo() sets up internal SB_NOUSER mounts that are never
path-reachable. Set both flags here so every pseudo filesystem gets
them by default instead of each caller setting them.
SB_I_NODEV is inert for unreachable mounts. SB_I_NOEXEC has one
visible effect: an executable mapping of a pseudo-fs fd, such as a
dma-buf, now fails with -EPERM, which is the invariant the assertion
enforces. No in-tree caller maps these executable.
Reproduce on CONFIG_DEBUG_VFS=y:
make -C tools/testing/selftests/dmabuf-heaps
sudo ./tools/testing/selftests/dmabuf-heaps/dmabuf-heap -t system
Fixes: 1e7ab6f678 ("anon_inode: rework assertions")
Suggested-by: Christoph Hellwig <hch@infradead.org>
Cc: stable@vger.kernel.org
Signed-off-by: John Hubbard <jhubbard@nvidia.com>
Link: https://patch.msgid.link/20260604025315.245910-2-jhubbard@nvidia.com
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
One should *not* be allowed to mount one of those, new API or not.
Reported-by: Denis Arefev <arefev@swemel.ru>
Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
Link: https://patch.msgid.link/20260602020444.GP2636677@ZenIV
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
A SOFTIRQ-safe to SOFTIRQ-unsafe lock order deadlock can occur in
send_sigio() and send_sigurg() when a process group receives a signal.
When FASYNC is configured for a process group (PIDTYPE_PGID), both
functions use read_lock(&tasklist_lock) to traverse the task list.
However, they are frequently called from softirq context:
- send_sigio() via input_inject_event -> kill_fasync
- send_sigurg() via tcp_check_urg -> sk_send_sigurg (NET_RX_SOFTIRQ)
The deadlock is caused by the rwlock writer fairness mechanism:
1. CPU 0 (process context) holds read_lock(&tasklist_lock) in do_wait().
2. CPU 1 (process context) attempts write_lock(&tasklist_lock) in
fork() or exit() and spins, which blocks all new readers.
3. CPU 0 is interrupted by a softirq (e.g., TCP URG packet reception).
4. The softirq calls send_sigurg() and attempts to acquire
read_lock(&tasklist_lock), deadlocking because CPU 1 is waiting.
Since PID hashing and do_each_pid_task() traversals are already
RCU-protected, the read_lock on tasklist_lock is no longer strictly
required for safe traversal. Fix this by replacing tasklist_lock with
rcu_read_lock(), aligning the process group signaling path with the
single-PID path. This also mitigates a potential remote denial of
service vector via TCP URG packets.
Lockdep splat:
=====================================================
WARNING: SOFTIRQ-safe -> SOFTIRQ-unsafe lock order detected
[...]
Chain exists of:
&dev->event_lock --> &f_owner->lock --> tasklist_lock
Possible interrupt unsafe locking scenario:
CPU0 CPU1
---- ----
lock(tasklist_lock);
local_irq_disable();
lock(&dev->event_lock);
lock(&f_owner->lock);
<Interrupt>
lock(&dev->event_lock);
*** DEADLOCK ***
Reviewed-by: Jeff Layton <jlayton@kernel.org>
Signed-off-by: Mingyu Wang <25181214217@stu.xidian.edu.cn>
Link: https://patch.msgid.link/20260523135210.590928-1-w15303746062@163.com
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
Breno Leitao <leitao@debian.org> says:
While profiling Meta's caching code[1], I found pipe->mutex contention
on the hot path. anon_pipe_write() currently calls alloc_page() once
per page while holding pipe->mutex. The allocation can sleep doing
direct reclaim and runs memcg charging, which extends the critical
section and stalls any concurrent reader on the same mutex.
This series pre-allocates pages outside pipe->mutex in
anon_pipe_write(): for writes that span more than one full page, up
to PIPE_PREALLOC_MAX (8) pages are allocated via a per-page
alloc_page() loop before the mutex is taken. anon_pipe_get_page()
then drains the prealloc array first, falls back to the per-pipe
tmp_page[] cache, and only enters the allocator under the mutex for
the leftover pages (writes larger than PIPE_PREALLOC_MAX, single-page
writes that skip prealloc, or shortfalls when the prealloc loop
fails). Leftover prealloc pages are recycled into tmp_page[] before
unlock and any remainder is put_page()'d after unlock, keeping the
allocator out of the critical section on both sides.
alloc_pages_bulk_mempolicy() looked tempting but the bulk allocator
refuses __GFP_ACCOUNT under memcg -- it returns at most one page
when memcg_kmem_online() && (gfp & __GFP_ACCOUNT), see commit
8dcb3060d8 ("memcg: page_alloc: skip bulk allocator for
__GFP_ACCOUNT"). A per-page loop keeps memcg accounting and the
task NUMA mempolicy honoured uniformly without open-coding the
charge.
I also vibe-coded a microbenchmark to validate the change. It sweeps
writers x readers over {1,2,5} x {1,5,10} with 64KB writes against a
1 MB pipe and prints throughput + latency percentiles per config.
Measured on arm64 and also on x86 using virtme-ng (16 vCPUs, 64KB
writes, 1 MB pipe). The numbers below were collected on v1
(alloc_pages_bulk()); v2's per-page loop preserves the dominant
"allocation outside the mutex" win and is expected to land in the same
range.
== No memory pressure (10s per config) ==
Throughput in MB/s (baseline -> patched, delta):
writers readers=1 readers=5 readers=10
1 1119 -> 1354 (+21%) 1132 -> 1195 (+6%) 1060 -> 1240 (+17%)
2 1162 -> 1487 (+28%) 1034 -> 1285 (+24%) 1069 -> 1213 (+14%)
5 1152 -> 1357 (+18%) 1021 -> 1164 (+14%) 997 -> 1239 (+24%)
Avg write latency in ns (baseline -> patched, delta):
writers readers=1 readers=5 readers=10
1 55786 -> 46103 (-17%) 55164 -> 52260 (-5%) 58906 -> 50370 (-14%)
2 107546 -> 84011 (-22%) 120837 -> 97206 (-20%) 116860 -> 103036 (-12%)
5 271293 -> 230170 (-15%) 306089 -> 268429 (-12%) 313300 -> 252232 (-19%)
Throughput improves +6% to +28% and average write latency drops 5%
to 22% across every configuration.
== Under memory pressure (--memory-pressure, 6s per config) ==
stress-ng --vm 2 --vm-bytes 50% --vm-keep is forked alongside the
sweep so the alloc_page() calls inside anon_pipe_write() routinely
hit direct reclaim -- exactly the regime the patch targets.
Throughput in MB/s (baseline -> patched, delta):
writers readers=1 readers=5 readers=10
1 1088 -> 1438 (+32%) 996 -> 1477 (+48%) 989 -> 1194 (+21%)
2 1076 -> 1378 (+28%) 1007 -> 1269 (+26%) 1018 -> 1234 (+21%)
5 1052 -> 1311 (+25%) 986 -> 1225 (+24%) 972 -> 1249 (+29%)
Avg write latency in ns (baseline -> patched, delta):
writers readers=1 readers=5 readers=10
1 57397 -> 43406 (-24%) 62690 -> 42272 (-33%) 63136 -> 52272 (-17%)
2 116121 -> 90700 (-22%) 124098 -> 98481 (-21%) 122754 -> 101217 (-18%)
5 297122 -> 238322 (-20%) 316836 -> 255095 (-19%) 321496 -> 250189 (-22%)
Throughput improves +21% to +48% and average write latency drops
17% to 33% -- a noticeably bigger win than the no-pressure run.
That tracks: when alloc_page() has to dip into reclaim, the cost
of holding pipe->mutex across it is highest, and pulling the
allocation out of the critical section pays the most.
* patches from https://patch.msgid.link/20260524-fix_pipe-v3-0-bb4a75d23a90@debian.org:
selftests/pipe: add pipe_bench microbenchmark
fs/pipe: pre-allocate pages outside pipe->mutex in anon_pipe_write
Link: https://www.usenix.org/system/files/conference/atc13/atc13-bronson.pdf [1]
Link: https://patch.msgid.link/20260524-fix_pipe-v3-0-bb4a75d23a90@debian.org
Signed-off-by: Christian Brauner <brauner@kernel.org>
Add a small selftest that stresses pipe->mutex contention by spawning N
writer threads that hammer a single pipe with multi-page writes, plus M
reader threads that drain. Each writer records its own write() latency
samples into a log2-bucketed histogram; main aggregates and prints
total writes, throughput, average and percentile (p50/p99) latencies,
and the maximum observed latency.
Pass --memory-pressure to fork stress-ng (--vm 4 --vm-bytes 80%
--vm-method all) for the duration of the run, so alloc_page() in
anon_pipe_write() routinely hits direct reclaim. The flag fails
fast if stress-ng is not on $PATH.
Program print something like the following, for different writes,
readers, msgsizes and memory pressure:
config: writers=X readers=Y msgsize=Z duration=3 pipe_size=1048576
memory_pressure=[no|yes]
writes: total=54451 rate=18150/s
throughput_MBps: 1134.40
lat_avg_ns: 275355
lat_p50_ns_upper: 262143
lat_p99_ns_upper: 1048575
lat_max_ns: 2145633
Reviewed-by: Jeff Layton <jlayton@kernel.org>
Signed-off-by: Breno Leitao <leitao@debian.org>
Link: https://patch.msgid.link/20260524-fix_pipe-v3-2-bb4a75d23a90@debian.org
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
anon_pipe_write() takes pipe->mutex (aka "mutex protecting the whole
thing") and then, from the per-iteration anon_pipe_get_page() helper,
used to call alloc_page(GFP_HIGHUSER | __GFP_ACCOUNT) once per page
while still holding it.
That allocation can sleep doing direct reclaim and/or runs memcg
charging, which extends the critical section and stalls a concurrent
reader on the very same mutex.
Just pre-alloc the required pages before the lock in an array and just pop
them inside the lock.
This can improve the pipe throughput up to 48% and reduce the
latency in 33%, easily seen when there is memory pressure and direct
reclaim.
Reviewed-by: Mateusz Guzik <mjguzik@gmail.com>
Reviewed-by: Jeff Layton <jlayton@kernel.org>
Signed-off-by: Breno Leitao <leitao@debian.org>
Link: https://patch.msgid.link/20260524-fix_pipe-v3-1-bb4a75d23a90@debian.org
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
The routine originally showed up in e9a53aeb5e ("file: Implement
task_lookup_next_fd_rcu"), afterwards it got renamed and started
entering RCU on its own in 8fd3395ec9 ("get rid of
...lookup...fdget_rcu() family").
Signed-off-by: Mateusz Guzik <mjguzik@gmail.com>
Link: https://patch.msgid.link/20260522142152.1515572-1-mjguzik@gmail.com
Reviewed-by: Jan Kara <jack@suse.cz>
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
Fix three spelling errors in the comment for an internal file structure
allocation function:
- happend → happened
- over → exceed (grammatical fix)
- int → in
Changes since v1:
- Fix comma after e.g.
- Fix incorrect use of "imbalance"
Signed-off-by: Qingshuang Fu <fuqingshuang@kylinos.cn>
Link: https://patch.msgid.link/20260527100025.960339-1-fffsqian@163.com
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
Mike Rapoport (Microsoft) <rppt@kernel.org> says:
This is a (small) part of larger work of replacing page allocator calls
with kmalloc.
* patches from https://patch.msgid.link/20260523-b4-fs-v1-0-275e36a83f0e@kernel.org:
bfs: replace get_zeroed_page() with kzalloc()
binfmt_misc: replace __get_free_page() with kmalloc()
configfs: replace __get_free_pages() with kzalloc()
fs/namespace: use __getname() to allocate mntpath buffer
fs/select: replace __get_free_page() with kmalloc()
fuse: replace __get_free_page() with kmalloc()
isofs: replace __get_free_page() with kmalloc()
jbd2: replace __get_free_pages() with kmalloc()
jfs: replace __get_free_page() with kmalloc()
libfs: simple_transaction_get(): replace get_zeroed_page() with kzalloc()
NFSD: replace __get_free_page() with kmalloc() in nfsd_buffered_readdir()
NFS: remove unused page and page2 in nfs4_replace_transport()
NFS: replace __get_free_page() with kmalloc() in nfs_show_devname()
nilfs2: replace get_zeroed_page() with kzalloc()
ocfs2/dlm: replace __get_free_page() with kmalloc()
proc: replace __get_free_page() with kmalloc()
quota: allocate dquot_hash with kmalloc()
Link: https://patch.msgid.link/20260523-b4-fs-v1-0-275e36a83f0e@kernel.org
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
bfs_dump_imap() allocates temporary buffer with get_zeroed_page().
kmalloc() is a better API for such use and it also provides better
scalability and more debugging possibilities.
Replace use of get_zeroed_page() with kzalloc().
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-17-275e36a83f0e@kernel.org
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
bm_entry_read() allocates temporary buffer using __get_free_page().
kmalloc() is a better API for such use and it also provides better
scalability and more debugging possibilities.
Replace use of __get_free_page() with kmalloc().
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-16-275e36a83f0e@kernel.org
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
configfs allocates staging buffers __get_free_pages().
kmalloc() is a better API for such use and it also provides better
scalability and more debugging possibilities.
Replace use of __get_free_pages() with kzalloc().
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-15-275e36a83f0e@kernel.org
Reviewed-by: Jan Kara <jack@suse.cz>
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
mnt_warn_timestamp_expiry() allocates memory for a path with
__get_free_page() although there is a dedicated helper for allocation of
file paths: __getname().
Replace __get_free_page() for allocation of a path buffer with __getname().
Christian Brauner <brauner@kernel.org> says:
Pass PATH_MAX (not PAGE_SIZE) to d_path() to match the size that
__getname() actually allocates, and drop the now-unnecessary NULL check
around __putname() since __putname() handles NULL. Both per Jan Kara's
review feedback, acked by the author.
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-14-275e36a83f0e@kernel.org
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
poll_get_entry() allocates new memory for poll_table entries using
__get_free_page().
kmalloc() is a better API for such use and it also provides better
scalability and more debugging possibilities.
Replace use of __get_free_page() with kmalloc().
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-13-275e36a83f0e@kernel.org
Reviewed-by: Jan Kara <jack@suse.cz>
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
fuse_do_ioctl allocates memory for struct iov array using
__get_free_page().
kmalloc() is a better API for such use and it also provides better
scalability and more debugging possibilities.
Replace use of __get_free_page() with kmalloc().
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-12-275e36a83f0e@kernel.org
Acked-by: Miklos Szeredi <mszeredi@redhat.com>
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
isofs_readdir() allocates a temporary buffer with __get_free_page().
kmalloc() is a better API for such use and it also provides better
scalability and more debugging possibilities.
Replace use of __get_free_page() with kmalloc().
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-11-275e36a83f0e@kernel.org
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
jbd2_alloc() falls back from kmem_cache_alloc() to __get_free_pages() for
allocations larger than PAGE_SIZE.
But kmalloc() can handle such cases with essentially the same fallback.
Replace use of __get_free_pages() with kmalloc() and simplify
jbd2_free() as both kmem_cache_alloc() and kmalloc() allocations can be
freed with kfree().
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-10-275e36a83f0e@kernel.org
Reviewed-by: Jan Kara <jack@suse.cz>
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
jfs_readdir() allocates dirent_buf with __get_free_page().
kmalloc() is a better API for such use and it also provides better
scalability and more debugging possibilities.
Replace use of __get_free_page() with kmalloc().
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-9-275e36a83f0e@kernel.org
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
simple_transaction_get() allocates memory with get_zeroed_page(). That
memory is used as a file local buffer that is accessed using
copy_from_user() and simple_read_from_buffer().
kmalloc() is a better API for such use and it also provides better
scalability and more debugging possibilities.
Replace use of get_zeroed_page() with kzalloc().
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-8-275e36a83f0e@kernel.org
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
nfsd_buffered_readdir() allocates a staging buffer with __get_free_page().
kmalloc() is a better API for such use and it also provides better
scalability and more debugging possibilities.
Replace use of __get_free_page() with kmalloc().
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-7-275e36a83f0e@kernel.org
Acked-by: Jeff Layton <jlayton@kernel.org>
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
Temporary buffers page and page2 allocated by nfs4_replace_transport() and
passed to nfs4_try_replacing_one_location() are never used.
Remove them and the code that allocates and frees memory for these buffers.
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-6-275e36a83f0e@kernel.org
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
nfs_show_devname() allocates a tmemporary buffer __get_free_page().
kmalloc() is a better API for such use and it also provides better
scalability and more debugging possibilities.
Replace use of __get_free_page() with kmalloc().
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-5-275e36a83f0e@kernel.org
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
nilfs_ioctl_wrap_copy() allocates a temporary buffer with
get_zeroed_page().
kzalloc() is a better API for such use and it also provides better
scalability and more debugging possibilities.
Replace use of get_zeroed_page() with kzalloc().
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-4-275e36a83f0e@kernel.org
Reviewed-by: Viacheslav Dubeyko <slava@dubeyko.com>
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
A few places in ocsfs2 allocate temporary buffers with __get_free_page() or
get_zeroed_page().
kmalloc() is a better API for such use and it also provides better
scalability and more debugging possibilities.
Replace use of __get_free_page() and get_zeroed_page() with kmalloc() and
kzalloc() respectively.
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-3-275e36a83f0e@kernel.org
Reviewed-by: Joseph Qi <joseph.qi@linux.alibaba.com>
Reviewed-by: Jan Kara <jack@suse.cz>
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
A few functions in fs/proc/base.c use __get_free_page() to allocate a
temporary buffer.
kmalloc() is a better API for such use and it also provides better
scalability and more debugging possibilities.
Replace use of __get_free_page() with kmalloc().
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-2-275e36a83f0e@kernel.org
Reviewed-by: Jan Kara <jack@suse.cz>
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
dquot_init() allocates a single page for dquot_hash with
__get_free_pages().
kmalloc() is a better API for such use and it also provides better
scalability and more debugging possibilities.
Replace use of __get_free_pages() with kmalloc() and get rid of the order
variable that remained 0 for more than 20 years.
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260523-b4-fs-v1-1-275e36a83f0e@kernel.org
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
Agatha Isabelle Moreira <code@agatha.dev> says:
Refactor code to use `clear_and_wake_up_bit()` instead of manual calls
to:
clear_bit_unlock();
smp_mb__after_atomic();
wake_up_bit();
The helper function `clear_and_wake_up_bit()` was introduced in
'commit 8236b0ae31 ("bdi: wake up concurrent wb_shutdown()
callers.")' as a generic way of doing the same sequence of operations,
but several pieces of code still remain.
Replace manual calls to the operations by a single call to
`clear_and_wake_up_bit()` to deduplicate code and standardize pathways.
* patches from https://patch.msgid.link/ag4PEP52c8rxrYPc@guidai:
fs: jbd2: use clear_and_wake_up_bit() in journal_end_buffer_io_sync()
fs: buffer: use clear_and_wake_up_bit() in unlock_buffer()
Link: https://patch.msgid.link/ag4PEP52c8rxrYPc@guidai
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
initramfs_test_extract() and friends call unpack_to_rootfs() from a
kunit kthread while do_populate_rootfs() may still be running
asynchronously from rootfs_initcall. unpack_to_rootfs() keeps its
parser state in module-static variables (victim, byte_count, state,
this_header, header_buf, name_buf, ...), so the two writers corrupt
each other.
On arm64 v7.0-rc5+ this oopses early in boot:
Unable to handle kernel paging request at virtual address ffff80018f9f0ffc
pc : do_reset+0x3c/0x98
Call trace:
do_reset
initramfs_test_extract
kunit_try_run_case
Initramfs unpacking failed: junk within compressed archive
do_reset() faults because 'victim' was overwritten by the boot-time
unpacker; the boot unpacker meanwhile logs the bogus "junk within
compressed archive" on the real initrd because the test wrecked its
state machine.
Add a .suite_init callback that calls wait_for_initramfs() so the async
unpack is quiescent before the first case runs. suite_init runs once per
suite rather than before every individual test case.
Fixes: 83c0b27266 ("initramfs_test: kunit tests for initramfs unpacking")
Signed-off-by: Jia He <justin.he@arm.com>
Link: https://patch.msgid.link/20260519093937.1064628-1-justin.he@arm.com
Reviewed-by: David Disseldorp <ddiss@suse.de>
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
Use `clear_and_wake_up_bit()` in `journal_end_buffer_io_sync()`, since
the helper was introduced in 'commit 8236b0ae31 ("bdi: wake up
concurrent wb_shutdown() callers.")' as a generic way of doing the same
sequence of operations:
clear_bit_unlock();
smp_mb__after_atomic();
wake_up_bit();
The helper was first implemented to avoid bugs caused by forgetting to
call `wake_up_bit()` after `clear_bit_unlock()`.
Since `journal_end_buffer_io_sync()` was first introduced by 'commit
470decc613 ("jbd2: initial copy of files from jbd")' and last
modified in this operation by 'commit 4e857c58ef ("arch: Mass
conversion of smp_mb__*()")', years before `clear_and_wake_up_bit()`, it
still uses the open-coded sequence.
Replace the open-coded sequence with the helper to avoid duplicate code
and reduce code paths to maintain.
Suggested-by: shuo chen <1289151713@qq.com>
Link: https://lore.kernel.org/kernelnewbies/agzoqV835-co4kAN@guidai/T/#t
Signed-off-by: Agatha Isabelle Moreira <code@agatha.dev>
Link: https://patch.msgid.link/ag4SrrOl7R2DcLLi@guidai
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
Use `clear_and_wake_up_bit()` in `unlock_buffer()`, since the helper was
introduced in 'commit 8236b0ae31 ("bdi: wake up concurrent
wb_shutdown() callers.")' as a generic way of doing the same sequence of
operations:
clear_bit_unlock();
smp_mb__after_atomic();
wake_up_bit();
The helper was implemented to avoid bugs caused by forgetting to call
`wake_up_bit()` after `clear_bit_unlock()`.
Since `unlock_buffer()` predates git and was last modified in
'commit 4e857c58ef ("arch: Mass conversion of smp_mb__*()")', years
before `clear_and_wake_up_bit()`, it still uses the open-coded sequence.
Replace the open-coded sequence with the helper to avoid duplicate code
and reduce code paths to maintain.
Suggested-by: shuo chen <1289151713@qq.com>
Link: https://lore.kernel.org/kernelnewbies/agzoqV835-co4kAN@guidai/T/#t
Signed-off-by: Agatha Isabelle Moreira <code@agatha.dev>
Link: https://patch.msgid.link/ag4SD-mkmn5IbuN7@guidai
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
At this point the superblock is already read, so jump to the label that
releases the buffer_head for it.
Fixes: d893fc670546 ("minix: handle set_blocksize failures")
Reviewed-by: Jan Kara <jack@suse.cz>
Signed-off-by: Christoph Hellwig <hch@lst.de>
Link: https://patch.msgid.link/20260518130330.529085-1-hch@lst.de
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
Several places in init/do_mounts.c allocate temporary buffers for
filesystem names or options using __get_free_page() or alloc_page().
Usage of alloc_page() APIs is not required there and only creates
unnecessary noise with castings or conversion from struct page to void *.
kmalloc() is a better API for these uses and it also provides better
scalability and more debugging possibilities.
Replace use of __get_free_page() and alloc_page() with kmalloc().
While on it, add a check for -ENOMEM condition in mount_root_generic().
Link: https://lore.kernel.org/all/635405e4-9423-4a25-a6e7-e03c8ea0bcbe@redhat.com
Signed-off-by: Mike Rapoport (Microsoft) <rppt@kernel.org>
Link: https://patch.msgid.link/20260520-init-v1-1-aaf2ebac5ad9@kernel.org
Reviewed-by: David Disseldorp <ddiss@suse.de>
Reviewed-by: SeongJae Park <sj@kernel.org>
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
Both GNU and BSD makes share a "token pipe" between their instances, as
a result a -j $BIGNUM invocation results in multicore perf problems in
the poll handler.
Avoiding the store will reduce it a little bit. However, the crux of the
problem is the locked queuing up in poll_wait().
Signed-off-by: Mateusz Guzik <mjguzik@gmail.com>
Link: https://patch.msgid.link/20260516021852.256932-1-mjguzik@gmail.com
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
Symlinks can't appear as opened file.
Signed-off-by: Alexey Dobriyan <adobriyan@gmail.com>
Link: https://patch.msgid.link/295235c7-7f68-4554-bb6f-85398beca350@p183
Reviewed-by: Jan Kara <jack@suse.cz>
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
Drop the hard-coded length argument and use the simpler QSTR(). Inline
the code and drop the local variable.
Reviewed-by: Jan Kara <jack@suse.cz>
Signed-off-by: Thorsten Blum <thorsten.blum@linux.dev>
Link: https://patch.msgid.link/20260505114242.158883-2-thorsten.blum@linux.dev
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
Christoph Hellwig <hch@lst.de> says:
Due to an almost comical failure on my part, my work in progress test
case failed to create any file system on a 64k block size loop device,
and then tried to mount it, leading to a probe of file system built
into my kernel. Roughly the first half of the series are file systems
that actually crashed, but I fixed up all the pattern of missing
error handling that I saw.
* patches from https://patch.msgid.link/20260511071701.2456211-1-hch@lst.de:
omfs: handle set_blocksize failures
ntfs3: handle set_blocksize failures
minix: handle set_blocksize failures
isofs: handle set_blocksize failures
affs: handle set_blocksize failures
befs: handle set_blocksize failures
jfs: handle set_blocksize failures
qnx4: handle set_blocksize failures
hpfs: handle set_blocksize failures
bfs: handle set_blocksize failures
Link: https://patch.msgid.link/20260511071701.2456211-1-hch@lst.de
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
omfs uses buffer_heads, which don't handle block size > PAGE_SIZE well.
Without this, mounting we will hit the
BUG_ON(offset >= folio_size(folio));
in folio_set_bh on the first __bread_gfp call.
Signed-off-by: Christoph Hellwig <hch@lst.de>
Signed-off-by: Christoph Hellwig <hch@lst.de>
Link: https://patch.msgid.link/20260511071701.2456211-11-hch@lst.de
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
ntfs3 uses buffer_heads, which don't handle block size > PAGE_SIZE well.
Without this, mounting we will hit the
BUG_ON(offset >= folio_size(folio));
in folio_set_bh on the first __bread_gfp call.
Signed-off-by: Christoph Hellwig <hch@lst.de>
Link: https://patch.msgid.link/20260511071701.2456211-10-hch@lst.de
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
minix uses buffer_heads, which don't handle block size > PAGE_SIZE well.
Without this, mounting we will hit the
BUG_ON(offset >= folio_size(folio));
in folio_set_bh on the first __bread_gfp call.
Signed-off-by: Christoph Hellwig <hch@lst.de>
Link: https://patch.msgid.link/20260511071701.2456211-9-hch@lst.de
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
isofs uses buffer_heads, which don't handle block size > PAGE_SIZE well.
Without this, mounting we will hit the
BUG_ON(offset >= folio_size(folio));
in folio_set_bh on the first __bread_gfp call.
Signed-off-by: Christoph Hellwig <hch@lst.de>
Link: https://patch.msgid.link/20260511071701.2456211-8-hch@lst.de
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
affs uses buffer_heads, which don't handle block size > PAGE_SIZE well.
Without this, mounting we will hit the
BUG_ON(offset >= folio_size(folio));
in folio_set_bh on the first __bread_gfp call.
Signed-off-by: Christoph Hellwig <hch@lst.de>
Link: https://patch.msgid.link/20260511071701.2456211-7-hch@lst.de
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
befs uses buffer_heads, which don't handle block size > PAGE_SIZE well.
Without this, mounting we will hit the
BUG_ON(offset >= folio_size(folio));
in folio_set_bh on the first __bread_gfp call.
Signed-off-by: Christoph Hellwig <hch@lst.de>
Link: https://patch.msgid.link/20260511071701.2456211-6-hch@lst.de
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
jfs uses buffer_heads, which don't handle block size > PAGE_SIZE well.
Without this, mounting we will hit the
BUG_ON(offset >= folio_size(folio));
in folio_set_bh on the first __bread_gfp call.
Signed-off-by: Christoph Hellwig <hch@lst.de>
Link: https://patch.msgid.link/20260511071701.2456211-5-hch@lst.de
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
qnx4 uses buffer_heads, which don't handle block size > PAGE_SIZE well.
Without this, mounting will hit the
BUG_ON(offset >= folio_size(folio));
in folio_set_bh on the first __bread_gfp call.
Signed-off-by: Christoph Hellwig <hch@lst.de>
Link: https://patch.msgid.link/20260511071701.2456211-4-hch@lst.de
Acked-by: Anders Larsen <al@alarsen.net>
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
hpfs uses buffer_heads, which don't handle block size > PAGE_SIZE well.
Without this, mounting will hit the
BUG_ON(offset >= folio_size(folio));
in folio_set_bh on the first __bread_gfp call.
Signed-off-by: Christoph Hellwig <hch@lst.de>
Link: https://patch.msgid.link/20260511071701.2456211-3-hch@lst.de
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
bfs uses buffer_heads, which don't handle block size > PAGE_SIZE well.
Without this, mounting will hit the
BUG_ON(offset >= folio_size(folio));
in folio_set_bh on the first __bread_gfp call.
Signed-off-by: Christoph Hellwig <hch@lst.de>
Link: https://patch.msgid.link/20260511071701.2456211-2-hch@lst.de
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>
This document is motivated by the ongoing maintenance burden that
abandoned and untestable filesystems impose on VFS developers, blocking
infrastructure changes such as folio conversions and iomap migration.
This week alone, two new filesystems were proposed on linux-fsdevel
(VMUFAT and FTRFS), highlighting the need for documented guidelines
that new filesystem authors can refer to before submission.
Multiple recent discussions on linux-fsdevel have touched on the
criteria for merging new filesystems and for deprecating old ones,
covering topics such as modern VFS interface adoption, testability,
userspace utilities, maintainer commitment, and user base viability.
Add Documentation/filesystems/adding-new-filesystems.rst describing
the technical requirements and community expectations for merging a
new filesystem into the kernel. The guidelines cover:
- Alternatives to consider before proposing a new in-kernel filesystem
- Technical requirements: modern VFS interfaces (iomap, folios,
fs_context mount API), testability, and userspace utilities
- Community expectations: identified maintainers, demonstrated
commitment, sustained backing, and a clear user base
- Ongoing obligations after merging, including the risk of deprecation
for unmaintained filesystems
Link: https://lore.kernel.org/linux-fsdevel/20260411151155.321214-1-adrianmcmenamin@gmail.com/
Link: https://lore.kernel.org/linux-fsdevel/20260413142357.515792-1-aurelien@hackers.camp/
Link: https://lore.kernel.org/linux-fsdevel/yndtg2jbj55fzd2kkhsmel4pp5ll5xfvfiaqh24tdct3jiqosd@jzbfzf3rrxrd/
Link: https://lore.kernel.org/linux-fsdevel/20260124091742.GA43313@macsyma.local/
Link: https://lore.kernel.org/lkml/20260111140345.3866-1-linkinjeon@kernel.org/
Cc: Christian Brauner <brauner@kernel.org>
Cc: Alexander Viro <viro@zeniv.linux.org.uk>
Cc: Jan Kara <jack@suse.cz>
Cc: Theodore Tso <tytso@mit.edu>
Cc: Christoph Hellwig <hch@lst.de>
Cc: Darrick J. Wong <djwong@kernel.org>
Cc: Matthew Wilcox <willy@infradead.org>
Assisted-by: Cursor:claude-4-opus
Signed-off-by: Amir Goldstein <amir73il@gmail.com>
Link: https://patch.msgid.link/20260422125212.1743006-1-amir73il@gmail.com
Reviewed-by: Jan Kara <jack@suse.cz>
Signed-off-by: Christian Brauner (Amutable) <brauner@kernel.org>