diff options
| author | Andy Adamson <andros@netapp.com> | 2009-04-01 09:22:26 -0400 |
|---|---|---|
| committer | Benny Halevy <bhalevy@panasas.com> | 2009-06-17 13:46:49 -0400 |
| commit | def6ed7ef45ed19c3d6ca765f3bfdff1fe4c6bba (patch) | |
| tree | 98e072aa00e6c284dac719c6c7f97abd7c930d90 | |
| parent | f11c88af26453aee2823a1fd9120d0cd8dae7b9a (diff) | |
nfs41 write sequence setup done support
Separate write calls from nfs41: sequence setup/done support
Implement the write rpc_call_prepare method for
asynchronuos nfs rpcs, call nfs41_setup_sequence from
respective rpc_call_validate_args methods.
Call nfs4_sequence_done from respective rpc_call_done methods.
Note that we need to pass a pointer to the nfs_server in calls data
for passing on to nfs4_sequence_done.
Signed-off-by: Andy Adamson <andros@netapp.com>
Signed-off-by: Benny Halevy <bhalevy@panasas.com>
[pnfs: client data server write validate and release]
Signed-off-by: Andy Adamson <andros@umich.edu>
Signed-off-by: Benny Halevy <bhalevy@panasas.com>
[move the nfs4_sequence_free_slot call in nfs_readpage_retry from]
[nfs41: separate free slot from sequence done
Signed-off-by: Andy Adamson <andros@umich.edu>
Signed-off-by: Benny Halevy <bhalevy@panasas.com>
[nfs41: Support sessions with O_DIRECT.]
Signed-off-by: Dean Hildebrand <dhildeb@us.ibm.com>
Signed-off-by: Benny Halevy <bhalevy@panasas.com>
[nfs41: nfs4_sequence_free_slot use nfs_client for data server]
Signed-off-by: Andy Adamson <andros@netapp.com>
Signed-off-by: Benny Halevy <bhalevy@panasas.com>
Signed-off-by: Trond Myklebust <Trond.Myklebust@netapp.com>
| -rw-r--r-- | fs/nfs/direct.c | 3 | ||||
| -rw-r--r-- | fs/nfs/internal.h | 3 | ||||
| -rw-r--r-- | fs/nfs/nfs4proc.c | 4 | ||||
| -rw-r--r-- | fs/nfs/write.c | 22 |
4 files changed, 32 insertions, 0 deletions
diff --git a/fs/nfs/direct.c b/fs/nfs/direct.c index c8c53a03a585..1955bfeb3551 100644 --- a/fs/nfs/direct.c +++ b/fs/nfs/direct.c | |||
| @@ -676,6 +676,9 @@ out_unlock: | |||
| 676 | } | 676 | } |
| 677 | 677 | ||
| 678 | static const struct rpc_call_ops nfs_write_direct_ops = { | 678 | static const struct rpc_call_ops nfs_write_direct_ops = { |
| 679 | #if defined(CONFIG_NFS_V4_1) | ||
| 680 | .rpc_call_prepare = nfs_write_prepare, | ||
| 681 | #endif /* CONFIG_NFS_V4_1 */ | ||
| 679 | .rpc_call_done = nfs_direct_write_result, | 682 | .rpc_call_done = nfs_direct_write_result, |
| 680 | .rpc_release = nfs_direct_write_release, | 683 | .rpc_release = nfs_direct_write_release, |
| 681 | }; | 684 | }; |
diff --git a/fs/nfs/internal.h b/fs/nfs/internal.h index 988c8b9aa78b..f62bc5226155 100644 --- a/fs/nfs/internal.h +++ b/fs/nfs/internal.h | |||
| @@ -209,6 +209,9 @@ extern int nfs4_path_walk(struct nfs_server *server, | |||
| 209 | /* read.c */ | 209 | /* read.c */ |
| 210 | extern void nfs_read_prepare(struct rpc_task *task, void *calldata); | 210 | extern void nfs_read_prepare(struct rpc_task *task, void *calldata); |
| 211 | 211 | ||
| 212 | /* write.c */ | ||
| 213 | extern void nfs_write_prepare(struct rpc_task *task, void *calldata); | ||
| 214 | |||
| 212 | /* nfs4proc.c */ | 215 | /* nfs4proc.c */ |
| 213 | extern int _nfs4_call_sync(struct nfs_server *server, | 216 | extern int _nfs4_call_sync(struct nfs_server *server, |
| 214 | struct rpc_message *msg, | 217 | struct rpc_message *msg, |
diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c index 6c0ac539d9c7..5f71832436fd 100644 --- a/fs/nfs/nfs4proc.c +++ b/fs/nfs/nfs4proc.c | |||
| @@ -2890,6 +2890,10 @@ static int nfs4_write_done(struct rpc_task *task, struct nfs_write_data *data) | |||
| 2890 | { | 2890 | { |
| 2891 | struct inode *inode = data->inode; | 2891 | struct inode *inode = data->inode; |
| 2892 | 2892 | ||
| 2893 | /* slot is freed in nfs_writeback_done */ | ||
| 2894 | nfs4_sequence_done(NFS_SERVER(inode), &data->res.seq_res, | ||
| 2895 | task->tk_status); | ||
| 2896 | |||
| 2893 | if (nfs4_async_handle_error(task, NFS_SERVER(inode), data->args.context->state) == -EAGAIN) { | 2897 | if (nfs4_async_handle_error(task, NFS_SERVER(inode), data->args.context->state) == -EAGAIN) { |
| 2894 | rpc_restart_call(task); | 2898 | rpc_restart_call(task); |
| 2895 | return -EAGAIN; | 2899 | return -EAGAIN; |
diff --git a/fs/nfs/write.c b/fs/nfs/write.c index 035e6fb9f57e..195fe7667529 100644 --- a/fs/nfs/write.c +++ b/fs/nfs/write.c | |||
| @@ -25,6 +25,7 @@ | |||
| 25 | #include "delegation.h" | 25 | #include "delegation.h" |
| 26 | #include "internal.h" | 26 | #include "internal.h" |
| 27 | #include "iostat.h" | 27 | #include "iostat.h" |
| 28 | #include "nfs4_fs.h" | ||
| 28 | 29 | ||
| 29 | #define NFSDBG_FACILITY NFSDBG_PAGECACHE | 30 | #define NFSDBG_FACILITY NFSDBG_PAGECACHE |
| 30 | 31 | ||
| @@ -1050,7 +1051,23 @@ out: | |||
| 1050 | nfs_writedata_release(calldata); | 1051 | nfs_writedata_release(calldata); |
| 1051 | } | 1052 | } |
| 1052 | 1053 | ||
| 1054 | #if defined(CONFIG_NFS_V4_1) | ||
| 1055 | void nfs_write_prepare(struct rpc_task *task, void *calldata) | ||
| 1056 | { | ||
| 1057 | struct nfs_write_data *data = calldata; | ||
| 1058 | struct nfs_client *clp = (NFS_SERVER(data->inode))->nfs_client; | ||
| 1059 | |||
| 1060 | if (nfs4_setup_sequence(clp, &data->args.seq_args, | ||
| 1061 | &data->res.seq_res, 1, task)) | ||
| 1062 | return; | ||
| 1063 | rpc_call_start(task); | ||
| 1064 | } | ||
| 1065 | #endif /* CONFIG_NFS_V4_1 */ | ||
| 1066 | |||
| 1053 | static const struct rpc_call_ops nfs_write_partial_ops = { | 1067 | static const struct rpc_call_ops nfs_write_partial_ops = { |
| 1068 | #if defined(CONFIG_NFS_V4_1) | ||
| 1069 | .rpc_call_prepare = nfs_write_prepare, | ||
| 1070 | #endif /* CONFIG_NFS_V4_1 */ | ||
| 1054 | .rpc_call_done = nfs_writeback_done_partial, | 1071 | .rpc_call_done = nfs_writeback_done_partial, |
| 1055 | .rpc_release = nfs_writeback_release_partial, | 1072 | .rpc_release = nfs_writeback_release_partial, |
| 1056 | }; | 1073 | }; |
| @@ -1113,6 +1130,9 @@ remove_request: | |||
| 1113 | } | 1130 | } |
| 1114 | 1131 | ||
| 1115 | static const struct rpc_call_ops nfs_write_full_ops = { | 1132 | static const struct rpc_call_ops nfs_write_full_ops = { |
| 1133 | #if defined(CONFIG_NFS_V4_1) | ||
| 1134 | .rpc_call_prepare = nfs_write_prepare, | ||
| 1135 | #endif /* CONFIG_NFS_V4_1 */ | ||
| 1116 | .rpc_call_done = nfs_writeback_done_full, | 1136 | .rpc_call_done = nfs_writeback_done_full, |
| 1117 | .rpc_release = nfs_writeback_release_full, | 1137 | .rpc_release = nfs_writeback_release_full, |
| 1118 | }; | 1138 | }; |
| @@ -1195,6 +1215,8 @@ int nfs_writeback_done(struct rpc_task *task, struct nfs_write_data *data) | |||
| 1195 | /* Can't do anything about it except throw an error. */ | 1215 | /* Can't do anything about it except throw an error. */ |
| 1196 | task->tk_status = -EIO; | 1216 | task->tk_status = -EIO; |
| 1197 | } | 1217 | } |
| 1218 | nfs4_sequence_free_slot(NFS_SERVER(data->inode)->nfs_client, | ||
| 1219 | &data->res.seq_res); | ||
| 1198 | return 0; | 1220 | return 0; |
| 1199 | } | 1221 | } |
| 1200 | 1222 | ||
