Linux NFS development
 help / color / mirror / Atom feed
* [PATCH 0/2]
@ 2025-12-08 20:03 Sergey Shtylyov
  2025-12-08 20:03 ` [PATCH 1/2] NFSv4: pass lease period in seconds to nfs4_set_lease_period() Sergey Shtylyov
                   ` (2 more replies)
  0 siblings, 3 replies; 4+ messages in thread
From: Sergey Shtylyov @ 2025-12-08 20:03 UTC (permalink / raw)
  To: Trond Myklebust, Anna Schumaker, linux-nfs; +Cc: Sergey Shtylyov

The nfs_client::cl_lease_time field (as well as the jiffies variable it's
used with) is declared as *unsigned long*, which is 32-bit type on 32-bit
arches and 64-bit type on 64-bit arches. When nfs4_set_lease_period() that
sets nfs_client::cl_lease_time is called, 32-bit nfs_fsinfo::lease_time
field is multiplied by HZ -- that might overflow before being implicitly
cast to *unsigned long*.  Actually, there's no need to multiply by HZ at
all the call sites of nfs4_set_lease_period() -- it makes more sense to do
that once, inside that function.  That way, we can avoid such overflow by
capping the lease period at e.g. 1 hour before multipying it by HZ...

The patches below are against the linux-next branch of Trond Myklebust's
linux-nfs.git repo.

Sergey Shtylyov (2):
  NFSv4: pass lease period in seconds to nfs4_set_lease_period()
  NFSv4: limit lease period in nfs4_set_lease_period()

 fs/nfs/nfs4_fs.h    |  3 +--
 fs/nfs/nfs4proc.c   |  2 +-
 fs/nfs/nfs4renewd.c | 15 ++++++++++++---
 fs/nfs/nfs4state.c  |  2 +-
 4 files changed, 15 insertions(+), 7 deletions(-)

-- 
2.52.0

^ permalink raw reply	[flat|nested] 4+ messages in thread

* [PATCH 1/2] NFSv4: pass lease period in seconds to nfs4_set_lease_period()
  2025-12-08 20:03 [PATCH 0/2] Sergey Shtylyov
@ 2025-12-08 20:03 ` Sergey Shtylyov
  2025-12-08 20:03 ` [PATCH 2/2] NFSv4: limit lease period in nfs4_set_lease_period() Sergey Shtylyov
  2025-12-08 20:07 ` [PATCH 0/2] Sergey Shtylyov
  2 siblings, 0 replies; 4+ messages in thread
From: Sergey Shtylyov @ 2025-12-08 20:03 UTC (permalink / raw)
  To: Trond Myklebust, Anna Schumaker, linux-nfs; +Cc: Sergey Shtylyov

There's no need to multiply the lease period by HZ at all the call sites of
nfs4_set_lease_period() -- it makes more sense to do that only once, inside
that function, by passing to it lease period as 32-bit # of seconds instead
of 32/64-bit *unsigned long* # of jiffies...

Signed-off-by: Sergey Shtylyov <s.shtylyov@omp.ru>
---
 fs/nfs/nfs4_fs.h    | 3 +--
 fs/nfs/nfs4proc.c   | 2 +-
 fs/nfs/nfs4renewd.c | 7 ++++---
 fs/nfs/nfs4state.c  | 2 +-
 4 files changed, 7 insertions(+), 7 deletions(-)

diff --git a/fs/nfs/nfs4_fs.h b/fs/nfs/nfs4_fs.h
index c34c89af9c7d..44cf167f65c6 100644
--- a/fs/nfs/nfs4_fs.h
+++ b/fs/nfs/nfs4_fs.h
@@ -464,8 +464,7 @@ struct nfs_client *nfs4_alloc_client(const struct nfs_client_initdata *);
 extern void nfs4_schedule_state_renewal(struct nfs_client *);
 extern void nfs4_kill_renewd(struct nfs_client *);
 extern void nfs4_renew_state(struct work_struct *);
-extern void nfs4_set_lease_period(struct nfs_client *clp, unsigned long lease);
-
+extern void nfs4_set_lease_period(struct nfs_client *clp, u32 period);
 
 /* nfs4state.c */
 extern const nfs4_stateid current_stateid;
diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c
index ec1ce593dea2..b66f97acafde 100644
--- a/fs/nfs/nfs4proc.c
+++ b/fs/nfs/nfs4proc.c
@@ -5556,7 +5556,7 @@ static int nfs4_do_fsinfo(struct nfs_server *server, struct nfs_fh *fhandle, str
 		err = _nfs4_do_fsinfo(server, fhandle, fsinfo);
 		trace_nfs4_fsinfo(server, fhandle, fsinfo->fattr, err);
 		if (err == 0) {
-			nfs4_set_lease_period(server->nfs_client, fsinfo->lease_time * HZ);
+			nfs4_set_lease_period(server->nfs_client, fsinfo->lease_time);
 			break;
 		}
 		err = nfs4_handle_exception(server, err, &exception);
diff --git a/fs/nfs/nfs4renewd.c b/fs/nfs/nfs4renewd.c
index 18ae614e5a6c..043b2de8d416 100644
--- a/fs/nfs/nfs4renewd.c
+++ b/fs/nfs/nfs4renewd.c
@@ -137,11 +137,12 @@ nfs4_kill_renewd(struct nfs_client *clp)
  * nfs4_set_lease_period - Sets the lease period on a nfs_client
  *
  * @clp: pointer to nfs_client
- * @lease: new value for lease period
+ * @period: new value for lease period (in seconds)
  */
-void nfs4_set_lease_period(struct nfs_client *clp,
-		unsigned long lease)
+void nfs4_set_lease_period(struct nfs_client *clp, u32 period)
 {
+	unsigned long lease = period * HZ;
+
 	spin_lock(&clp->cl_lock);
 	clp->cl_lease_time = lease;
 	spin_unlock(&clp->cl_lock);
diff --git a/fs/nfs/nfs4state.c b/fs/nfs/nfs4state.c
index 01179f7de322..a435d4d47b3c 100644
--- a/fs/nfs/nfs4state.c
+++ b/fs/nfs/nfs4state.c
@@ -103,7 +103,7 @@ static int nfs4_setup_state_renewal(struct nfs_client *clp)
 
 	status = nfs4_proc_get_lease_time(clp, &fsinfo);
 	if (status == 0) {
-		nfs4_set_lease_period(clp, fsinfo.lease_time * HZ);
+		nfs4_set_lease_period(clp, fsinfo.lease_time);
 		nfs4_schedule_state_renewal(clp);
 	}
 
-- 
2.52.0


^ permalink raw reply related	[flat|nested] 4+ messages in thread

* [PATCH 2/2] NFSv4: limit lease period in nfs4_set_lease_period()
  2025-12-08 20:03 [PATCH 0/2] Sergey Shtylyov
  2025-12-08 20:03 ` [PATCH 1/2] NFSv4: pass lease period in seconds to nfs4_set_lease_period() Sergey Shtylyov
