diff options
author | Linus Torvalds <torvalds@linux-foundation.org> | 2009-06-22 15:53:06 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@linux-foundation.org> | 2009-06-22 15:53:06 -0400 |
commit | df36b439c5fedefe013d4449cb6a50d15e2f4d70 (patch) | |
tree | 537c58db778cbf11b74e28091f89d1b8139fb84d /fs/nfs/write.c | |
parent | a9b011f5ac57cbaedb32a8149f3d39d7b2c1f0e0 (diff) | |
parent | e9f029855865e917821ef6034b31e340a4cfc815 (diff) |
Merge branch 'for-2.6.31' of git://git.linux-nfs.org/projects/trondmy/nfs-2.6
* 'for-2.6.31' of git://git.linux-nfs.org/projects/trondmy/nfs-2.6: (128 commits)
nfs41: sunrpc: xprt_alloc_bc_request() should not use spin_lock_bh()
nfs41: Move initialization of nfs4_opendata seq_res to nfs4_init_opendata_res
nfs: remove unnecessary NFS_INO_INVALID_ACL checks
NFS: More "sloppy" parsing problems
NFS: Invalid mount option values should always fail, even with "sloppy"
NFS: Remove unused XDR decoder functions
NFS: Update MNT and MNT3 reply decoding functions
NFS: add XDR decoder for mountd version 3 auth-flavor lists
NFS: add new file handle decoders to in-kernel mountd client
NFS: Add separate mountd status code decoders for each mountd version
NFS: remove unused function in fs/nfs/mount_clnt.c
NFS: Use xdr_stream-based XDR encoder for MNT's dirpath argument
NFS: Clean up MNT program definitions
lockd: Don't bother with RPC ping for NSM upcalls
lockd: Update NSM state from SM_MON replies
NFS: Fix false error return from nfs_callback_up() if ipv6.ko is not available
NFS: Return error code from nfs_callback_up() to user space
NFS: Do not display the setting of the "intr" mount option
NFS: add support for splice writes
nfs41: Backchannel: CB_SEQUENCE validation
...
Diffstat (limited to 'fs/nfs/write.c')
-rw-r--r-- | fs/nfs/write.c | 31 |
1 files changed, 29 insertions, 2 deletions
diff --git a/fs/nfs/write.c b/fs/nfs/write.c index e560a78995a3..ce728829f79a 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 | ||
@@ -52,6 +53,7 @@ struct nfs_write_data *nfs_commitdata_alloc(void) | |||
52 | if (p) { | 53 | if (p) { |
53 | memset(p, 0, sizeof(*p)); | 54 | memset(p, 0, sizeof(*p)); |
54 | INIT_LIST_HEAD(&p->pages); | 55 | INIT_LIST_HEAD(&p->pages); |
56 | p->res.seq_res.sr_slotid = NFS4_MAX_SLOT_TABLE; | ||
55 | } | 57 | } |
56 | return p; | 58 | return p; |
57 | } | 59 | } |
@@ -71,6 +73,7 @@ struct nfs_write_data *nfs_writedata_alloc(unsigned int pagecount) | |||
71 | memset(p, 0, sizeof(*p)); | 73 | memset(p, 0, sizeof(*p)); |
72 | INIT_LIST_HEAD(&p->pages); | 74 | INIT_LIST_HEAD(&p->pages); |
73 | p->npages = pagecount; | 75 | p->npages = pagecount; |
76 | p->res.seq_res.sr_slotid = NFS4_MAX_SLOT_TABLE; | ||
74 | if (pagecount <= ARRAY_SIZE(p->page_array)) | 77 | if (pagecount <= ARRAY_SIZE(p->page_array)) |
75 | p->pagevec = p->page_array; | 78 | p->pagevec = p->page_array; |
76 | else { | 79 | else { |
@@ -1048,7 +1051,23 @@ out: | |||
1048 | nfs_writedata_release(calldata); | 1051 | nfs_writedata_release(calldata); |
1049 | } | 1052 | } |
1050 | 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 | |||
1051 | 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 */ | ||
1052 | .rpc_call_done = nfs_writeback_done_partial, | 1071 | .rpc_call_done = nfs_writeback_done_partial, |
1053 | .rpc_release = nfs_writeback_release_partial, | 1072 | .rpc_release = nfs_writeback_release_partial, |
1054 | }; | 1073 | }; |
@@ -1111,6 +1130,9 @@ remove_request: | |||
1111 | } | 1130 | } |
1112 | 1131 | ||
1113 | 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 */ | ||
1114 | .rpc_call_done = nfs_writeback_done_full, | 1136 | .rpc_call_done = nfs_writeback_done_full, |
1115 | .rpc_release = nfs_writeback_release_full, | 1137 | .rpc_release = nfs_writeback_release_full, |
1116 | }; | 1138 | }; |
@@ -1123,6 +1145,7 @@ int nfs_writeback_done(struct rpc_task *task, struct nfs_write_data *data) | |||
1123 | { | 1145 | { |
1124 | struct nfs_writeargs *argp = &data->args; | 1146 | struct nfs_writeargs *argp = &data->args; |
1125 | struct nfs_writeres *resp = &data->res; | 1147 | struct nfs_writeres *resp = &data->res; |
1148 | struct nfs_server *server = NFS_SERVER(data->inode); | ||
1126 | int status; | 1149 | int status; |
1127 | 1150 | ||
1128 | dprintk("NFS: %5u nfs_writeback_done (status %d)\n", | 1151 | dprintk("NFS: %5u nfs_writeback_done (status %d)\n", |
@@ -1155,7 +1178,7 @@ int nfs_writeback_done(struct rpc_task *task, struct nfs_write_data *data) | |||
1155 | if (time_before(complain, jiffies)) { | 1178 | if (time_before(complain, jiffies)) { |
1156 | dprintk("NFS: faulty NFS server %s:" | 1179 | dprintk("NFS: faulty NFS server %s:" |
1157 | " (committed = %d) != (stable = %d)\n", | 1180 | " (committed = %d) != (stable = %d)\n", |
1158 | NFS_SERVER(data->inode)->nfs_client->cl_hostname, | 1181 | server->nfs_client->cl_hostname, |
1159 | resp->verf->committed, argp->stable); | 1182 | resp->verf->committed, argp->stable); |
1160 | complain = jiffies + 300 * HZ; | 1183 | complain = jiffies + 300 * HZ; |
1161 | } | 1184 | } |
@@ -1181,7 +1204,7 @@ int nfs_writeback_done(struct rpc_task *task, struct nfs_write_data *data) | |||
1181 | */ | 1204 | */ |
1182 | argp->stable = NFS_FILE_SYNC; | 1205 | argp->stable = NFS_FILE_SYNC; |
1183 | } | 1206 | } |
1184 | rpc_restart_call(task); | 1207 | nfs4_restart_rpc(task, server->nfs_client); |
1185 | return -EAGAIN; | 1208 | return -EAGAIN; |
1186 | } | 1209 | } |
1187 | if (time_before(complain, jiffies)) { | 1210 | if (time_before(complain, jiffies)) { |
@@ -1193,6 +1216,7 @@ int nfs_writeback_done(struct rpc_task *task, struct nfs_write_data *data) | |||
1193 | /* Can't do anything about it except throw an error. */ | 1216 | /* Can't do anything about it except throw an error. */ |
1194 | task->tk_status = -EIO; | 1217 | task->tk_status = -EIO; |
1195 | } | 1218 | } |
1219 | nfs4_sequence_free_slot(server->nfs_client, &data->res.seq_res); | ||
1196 | return 0; | 1220 | return 0; |
1197 | } | 1221 | } |
1198 | 1222 | ||
@@ -1349,6 +1373,9 @@ static void nfs_commit_release(void *calldata) | |||
1349 | } | 1373 | } |
1350 | 1374 | ||
1351 | static const struct rpc_call_ops nfs_commit_ops = { | 1375 | static const struct rpc_call_ops nfs_commit_ops = { |
1376 | #if defined(CONFIG_NFS_V4_1) | ||
1377 | .rpc_call_prepare = nfs_write_prepare, | ||
1378 | #endif /* CONFIG_NFS_V4_1 */ | ||
1352 | .rpc_call_done = nfs_commit_done, | 1379 | .rpc_call_done = nfs_commit_done, |
1353 | .rpc_release = nfs_commit_release, | 1380 | .rpc_release = nfs_commit_release, |
1354 | }; | 1381 | }; |