NFSv4.1: Work around a Linux server bug...
authorTrond Myklebust <trond.myklebust@primarydata.com>
Tue, 9 May 2017 19:47:15 +0000 (15:47 -0400)
committerTrond Myklebust <trond.myklebust@primarydata.com>
Tue, 9 May 2017 19:52:15 +0000 (15:52 -0400)
It turns out the Linux server has a bug in its implementation of
supattr_exclcreat; it returns the set of all attributes, whether
or not they are supported by minor version 1.
In order to avoid a regression, we therefore apply the supported_attrs
as a mask on top of whatever the server sent us.

Reported-by: Anna Schumaker <Anna.Schumaker@Netapp.com>
Signed-off-by: Trond Myklebust <trond.myklebust@primarydata.com>
fs/nfs/nfs4proc.c

index f48dfb7f36916b728c7446269aea5afc7536a420..c08c46a3b8cde00ef5aa40fae87ed2fce06faea1 100644 (file)
@@ -3268,6 +3268,7 @@ static int _nfs4_server_capabilities(struct nfs_server *server, struct nfs_fh *f
                .rpc_resp = &res,
        };
        int status;
+       int i;
 
        bitmask[0] = FATTR4_WORD0_SUPPORTED_ATTRS |
                     FATTR4_WORD0_FH_EXPIRE_TYPE |
@@ -3333,8 +3334,13 @@ static int _nfs4_server_capabilities(struct nfs_server *server, struct nfs_fh *f
                server->cache_consistency_bitmask[0] &= FATTR4_WORD0_CHANGE|FATTR4_WORD0_SIZE;
                server->cache_consistency_bitmask[1] &= FATTR4_WORD1_TIME_METADATA|FATTR4_WORD1_TIME_MODIFY;
                server->cache_consistency_bitmask[2] = 0;
+
+               /* Avoid a regression due to buggy server */
+               for (i = 0; i < ARRAY_SIZE(res.exclcreat_bitmask); i++)
+                       res.exclcreat_bitmask[i] &= res.attr_bitmask[i];
                memcpy(server->exclcreat_bitmask, res.exclcreat_bitmask,
                        sizeof(server->exclcreat_bitmask));
+
                server->acl_bitmask = res.acl_bitmask;
                server->fh_expire_type = res.fh_expire_type;
        }