]> git.ipfire.org Git - thirdparty/linux.git/commitdiff
lockd: Introduce nlm__int__deadlock
authorChuck Lever <chuck.lever@oracle.com>
Wed, 28 Jan 2026 15:19:24 +0000 (10:19 -0500)
committerChuck Lever <chuck.lever@oracle.com>
Mon, 30 Mar 2026 01:25:09 +0000 (21:25 -0400)
The use of CONFIG_LOCKD_V4 in combination with a later cast_status()
in the NLMv3 code is difficult to reason about. Instead, replace the
use of nlm_deadlock with an implementation-defined status value that
version-specific code translates appropriately.

The new approach establishes a translation boundary: generic lockd
code returns nlm__int__deadlock when posix_lock_file() yields
-EDEADLK. Version-specific handlers (svc4proc.c for NLMv4,
svcproc.c for NLMv3) translate this internal status to the
appropriate wire protocol value. NLMv4 maps to nlm4_deadlock;
NLMv3 maps to nlm_lck_denied (since NLMv3 lacks a deadlock-specific
status code).

Later this modification will also remove the need to include NLMv4
headers in NLMv3 and generic code.

Reviewed-by: Jeff Layton <jlayton@kernel.org>
Signed-off-by: Chuck Lever <chuck.lever@oracle.com>
fs/lockd/svc4proc.c
fs/lockd/svclock.c
fs/lockd/svcproc.c
include/linux/lockd/lockd.h

index 9c756d07223afd1a9b03fd9bef3bf6400a4b66f4..55b6dcc56db135d7dd28cba81fd31355479fc73a 100644 (file)
@@ -148,10 +148,16 @@ __nlm4svc_proc_lock(struct svc_rqst *rqstp, struct nlm_res *resp)
        resp->status = nlmsvc_lock(rqstp, file, host, &argp->lock,
                                        argp->block, &argp->cookie,
                                        argp->reclaim);
-       if (resp->status == nlm__int__drop_reply)
+       switch (resp->status) {
+       case nlm__int__drop_reply:
                rc = rpc_drop_reply;
-       else
+               break;
+       case nlm__int__deadlock:
+               resp->status = nlm4_deadlock;
+               fallthrough;
+       default:
                dprintk("lockd: LOCK         status %d\n", ntohl(resp->status));
+       }
 
        nlmsvc_release_lockowner(&argp->lock);
        nlmsvc_release_host(host);
index d86b02153c7c36d1b757802e28edb4b8edc4f33e..5edf00751a1e7ef6fbcb4e92c77efd44c3907fa1 100644 (file)
 
 #define NLMDBG_FACILITY                NLMDBG_SVCLOCK
 
-#ifdef CONFIG_LOCKD_V4
-#define nlm_deadlock   nlm4_deadlock
-#else
-#define nlm_deadlock   nlm_lck_denied
-#endif
-
 static void nlmsvc_release_block(struct nlm_block *block);
 static void    nlmsvc_insert_block(struct nlm_block *block, unsigned long);
 static void    nlmsvc_remove_block(struct nlm_block *block);
@@ -589,7 +583,7 @@ nlmsvc_lock(struct svc_rqst *rqstp, struct nlm_file *file,
                        goto out;
                case -EDEADLK:
                        nlmsvc_remove_block(block);
-                       ret = nlm_deadlock;
+                       ret = nlm__int__deadlock;
                        goto out;
                default:                        /* includes ENOLCK */
                        nlmsvc_remove_block(block);
index 2a2e48a9bd12ba675f38fa66522b1f4d6322dc0e..27ed71935e45256d4624cbc8ac6f106162c82d28 100644 (file)
@@ -27,7 +27,7 @@ static inline __be32 cast_status(__be32 status)
        case nlm_lck_denied_grace_period:
        case nlm__int__drop_reply:
                break;
-       case nlm4_deadlock:
+       case nlm__int__deadlock:
                status = nlm_lck_denied;
                break;
        default:
@@ -39,6 +39,8 @@ static inline __be32 cast_status(__be32 status)
 #else
 static inline __be32 cast_status(__be32 status)
 {
+       if (status == nlm__int__deadlock)
+               status = nlm_lck_denied;
        return status;
 }
 #endif
index fdefec39553f044aceff19e1ae4f1ee871c14cb6..7936919121379e1daf2f897afc6c3a573c7b250c 100644 (file)
@@ -43,6 +43,7 @@
  * Version handlers translate these to appropriate wire values.
  */
 #define nlm__int__drop_reply   cpu_to_be32(30000)
+#define nlm__int__deadlock     cpu_to_be32(30001)
 
 /*
  * Lockd host handle (used both by the client and server personality).