linux-yocto/fs/nfsd
Li Lingfeng 7d192e27a4 nfsd: decrease sc_count directly if fail to queue dl_recall
[ Upstream commit a1d14d931bf700c1025db8c46d6731aa5cf440f9 ]

A deadlock warning occurred when invoking nfs4_put_stid following a failed
dl_recall queue operation:
            T1                            T2
                                nfs4_laundromat
                                 nfs4_get_client_reaplist
                                  nfs4_anylock_blockers
__break_lease
 spin_lock // ctx->flc_lock
                                   spin_lock // clp->cl_lock
                                   nfs4_lockowner_has_blockers
                                    locks_owner_has_blockers
                                     spin_lock // flctx->flc_lock
 nfsd_break_deleg_cb
  nfsd_break_one_deleg
   nfs4_put_stid
    refcount_dec_and_lock
     spin_lock // clp->cl_lock

When a file is opened, an nfs4_delegation is allocated with sc_count
initialized to 1, and the file_lease holds a reference to the delegation.
The file_lease is then associated with the file through kernel_setlease.

The disassociation is performed in nfsd4_delegreturn via the following
call chain:
nfsd4_delegreturn --> destroy_delegation --> destroy_unhashed_deleg -->
nfs4_unlock_deleg_lease --> kernel_setlease --> generic_delete_lease
The corresponding sc_count reference will be released after this
disassociation.

Since nfsd_break_one_deleg executes while holding the flc_lock, the
disassociation process becomes blocked when attempting to acquire flc_lock
in generic_delete_lease. This means:
1) sc_count in nfsd_break_one_deleg will not be decremented to 0;
2) The nfs4_put_stid called by nfsd_break_one_deleg will not attempt to
acquire cl_lock;
3) Consequently, no deadlock condition is created.

Given that sc_count in nfsd_break_one_deleg remains non-zero, we can
safely perform refcount_dec on sc_count directly. This approach
effectively avoids triggering deadlock warnings.

Fixes: 230ca758453c ("nfsd: put dl_stid if fail to queue dl_recall")
Signed-off-by: Li Lingfeng <lilingfeng3@huawei.com>
Reviewed-by: Jeff Layton <jlayton@kernel.org>
Signed-off-by: Chuck Lever <chuck.lever@oracle.com>
Signed-off-by: Sasha Levin <sashal@kernel.org>
2025-04-25 10:45:46 +02:00
..
acl.h
auth.c
auth.h
blocklayout.c
blocklayoutxdr.c
blocklayoutxdr.h
cache.h nfsd: make all of the nfsd stats per-network namespace 2024-08-19 06:04:23 +02:00
current_stateid.h
export.c nfsd: Revert "nfsd: release svc_expkey/svc_export with rcu_work" 2025-01-02 10:32:00 +01:00
export.h nfsd: Revert "nfsd: release svc_expkey/svc_export with rcu_work" 2025-01-02 10:32:00 +01:00
filecache.c nfsd: add list_head nf_gc to struct nfsd_file 2025-01-23 17:21:19 +01:00
filecache.h nfsd: add list_head nf_gc to struct nfsd_file 2025-01-23 17:21:19 +01:00
flexfilelayout.c
flexfilelayoutxdr.c
flexfilelayoutxdr.h
idmap.h
Kconfig nfs: add missing selections of CONFIG_CRC32 2025-04-25 10:45:46 +02:00
lockd.c
Makefile
netns.h NFSD: Limit the number of concurrent async COPY operations 2024-11-22 15:38:36 +01:00
nfs2acl.c nfsd: clear acl_access/acl_default after releasing them 2025-02-21 13:57:06 +01:00
nfs3acl.c nfsd: clear acl_access/acl_default after releasing them 2025-02-21 13:57:06 +01:00
nfs3proc.c
nfs3xdr.c
nfs4acl.c
nfs4callback.c NFSD: fix hang in nfsd4_shutdown_callback 2025-02-21 13:57:06 +01:00
nfs4idmap.c nfsd: call cache_put if xdr_reserve_space returns NULL 2024-10-04 16:29:35 +02:00
nfs4layouts.c
nfs4proc.c NFSD: Fix nfsd4_shutdown_copy() 2024-12-09 10:32:30 +01:00
nfs4recover.c NFSD: Cap the number of bytes copied by nfs4_reset_recoverydir() 2024-12-09 10:32:30 +01:00
nfs4state.c nfsd: decrease sc_count directly if fail to queue dl_recall 2025-04-25 10:45:46 +02:00
nfs4xdr.c NFSD: Fix NFSv4's PUTPUBFH operation 2024-10-10 11:57:53 +02:00
nfscache.c nfsd: make all of the nfsd stats per-network namespace 2024-08-19 06:04:23 +02:00
nfsctl.c nfsd: make svc_stat per-network namespace instead of global 2024-08-19 06:04:24 +02:00
nfsd.h nfsd: remove nfsd_stats, make th_cnt a global counter 2024-08-19 06:04:24 +02:00
nfsfh.c nfsd: make all of the nfsd stats per-network namespace 2024-08-19 06:04:23 +02:00
nfsfh.h nfs: add missing selections of CONFIG_CRC32 2025-04-25 10:45:46 +02:00
nfsproc.c
nfssvc.c NFSD: simplify error paths in nfsd_svc() 2024-08-29 17:33:58 +02:00
nfsxdr.c
pnfs.h
state.h
stats.c nfsd: make svc_stat per-network namespace instead of global 2024-08-19 06:04:24 +02:00
stats.h nfsd: make svc_stat per-network namespace instead of global 2024-08-19 06:04:24 +02:00
trace.c
trace.h
vfs.c nfsd: map the EBADMSG to nfserr_io to avoid warning 2024-10-10 11:57:52 +02:00
vfs.h
xdr.h
xdr3.h
xdr4.h NFSD: Limit the number of concurrent async COPY operations 2024-11-22 15:38:36 +01:00
xdr4cb.h