diff options
author | Trond Myklebust <Trond.Myklebust@netapp.com> | 2009-03-11 14:10:28 -0400 |
---|---|---|
committer | Trond Myklebust <Trond.Myklebust@netapp.com> | 2009-03-11 14:10:28 -0400 |
commit | a65318bf3afc93ce49227e849d213799b072c5fd (patch) | |
tree | 754aad8596310825b96956012b7f584fff5b7a54 | |
parent | 69aaaae18f7027d9594bce100378f102926cc0be (diff) |
NFSv4: Simplify some cache consistency post-op GETATTRs
Certain asynchronous operations such as write() do not expect
(or care) that other metadata such as the file owner, mode, acls, ...
change. All they want to do is update and/or check the change attribute,
ctime, and mtime.
By skipping the file owner and group update, we also avoid having to do a
potential idmapper upcall for these asynchronous RPC calls.
Signed-off-by: Trond Myklebust <Trond.Myklebust@netapp.com>
-rw-r--r-- | fs/nfs/nfs4proc.c | 13 | ||||
-rw-r--r-- | include/linux/nfs_fs_sb.h | 5 |
2 files changed, 13 insertions, 5 deletions
diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c index aa433d077945..101f5f4c304f 100644 --- a/fs/nfs/nfs4proc.c +++ b/fs/nfs/nfs4proc.c | |||
@@ -1439,7 +1439,7 @@ int nfs4_do_close(struct path *path, struct nfs4_state *state, int wait) | |||
1439 | if (calldata->arg.seqid == NULL) | 1439 | if (calldata->arg.seqid == NULL) |
1440 | goto out_free_calldata; | 1440 | goto out_free_calldata; |
1441 | calldata->arg.fmode = 0; | 1441 | calldata->arg.fmode = 0; |
1442 | calldata->arg.bitmask = server->attr_bitmask; | 1442 | calldata->arg.bitmask = server->cache_consistency_bitmask; |
1443 | calldata->res.fattr = &calldata->fattr; | 1443 | calldata->res.fattr = &calldata->fattr; |
1444 | calldata->res.seqid = calldata->arg.seqid; | 1444 | calldata->res.seqid = calldata->arg.seqid; |
1445 | calldata->res.server = server; | 1445 | calldata->res.server = server; |
@@ -1600,6 +1600,9 @@ static int _nfs4_server_capabilities(struct nfs_server *server, struct nfs_fh *f | |||
1600 | server->caps |= NFS_CAP_HARDLINKS; | 1600 | server->caps |= NFS_CAP_HARDLINKS; |
1601 | if (res.has_symlinks != 0) | 1601 | if (res.has_symlinks != 0) |
1602 | server->caps |= NFS_CAP_SYMLINKS; | 1602 | server->caps |= NFS_CAP_SYMLINKS; |
1603 | memcpy(server->cache_consistency_bitmask, res.attr_bitmask, sizeof(server->cache_consistency_bitmask)); | ||
1604 | server->cache_consistency_bitmask[0] &= FATTR4_WORD0_CHANGE|FATTR4_WORD0_SIZE; | ||
1605 | server->cache_consistency_bitmask[1] &= FATTR4_WORD1_TIME_METADATA|FATTR4_WORD1_TIME_MODIFY; | ||
1603 | server->acl_bitmask = res.acl_bitmask; | 1606 | server->acl_bitmask = res.acl_bitmask; |
1604 | } | 1607 | } |
1605 | return status; | 1608 | return status; |
@@ -2079,7 +2082,7 @@ static void nfs4_proc_unlink_setup(struct rpc_message *msg, struct inode *dir) | |||
2079 | struct nfs_removeargs *args = msg->rpc_argp; | 2082 | struct nfs_removeargs *args = msg->rpc_argp; |
2080 | struct nfs_removeres *res = msg->rpc_resp; | 2083 | struct nfs_removeres *res = msg->rpc_resp; |
2081 | 2084 | ||
2082 | args->bitmask = server->attr_bitmask; | 2085 | args->bitmask = server->cache_consistency_bitmask; |
2083 | res->server = server; | 2086 | res->server = server; |
2084 | msg->rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_REMOVE]; | 2087 | msg->rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_REMOVE]; |
2085 | } | 2088 | } |
@@ -2323,7 +2326,7 @@ static int _nfs4_proc_readdir(struct dentry *dentry, struct rpc_cred *cred, | |||
2323 | .pages = &page, | 2326 | .pages = &page, |
2324 | .pgbase = 0, | 2327 | .pgbase = 0, |
2325 | .count = count, | 2328 | .count = count, |
2326 | .bitmask = NFS_SERVER(dentry->d_inode)->attr_bitmask, | 2329 | .bitmask = NFS_SERVER(dentry->d_inode)->cache_consistency_bitmask, |
2327 | }; | 2330 | }; |
2328 | struct nfs4_readdir_res res; | 2331 | struct nfs4_readdir_res res; |
2329 | struct rpc_message msg = { | 2332 | struct rpc_message msg = { |
@@ -2552,7 +2555,7 @@ static void nfs4_proc_write_setup(struct nfs_write_data *data, struct rpc_messag | |||
2552 | { | 2555 | { |
2553 | struct nfs_server *server = NFS_SERVER(data->inode); | 2556 | struct nfs_server *server = NFS_SERVER(data->inode); |
2554 | 2557 | ||
2555 | data->args.bitmask = server->attr_bitmask; | 2558 | data->args.bitmask = server->cache_consistency_bitmask; |
2556 | data->res.server = server; | 2559 | data->res.server = server; |
2557 | data->timestamp = jiffies; | 2560 | data->timestamp = jiffies; |
2558 | 2561 | ||
@@ -2575,7 +2578,7 @@ static void nfs4_proc_commit_setup(struct nfs_write_data *data, struct rpc_messa | |||
2575 | { | 2578 | { |
2576 | struct nfs_server *server = NFS_SERVER(data->inode); | 2579 | struct nfs_server *server = NFS_SERVER(data->inode); |
2577 | 2580 | ||
2578 | data->args.bitmask = server->attr_bitmask; | 2581 | data->args.bitmask = server->cache_consistency_bitmask; |
2579 | data->res.server = server; | 2582 | data->res.server = server; |
2580 | msg->rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_COMMIT]; | 2583 | msg->rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_COMMIT]; |
2581 | } | 2584 | } |
diff --git a/include/linux/nfs_fs_sb.h b/include/linux/nfs_fs_sb.h index 9bb81aec91cf..29b1e40dce99 100644 --- a/include/linux/nfs_fs_sb.h +++ b/include/linux/nfs_fs_sb.h | |||
@@ -106,6 +106,11 @@ struct nfs_server { | |||
106 | u32 attr_bitmask[2];/* V4 bitmask representing the set | 106 | u32 attr_bitmask[2];/* V4 bitmask representing the set |
107 | of attributes supported on this | 107 | of attributes supported on this |
108 | filesystem */ | 108 | filesystem */ |
109 | u32 cache_consistency_bitmask[2]; | ||
110 | /* V4 bitmask representing the subset | ||
111 | of change attribute, size, ctime | ||
112 | and mtime attributes supported by | ||
113 | the server */ | ||
109 | u32 acl_bitmask; /* V4 bitmask representing the ACEs | 114 | u32 acl_bitmask; /* V4 bitmask representing the ACEs |
110 | that are supported on this | 115 | that are supported on this |
111 | filesystem */ | 116 | filesystem */ |