@ 2025-12-08 20:03 ` Sergey Shtylyov
  2025-12-08 20:07 ` [PATCH 0/2] Sergey Shtylyov
  2 siblings, 0 replies; 4+ messages in thread
From: Sergey Shtylyov @ 2025-12-08 20:03 UTC (permalink / raw)
  To: Trond Myklebust, Anna Schumaker, linux-nfs; +Cc: Sergey Shtylyov

In nfs4_set_lease_period(), the passed 32-bit lease period in seconds is
multiplied by HZ -- that might overflow before being implicitly cast to
*unsigned long* (32/64-bit type), while initializing the lease variable.
Cap the lease period at MAX_LEASE_PERIOD (#define'd to 1 hour for now),
before multipying to avoid such overflow...

Found by Linux Verification Center (linuxtesting.org) with the Svace static
analysis tool.

Signed-off-by: Sergey Shtylyov <s.shtylyov@omp.ru>
Suggested-by: Trond Myklebust <trondmy@kernel.org>
---
 fs/nfs/nfs4renewd.c | 10 +++++++++-
 1 file changed, 9 insertions(+), 1 deletion(-)

diff --git a/fs/nfs/nfs4renewd.c b/fs/nfs/nfs4renewd.c
index 043b2de8d416..30065df1482e 100644
--- a/fs/nfs/nfs4renewd.c
+++ b/fs/nfs/nfs4renewd.c
@@ -133,6 +133,8 @@ nfs4_kill_renewd(struct nfs_client *clp)
 	cancel_delayed_work_sync(&clp->cl_renewd);
 }
 
+#define MAX_LEASE_PERIOD (60 * 60)	/* 1 hour */
+
 /**
  * nfs4_set_lease_period - Sets the lease period on a nfs_client
  *
@@ -141,7 +143,13 @@ nfs4_kill_renewd(struct nfs_client *clp)
  */
 void nfs4_set_lease_period(struct nfs_client *clp, u32 period)
 {
-	unsigned long lease = period * HZ;
+	unsigned long lease;
+
+	/* Limit the lease period */
+	if (period < MAX_LEASE_PERIOD)
+		lease = period * HZ;
+	else
+		lease = MAX_LEASE_PERIOD * HZ;
 
 	spin_lock(&clp->cl_lock);
 	clp->cl_lease_time = lease;
-- 
2.52.0


^ permalink raw reply related	[flat|nested] 4+ messages in thread

* Re: [PATCH 0/2]
  2025-12-08 20:03 [PATCH 0/2] Sergey Shtylyov
  2025-12-08 20:03 ` [PATCH 1/2] NFSv4: pass lease period in seconds to nfs4_set_lease_period() Sergey Shtylyov
  2025-12-08 20:03 ` [PATCH 2/2] NFSv4: limit lease period in nfs4_set_lease_period() Sergey Shtylyov
@ 2025-12-08 20:07 ` Sergey Shtylyov
  2 siblings, 0 replies; 4+ messages in thread
From: Sergey Shtylyov @ 2025-12-08 20:07 UTC (permalink / raw)
  To: Trond Myklebust, Anna Schumaker, linux-nfs

Argh, I forgot to finish the subject! :-/ I'll repost...


^ permalink raw reply	[flat|nested] 4+ messages in thread

end of thread, other threads:[~2025-12-08 20:19 UTC | newest]

Thread overview: 4+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2025-12-08 20:03 [PATCH 0/2] Sergey Shtylyov
2025-12-08 20:03 ` [PATCH 1/2] NFSv4: pass lease period in seconds to nfs4_set_lease_period() Sergey Shtylyov
2025-12-08 20:03 ` [PATCH 2/2] NFSv4: limit lease period in nfs4_set_lease_period() Sergey Shtylyov
2025-12-08 20:07 ` [PATCH 0/2] Sergey Shtylyov

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox