[PATCH 1/2] ceph: use GFP_NOFS for cap flush allocation in writeback path
Xiubo Li via B4 Relay <[email protected]> Thu, 23 Jul 2026 13:47:42 +0800
| Newsgroups | org.kernel.vger.ceph-devel,org.kernel.feeds.b4-sent,org.kernel.vger.linux-kernel |
|---|---|
| Message-ID | <[email protected]> |
From: Xiubo Li <[email protected]> ceph_alloc_cap_flush() is called from ceph_writepages_start() inside the writeback layer, where other allocations in the same path (ceph_osdc_alloc_request, ceph_osdc_alloc_messages) already use GFP_NOFS. A GFP_KERNEL allocation here can trigger direct reclaim that recursively enters the filesystem writeback path: ceph_writepages_start() // inode A writeback ceph_alloc_cap_flush() kmem_cache_alloc(..., GFP_KERNEL) [direct reclaim] try_to_free_pages() shrink_slab() super_cache_scan() prune_icache_sb() inode_lru_isolate() iput() -> evict(inode_B) [inode_B has dirty pages] filemap_flush() ceph_writepages_start() // re-enters writeback ceph_alloc_cap_flush() -> RECURSION / STACK OVERFLOW All 11 callers of ceph_alloc_cap_flush() are in write or writeback contexts: writepages (x2), write_iter, fallocate, copy_file_range, setxattr, setattr, and page_mkwrite. Signed-off-by: Xiubo Li <[email protected]> --- fs/ceph/caps.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/fs/ceph/caps.c b/fs/ceph/caps.c index f8d898ad091e..cbaebeac06f7 100644 --- a/fs/ceph/caps.c +++ b/fs/ceph/caps.c @@ -1875,7 +1875,7 @@ struct ceph_cap_flush *ceph_alloc_cap_flush(void) { struct ceph_cap_flush *cf; - cf = kmem_cache_alloc(ceph_cap_flush_cachep, GFP_KERNEL); + cf = kmem_cache_alloc(ceph_cap_flush_cachep, GFP_NOFS); if (!cf) return NULL; -- 2.53.0