From: Stanislav Kinsburskiy <skinsbur...@virtuozzo.com>

Current NFS client implementation can zap inode caches or just re-validate the
inode after successful lock request using it as a synchronization point.

Inode caches zapping or re-validation depends on server's file system time
granularity status: if time granularity is less than second, then
re-validation
is assumed to be enough. But Linux NFS server always return "1 second" value
for any file system. This looks like an old artefact.

So, let's so the following: return "sb->s_time_gran" to NFS client.
But only for EXT4 file system for a while.
This will remove bottleneck when many processes are concurrently trying to
lock large file like SQL database.

Ported from rhel6.

https://jira.sw.ru/browse/PSBM-66572

Signed-off-by: Stanislav Kinsburskiy <skinsbur...@virtuozzo.com>

(cherry-picked from vz8 commit bcd8b870950a ("nfsd: return file system
superblock time granulaty on FSINFO request"))

Adopt to refactored nfs3xdr encoder code.

Signed-off-by: Nikita Yushchenko <nikita.yushche...@virtuozzo.com>
---
 fs/nfsd/nfs3proc.c |  3 +++
 fs/nfsd/nfs3xdr.c  | 22 +++++++++++++---------
 fs/nfsd/xdr3.h     |  1 +
 3 files changed, 17 insertions(+), 9 deletions(-)

diff --git a/fs/nfsd/nfs3proc.c b/fs/nfsd/nfs3proc.c
index 17715a6c7a40..986d5a632832 100644
--- a/fs/nfsd/nfs3proc.c
+++ b/fs/nfsd/nfs3proc.c
@@ -597,6 +597,9 @@ nfsd3_proc_fsinfo(struct svc_rqst *rqstp)
                        resp->f_properties = NFS3_FSF_BILLYBOY;
                }
                resp->f_maxfilesize = sb->s_maxbytes;
+               resp->f_time_gran = 0;
+               if (!strcmp(sb->s_type->name, "ext4"))
+                       resp->f_time_gran = sb->s_time_gran;
        }
 
        fh_put(&argp->fh);
diff --git a/fs/nfsd/nfs3xdr.c b/fs/nfsd/nfs3xdr.c
index 0a5ebc52e6a9..704e727464ca 100644
--- a/fs/nfsd/nfs3xdr.c
+++ b/fs/nfsd/nfs3xdr.c
@@ -21,15 +21,6 @@ static const struct svc_fh nfs3svc_null_fh = {
        .fh_no_wcc      = true,
 };
 
-/*
- * time_delta. {1, 0} means the server is accurate only
- * to the nearest second.
- */
-static const struct timespec64 nfs3svc_time_delta = {
-       .tv_sec         = 1,
-       .tv_nsec        = 0,
-};
-
 /*
  * Mapping of S_IF* types to NFS file types
  */
@@ -1336,6 +1327,19 @@ svcxdr_encode_fsinfo3resok(struct xdr_stream *xdr,
                           const struct nfsd3_fsinfores *resp)
 {
        __be32 *p;
+       struct timespec64 nfs3svc_time_delta;
+
+       if (resp->f_time_gran) {
+               nfs3svc_time_delta.tv_sec = 0;
+               nfs3svc_time_delta.tv_nsec = resp->f_time_gran;
+       } else {
+               /*
+                * {1, 0} means the server is accurate only to the nearest
+                * second.
+                */
+               nfs3svc_time_delta.tv_sec = 1;
+               nfs3svc_time_delta.tv_nsec = 0;
+       }
 
        p = xdr_reserve_space(xdr, XDR_UNIT * 12);
        if (!p)
diff --git a/fs/nfsd/xdr3.h b/fs/nfsd/xdr3.h
index 933008382bbe..9a33ea0b678d 100644
--- a/fs/nfsd/xdr3.h
+++ b/fs/nfsd/xdr3.h
@@ -201,6 +201,7 @@ struct nfsd3_fsinfores {
        __u32                   f_dtpref;
        __u64                   f_maxfilesize;
        __u32                   f_properties;
+       __u32                   f_time_gran;
 };
 
 struct nfsd3_pathconfres {
-- 
2.30.2

_______________________________________________
Devel mailing list
Devel@openvz.org
https://lists.openvz.org/mailman/listinfo/devel

Reply via email to