aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorLinus Torvalds <torvalds@g5.osdl.org>2006-01-06 18:22:57 -0500
committerLinus Torvalds <torvalds@g5.osdl.org>2006-01-06 18:22:57 -0500
commit47853e7fa588bef826c9799a87b33904b32bd905 (patch)
treebd7681d1aedf28125b86fb0218e64297f4d71ac9
parent221fc10ec89834329e5613e3cab4569ba22da410 (diff)
parent9e56904e41e242169007e69d9916059dab995d90 (diff)
Merge git://git.linux-nfs.org/pub/linux/nfs-2.6
-rw-r--r--Documentation/kernel-parameters.txt8
-rw-r--r--fs/lockd/clntproc.c41
-rw-r--r--fs/lockd/host.c4
-rw-r--r--fs/lockd/mon.c1
-rw-r--r--fs/lockd/svc.c4
-rw-r--r--fs/lockd/svc4proc.c15
-rw-r--r--fs/lockd/svclock.c42
-rw-r--r--fs/lockd/svcproc.c14
-rw-r--r--fs/lockd/xdr4.c4
-rw-r--r--fs/locks.c20
-rw-r--r--fs/nfs/Makefile1
-rw-r--r--fs/nfs/callback.c3
-rw-r--r--fs/nfs/callback.h1
-rw-r--r--fs/nfs/callback_proc.c4
-rw-r--r--fs/nfs/delegation.c47
-rw-r--r--fs/nfs/delegation.h2
-rw-r--r--fs/nfs/dir.c4
-rw-r--r--fs/nfs/direct.c57
-rw-r--r--fs/nfs/idmap.c9
-rw-r--r--fs/nfs/inode.c178
-rw-r--r--fs/nfs/mount_clnt.c1
-rw-r--r--fs/nfs/nfs2xdr.c21
-rw-r--r--fs/nfs/nfs3proc.c70
-rw-r--r--fs/nfs/nfs3xdr.c2
-rw-r--r--fs/nfs/nfs4_fs.h20
-rw-r--r--fs/nfs/nfs4proc.c1480
-rw-r--r--fs/nfs/nfs4renewd.c14
-rw-r--r--fs/nfs/nfs4state.c183
-rw-r--r--fs/nfs/nfs4xdr.c187
-rw-r--r--fs/nfs/nfsroot.c4
-rw-r--r--fs/nfs/proc.c31
-rw-r--r--fs/nfs/read.c16
-rw-r--r--fs/nfs/sysctl.c84
-rw-r--r--fs/nfs/unlink.c30
-rw-r--r--fs/nfs/write.c89
-rw-r--r--fs/nfsd/nfs4callback.c11
-rw-r--r--include/linux/fs.h2
-rw-r--r--include/linux/lockd/lockd.h2
-rw-r--r--include/linux/nfs_fs.h65
-rw-r--r--include/linux/nfs_idmap.h2
-rw-r--r--include/linux/nfs_page.h12
-rw-r--r--include/linux/nfs_xdr.h89
-rw-r--r--include/linux/sunrpc/clnt.h5
-rw-r--r--include/linux/sunrpc/gss_spkm3.h2
-rw-r--r--include/linux/sunrpc/sched.h48
-rw-r--r--include/linux/sunrpc/xdr.h6
-rw-r--r--include/linux/sunrpc/xprt.h12
-rw-r--r--include/linux/writeback.h9
-rw-r--r--mm/page-writeback.c10
-rw-r--r--net/sunrpc/auth_gss/gss_krb5_mech.c10
-rw-r--r--net/sunrpc/auth_gss/gss_spkm3_mech.c10
-rw-r--r--net/sunrpc/auth_gss/gss_spkm3_seal.c11
-rw-r--r--net/sunrpc/auth_gss/gss_spkm3_token.c3
-rw-r--r--net/sunrpc/auth_gss/gss_spkm3_unseal.c2
-rw-r--r--net/sunrpc/clnt.c107
-rw-r--r--net/sunrpc/pmap_clnt.c17
-rw-r--r--net/sunrpc/rpc_pipe.c9
-rw-r--r--net/sunrpc/sched.c222
-rw-r--r--net/sunrpc/sunrpc_syms.c4
-rw-r--r--net/sunrpc/xdr.c21
-rw-r--r--net/sunrpc/xprt.c66
-rw-r--r--net/sunrpc/xprtsock.c31
62 files changed, 2140 insertions, 1339 deletions
diff --git a/Documentation/kernel-parameters.txt b/Documentation/kernel-parameters.txt
index 61a56b100c62..a482fde09bbb 100644
--- a/Documentation/kernel-parameters.txt
+++ b/Documentation/kernel-parameters.txt
@@ -910,6 +910,14 @@ running once the system is up.
910 nfsroot= [NFS] nfs root filesystem for disk-less boxes. 910 nfsroot= [NFS] nfs root filesystem for disk-less boxes.
911 See Documentation/nfsroot.txt. 911 See Documentation/nfsroot.txt.
912 912
913 nfs.callback_tcpport=
914 [NFS] set the TCP port on which the NFSv4 callback
915 channel should listen.
916
917 nfs.idmap_cache_timeout=
918 [NFS] set the maximum lifetime for idmapper cache
919 entries.
920
913 nmi_watchdog= [KNL,BUGS=IA-32] Debugging features for SMP kernels 921 nmi_watchdog= [KNL,BUGS=IA-32] Debugging features for SMP kernels
914 922
915 no387 [BUGS=IA-32] Tells the kernel to use the 387 maths 923 no387 [BUGS=IA-32] Tells the kernel to use the 387 maths
diff --git a/fs/lockd/clntproc.c b/fs/lockd/clntproc.c
index c5a33648e9fd..145524039577 100644
--- a/fs/lockd/clntproc.c
+++ b/fs/lockd/clntproc.c
@@ -26,11 +26,12 @@
26static int nlmclnt_test(struct nlm_rqst *, struct file_lock *); 26static int nlmclnt_test(struct nlm_rqst *, struct file_lock *);
27static int nlmclnt_lock(struct nlm_rqst *, struct file_lock *); 27static int nlmclnt_lock(struct nlm_rqst *, struct file_lock *);
28static int nlmclnt_unlock(struct nlm_rqst *, struct file_lock *); 28static int nlmclnt_unlock(struct nlm_rqst *, struct file_lock *);
29static void nlmclnt_unlock_callback(struct rpc_task *);
30static void nlmclnt_cancel_callback(struct rpc_task *);
31static int nlm_stat_to_errno(u32 stat); 29static int nlm_stat_to_errno(u32 stat);
32static void nlmclnt_locks_init_private(struct file_lock *fl, struct nlm_host *host); 30static void nlmclnt_locks_init_private(struct file_lock *fl, struct nlm_host *host);
33 31
32static const struct rpc_call_ops nlmclnt_unlock_ops;
33static const struct rpc_call_ops nlmclnt_cancel_ops;
34
34/* 35/*
35 * Cookie counter for NLM requests 36 * Cookie counter for NLM requests
36 */ 37 */
@@ -221,8 +222,7 @@ nlmclnt_proc(struct inode *inode, int cmd, struct file_lock *fl)
221 goto done; 222 goto done;
222 } 223 }
223 clnt->cl_softrtry = nfssrv->client->cl_softrtry; 224 clnt->cl_softrtry = nfssrv->client->cl_softrtry;
224 clnt->cl_intr = nfssrv->client->cl_intr; 225 clnt->cl_intr = nfssrv->client->cl_intr;
225 clnt->cl_chatty = nfssrv->client->cl_chatty;
226 } 226 }
227 227
228 /* Keep the old signal mask */ 228 /* Keep the old signal mask */
@@ -399,8 +399,7 @@ in_grace_period:
399/* 399/*
400 * Generic NLM call, async version. 400 * Generic NLM call, async version.
401 */ 401 */
402int 402int nlmsvc_async_call(struct nlm_rqst *req, u32 proc, const struct rpc_call_ops *tk_ops)
403nlmsvc_async_call(struct nlm_rqst *req, u32 proc, rpc_action callback)
404{ 403{
405 struct nlm_host *host = req->a_host; 404 struct nlm_host *host = req->a_host;
406 struct rpc_clnt *clnt; 405 struct rpc_clnt *clnt;
@@ -419,13 +418,12 @@ nlmsvc_async_call(struct nlm_rqst *req, u32 proc, rpc_action callback)
419 msg.rpc_proc = &clnt->cl_procinfo[proc]; 418 msg.rpc_proc = &clnt->cl_procinfo[proc];
420 419
421 /* bootstrap and kick off the async RPC call */ 420 /* bootstrap and kick off the async RPC call */
422 status = rpc_call_async(clnt, &msg, RPC_TASK_ASYNC, callback, req); 421 status = rpc_call_async(clnt, &msg, RPC_TASK_ASYNC, tk_ops, req);
423 422
424 return status; 423 return status;
425} 424}
426 425
427static int 426static int nlmclnt_async_call(struct nlm_rqst *req, u32 proc, const struct rpc_call_ops *tk_ops)
428nlmclnt_async_call(struct nlm_rqst *req, u32 proc, rpc_action callback)
429{ 427{
430 struct nlm_host *host = req->a_host; 428 struct nlm_host *host = req->a_host;
431 struct rpc_clnt *clnt; 429 struct rpc_clnt *clnt;
@@ -448,7 +446,7 @@ nlmclnt_async_call(struct nlm_rqst *req, u32 proc, rpc_action callback)
448 /* Increment host refcount */ 446 /* Increment host refcount */
449 nlm_get_host(host); 447 nlm_get_host(host);
450 /* bootstrap and kick off the async RPC call */ 448 /* bootstrap and kick off the async RPC call */
451 status = rpc_call_async(clnt, &msg, RPC_TASK_ASYNC, callback, req); 449 status = rpc_call_async(clnt, &msg, RPC_TASK_ASYNC, tk_ops, req);
452 if (status < 0) 450 if (status < 0)
453 nlm_release_host(host); 451 nlm_release_host(host);
454 return status; 452 return status;
@@ -664,7 +662,7 @@ nlmclnt_unlock(struct nlm_rqst *req, struct file_lock *fl)
664 662
665 if (req->a_flags & RPC_TASK_ASYNC) { 663 if (req->a_flags & RPC_TASK_ASYNC) {
666 status = nlmclnt_async_call(req, NLMPROC_UNLOCK, 664 status = nlmclnt_async_call(req, NLMPROC_UNLOCK,
667 nlmclnt_unlock_callback); 665 &nlmclnt_unlock_ops);
668 /* Hrmf... Do the unlock early since locks_remove_posix() 666 /* Hrmf... Do the unlock early since locks_remove_posix()
669 * really expects us to free the lock synchronously */ 667 * really expects us to free the lock synchronously */
670 do_vfs_lock(fl); 668 do_vfs_lock(fl);
@@ -692,10 +690,9 @@ nlmclnt_unlock(struct nlm_rqst *req, struct file_lock *fl)
692 return -ENOLCK; 690 return -ENOLCK;
693} 691}
694 692
695static void 693static void nlmclnt_unlock_callback(struct rpc_task *task, void *data)
696nlmclnt_unlock_callback(struct rpc_task *task)
697{ 694{
698 struct nlm_rqst *req = (struct nlm_rqst *) task->tk_calldata; 695 struct nlm_rqst *req = data;
699 int status = req->a_res.status; 696 int status = req->a_res.status;
700 697
701 if (RPC_ASSASSINATED(task)) 698 if (RPC_ASSASSINATED(task))
@@ -722,6 +719,10 @@ die:
722 rpc_restart_call(task); 719 rpc_restart_call(task);
723} 720}
724 721
722static const struct rpc_call_ops nlmclnt_unlock_ops = {
723 .rpc_call_done = nlmclnt_unlock_callback,
724};
725
725/* 726/*
726 * Cancel a blocked lock request. 727 * Cancel a blocked lock request.
727 * We always use an async RPC call for this in order not to hang a 728 * We always use an async RPC call for this in order not to hang a
@@ -750,8 +751,7 @@ nlmclnt_cancel(struct nlm_host *host, struct file_lock *fl)
750 751
751 nlmclnt_setlockargs(req, fl); 752 nlmclnt_setlockargs(req, fl);
752 753
753 status = nlmclnt_async_call(req, NLMPROC_CANCEL, 754 status = nlmclnt_async_call(req, NLMPROC_CANCEL, &nlmclnt_cancel_ops);
754 nlmclnt_cancel_callback);
755 if (status < 0) { 755 if (status < 0) {
756 nlmclnt_release_lockargs(req); 756 nlmclnt_release_lockargs(req);
757 kfree(req); 757 kfree(req);
@@ -765,10 +765,9 @@ nlmclnt_cancel(struct nlm_host *host, struct file_lock *fl)
765 return status; 765 return status;
766} 766}
767 767
768static void 768static void nlmclnt_cancel_callback(struct rpc_task *task, void *data)
769nlmclnt_cancel_callback(struct rpc_task *task)
770{ 769{
771 struct nlm_rqst *req = (struct nlm_rqst *) task->tk_calldata; 770 struct nlm_rqst *req = data;
772 771
773 if (RPC_ASSASSINATED(task)) 772 if (RPC_ASSASSINATED(task))
774 goto die; 773 goto die;
@@ -807,6 +806,10 @@ retry_cancel:
807 rpc_delay(task, 30 * HZ); 806 rpc_delay(task, 30 * HZ);
808} 807}
809 808
809static const struct rpc_call_ops nlmclnt_cancel_ops = {
810 .rpc_call_done = nlmclnt_cancel_callback,
811};
812
810/* 813/*
811 * Convert an NLM status code to a generic kernel errno 814 * Convert an NLM status code to a generic kernel errno
812 */ 815 */
diff --git a/fs/lockd/host.c b/fs/lockd/host.c
index c4c8601096e0..82f7a0b1d8ae 100644
--- a/fs/lockd/host.c
+++ b/fs/lockd/host.c
@@ -177,7 +177,7 @@ nlm_bind_host(struct nlm_host *host)
177 if ((clnt = host->h_rpcclnt) != NULL) { 177 if ((clnt = host->h_rpcclnt) != NULL) {
178 xprt = clnt->cl_xprt; 178 xprt = clnt->cl_xprt;
179 if (time_after_eq(jiffies, host->h_nextrebind)) { 179 if (time_after_eq(jiffies, host->h_nextrebind)) {
180 clnt->cl_port = 0; 180 rpc_force_rebind(clnt);
181 host->h_nextrebind = jiffies + NLM_HOST_REBIND; 181 host->h_nextrebind = jiffies + NLM_HOST_REBIND;
182 dprintk("lockd: next rebind in %ld jiffies\n", 182 dprintk("lockd: next rebind in %ld jiffies\n",
183 host->h_nextrebind - jiffies); 183 host->h_nextrebind - jiffies);
@@ -217,7 +217,7 @@ nlm_rebind_host(struct nlm_host *host)
217{ 217{
218 dprintk("lockd: rebind host %s\n", host->h_name); 218 dprintk("lockd: rebind host %s\n", host->h_name);
219 if (host->h_rpcclnt && time_after_eq(jiffies, host->h_nextrebind)) { 219 if (host->h_rpcclnt && time_after_eq(jiffies, host->h_nextrebind)) {
220 host->h_rpcclnt->cl_port = 0; 220 rpc_force_rebind(host->h_rpcclnt);
221 host->h_nextrebind = jiffies + NLM_HOST_REBIND; 221 host->h_nextrebind = jiffies + NLM_HOST_REBIND;
222 } 222 }
223} 223}
diff --git a/fs/lockd/mon.c b/fs/lockd/mon.c
index 2d144abe84ad..0edc03e67966 100644
--- a/fs/lockd/mon.c
+++ b/fs/lockd/mon.c
@@ -123,7 +123,6 @@ nsm_create(void)
123 if (IS_ERR(clnt)) 123 if (IS_ERR(clnt))
124 goto out_err; 124 goto out_err;
125 clnt->cl_softrtry = 1; 125 clnt->cl_softrtry = 1;
126 clnt->cl_chatty = 1;
127 clnt->cl_oneshot = 1; 126 clnt->cl_oneshot = 1;
128 return clnt; 127 return clnt;
129 128
diff --git a/fs/lockd/svc.c b/fs/lockd/svc.c
index 12a857c29e25..71a30b416d1a 100644
--- a/fs/lockd/svc.c
+++ b/fs/lockd/svc.c
@@ -178,6 +178,8 @@ lockd(struct svc_rqst *rqstp)
178 178
179 } 179 }
180 180
181 flush_signals(current);
182
181 /* 183 /*
182 * Check whether there's a new lockd process before 184 * Check whether there's a new lockd process before
183 * shutting down the hosts and clearing the slot. 185 * shutting down the hosts and clearing the slot.
@@ -192,8 +194,6 @@ lockd(struct svc_rqst *rqstp)
192 "lockd: new process, skipping host shutdown\n"); 194 "lockd: new process, skipping host shutdown\n");
193 wake_up(&lockd_exit); 195 wake_up(&lockd_exit);
194 196
195 flush_signals(current);
196
197 /* Exit the RPC thread */ 197 /* Exit the RPC thread */
198 svc_exit_thread(rqstp); 198 svc_exit_thread(rqstp);
199 199
diff --git a/fs/lockd/svc4proc.c b/fs/lockd/svc4proc.c
index 489670e21769..4063095d849e 100644
--- a/fs/lockd/svc4proc.c
+++ b/fs/lockd/svc4proc.c
@@ -22,7 +22,8 @@
22#define NLMDBG_FACILITY NLMDBG_CLIENT 22#define NLMDBG_FACILITY NLMDBG_CLIENT
23 23
24static u32 nlm4svc_callback(struct svc_rqst *, u32, struct nlm_res *); 24static u32 nlm4svc_callback(struct svc_rqst *, u32, struct nlm_res *);
25static void nlm4svc_callback_exit(struct rpc_task *); 25
26static const struct rpc_call_ops nlm4svc_callback_ops;
26 27
27/* 28/*
28 * Obtain client and file from arguments 29 * Obtain client and file from arguments
@@ -470,7 +471,6 @@ nlm4svc_proc_granted_res(struct svc_rqst *rqstp, struct nlm_res *argp,
470} 471}
471 472
472 473
473
474/* 474/*
475 * This is the generic lockd callback for async RPC calls 475 * This is the generic lockd callback for async RPC calls
476 */ 476 */
@@ -494,7 +494,7 @@ nlm4svc_callback(struct svc_rqst *rqstp, u32 proc, struct nlm_res *resp)
494 call->a_host = host; 494 call->a_host = host;
495 memcpy(&call->a_args, resp, sizeof(*resp)); 495 memcpy(&call->a_args, resp, sizeof(*resp));
496 496
497 if (nlmsvc_async_call(call, proc, nlm4svc_callback_exit) < 0) 497 if (nlmsvc_async_call(call, proc, &nlm4svc_callback_ops) < 0)
498 goto error; 498 goto error;
499 499
500 return rpc_success; 500 return rpc_success;
@@ -504,10 +504,9 @@ nlm4svc_callback(struct svc_rqst *rqstp, u32 proc, struct nlm_res *resp)
504 return rpc_system_err; 504 return rpc_system_err;
505} 505}
506 506
507static void 507static void nlm4svc_callback_exit(struct rpc_task *task, void *data)
508nlm4svc_callback_exit(struct rpc_task *task)
509{ 508{
510 struct nlm_rqst *call = (struct nlm_rqst *) task->tk_calldata; 509 struct nlm_rqst *call = data;
511 510
512 if (task->tk_status < 0) { 511 if (task->tk_status < 0) {
513 dprintk("lockd: %4d callback failed (errno = %d)\n", 512 dprintk("lockd: %4d callback failed (errno = %d)\n",
@@ -517,6 +516,10 @@ nlm4svc_callback_exit(struct rpc_task *task)
517 kfree(call); 516 kfree(call);
518} 517}
519 518
519static const struct rpc_call_ops nlm4svc_callback_ops = {
520 .rpc_call_done = nlm4svc_callback_exit,
521};
522
520/* 523/*
521 * NLM Server procedures. 524 * NLM Server procedures.
522 */ 525 */
diff --git a/fs/lockd/svclock.c b/fs/lockd/svclock.c
index 49f959796b66..9cfced65d4a2 100644
--- a/fs/lockd/svclock.c
+++ b/fs/lockd/svclock.c
@@ -41,7 +41,8 @@
41 41
42static void nlmsvc_insert_block(struct nlm_block *block, unsigned long); 42static void nlmsvc_insert_block(struct nlm_block *block, unsigned long);
43static int nlmsvc_remove_block(struct nlm_block *block); 43static int nlmsvc_remove_block(struct nlm_block *block);
44static void nlmsvc_grant_callback(struct rpc_task *task); 44
45static const struct rpc_call_ops nlmsvc_grant_ops;
45 46
46/* 47/*
47 * The list of blocked locks to retry 48 * The list of blocked locks to retry
@@ -226,31 +227,27 @@ failed:
226 * It is the caller's responsibility to check whether the file 227 * It is the caller's responsibility to check whether the file
227 * can be closed hereafter. 228 * can be closed hereafter.
228 */ 229 */
229static void 230static int
230nlmsvc_delete_block(struct nlm_block *block, int unlock) 231nlmsvc_delete_block(struct nlm_block *block, int unlock)
231{ 232{
232 struct file_lock *fl = &block->b_call.a_args.lock.fl; 233 struct file_lock *fl = &block->b_call.a_args.lock.fl;
233 struct nlm_file *file = block->b_file; 234 struct nlm_file *file = block->b_file;
234 struct nlm_block **bp; 235 struct nlm_block **bp;
236 int status = 0;
235 237
236 dprintk("lockd: deleting block %p...\n", block); 238 dprintk("lockd: deleting block %p...\n", block);
237 239
238 /* Remove block from list */ 240 /* Remove block from list */
239 nlmsvc_remove_block(block); 241 nlmsvc_remove_block(block);
240 if (fl->fl_next) 242 if (unlock)
241 posix_unblock_lock(file->f_file, fl); 243 status = posix_unblock_lock(file->f_file, fl);
242 if (unlock) {
243 fl->fl_type = F_UNLCK;
244 posix_lock_file(file->f_file, fl);
245 block->b_granted = 0;
246 }
247 244
248 /* If the block is in the middle of a GRANT callback, 245 /* If the block is in the middle of a GRANT callback,
249 * don't kill it yet. */ 246 * don't kill it yet. */
250 if (block->b_incall) { 247 if (block->b_incall) {
251 nlmsvc_insert_block(block, NLM_NEVER); 248 nlmsvc_insert_block(block, NLM_NEVER);
252 block->b_done = 1; 249 block->b_done = 1;
253 return; 250 return status;
254 } 251 }
255 252
256 /* Remove block from file's list of blocks */ 253 /* Remove block from file's list of blocks */
@@ -265,6 +262,7 @@ nlmsvc_delete_block(struct nlm_block *block, int unlock)
265 nlm_release_host(block->b_host); 262 nlm_release_host(block->b_host);
266 nlmclnt_freegrantargs(&block->b_call); 263 nlmclnt_freegrantargs(&block->b_call);
267 kfree(block); 264 kfree(block);
265 return status;
268} 266}
269 267
270/* 268/*
@@ -275,6 +273,7 @@ int
275nlmsvc_traverse_blocks(struct nlm_host *host, struct nlm_file *file, int action) 273nlmsvc_traverse_blocks(struct nlm_host *host, struct nlm_file *file, int action)
276{ 274{
277 struct nlm_block *block, *next; 275 struct nlm_block *block, *next;
276 /* XXX: Will everything get cleaned up if we don't unlock here? */
278 277
279 down(&file->f_sema); 278 down(&file->f_sema);
280 for (block = file->f_blocks; block; block = next) { 279 for (block = file->f_blocks; block; block = next) {
@@ -444,6 +443,7 @@ u32
444nlmsvc_cancel_blocked(struct nlm_file *file, struct nlm_lock *lock) 443nlmsvc_cancel_blocked(struct nlm_file *file, struct nlm_lock *lock)
445{ 444{
446 struct nlm_block *block; 445 struct nlm_block *block;
446 int status = 0;
447 447
448 dprintk("lockd: nlmsvc_cancel(%s/%ld, pi=%d, %Ld-%Ld)\n", 448 dprintk("lockd: nlmsvc_cancel(%s/%ld, pi=%d, %Ld-%Ld)\n",
449 file->f_file->f_dentry->d_inode->i_sb->s_id, 449 file->f_file->f_dentry->d_inode->i_sb->s_id,
@@ -454,9 +454,9 @@ nlmsvc_cancel_blocked(struct nlm_file *file, struct nlm_lock *lock)
454 454
455 down(&file->f_sema); 455 down(&file->f_sema);
456 if ((block = nlmsvc_lookup_block(file, lock, 1)) != NULL) 456 if ((block = nlmsvc_lookup_block(file, lock, 1)) != NULL)
457 nlmsvc_delete_block(block, 1); 457 status = nlmsvc_delete_block(block, 1);
458 up(&file->f_sema); 458 up(&file->f_sema);
459 return nlm_granted; 459 return status ? nlm_lck_denied : nlm_granted;
460} 460}
461 461
462/* 462/*
@@ -562,7 +562,7 @@ callback:
562 /* Call the client */ 562 /* Call the client */
563 nlm_get_host(block->b_call.a_host); 563 nlm_get_host(block->b_call.a_host);
564 if (nlmsvc_async_call(&block->b_call, NLMPROC_GRANTED_MSG, 564 if (nlmsvc_async_call(&block->b_call, NLMPROC_GRANTED_MSG,
565 nlmsvc_grant_callback) < 0) 565 &nlmsvc_grant_ops) < 0)
566 nlm_release_host(block->b_call.a_host); 566 nlm_release_host(block->b_call.a_host);
567 up(&file->f_sema); 567 up(&file->f_sema);
568} 568}
@@ -575,10 +575,9 @@ callback:
575 * chain once more in order to have it removed by lockd itself (which can 575 * chain once more in order to have it removed by lockd itself (which can
576 * then sleep on the file semaphore without disrupting e.g. the nfs client). 576 * then sleep on the file semaphore without disrupting e.g. the nfs client).
577 */ 577 */
578static void 578static void nlmsvc_grant_callback(struct rpc_task *task, void *data)
579nlmsvc_grant_callback(struct rpc_task *task)
580{ 579{
581 struct nlm_rqst *call = (struct nlm_rqst *) task->tk_calldata; 580 struct nlm_rqst *call = data;
582 struct nlm_block *block; 581 struct nlm_block *block;
583 unsigned long timeout; 582 unsigned long timeout;
584 struct sockaddr_in *peer_addr = RPC_PEERADDR(task->tk_client); 583 struct sockaddr_in *peer_addr = RPC_PEERADDR(task->tk_client);
@@ -614,6 +613,10 @@ nlmsvc_grant_callback(struct rpc_task *task)
614 nlm_release_host(call->a_host); 613 nlm_release_host(call->a_host);
615} 614}
616 615
616static const struct rpc_call_ops nlmsvc_grant_ops = {
617 .rpc_call_done = nlmsvc_grant_callback,
618};
619
617/* 620/*
618 * We received a GRANT_RES callback. Try to find the corresponding 621 * We received a GRANT_RES callback. Try to find the corresponding
619 * block. 622 * block.
@@ -633,11 +636,12 @@ nlmsvc_grant_reply(struct svc_rqst *rqstp, struct nlm_cookie *cookie, u32 status
633 636
634 file->f_count++; 637 file->f_count++;
635 down(&file->f_sema); 638 down(&file->f_sema);
636 if ((block = nlmsvc_find_block(cookie,&rqstp->rq_addr)) != NULL) { 639 block = nlmsvc_find_block(cookie, &rqstp->rq_addr);
640 if (block) {
637 if (status == NLM_LCK_DENIED_GRACE_PERIOD) { 641 if (status == NLM_LCK_DENIED_GRACE_PERIOD) {
638 /* Try again in a couple of seconds */ 642 /* Try again in a couple of seconds */
639 nlmsvc_insert_block(block, 10 * HZ); 643 nlmsvc_insert_block(block, 10 * HZ);
640 block = NULL; 644 up(&file->f_sema);
641 } else { 645 } else {
642 /* Lock is now held by client, or has been rejected. 646 /* Lock is now held by client, or has been rejected.
643 * In both cases, the block should be removed. */ 647 * In both cases, the block should be removed. */
@@ -648,8 +652,6 @@ nlmsvc_grant_reply(struct svc_rqst *rqstp, struct nlm_cookie *cookie, u32 status
648 nlmsvc_delete_block(block, 1); 652 nlmsvc_delete_block(block, 1);
649 } 653 }
650 } 654 }
651 if (!block)
652 up(&file->f_sema);
653 nlm_release_file(file); 655 nlm_release_file(file);
654} 656}
655 657
diff --git a/fs/lockd/svcproc.c b/fs/lockd/svcproc.c
index 757e344cf200..3bc437e0cf5b 100644
--- a/fs/lockd/svcproc.c
+++ b/fs/lockd/svcproc.c
@@ -23,7 +23,8 @@
23#define NLMDBG_FACILITY NLMDBG_CLIENT 23#define NLMDBG_FACILITY NLMDBG_CLIENT
24 24
25static u32 nlmsvc_callback(struct svc_rqst *, u32, struct nlm_res *); 25static u32 nlmsvc_callback(struct svc_rqst *, u32, struct nlm_res *);
26static void nlmsvc_callback_exit(struct rpc_task *); 26
27static const struct rpc_call_ops nlmsvc_callback_ops;
27 28
28#ifdef CONFIG_LOCKD_V4 29#ifdef CONFIG_LOCKD_V4
29static u32 30static u32
@@ -518,7 +519,7 @@ nlmsvc_callback(struct svc_rqst *rqstp, u32 proc, struct nlm_res *resp)
518 call->a_host = host; 519 call->a_host = host;
519 memcpy(&call->a_args, resp, sizeof(*resp)); 520 memcpy(&call->a_args, resp, sizeof(*resp));
520 521
521 if (nlmsvc_async_call(call, proc, nlmsvc_callback_exit) < 0) 522 if (nlmsvc_async_call(call, proc, &nlmsvc_callback_ops) < 0)
522 goto error; 523 goto error;
523 524
524 return rpc_success; 525 return rpc_success;
@@ -528,10 +529,9 @@ nlmsvc_callback(struct svc_rqst *rqstp, u32 proc, struct nlm_res *resp)
528 return rpc_system_err; 529 return rpc_system_err;
529} 530}
530 531
531static void 532static void nlmsvc_callback_exit(struct rpc_task *task, void *data)
532nlmsvc_callback_exit(struct rpc_task *task)
533{ 533{
534 struct nlm_rqst *call = (struct nlm_rqst *) task->tk_calldata; 534 struct nlm_rqst *call = data;
535 535
536 if (task->tk_status < 0) { 536 if (task->tk_status < 0) {
537 dprintk("lockd: %4d callback failed (errno = %d)\n", 537 dprintk("lockd: %4d callback failed (errno = %d)\n",
@@ -541,6 +541,10 @@ nlmsvc_callback_exit(struct rpc_task *task)
541 kfree(call); 541 kfree(call);
542} 542}
543 543
544static const struct rpc_call_ops nlmsvc_callback_ops = {
545 .rpc_call_done = nlmsvc_callback_exit,
546};
547
544/* 548/*
545 * NLM Server procedures. 549 * NLM Server procedures.
546 */ 550 */
diff --git a/fs/lockd/xdr4.c b/fs/lockd/xdr4.c
index ae4d6b426c62..fdcf105a5303 100644
--- a/fs/lockd/xdr4.c
+++ b/fs/lockd/xdr4.c
@@ -354,7 +354,9 @@ nlm4svc_decode_reboot(struct svc_rqst *rqstp, u32 *p, struct nlm_reboot *argp)
354 return 0; 354 return 0;
355 argp->state = ntohl(*p++); 355 argp->state = ntohl(*p++);
356 /* Preserve the address in network byte order */ 356 /* Preserve the address in network byte order */
357 argp->addr = *p++; 357 argp->addr = *p++;
358 argp->vers = *p++;
359 argp->proto = *p++;
358 return xdr_argsize_check(rqstp, p); 360 return xdr_argsize_check(rqstp, p);
359} 361}
360 362
diff --git a/fs/locks.c b/fs/locks.c
index 250ef53d25ef..fb32d6218e21 100644
--- a/fs/locks.c
+++ b/fs/locks.c
@@ -1958,22 +1958,18 @@ EXPORT_SYMBOL(posix_block_lock);
1958 * 1958 *
1959 * lockd needs to block waiting for locks. 1959 * lockd needs to block waiting for locks.
1960 */ 1960 */
1961void 1961int
1962posix_unblock_lock(struct file *filp, struct file_lock *waiter) 1962posix_unblock_lock(struct file *filp, struct file_lock *waiter)
1963{ 1963{
1964 /* 1964 int status = 0;
1965 * A remote machine may cancel the lock request after it's been 1965
1966 * granted locally. If that happens, we need to delete the lock.
1967 */
1968 lock_kernel(); 1966 lock_kernel();
1969 if (waiter->fl_next) { 1967 if (waiter->fl_next)
1970 __locks_delete_block(waiter); 1968 __locks_delete_block(waiter);
1971 unlock_kernel(); 1969 else
1972 } else { 1970 status = -ENOENT;
1973 unlock_kernel(); 1971 unlock_kernel();
1974 waiter->fl_type = F_UNLCK; 1972 return status;
1975 posix_lock_file(filp, waiter);
1976 }
1977} 1973}
1978 1974
1979EXPORT_SYMBOL(posix_unblock_lock); 1975EXPORT_SYMBOL(posix_unblock_lock);
diff --git a/fs/nfs/Makefile b/fs/nfs/Makefile
index 8b3bb715d177..ec61fd56a1a9 100644
--- a/fs/nfs/Makefile
+++ b/fs/nfs/Makefile
@@ -13,4 +13,5 @@ nfs-$(CONFIG_NFS_V4) += nfs4proc.o nfs4xdr.o nfs4state.o nfs4renewd.o \
13 delegation.o idmap.o \ 13 delegation.o idmap.o \
14 callback.o callback_xdr.o callback_proc.o 14 callback.o callback_xdr.o callback_proc.o
15nfs-$(CONFIG_NFS_DIRECTIO) += direct.o 15nfs-$(CONFIG_NFS_DIRECTIO) += direct.o
16nfs-$(CONFIG_SYSCTL) += sysctl.o
16nfs-objs := $(nfs-y) 17nfs-objs := $(nfs-y)
diff --git a/fs/nfs/callback.c b/fs/nfs/callback.c
index 30cae3602867..fcd97406a778 100644
--- a/fs/nfs/callback.c
+++ b/fs/nfs/callback.c
@@ -34,6 +34,7 @@ static struct nfs_callback_data nfs_callback_info;
34static DECLARE_MUTEX(nfs_callback_sema); 34static DECLARE_MUTEX(nfs_callback_sema);
35static struct svc_program nfs4_callback_program; 35static struct svc_program nfs4_callback_program;
36 36
37unsigned int nfs_callback_set_tcpport;
37unsigned short nfs_callback_tcpport; 38unsigned short nfs_callback_tcpport;
38 39
39/* 40/*
@@ -98,7 +99,7 @@ int nfs_callback_up(void)
98 if (!serv) 99 if (!serv)
99 goto out_err; 100 goto out_err;
100 /* FIXME: We don't want to register this socket with the portmapper */ 101 /* FIXME: We don't want to register this socket with the portmapper */
101 ret = svc_makesock(serv, IPPROTO_TCP, 0); 102 ret = svc_makesock(serv, IPPROTO_TCP, nfs_callback_set_tcpport);
102 if (ret < 0) 103 if (ret < 0)
103 goto out_destroy; 104 goto out_destroy;
104 if (!list_empty(&serv->sv_permsocks)) { 105 if (!list_empty(&serv->sv_permsocks)) {
diff --git a/fs/nfs/callback.h b/fs/nfs/callback.h
index a0db2d4f9415..b252e7fe53a5 100644
--- a/fs/nfs/callback.h
+++ b/fs/nfs/callback.h
@@ -65,6 +65,7 @@ extern unsigned nfs4_callback_recall(struct cb_recallargs *args, void *dummy);
65extern int nfs_callback_up(void); 65extern int nfs_callback_up(void);
66extern int nfs_callback_down(void); 66extern int nfs_callback_down(void);
67 67
68extern unsigned int nfs_callback_set_tcpport;
68extern unsigned short nfs_callback_tcpport; 69extern unsigned short nfs_callback_tcpport;
69 70
70#endif /* __LINUX_FS_NFS_CALLBACK_H */ 71#endif /* __LINUX_FS_NFS_CALLBACK_H */
diff --git a/fs/nfs/callback_proc.c b/fs/nfs/callback_proc.c
index 65f1e19e4d19..462cfceb50c5 100644
--- a/fs/nfs/callback_proc.c
+++ b/fs/nfs/callback_proc.c
@@ -35,7 +35,9 @@ unsigned nfs4_callback_getattr(struct cb_getattrargs *args, struct cb_getattrres
35 if (delegation == NULL || (delegation->type & FMODE_WRITE) == 0) 35 if (delegation == NULL || (delegation->type & FMODE_WRITE) == 0)
36 goto out_iput; 36 goto out_iput;
37 res->size = i_size_read(inode); 37 res->size = i_size_read(inode);
38 res->change_attr = NFS_CHANGE_ATTR(inode); 38 res->change_attr = delegation->change_attr;
39 if (nfsi->npages != 0)
40 res->change_attr++;
39 res->ctime = inode->i_ctime; 41 res->ctime = inode->i_ctime;
40 res->mtime = inode->i_mtime; 42 res->mtime = inode->i_mtime;
41 res->bitmap[0] = (FATTR4_WORD0_CHANGE|FATTR4_WORD0_SIZE) & 43 res->bitmap[0] = (FATTR4_WORD0_CHANGE|FATTR4_WORD0_SIZE) &
diff --git a/fs/nfs/delegation.c b/fs/nfs/delegation.c
index 618a327027b3..c6f07c1c71e6 100644
--- a/fs/nfs/delegation.c
+++ b/fs/nfs/delegation.c
@@ -8,6 +8,7 @@
8 */ 8 */
9#include <linux/config.h> 9#include <linux/config.h>
10#include <linux/completion.h> 10#include <linux/completion.h>
11#include <linux/kthread.h>
11#include <linux/module.h> 12#include <linux/module.h>
12#include <linux/sched.h> 13#include <linux/sched.h>
13#include <linux/spinlock.h> 14#include <linux/spinlock.h>
@@ -130,6 +131,7 @@ int nfs_inode_set_delegation(struct inode *inode, struct rpc_cred *cred, struct
130 sizeof(delegation->stateid.data)); 131 sizeof(delegation->stateid.data));
131 delegation->type = res->delegation_type; 132 delegation->type = res->delegation_type;
132 delegation->maxsize = res->maxsize; 133 delegation->maxsize = res->maxsize;
134 delegation->change_attr = nfsi->change_attr;
133 delegation->cred = get_rpccred(cred); 135 delegation->cred = get_rpccred(cred);
134 delegation->inode = inode; 136 delegation->inode = inode;
135 137
@@ -157,8 +159,6 @@ static int nfs_do_return_delegation(struct inode *inode, struct nfs_delegation *
157{ 159{
158 int res = 0; 160 int res = 0;
159 161
160 __nfs_revalidate_inode(NFS_SERVER(inode), inode);
161
162 res = nfs4_proc_delegreturn(inode, delegation->cred, &delegation->stateid); 162 res = nfs4_proc_delegreturn(inode, delegation->cred, &delegation->stateid);
163 nfs_free_delegation(delegation); 163 nfs_free_delegation(delegation);
164 return res; 164 return res;
@@ -231,6 +231,49 @@ restart:
231 spin_unlock(&clp->cl_lock); 231 spin_unlock(&clp->cl_lock);
232} 232}
233 233
234int nfs_do_expire_all_delegations(void *ptr)
235{
236 struct nfs4_client *clp = ptr;
237 struct nfs_delegation *delegation;
238 struct inode *inode;
239
240 allow_signal(SIGKILL);
241restart:
242 spin_lock(&clp->cl_lock);
243 if (test_bit(NFS4CLNT_STATE_RECOVER, &clp->cl_state) != 0)
244 goto out;
245 if (test_bit(NFS4CLNT_LEASE_EXPIRED, &clp->cl_state) == 0)
246 goto out;
247 list_for_each_entry(delegation, &clp->cl_delegations, super_list) {
248 inode = igrab(delegation->inode);
249 if (inode == NULL)
250 continue;
251 spin_unlock(&clp->cl_lock);
252 nfs_inode_return_delegation(inode);
253 iput(inode);
254 goto restart;
255 }
256out:
257 spin_unlock(&clp->cl_lock);
258 nfs4_put_client(clp);
259 module_put_and_exit(0);
260}
261
262void nfs_expire_all_delegations(struct nfs4_client *clp)
263{
264 struct task_struct *task;
265
266 __module_get(THIS_MODULE);
267 atomic_inc(&clp->cl_count);
268 task = kthread_run(nfs_do_expire_all_delegations, clp,
269 "%u.%u.%u.%u-delegreturn",
270 NIPQUAD(clp->cl_addr));
271 if (!IS_ERR(task))
272 return;
273 nfs4_put_client(clp);
274 module_put(THIS_MODULE);
275}
276
234/* 277/*
235 * Return all delegations following an NFS4ERR_CB_PATH_DOWN error. 278 * Return all delegations following an NFS4ERR_CB_PATH_DOWN error.
236 */ 279 */
diff --git a/fs/nfs/delegation.h b/fs/nfs/delegation.h
index 2fcc30de924b..7a0b2bfce771 100644
--- a/fs/nfs/delegation.h
+++ b/fs/nfs/delegation.h
@@ -21,6 +21,7 @@ struct nfs_delegation {
21#define NFS_DELEGATION_NEED_RECLAIM 1 21#define NFS_DELEGATION_NEED_RECLAIM 1
22 long flags; 22 long flags;
23 loff_t maxsize; 23 loff_t maxsize;
24 __u64 change_attr;
24}; 25};
25 26
26int nfs_inode_set_delegation(struct inode *inode, struct rpc_cred *cred, struct nfs_openres *res); 27int nfs_inode_set_delegation(struct inode *inode, struct rpc_cred *cred, struct nfs_openres *res);
@@ -30,6 +31,7 @@ int nfs_async_inode_return_delegation(struct inode *inode, const nfs4_stateid *s
30 31
31struct inode *nfs_delegation_find_inode(struct nfs4_client *clp, const struct nfs_fh *fhandle); 32struct inode *nfs_delegation_find_inode(struct nfs4_client *clp, const struct nfs_fh *fhandle);
32void nfs_return_all_delegations(struct super_block *sb); 33void nfs_return_all_delegations(struct super_block *sb);
34void nfs_expire_all_delegations(struct nfs4_client *clp);
33void nfs_handle_cb_pathdown(struct nfs4_client *clp); 35void nfs_handle_cb_pathdown(struct nfs4_client *clp);
34 36
35void nfs_delegation_mark_reclaim(struct nfs4_client *clp); 37void nfs_delegation_mark_reclaim(struct nfs4_client *clp);
diff --git a/fs/nfs/dir.c b/fs/nfs/dir.c
index c0d1a214572c..e9255198f767 100644
--- a/fs/nfs/dir.c
+++ b/fs/nfs/dir.c
@@ -1550,8 +1550,10 @@ go_ahead:
1550 } 1550 }
1551 nfs_inode_return_delegation(old_inode); 1551 nfs_inode_return_delegation(old_inode);
1552 1552
1553 if (new_inode) 1553 if (new_inode != NULL) {
1554 nfs_inode_return_delegation(new_inode);
1554 d_delete(new_dentry); 1555 d_delete(new_dentry);
1556 }
1555 1557
1556 nfs_begin_data_update(old_dir); 1558 nfs_begin_data_update(old_dir);
1557 nfs_begin_data_update(new_dir); 1559 nfs_begin_data_update(new_dir);
diff --git a/fs/nfs/direct.c b/fs/nfs/direct.c
index 079228817603..10ae377e68ff 100644
--- a/fs/nfs/direct.c
+++ b/fs/nfs/direct.c
@@ -122,9 +122,10 @@ nfs_free_user_pages(struct page **pages, int npages, int do_dirty)
122{ 122{
123 int i; 123 int i;
124 for (i = 0; i < npages; i++) { 124 for (i = 0; i < npages; i++) {
125 if (do_dirty) 125 struct page *page = pages[i];
126 set_page_dirty_lock(pages[i]); 126 if (do_dirty && !PageCompound(page))
127 page_cache_release(pages[i]); 127 set_page_dirty_lock(page);
128 page_cache_release(page);
128 } 129 }
129 kfree(pages); 130 kfree(pages);
130} 131}
@@ -154,6 +155,7 @@ static struct nfs_direct_req *nfs_direct_read_alloc(size_t nbytes, unsigned int
154 struct list_head *list; 155 struct list_head *list;
155 struct nfs_direct_req *dreq; 156 struct nfs_direct_req *dreq;
156 unsigned int reads = 0; 157 unsigned int reads = 0;
158 unsigned int rpages = (rsize + PAGE_CACHE_SIZE - 1) >> PAGE_CACHE_SHIFT;
157 159
158 dreq = kmem_cache_alloc(nfs_direct_cachep, SLAB_KERNEL); 160 dreq = kmem_cache_alloc(nfs_direct_cachep, SLAB_KERNEL);
159 if (!dreq) 161 if (!dreq)
@@ -167,7 +169,7 @@ static struct nfs_direct_req *nfs_direct_read_alloc(size_t nbytes, unsigned int
167 169
168 list = &dreq->list; 170 list = &dreq->list;
169 for(;;) { 171 for(;;) {
170 struct nfs_read_data *data = nfs_readdata_alloc(); 172 struct nfs_read_data *data = nfs_readdata_alloc(rpages);
171 173
172 if (unlikely(!data)) { 174 if (unlikely(!data)) {
173 while (!list_empty(list)) { 175 while (!list_empty(list)) {
@@ -268,8 +270,6 @@ static void nfs_direct_read_schedule(struct nfs_direct_req *dreq,
268 NFS_PROTO(inode)->read_setup(data); 270 NFS_PROTO(inode)->read_setup(data);
269 271
270 data->task.tk_cookie = (unsigned long) inode; 272 data->task.tk_cookie = (unsigned long) inode;
271 data->task.tk_calldata = data;
272 data->task.tk_release = nfs_readdata_release;
273 data->complete = nfs_direct_read_result; 273 data->complete = nfs_direct_read_result;
274 274
275 lock_kernel(); 275 lock_kernel();
@@ -433,7 +433,7 @@ static ssize_t nfs_direct_write_seg(struct inode *inode,
433 struct nfs_writeverf first_verf; 433 struct nfs_writeverf first_verf;
434 struct nfs_write_data *wdata; 434 struct nfs_write_data *wdata;
435 435
436 wdata = nfs_writedata_alloc(); 436 wdata = nfs_writedata_alloc(NFS_SERVER(inode)->wpages);
437 if (!wdata) 437 if (!wdata)
438 return -ENOMEM; 438 return -ENOMEM;
439 439
@@ -662,10 +662,10 @@ nfs_file_direct_read(struct kiocb *iocb, char __user *buf, size_t count, loff_t
662 .iov_len = count, 662 .iov_len = count,
663 }; 663 };
664 664
665 dprintk("nfs: direct read(%s/%s, %lu@%lu)\n", 665 dprintk("nfs: direct read(%s/%s, %lu@%Ld)\n",
666 file->f_dentry->d_parent->d_name.name, 666 file->f_dentry->d_parent->d_name.name,
667 file->f_dentry->d_name.name, 667 file->f_dentry->d_name.name,
668 (unsigned long) count, (unsigned long) pos); 668 (unsigned long) count, (long long) pos);
669 669
670 if (!is_sync_kiocb(iocb)) 670 if (!is_sync_kiocb(iocb))
671 goto out; 671 goto out;
@@ -718,9 +718,7 @@ out:
718ssize_t 718ssize_t
719nfs_file_direct_write(struct kiocb *iocb, const char __user *buf, size_t count, loff_t pos) 719nfs_file_direct_write(struct kiocb *iocb, const char __user *buf, size_t count, loff_t pos)
720{ 720{
721 ssize_t retval = -EINVAL; 721 ssize_t retval;
722 loff_t *ppos = &iocb->ki_pos;
723 unsigned long limit = current->signal->rlim[RLIMIT_FSIZE].rlim_cur;
724 struct file *file = iocb->ki_filp; 722 struct file *file = iocb->ki_filp;
725 struct nfs_open_context *ctx = 723 struct nfs_open_context *ctx =
726 (struct nfs_open_context *) file->private_data; 724 (struct nfs_open_context *) file->private_data;
@@ -728,35 +726,32 @@ nfs_file_direct_write(struct kiocb *iocb, const char __user *buf, size_t count,
728 struct inode *inode = mapping->host; 726 struct inode *inode = mapping->host;
729 struct iovec iov = { 727 struct iovec iov = {
730 .iov_base = (char __user *)buf, 728 .iov_base = (char __user *)buf,
731 .iov_len = count,
732 }; 729 };
733 730
734 dfprintk(VFS, "nfs: direct write(%s/%s(%ld), %lu@%lu)\n", 731 dfprintk(VFS, "nfs: direct write(%s/%s, %lu@%Ld)\n",
735 file->f_dentry->d_parent->d_name.name, 732 file->f_dentry->d_parent->d_name.name,
736 file->f_dentry->d_name.name, inode->i_ino, 733 file->f_dentry->d_name.name,
737 (unsigned long) count, (unsigned long) pos); 734 (unsigned long) count, (long long) pos);
738 735
736 retval = -EINVAL;
739 if (!is_sync_kiocb(iocb)) 737 if (!is_sync_kiocb(iocb))
740 goto out; 738 goto out;
741 if (count < 0) 739
742 goto out; 740 retval = generic_write_checks(file, &pos, &count, 0);
743 if (pos < 0) 741 if (retval)
744 goto out; 742 goto out;
745 retval = -EFAULT; 743
746 if (!access_ok(VERIFY_READ, iov.iov_base, iov.iov_len)) 744 retval = -EINVAL;
745 if ((ssize_t) count < 0)
747 goto out; 746 goto out;
748 retval = -EFBIG;
749 if (limit != RLIM_INFINITY) {
750 if (pos >= limit) {
751 send_sig(SIGXFSZ, current, 0);
752 goto out;
753 }
754 if (count > limit - (unsigned long) pos)
755 count = limit - (unsigned long) pos;
756 }
757 retval = 0; 747 retval = 0;
758 if (!count) 748 if (!count)
759 goto out; 749 goto out;
750 iov.iov_len = count,
751
752 retval = -EFAULT;
753 if (!access_ok(VERIFY_READ, iov.iov_base, iov.iov_len))
754 goto out;
760 755
761 retval = nfs_sync_mapping(mapping); 756 retval = nfs_sync_mapping(mapping);
762 if (retval) 757 if (retval)
@@ -766,7 +761,7 @@ nfs_file_direct_write(struct kiocb *iocb, const char __user *buf, size_t count,
766 if (mapping->nrpages) 761 if (mapping->nrpages)
767 invalidate_inode_pages2(mapping); 762 invalidate_inode_pages2(mapping);
768 if (retval > 0) 763 if (retval > 0)
769 *ppos = pos + retval; 764 iocb->ki_pos = pos + retval;
770 765
771out: 766out:
772 return retval; 767 return retval;
diff --git a/fs/nfs/idmap.c b/fs/nfs/idmap.c
index ffb8df91dc34..821edd30333b 100644
--- a/fs/nfs/idmap.c
+++ b/fs/nfs/idmap.c
@@ -54,7 +54,11 @@
54 54
55#define IDMAP_HASH_SZ 128 55#define IDMAP_HASH_SZ 128
56 56
57/* Default cache timeout is 10 minutes */
58unsigned int nfs_idmap_cache_timeout = 600 * HZ;
59
57struct idmap_hashent { 60struct idmap_hashent {
61 unsigned long ih_expires;
58 __u32 ih_id; 62 __u32 ih_id;
59 int ih_namelen; 63 int ih_namelen;
60 char ih_name[IDMAP_NAMESZ]; 64 char ih_name[IDMAP_NAMESZ];
@@ -149,6 +153,8 @@ idmap_lookup_name(struct idmap_hashtable *h, const char *name, size_t len)
149 153
150 if (he->ih_namelen != len || memcmp(he->ih_name, name, len) != 0) 154 if (he->ih_namelen != len || memcmp(he->ih_name, name, len) != 0)
151 return NULL; 155 return NULL;
156 if (time_after(jiffies, he->ih_expires))
157 return NULL;
152 return he; 158 return he;
153} 159}
154 160
@@ -164,6 +170,8 @@ idmap_lookup_id(struct idmap_hashtable *h, __u32 id)
164 struct idmap_hashent *he = idmap_id_hash(h, id); 170 struct idmap_hashent *he = idmap_id_hash(h, id);
165 if (he->ih_id != id || he->ih_namelen == 0) 171 if (he->ih_id != id || he->ih_namelen == 0)
166 return NULL; 172 return NULL;
173 if (time_after(jiffies, he->ih_expires))
174 return NULL;
167 return he; 175 return he;
168} 176}
169 177
@@ -192,6 +200,7 @@ idmap_update_entry(struct idmap_hashent *he, const char *name,
192 memcpy(he->ih_name, name, namelen); 200 memcpy(he->ih_name, name, namelen);
193 he->ih_name[namelen] = '\0'; 201 he->ih_name[namelen] = '\0';
194 he->ih_namelen = namelen; 202 he->ih_namelen = namelen;
203 he->ih_expires = jiffies + nfs_idmap_cache_timeout;
195} 204}
196 205
197/* 206/*
diff --git a/fs/nfs/inode.c b/fs/nfs/inode.c
index 432f41cd75e6..e7bd0d92600f 100644
--- a/fs/nfs/inode.c
+++ b/fs/nfs/inode.c
@@ -40,6 +40,7 @@
40#include <asm/uaccess.h> 40#include <asm/uaccess.h>
41 41
42#include "nfs4_fs.h" 42#include "nfs4_fs.h"
43#include "callback.h"
43#include "delegation.h" 44#include "delegation.h"
44 45
45#define NFSDBG_FACILITY NFSDBG_VFS 46#define NFSDBG_FACILITY NFSDBG_VFS
@@ -221,10 +222,10 @@ nfs_calc_block_size(u64 tsize)
221static inline unsigned long 222static inline unsigned long
222nfs_block_size(unsigned long bsize, unsigned char *nrbitsp) 223nfs_block_size(unsigned long bsize, unsigned char *nrbitsp)
223{ 224{
224 if (bsize < 1024) 225 if (bsize < NFS_MIN_FILE_IO_SIZE)
225 bsize = NFS_DEF_FILE_IO_BUFFER_SIZE; 226 bsize = NFS_DEF_FILE_IO_SIZE;
226 else if (bsize >= NFS_MAX_FILE_IO_BUFFER_SIZE) 227 else if (bsize >= NFS_MAX_FILE_IO_SIZE)
227 bsize = NFS_MAX_FILE_IO_BUFFER_SIZE; 228 bsize = NFS_MAX_FILE_IO_SIZE;
228 229
229 return nfs_block_bits(bsize, nrbitsp); 230 return nfs_block_bits(bsize, nrbitsp);
230} 231}
@@ -307,20 +308,15 @@ nfs_sb_init(struct super_block *sb, rpc_authflavor_t authflavor)
307 max_rpc_payload = nfs_block_size(rpc_max_payload(server->client), NULL); 308 max_rpc_payload = nfs_block_size(rpc_max_payload(server->client), NULL);
308 if (server->rsize > max_rpc_payload) 309 if (server->rsize > max_rpc_payload)
309 server->rsize = max_rpc_payload; 310 server->rsize = max_rpc_payload;
310 if (server->wsize > max_rpc_payload) 311 if (server->rsize > NFS_MAX_FILE_IO_SIZE)
311 server->wsize = max_rpc_payload; 312 server->rsize = NFS_MAX_FILE_IO_SIZE;
312
313 server->rpages = (server->rsize + PAGE_CACHE_SIZE - 1) >> PAGE_CACHE_SHIFT; 313 server->rpages = (server->rsize + PAGE_CACHE_SIZE - 1) >> PAGE_CACHE_SHIFT;
314 if (server->rpages > NFS_READ_MAXIOV) {
315 server->rpages = NFS_READ_MAXIOV;
316 server->rsize = server->rpages << PAGE_CACHE_SHIFT;
317 }
318 314
315 if (server->wsize > max_rpc_payload)
316 server->wsize = max_rpc_payload;
317 if (server->wsize > NFS_MAX_FILE_IO_SIZE)
318 server->wsize = NFS_MAX_FILE_IO_SIZE;
319 server->wpages = (server->wsize + PAGE_CACHE_SIZE - 1) >> PAGE_CACHE_SHIFT; 319 server->wpages = (server->wsize + PAGE_CACHE_SIZE - 1) >> PAGE_CACHE_SHIFT;
320 if (server->wpages > NFS_WRITE_MAXIOV) {
321 server->wpages = NFS_WRITE_MAXIOV;
322 server->wsize = server->wpages << PAGE_CACHE_SHIFT;
323 }
324 320
325 if (sb->s_blocksize == 0) 321 if (sb->s_blocksize == 0)
326 sb->s_blocksize = nfs_block_bits(server->wsize, 322 sb->s_blocksize = nfs_block_bits(server->wsize,
@@ -417,7 +413,6 @@ nfs_create_client(struct nfs_server *server, const struct nfs_mount_data *data)
417 413
418 clnt->cl_intr = 1; 414 clnt->cl_intr = 1;
419 clnt->cl_softrtry = 1; 415 clnt->cl_softrtry = 1;
420 clnt->cl_chatty = 1;
421 416
422 return clnt; 417 return clnt;
423 418
@@ -575,11 +570,10 @@ nfs_statfs(struct super_block *sb, struct kstatfs *buf)
575 buf->f_namelen = server->namelen; 570 buf->f_namelen = server->namelen;
576 out: 571 out:
577 unlock_kernel(); 572 unlock_kernel();
578
579 return 0; 573 return 0;
580 574
581 out_err: 575 out_err:
582 printk(KERN_WARNING "nfs_statfs: statfs error = %d\n", -error); 576 dprintk("%s: statfs error = %d\n", __FUNCTION__, -error);
583 buf->f_bsize = buf->f_blocks = buf->f_bfree = buf->f_bavail = -1; 577 buf->f_bsize = buf->f_blocks = buf->f_bfree = buf->f_bavail = -1;
584 goto out; 578 goto out;
585 579
@@ -958,6 +952,8 @@ int nfs_getattr(struct vfsmount *mnt, struct dentry *dentry, struct kstat *stat)
958 int need_atime = NFS_I(inode)->cache_validity & NFS_INO_INVALID_ATIME; 952 int need_atime = NFS_I(inode)->cache_validity & NFS_INO_INVALID_ATIME;
959 int err; 953 int err;
960 954
955 /* Flush out writes to the server in order to update c/mtime */
956 nfs_sync_inode(inode, 0, 0, FLUSH_WAIT|FLUSH_NOCOMMIT);
961 if (__IS_FLG(inode, MS_NOATIME)) 957 if (__IS_FLG(inode, MS_NOATIME))
962 need_atime = 0; 958 need_atime = 0;
963 else if (__IS_FLG(inode, MS_NODIRATIME) && S_ISDIR(inode->i_mode)) 959 else if (__IS_FLG(inode, MS_NODIRATIME) && S_ISDIR(inode->i_mode))
@@ -1252,6 +1248,33 @@ void nfs_end_data_update(struct inode *inode)
1252 atomic_dec(&nfsi->data_updates); 1248 atomic_dec(&nfsi->data_updates);
1253} 1249}
1254 1250
1251static void nfs_wcc_update_inode(struct inode *inode, struct nfs_fattr *fattr)
1252{
1253 struct nfs_inode *nfsi = NFS_I(inode);
1254
1255 if ((fattr->valid & NFS_ATTR_PRE_CHANGE) != 0
1256 && nfsi->change_attr == fattr->pre_change_attr) {
1257 nfsi->change_attr = fattr->change_attr;
1258 nfsi->cache_change_attribute = jiffies;
1259 }
1260
1261 /* If we have atomic WCC data, we may update some attributes */
1262 if ((fattr->valid & NFS_ATTR_WCC) != 0) {
1263 if (timespec_equal(&inode->i_ctime, &fattr->pre_ctime)) {
1264 memcpy(&inode->i_ctime, &fattr->ctime, sizeof(inode->i_ctime));
1265 nfsi->cache_change_attribute = jiffies;
1266 }
1267 if (timespec_equal(&inode->i_mtime, &fattr->pre_mtime)) {
1268 memcpy(&inode->i_mtime, &fattr->mtime, sizeof(inode->i_mtime));
1269 nfsi->cache_change_attribute = jiffies;
1270 }
1271 if (inode->i_size == fattr->pre_size && nfsi->npages == 0) {
1272 inode->i_size = fattr->size;
1273 nfsi->cache_change_attribute = jiffies;
1274 }
1275 }
1276}
1277
1255/** 1278/**
1256 * nfs_check_inode_attributes - verify consistency of the inode attribute cache 1279 * nfs_check_inode_attributes - verify consistency of the inode attribute cache
1257 * @inode - pointer to inode 1280 * @inode - pointer to inode
@@ -1268,22 +1291,20 @@ static int nfs_check_inode_attributes(struct inode *inode, struct nfs_fattr *fat
1268 int data_unstable; 1291 int data_unstable;
1269 1292
1270 1293
1294 if ((fattr->valid & NFS_ATTR_FATTR) == 0)
1295 return 0;
1296
1271 /* Are we in the process of updating data on the server? */ 1297 /* Are we in the process of updating data on the server? */
1272 data_unstable = nfs_caches_unstable(inode); 1298 data_unstable = nfs_caches_unstable(inode);
1273 1299
1274 if (fattr->valid & NFS_ATTR_FATTR_V4) { 1300 /* Do atomic weak cache consistency updates */
1275 if ((fattr->valid & NFS_ATTR_PRE_CHANGE) != 0 1301 nfs_wcc_update_inode(inode, fattr);
1276 && nfsi->change_attr == fattr->pre_change_attr)
1277 nfsi->change_attr = fattr->change_attr;
1278 if (nfsi->change_attr != fattr->change_attr) {
1279 nfsi->cache_validity |= NFS_INO_INVALID_ATTR;
1280 if (!data_unstable)
1281 nfsi->cache_validity |= NFS_INO_REVAL_PAGECACHE;
1282 }
1283 }
1284 1302
1285 if ((fattr->valid & NFS_ATTR_FATTR) == 0) { 1303 if ((fattr->valid & NFS_ATTR_FATTR_V4) != 0 &&
1286 return 0; 1304 nfsi->change_attr != fattr->change_attr) {
1305 nfsi->cache_validity |= NFS_INO_INVALID_ATTR;
1306 if (!data_unstable)
1307 nfsi->cache_validity |= NFS_INO_REVAL_PAGECACHE;
1287 } 1308 }
1288 1309
1289 /* Has the inode gone and changed behind our back? */ 1310 /* Has the inode gone and changed behind our back? */
@@ -1295,14 +1316,6 @@ static int nfs_check_inode_attributes(struct inode *inode, struct nfs_fattr *fat
1295 cur_size = i_size_read(inode); 1316 cur_size = i_size_read(inode);
1296 new_isize = nfs_size_to_loff_t(fattr->size); 1317 new_isize = nfs_size_to_loff_t(fattr->size);
1297 1318
1298 /* If we have atomic WCC data, we may update some attributes */
1299 if ((fattr->valid & NFS_ATTR_WCC) != 0) {
1300 if (timespec_equal(&inode->i_ctime, &fattr->pre_ctime))
1301 memcpy(&inode->i_ctime, &fattr->ctime, sizeof(inode->i_ctime));
1302 if (timespec_equal(&inode->i_mtime, &fattr->pre_mtime))
1303 memcpy(&inode->i_mtime, &fattr->mtime, sizeof(inode->i_mtime));
1304 }
1305
1306 /* Verify a few of the more important attributes */ 1319 /* Verify a few of the more important attributes */
1307 if (!timespec_equal(&inode->i_mtime, &fattr->mtime)) { 1320 if (!timespec_equal(&inode->i_mtime, &fattr->mtime)) {
1308 nfsi->cache_validity |= NFS_INO_INVALID_ATTR; 1321 nfsi->cache_validity |= NFS_INO_INVALID_ATTR;
@@ -1410,14 +1423,8 @@ static int nfs_update_inode(struct inode *inode, struct nfs_fattr *fattr)
1410 if ((fattr->valid & NFS_ATTR_FATTR) == 0) 1423 if ((fattr->valid & NFS_ATTR_FATTR) == 0)
1411 return 0; 1424 return 0;
1412 1425
1413 if (nfsi->fileid != fattr->fileid) { 1426 if (nfsi->fileid != fattr->fileid)
1414 printk(KERN_ERR "%s: inode number mismatch\n" 1427 goto out_fileid;
1415 "expected (%s/0x%Lx), got (%s/0x%Lx)\n",
1416 __FUNCTION__,
1417 inode->i_sb->s_id, (long long)nfsi->fileid,
1418 inode->i_sb->s_id, (long long)fattr->fileid);
1419 goto out_err;
1420 }
1421 1428
1422 /* 1429 /*
1423 * Make sure the inode's type hasn't changed. 1430 * Make sure the inode's type hasn't changed.
@@ -1436,6 +1443,9 @@ static int nfs_update_inode(struct inode *inode, struct nfs_fattr *fattr)
1436 if (data_stable) 1443 if (data_stable)
1437 nfsi->cache_validity &= ~(NFS_INO_INVALID_ATTR|NFS_INO_INVALID_ATIME); 1444 nfsi->cache_validity &= ~(NFS_INO_INVALID_ATTR|NFS_INO_INVALID_ATIME);
1438 1445
1446 /* Do atomic weak cache consistency updates */
1447 nfs_wcc_update_inode(inode, fattr);
1448
1439 /* Check if our cached file size is stale */ 1449 /* Check if our cached file size is stale */
1440 new_isize = nfs_size_to_loff_t(fattr->size); 1450 new_isize = nfs_size_to_loff_t(fattr->size);
1441 cur_isize = i_size_read(inode); 1451 cur_isize = i_size_read(inode);
@@ -1539,6 +1549,13 @@ static int nfs_update_inode(struct inode *inode, struct nfs_fattr *fattr)
1539 */ 1549 */
1540 nfs_invalidate_inode(inode); 1550 nfs_invalidate_inode(inode);
1541 return -ESTALE; 1551 return -ESTALE;
1552
1553 out_fileid:
1554 printk(KERN_ERR "NFS: server %s error: fileid changed\n"
1555 "fsid %s: expected fileid 0x%Lx, got 0x%Lx\n",
1556 NFS_SERVER(inode)->hostname, inode->i_sb->s_id,
1557 (long long)nfsi->fileid, (long long)fattr->fileid);
1558 goto out_err;
1542} 1559}
1543 1560
1544/* 1561/*
@@ -1820,25 +1837,10 @@ static int nfs4_fill_super(struct super_block *sb, struct nfs4_mount_data *data,
1820 } 1837 }
1821 clnt->cl_intr = 1; 1838 clnt->cl_intr = 1;
1822 clnt->cl_softrtry = 1; 1839 clnt->cl_softrtry = 1;
1823 clnt->cl_chatty = 1;
1824 clp->cl_rpcclient = clnt; 1840 clp->cl_rpcclient = clnt;
1825 clp->cl_cred = rpcauth_lookupcred(clnt->cl_auth, 0);
1826 if (IS_ERR(clp->cl_cred)) {
1827 up_write(&clp->cl_sem);
1828 err = PTR_ERR(clp->cl_cred);
1829 clp->cl_cred = NULL;
1830 goto out_fail;
1831 }
1832 memcpy(clp->cl_ipaddr, server->ip_addr, sizeof(clp->cl_ipaddr)); 1841 memcpy(clp->cl_ipaddr, server->ip_addr, sizeof(clp->cl_ipaddr));
1833 nfs_idmap_new(clp); 1842 nfs_idmap_new(clp);
1834 } 1843 }
1835 if (list_empty(&clp->cl_superblocks)) {
1836 err = nfs4_init_client(clp);
1837 if (err != 0) {
1838 up_write(&clp->cl_sem);
1839 goto out_fail;
1840 }
1841 }
1842 list_add_tail(&server->nfs4_siblings, &clp->cl_superblocks); 1844 list_add_tail(&server->nfs4_siblings, &clp->cl_superblocks);
1843 clnt = rpc_clone_client(clp->cl_rpcclient); 1845 clnt = rpc_clone_client(clp->cl_rpcclient);
1844 if (!IS_ERR(clnt)) 1846 if (!IS_ERR(clnt))
@@ -2033,6 +2035,35 @@ static struct file_system_type nfs4_fs_type = {
2033 .fs_flags = FS_ODD_RENAME|FS_REVAL_DOT|FS_BINARY_MOUNTDATA, 2035 .fs_flags = FS_ODD_RENAME|FS_REVAL_DOT|FS_BINARY_MOUNTDATA,
2034}; 2036};
2035 2037
2038static const int nfs_set_port_min = 0;
2039static const int nfs_set_port_max = 65535;
2040static int param_set_port(const char *val, struct kernel_param *kp)
2041{
2042 char *endp;
2043 int num = simple_strtol(val, &endp, 0);
2044 if (endp == val || *endp || num < nfs_set_port_min || num > nfs_set_port_max)
2045 return -EINVAL;
2046 *((int *)kp->arg) = num;
2047 return 0;
2048}
2049
2050module_param_call(callback_tcpport, param_set_port, param_get_int,
2051 &nfs_callback_set_tcpport, 0644);
2052
2053static int param_set_idmap_timeout(const char *val, struct kernel_param *kp)
2054{
2055 char *endp;
2056 int num = simple_strtol(val, &endp, 0);
2057 int jif = num * HZ;
2058 if (endp == val || *endp || num < 0 || jif < num)
2059 return -EINVAL;
2060 *((int *)kp->arg) = jif;
2061 return 0;
2062}
2063
2064module_param_call(idmap_cache_timeout, param_set_idmap_timeout, param_get_int,
2065 &nfs_idmap_cache_timeout, 0644);
2066
2036#define nfs4_init_once(nfsi) \ 2067#define nfs4_init_once(nfsi) \
2037 do { \ 2068 do { \
2038 INIT_LIST_HEAD(&(nfsi)->open_states); \ 2069 INIT_LIST_HEAD(&(nfsi)->open_states); \
@@ -2040,8 +2071,25 @@ static struct file_system_type nfs4_fs_type = {
2040 nfsi->delegation_state = 0; \ 2071 nfsi->delegation_state = 0; \
2041 init_rwsem(&nfsi->rwsem); \ 2072 init_rwsem(&nfsi->rwsem); \
2042 } while(0) 2073 } while(0)
2043#define register_nfs4fs() register_filesystem(&nfs4_fs_type) 2074
2044#define unregister_nfs4fs() unregister_filesystem(&nfs4_fs_type) 2075static inline int register_nfs4fs(void)
2076{
2077 int ret;
2078
2079 ret = nfs_register_sysctl();
2080 if (ret != 0)
2081 return ret;
2082 ret = register_filesystem(&nfs4_fs_type);
2083 if (ret != 0)
2084 nfs_unregister_sysctl();
2085 return ret;
2086}
2087
2088static inline void unregister_nfs4fs(void)
2089{
2090 unregister_filesystem(&nfs4_fs_type);
2091 nfs_unregister_sysctl();
2092}
2045#else 2093#else
2046#define nfs4_init_once(nfsi) \ 2094#define nfs4_init_once(nfsi) \
2047 do { } while (0) 2095 do { } while (0)
@@ -2166,11 +2214,11 @@ out:
2166#ifdef CONFIG_PROC_FS 2214#ifdef CONFIG_PROC_FS
2167 rpc_proc_unregister("nfs"); 2215 rpc_proc_unregister("nfs");
2168#endif 2216#endif
2169 nfs_destroy_writepagecache();
2170#ifdef CONFIG_NFS_DIRECTIO 2217#ifdef CONFIG_NFS_DIRECTIO
2171out0:
2172 nfs_destroy_directcache(); 2218 nfs_destroy_directcache();
2219out0:
2173#endif 2220#endif
2221 nfs_destroy_writepagecache();
2174out1: 2222out1:
2175 nfs_destroy_readpagecache(); 2223 nfs_destroy_readpagecache();
2176out2: 2224out2:
diff --git a/fs/nfs/mount_clnt.c b/fs/nfs/mount_clnt.c
index 0e82617f2de0..db99b8f678f8 100644
--- a/fs/nfs/mount_clnt.c
+++ b/fs/nfs/mount_clnt.c
@@ -82,7 +82,6 @@ mnt_create(char *hostname, struct sockaddr_in *srvaddr, int version,
82 RPC_AUTH_UNIX); 82 RPC_AUTH_UNIX);
83 if (!IS_ERR(clnt)) { 83 if (!IS_ERR(clnt)) {
84 clnt->cl_softrtry = 1; 84 clnt->cl_softrtry = 1;
85 clnt->cl_chatty = 1;
86 clnt->cl_oneshot = 1; 85 clnt->cl_oneshot = 1;
87 clnt->cl_intr = 1; 86 clnt->cl_intr = 1;
88 } 87 }
diff --git a/fs/nfs/nfs2xdr.c b/fs/nfs/nfs2xdr.c
index 59049e864ca7..7fc0560c89c9 100644
--- a/fs/nfs/nfs2xdr.c
+++ b/fs/nfs/nfs2xdr.c
@@ -146,23 +146,23 @@ xdr_decode_fattr(u32 *p, struct nfs_fattr *fattr)
146 return p; 146 return p;
147} 147}
148 148
149#define SATTR(p, attr, flag, field) \
150 *p++ = (attr->ia_valid & flag) ? htonl(attr->field) : ~(u32) 0
151static inline u32 * 149static inline u32 *
152xdr_encode_sattr(u32 *p, struct iattr *attr) 150xdr_encode_sattr(u32 *p, struct iattr *attr)
153{ 151{
154 SATTR(p, attr, ATTR_MODE, ia_mode); 152 const u32 not_set = __constant_htonl(0xFFFFFFFF);
155 SATTR(p, attr, ATTR_UID, ia_uid); 153
156 SATTR(p, attr, ATTR_GID, ia_gid); 154 *p++ = (attr->ia_valid & ATTR_MODE) ? htonl(attr->ia_mode) : not_set;
157 SATTR(p, attr, ATTR_SIZE, ia_size); 155 *p++ = (attr->ia_valid & ATTR_UID) ? htonl(attr->ia_uid) : not_set;
156 *p++ = (attr->ia_valid & ATTR_GID) ? htonl(attr->ia_gid) : not_set;
157 *p++ = (attr->ia_valid & ATTR_SIZE) ? htonl(attr->ia_size) : not_set;
158 158
159 if (attr->ia_valid & ATTR_ATIME_SET) { 159 if (attr->ia_valid & ATTR_ATIME_SET) {
160 p = xdr_encode_time(p, &attr->ia_atime); 160 p = xdr_encode_time(p, &attr->ia_atime);
161 } else if (attr->ia_valid & ATTR_ATIME) { 161 } else if (attr->ia_valid & ATTR_ATIME) {
162 p = xdr_encode_current_server_time(p, &attr->ia_atime); 162 p = xdr_encode_current_server_time(p, &attr->ia_atime);
163 } else { 163 } else {
164 *p++ = ~(u32) 0; 164 *p++ = not_set;
165 *p++ = ~(u32) 0; 165 *p++ = not_set;
166 } 166 }
167 167
168 if (attr->ia_valid & ATTR_MTIME_SET) { 168 if (attr->ia_valid & ATTR_MTIME_SET) {
@@ -170,12 +170,11 @@ xdr_encode_sattr(u32 *p, struct iattr *attr)
170 } else if (attr->ia_valid & ATTR_MTIME) { 170 } else if (attr->ia_valid & ATTR_MTIME) {
171 p = xdr_encode_current_server_time(p, &attr->ia_mtime); 171 p = xdr_encode_current_server_time(p, &attr->ia_mtime);
172 } else { 172 } else {
173 *p++ = ~(u32) 0; 173 *p++ = not_set;
174 *p++ = ~(u32) 0; 174 *p++ = not_set;
175 } 175 }
176 return p; 176 return p;
177} 177}
178#undef SATTR
179 178
180/* 179/*
181 * NFS encode functions 180 * NFS encode functions
diff --git a/fs/nfs/nfs3proc.c b/fs/nfs/nfs3proc.c
index 92c870d19ccd..ed67567f0556 100644
--- a/fs/nfs/nfs3proc.c
+++ b/fs/nfs/nfs3proc.c
@@ -68,27 +68,39 @@ nfs3_async_handle_jukebox(struct rpc_task *task)
68 return 1; 68 return 1;
69} 69}
70 70
71/*
72 * Bare-bones access to getattr: this is for nfs_read_super.
73 */
74static int 71static int
75nfs3_proc_get_root(struct nfs_server *server, struct nfs_fh *fhandle, 72do_proc_get_root(struct rpc_clnt *client, struct nfs_fh *fhandle,
76 struct nfs_fsinfo *info) 73 struct nfs_fsinfo *info)
77{ 74{
78 int status; 75 int status;
79 76
80 dprintk("%s: call fsinfo\n", __FUNCTION__); 77 dprintk("%s: call fsinfo\n", __FUNCTION__);
81 nfs_fattr_init(info->fattr); 78 nfs_fattr_init(info->fattr);
82 status = rpc_call(server->client_sys, NFS3PROC_FSINFO, fhandle, info, 0); 79 status = rpc_call(client, NFS3PROC_FSINFO, fhandle, info, 0);
83 dprintk("%s: reply fsinfo: %d\n", __FUNCTION__, status); 80 dprintk("%s: reply fsinfo: %d\n", __FUNCTION__, status);
84 if (!(info->fattr->valid & NFS_ATTR_FATTR)) { 81 if (!(info->fattr->valid & NFS_ATTR_FATTR)) {
85 status = rpc_call(server->client_sys, NFS3PROC_GETATTR, fhandle, info->fattr, 0); 82 status = rpc_call(client, NFS3PROC_GETATTR, fhandle, info->fattr, 0);
86 dprintk("%s: reply getattr: %d\n", __FUNCTION__, status); 83 dprintk("%s: reply getattr: %d\n", __FUNCTION__, status);
87 } 84 }
88 return status; 85 return status;
89} 86}
90 87
91/* 88/*
89 * Bare-bones access to getattr: this is for nfs_read_super.
90 */
91static int
92nfs3_proc_get_root(struct nfs_server *server, struct nfs_fh *fhandle,
93 struct nfs_fsinfo *info)
94{
95 int status;
96
97 status = do_proc_get_root(server->client, fhandle, info);
98 if (status && server->client_sys != server->client)
99 status = do_proc_get_root(server->client_sys, fhandle, info);
100 return status;
101}
102
103/*
92 * One function for each procedure in the NFS protocol. 104 * One function for each procedure in the NFS protocol.
93 */ 105 */
94static int 106static int
@@ -732,19 +744,23 @@ nfs3_proc_pathconf(struct nfs_server *server, struct nfs_fh *fhandle,
732 744
733extern u32 *nfs3_decode_dirent(u32 *, struct nfs_entry *, int); 745extern u32 *nfs3_decode_dirent(u32 *, struct nfs_entry *, int);
734 746
735static void 747static void nfs3_read_done(struct rpc_task *task, void *calldata)
736nfs3_read_done(struct rpc_task *task)
737{ 748{
738 struct nfs_read_data *data = (struct nfs_read_data *) task->tk_calldata; 749 struct nfs_read_data *data = calldata;
739 750
740 if (nfs3_async_handle_jukebox(task)) 751 if (nfs3_async_handle_jukebox(task))
741 return; 752 return;
742 /* Call back common NFS readpage processing */ 753 /* Call back common NFS readpage processing */
743 if (task->tk_status >= 0) 754 if (task->tk_status >= 0)
744 nfs_refresh_inode(data->inode, &data->fattr); 755 nfs_refresh_inode(data->inode, &data->fattr);
745 nfs_readpage_result(task); 756 nfs_readpage_result(task, calldata);
746} 757}
747 758
759static const struct rpc_call_ops nfs3_read_ops = {
760 .rpc_call_done = nfs3_read_done,
761 .rpc_release = nfs_readdata_release,
762};
763
748static void 764static void
749nfs3_proc_read_setup(struct nfs_read_data *data) 765nfs3_proc_read_setup(struct nfs_read_data *data)
750{ 766{
@@ -762,23 +778,26 @@ nfs3_proc_read_setup(struct nfs_read_data *data)
762 flags = RPC_TASK_ASYNC | (IS_SWAPFILE(inode)? NFS_RPC_SWAPFLAGS : 0); 778 flags = RPC_TASK_ASYNC | (IS_SWAPFILE(inode)? NFS_RPC_SWAPFLAGS : 0);
763 779
764 /* Finalize the task. */ 780 /* Finalize the task. */
765 rpc_init_task(task, NFS_CLIENT(inode), nfs3_read_done, flags); 781 rpc_init_task(task, NFS_CLIENT(inode), flags, &nfs3_read_ops, data);
766 rpc_call_setup(task, &msg, 0); 782 rpc_call_setup(task, &msg, 0);
767} 783}
768 784
769static void 785static void nfs3_write_done(struct rpc_task *task, void *calldata)
770nfs3_write_done(struct rpc_task *task)
771{ 786{
772 struct nfs_write_data *data; 787 struct nfs_write_data *data = calldata;
773 788
774 if (nfs3_async_handle_jukebox(task)) 789 if (nfs3_async_handle_jukebox(task))
775 return; 790 return;
776 data = (struct nfs_write_data *)task->tk_calldata;
777 if (task->tk_status >= 0) 791 if (task->tk_status >= 0)
778 nfs_post_op_update_inode(data->inode, data->res.fattr); 792 nfs_post_op_update_inode(data->inode, data->res.fattr);
779 nfs_writeback_done(task); 793 nfs_writeback_done(task, calldata);
780} 794}
781 795
796static const struct rpc_call_ops nfs3_write_ops = {
797 .rpc_call_done = nfs3_write_done,
798 .rpc_release = nfs_writedata_release,
799};
800
782static void 801static void
783nfs3_proc_write_setup(struct nfs_write_data *data, int how) 802nfs3_proc_write_setup(struct nfs_write_data *data, int how)
784{ 803{
@@ -806,23 +825,26 @@ nfs3_proc_write_setup(struct nfs_write_data *data, int how)
806 flags = (how & FLUSH_SYNC) ? 0 : RPC_TASK_ASYNC; 825 flags = (how & FLUSH_SYNC) ? 0 : RPC_TASK_ASYNC;
807 826
808 /* Finalize the task. */ 827 /* Finalize the task. */
809 rpc_init_task(task, NFS_CLIENT(inode), nfs3_write_done, flags); 828 rpc_init_task(task, NFS_CLIENT(inode), flags, &nfs3_write_ops, data);
810 rpc_call_setup(task, &msg, 0); 829 rpc_call_setup(task, &msg, 0);
811} 830}
812 831
813static void 832static void nfs3_commit_done(struct rpc_task *task, void *calldata)
814nfs3_commit_done(struct rpc_task *task)
815{ 833{
816 struct nfs_write_data *data; 834 struct nfs_write_data *data = calldata;
817 835
818 if (nfs3_async_handle_jukebox(task)) 836 if (nfs3_async_handle_jukebox(task))
819 return; 837 return;
820 data = (struct nfs_write_data *)task->tk_calldata;
821 if (task->tk_status >= 0) 838 if (task->tk_status >= 0)
822 nfs_post_op_update_inode(data->inode, data->res.fattr); 839 nfs_post_op_update_inode(data->inode, data->res.fattr);
823 nfs_commit_done(task); 840 nfs_commit_done(task, calldata);
824} 841}
825 842
843static const struct rpc_call_ops nfs3_commit_ops = {
844 .rpc_call_done = nfs3_commit_done,
845 .rpc_release = nfs_commit_release,
846};
847
826static void 848static void
827nfs3_proc_commit_setup(struct nfs_write_data *data, int how) 849nfs3_proc_commit_setup(struct nfs_write_data *data, int how)
828{ 850{
@@ -840,7 +862,7 @@ nfs3_proc_commit_setup(struct nfs_write_data *data, int how)
840 flags = (how & FLUSH_SYNC) ? 0 : RPC_TASK_ASYNC; 862 flags = (how & FLUSH_SYNC) ? 0 : RPC_TASK_ASYNC;
841 863
842 /* Finalize the task. */ 864 /* Finalize the task. */
843 rpc_init_task(task, NFS_CLIENT(inode), nfs3_commit_done, flags); 865 rpc_init_task(task, NFS_CLIENT(inode), flags, &nfs3_commit_ops, data);
844 rpc_call_setup(task, &msg, 0); 866 rpc_call_setup(task, &msg, 0);
845} 867}
846 868
diff --git a/fs/nfs/nfs3xdr.c b/fs/nfs/nfs3xdr.c
index 0498bd36602c..b6c0b5012bce 100644
--- a/fs/nfs/nfs3xdr.c
+++ b/fs/nfs/nfs3xdr.c
@@ -182,7 +182,7 @@ xdr_encode_sattr(u32 *p, struct iattr *attr)
182{ 182{
183 if (attr->ia_valid & ATTR_MODE) { 183 if (attr->ia_valid & ATTR_MODE) {
184 *p++ = xdr_one; 184 *p++ = xdr_one;
185 *p++ = htonl(attr->ia_mode); 185 *p++ = htonl(attr->ia_mode & S_IALLUGO);
186 } else { 186 } else {
187 *p++ = xdr_zero; 187 *p++ = xdr_zero;
188 } 188 }
diff --git a/fs/nfs/nfs4_fs.h b/fs/nfs/nfs4_fs.h
index b7f262dcb6e3..0f5e4e7cddec 100644
--- a/fs/nfs/nfs4_fs.h
+++ b/fs/nfs/nfs4_fs.h
@@ -38,7 +38,8 @@ struct idmap;
38 ((err) != NFSERR_NOFILEHANDLE)) 38 ((err) != NFSERR_NOFILEHANDLE))
39 39
40enum nfs4_client_state { 40enum nfs4_client_state {
41 NFS4CLNT_OK = 0, 41 NFS4CLNT_STATE_RECOVER = 0,
42 NFS4CLNT_LEASE_EXPIRED,
42}; 43};
43 44
44/* 45/*
@@ -67,7 +68,6 @@ struct nfs4_client {
67 atomic_t cl_count; 68 atomic_t cl_count;
68 69
69 struct rpc_clnt * cl_rpcclient; 70 struct rpc_clnt * cl_rpcclient;
70 struct rpc_cred * cl_cred;
71 71
72 struct list_head cl_superblocks; /* List of nfs_server structs */ 72 struct list_head cl_superblocks; /* List of nfs_server structs */
73 73
@@ -76,7 +76,6 @@ struct nfs4_client {
76 struct work_struct cl_renewd; 76 struct work_struct cl_renewd;
77 struct work_struct cl_recoverd; 77 struct work_struct cl_recoverd;
78 78
79 wait_queue_head_t cl_waitq;
80 struct rpc_wait_queue cl_rpcwaitq; 79 struct rpc_wait_queue cl_rpcwaitq;
81 80
82 /* used for the setclientid verifier */ 81 /* used for the setclientid verifier */
@@ -182,8 +181,9 @@ struct nfs4_state {
182 181
183 nfs4_stateid stateid; 182 nfs4_stateid stateid;
184 183
185 unsigned int nreaders; 184 unsigned int n_rdonly;
186 unsigned int nwriters; 185 unsigned int n_wronly;
186 unsigned int n_rdwr;
187 int state; /* State on the server (R,W, or RW) */ 187 int state; /* State on the server (R,W, or RW) */
188 atomic_t count; 188 atomic_t count;
189}; 189};
@@ -210,10 +210,10 @@ extern ssize_t nfs4_listxattr(struct dentry *, char *, size_t);
210 210
211/* nfs4proc.c */ 211/* nfs4proc.c */
212extern int nfs4_map_errors(int err); 212extern int nfs4_map_errors(int err);
213extern int nfs4_proc_setclientid(struct nfs4_client *, u32, unsigned short); 213extern int nfs4_proc_setclientid(struct nfs4_client *, u32, unsigned short, struct rpc_cred *);
214extern int nfs4_proc_setclientid_confirm(struct nfs4_client *); 214extern int nfs4_proc_setclientid_confirm(struct nfs4_client *, struct rpc_cred *);
215extern int nfs4_proc_async_renew(struct nfs4_client *); 215extern int nfs4_proc_async_renew(struct nfs4_client *, struct rpc_cred *);
216extern int nfs4_proc_renew(struct nfs4_client *); 216extern int nfs4_proc_renew(struct nfs4_client *, struct rpc_cred *);
217extern int nfs4_do_close(struct inode *inode, struct nfs4_state *state); 217extern int nfs4_do_close(struct inode *inode, struct nfs4_state *state);
218extern struct dentry *nfs4_atomic_open(struct inode *, struct dentry *, struct nameidata *); 218extern struct dentry *nfs4_atomic_open(struct inode *, struct dentry *, struct nameidata *);
219extern int nfs4_open_revalidate(struct inode *, struct dentry *, int, struct nameidata *); 219extern int nfs4_open_revalidate(struct inode *, struct dentry *, int, struct nameidata *);
@@ -237,8 +237,8 @@ extern void init_nfsv4_state(struct nfs_server *);
237extern void destroy_nfsv4_state(struct nfs_server *); 237extern void destroy_nfsv4_state(struct nfs_server *);
238extern struct nfs4_client *nfs4_get_client(struct in_addr *); 238extern struct nfs4_client *nfs4_get_client(struct in_addr *);
239extern void nfs4_put_client(struct nfs4_client *clp); 239extern void nfs4_put_client(struct nfs4_client *clp);
240extern int nfs4_init_client(struct nfs4_client *clp);
241extern struct nfs4_client *nfs4_find_client(struct in_addr *); 240extern struct nfs4_client *nfs4_find_client(struct in_addr *);
241struct rpc_cred *nfs4_get_renew_cred(struct nfs4_client *clp);
242extern u32 nfs4_alloc_lockowner_id(struct nfs4_client *); 242extern u32 nfs4_alloc_lockowner_id(struct nfs4_client *);
243 243
244extern struct nfs4_state_owner * nfs4_get_state_owner(struct nfs_server *, struct rpc_cred *); 244extern struct nfs4_state_owner * nfs4_get_state_owner(struct nfs_server *, struct rpc_cred *);
diff --git a/fs/nfs/nfs4proc.c b/fs/nfs/nfs4proc.c
index f988a9417b13..984ca3454d04 100644
--- a/fs/nfs/nfs4proc.c
+++ b/fs/nfs/nfs4proc.c
@@ -57,11 +57,13 @@
57#define NFS4_POLL_RETRY_MIN (1*HZ) 57#define NFS4_POLL_RETRY_MIN (1*HZ)
58#define NFS4_POLL_RETRY_MAX (15*HZ) 58#define NFS4_POLL_RETRY_MAX (15*HZ)
59 59
60static int _nfs4_proc_open_confirm(struct rpc_clnt *clnt, const struct nfs_fh *fh, struct nfs4_state_owner *sp, nfs4_stateid *stateid, struct nfs_seqid *seqid); 60struct nfs4_opendata;
61static int _nfs4_proc_open(struct nfs4_opendata *data);
61static int nfs4_do_fsinfo(struct nfs_server *, struct nfs_fh *, struct nfs_fsinfo *); 62static int nfs4_do_fsinfo(struct nfs_server *, struct nfs_fh *, struct nfs_fsinfo *);
62static int nfs4_async_handle_error(struct rpc_task *, const struct nfs_server *); 63static int nfs4_async_handle_error(struct rpc_task *, const struct nfs_server *);
63static int _nfs4_proc_access(struct inode *inode, struct nfs_access_entry *entry); 64static int _nfs4_proc_access(struct inode *inode, struct nfs_access_entry *entry);
64static int nfs4_handle_exception(const struct nfs_server *server, int errorcode, struct nfs4_exception *exception); 65static int nfs4_handle_exception(const struct nfs_server *server, int errorcode, struct nfs4_exception *exception);
66static int nfs4_wait_clnt_recover(struct rpc_clnt *clnt, struct nfs4_client *clp);
65extern u32 *nfs4_decode_dirent(u32 *p, struct nfs_entry *entry, int plus); 67extern u32 *nfs4_decode_dirent(u32 *p, struct nfs_entry *entry, int plus);
66extern struct rpc_procinfo nfs4_procedures[]; 68extern struct rpc_procinfo nfs4_procedures[];
67 69
@@ -173,8 +175,7 @@ static void nfs4_setup_readdir(u64 cookie, u32 *verifier, struct dentry *dentry,
173 kunmap_atomic(start, KM_USER0); 175 kunmap_atomic(start, KM_USER0);
174} 176}
175 177
176static void 178static void renew_lease(const struct nfs_server *server, unsigned long timestamp)
177renew_lease(struct nfs_server *server, unsigned long timestamp)
178{ 179{
179 struct nfs4_client *clp = server->nfs4_state; 180 struct nfs4_client *clp = server->nfs4_state;
180 spin_lock(&clp->cl_lock); 181 spin_lock(&clp->cl_lock);
@@ -194,21 +195,123 @@ static void update_changeattr(struct inode *inode, struct nfs4_change_info *cinf
194 spin_unlock(&inode->i_lock); 195 spin_unlock(&inode->i_lock);
195} 196}
196 197
198struct nfs4_opendata {
199 atomic_t count;
200 struct nfs_openargs o_arg;
201 struct nfs_openres o_res;
202 struct nfs_open_confirmargs c_arg;
203 struct nfs_open_confirmres c_res;
204 struct nfs_fattr f_attr;
205 struct nfs_fattr dir_attr;
206 struct dentry *dentry;
207 struct dentry *dir;
208 struct nfs4_state_owner *owner;
209 struct iattr attrs;
210 unsigned long timestamp;
211 int rpc_status;
212 int cancelled;
213};
214
215static struct nfs4_opendata *nfs4_opendata_alloc(struct dentry *dentry,
216 struct nfs4_state_owner *sp, int flags,
217 const struct iattr *attrs)
218{
219 struct dentry *parent = dget_parent(dentry);
220 struct inode *dir = parent->d_inode;
221 struct nfs_server *server = NFS_SERVER(dir);
222 struct nfs4_opendata *p;
223
224 p = kzalloc(sizeof(*p), GFP_KERNEL);
225 if (p == NULL)
226 goto err;
227 p->o_arg.seqid = nfs_alloc_seqid(&sp->so_seqid);
228 if (p->o_arg.seqid == NULL)
229 goto err_free;
230 atomic_set(&p->count, 1);
231 p->dentry = dget(dentry);
232 p->dir = parent;
233 p->owner = sp;
234 atomic_inc(&sp->so_count);
235 p->o_arg.fh = NFS_FH(dir);
236 p->o_arg.open_flags = flags,
237 p->o_arg.clientid = server->nfs4_state->cl_clientid;
238 p->o_arg.id = sp->so_id;
239 p->o_arg.name = &dentry->d_name;
240 p->o_arg.server = server;
241 p->o_arg.bitmask = server->attr_bitmask;
242 p->o_arg.claim = NFS4_OPEN_CLAIM_NULL;
243 p->o_res.f_attr = &p->f_attr;
244 p->o_res.dir_attr = &p->dir_attr;
245 p->o_res.server = server;
246 nfs_fattr_init(&p->f_attr);
247 nfs_fattr_init(&p->dir_attr);
248 if (flags & O_EXCL) {
249 u32 *s = (u32 *) p->o_arg.u.verifier.data;
250 s[0] = jiffies;
251 s[1] = current->pid;
252 } else if (flags & O_CREAT) {
253 p->o_arg.u.attrs = &p->attrs;
254 memcpy(&p->attrs, attrs, sizeof(p->attrs));
255 }
256 p->c_arg.fh = &p->o_res.fh;
257 p->c_arg.stateid = &p->o_res.stateid;
258 p->c_arg.seqid = p->o_arg.seqid;
259 return p;
260err_free:
261 kfree(p);
262err:
263 dput(parent);
264 return NULL;
265}
266
267static void nfs4_opendata_free(struct nfs4_opendata *p)
268{
269 if (p != NULL && atomic_dec_and_test(&p->count)) {
270 nfs_free_seqid(p->o_arg.seqid);
271 nfs4_put_state_owner(p->owner);
272 dput(p->dir);
273 dput(p->dentry);
274 kfree(p);
275 }
276}
277
197/* Helper for asynchronous RPC calls */ 278/* Helper for asynchronous RPC calls */
198static int nfs4_call_async(struct rpc_clnt *clnt, rpc_action tk_begin, 279static int nfs4_call_async(struct rpc_clnt *clnt,
199 rpc_action tk_exit, void *calldata) 280 const struct rpc_call_ops *tk_ops, void *calldata)
200{ 281{
201 struct rpc_task *task; 282 struct rpc_task *task;
202 283
203 if (!(task = rpc_new_task(clnt, tk_exit, RPC_TASK_ASYNC))) 284 if (!(task = rpc_new_task(clnt, RPC_TASK_ASYNC, tk_ops, calldata)))
204 return -ENOMEM; 285 return -ENOMEM;
205
206 task->tk_calldata = calldata;
207 task->tk_action = tk_begin;
208 rpc_execute(task); 286 rpc_execute(task);
209 return 0; 287 return 0;
210} 288}
211 289
290static int nfs4_wait_for_completion_rpc_task(struct rpc_task *task)
291{
292 sigset_t oldset;
293 int ret;
294
295 rpc_clnt_sigmask(task->tk_client, &oldset);
296 ret = rpc_wait_for_completion_task(task);
297 rpc_clnt_sigunmask(task->tk_client, &oldset);
298 return ret;
299}
300
301static inline void update_open_stateflags(struct nfs4_state *state, mode_t open_flags)
302{
303 switch (open_flags) {
304 case FMODE_WRITE:
305 state->n_wronly++;
306 break;
307 case FMODE_READ:
308 state->n_rdonly++;
309 break;
310 case FMODE_READ|FMODE_WRITE:
311 state->n_rdwr++;
312 }
313}
314
212static void update_open_stateid(struct nfs4_state *state, nfs4_stateid *stateid, int open_flags) 315static void update_open_stateid(struct nfs4_state *state, nfs4_stateid *stateid, int open_flags)
213{ 316{
214 struct inode *inode = state->inode; 317 struct inode *inode = state->inode;
@@ -218,41 +321,134 @@ static void update_open_stateid(struct nfs4_state *state, nfs4_stateid *stateid,
218 spin_lock(&state->owner->so_lock); 321 spin_lock(&state->owner->so_lock);
219 spin_lock(&inode->i_lock); 322 spin_lock(&inode->i_lock);
220 memcpy(&state->stateid, stateid, sizeof(state->stateid)); 323 memcpy(&state->stateid, stateid, sizeof(state->stateid));
221 if ((open_flags & FMODE_WRITE)) 324 update_open_stateflags(state, open_flags);
222 state->nwriters++;
223 if (open_flags & FMODE_READ)
224 state->nreaders++;
225 nfs4_state_set_mode_locked(state, state->state | open_flags); 325 nfs4_state_set_mode_locked(state, state->state | open_flags);
226 spin_unlock(&inode->i_lock); 326 spin_unlock(&inode->i_lock);
227 spin_unlock(&state->owner->so_lock); 327 spin_unlock(&state->owner->so_lock);
228} 328}
229 329
330static struct nfs4_state *nfs4_opendata_to_nfs4_state(struct nfs4_opendata *data)
331{
332 struct inode *inode;
333 struct nfs4_state *state = NULL;
334
335 if (!(data->f_attr.valid & NFS_ATTR_FATTR))
336 goto out;
337 inode = nfs_fhget(data->dir->d_sb, &data->o_res.fh, &data->f_attr);
338 if (inode == NULL)
339 goto out;
340 state = nfs4_get_open_state(inode, data->owner);
341 if (state == NULL)
342 goto put_inode;
343 update_open_stateid(state, &data->o_res.stateid, data->o_arg.open_flags);
344put_inode:
345 iput(inode);
346out:
347 return state;
348}
349
350static struct nfs_open_context *nfs4_state_find_open_context(struct nfs4_state *state)
351{
352 struct nfs_inode *nfsi = NFS_I(state->inode);
353 struct nfs_open_context *ctx;
354
355 spin_lock(&state->inode->i_lock);
356 list_for_each_entry(ctx, &nfsi->open_files, list) {
357 if (ctx->state != state)
358 continue;
359 get_nfs_open_context(ctx);
360 spin_unlock(&state->inode->i_lock);
361 return ctx;
362 }
363 spin_unlock(&state->inode->i_lock);
364 return ERR_PTR(-ENOENT);
365}
366
367static int nfs4_open_recover_helper(struct nfs4_opendata *opendata, mode_t openflags, nfs4_stateid *stateid)
368{
369 int ret;
370
371 opendata->o_arg.open_flags = openflags;
372 ret = _nfs4_proc_open(opendata);
373 if (ret != 0)
374 return ret;
375 memcpy(stateid->data, opendata->o_res.stateid.data,
376 sizeof(stateid->data));
377 return 0;
378}
379
380static int nfs4_open_recover(struct nfs4_opendata *opendata, struct nfs4_state *state)
381{
382 nfs4_stateid stateid;
383 struct nfs4_state *newstate;
384 int mode = 0;
385 int delegation = 0;
386 int ret;
387
388 /* memory barrier prior to reading state->n_* */
389 smp_rmb();
390 if (state->n_rdwr != 0) {
391 ret = nfs4_open_recover_helper(opendata, FMODE_READ|FMODE_WRITE, &stateid);
392 if (ret != 0)
393 return ret;
394 mode |= FMODE_READ|FMODE_WRITE;
395 if (opendata->o_res.delegation_type != 0)
396 delegation = opendata->o_res.delegation_type;
397 smp_rmb();
398 }
399 if (state->n_wronly != 0) {
400 ret = nfs4_open_recover_helper(opendata, FMODE_WRITE, &stateid);
401 if (ret != 0)
402 return ret;
403 mode |= FMODE_WRITE;
404 if (opendata->o_res.delegation_type != 0)
405 delegation = opendata->o_res.delegation_type;
406 smp_rmb();
407 }
408 if (state->n_rdonly != 0) {
409 ret = nfs4_open_recover_helper(opendata, FMODE_READ, &stateid);
410 if (ret != 0)
411 return ret;
412 mode |= FMODE_READ;
413 }
414 clear_bit(NFS_DELEGATED_STATE, &state->flags);
415 if (mode == 0)
416 return 0;
417 if (opendata->o_res.delegation_type == 0)
418 opendata->o_res.delegation_type = delegation;
419 opendata->o_arg.open_flags |= mode;
420 newstate = nfs4_opendata_to_nfs4_state(opendata);
421 if (newstate != NULL) {
422 if (opendata->o_res.delegation_type != 0) {
423 struct nfs_inode *nfsi = NFS_I(newstate->inode);
424 int delegation_flags = 0;
425 if (nfsi->delegation)
426 delegation_flags = nfsi->delegation->flags;
427 if (!(delegation_flags & NFS_DELEGATION_NEED_RECLAIM))
428 nfs_inode_set_delegation(newstate->inode,
429 opendata->owner->so_cred,
430 &opendata->o_res);
431 else
432 nfs_inode_reclaim_delegation(newstate->inode,
433 opendata->owner->so_cred,
434 &opendata->o_res);
435 }
436 nfs4_close_state(newstate, opendata->o_arg.open_flags);
437 }
438 if (newstate != state)
439 return -ESTALE;
440 return 0;
441}
442
230/* 443/*
231 * OPEN_RECLAIM: 444 * OPEN_RECLAIM:
232 * reclaim state on the server after a reboot. 445 * reclaim state on the server after a reboot.
233 */ 446 */
234static int _nfs4_open_reclaim(struct nfs4_state_owner *sp, struct nfs4_state *state) 447static int _nfs4_do_open_reclaim(struct nfs4_state_owner *sp, struct nfs4_state *state, struct dentry *dentry)
235{ 448{
236 struct inode *inode = state->inode; 449 struct nfs_delegation *delegation = NFS_I(state->inode)->delegation;
237 struct nfs_server *server = NFS_SERVER(inode); 450 struct nfs4_opendata *opendata;
238 struct nfs_delegation *delegation = NFS_I(inode)->delegation; 451 int delegation_type = 0;
239 struct nfs_openargs o_arg = {
240 .fh = NFS_FH(inode),
241 .id = sp->so_id,
242 .open_flags = state->state,
243 .clientid = server->nfs4_state->cl_clientid,
244 .claim = NFS4_OPEN_CLAIM_PREVIOUS,
245 .bitmask = server->attr_bitmask,
246 };
247 struct nfs_openres o_res = {
248 .server = server, /* Grrr */
249 };
250 struct rpc_message msg = {
251 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_OPEN_NOATTR],
252 .rpc_argp = &o_arg,
253 .rpc_resp = &o_res,
254 .rpc_cred = sp->so_cred,
255 };
256 int status; 452 int status;
257 453
258 if (delegation != NULL) { 454 if (delegation != NULL) {
@@ -262,38 +458,27 @@ static int _nfs4_open_reclaim(struct nfs4_state_owner *sp, struct nfs4_state *st
262 set_bit(NFS_DELEGATED_STATE, &state->flags); 458 set_bit(NFS_DELEGATED_STATE, &state->flags);
263 return 0; 459 return 0;
264 } 460 }
265 o_arg.u.delegation_type = delegation->type; 461 delegation_type = delegation->type;
266 } 462 }
267 o_arg.seqid = nfs_alloc_seqid(&sp->so_seqid); 463 opendata = nfs4_opendata_alloc(dentry, sp, 0, NULL);
268 if (o_arg.seqid == NULL) 464 if (opendata == NULL)
269 return -ENOMEM; 465 return -ENOMEM;
270 status = rpc_call_sync(server->client, &msg, RPC_TASK_NOINTR); 466 opendata->o_arg.claim = NFS4_OPEN_CLAIM_PREVIOUS;
271 /* Confirm the sequence as being established */ 467 opendata->o_arg.fh = NFS_FH(state->inode);
272 nfs_confirm_seqid(&sp->so_seqid, status); 468 nfs_copy_fh(&opendata->o_res.fh, opendata->o_arg.fh);
273 nfs_increment_open_seqid(status, o_arg.seqid); 469 opendata->o_arg.u.delegation_type = delegation_type;
274 if (status == 0) { 470 status = nfs4_open_recover(opendata, state);
275 memcpy(&state->stateid, &o_res.stateid, sizeof(state->stateid)); 471 nfs4_opendata_free(opendata);
276 if (o_res.delegation_type != 0) {
277 nfs_inode_reclaim_delegation(inode, sp->so_cred, &o_res);
278 /* Did the server issue an immediate delegation recall? */
279 if (o_res.do_recall)
280 nfs_async_inode_return_delegation(inode, &o_res.stateid);
281 }
282 }
283 nfs_free_seqid(o_arg.seqid);
284 clear_bit(NFS_DELEGATED_STATE, &state->flags);
285 /* Ensure we update the inode attributes */
286 NFS_CACHEINV(inode);
287 return status; 472 return status;
288} 473}
289 474
290static int nfs4_open_reclaim(struct nfs4_state_owner *sp, struct nfs4_state *state) 475static int nfs4_do_open_reclaim(struct nfs4_state_owner *sp, struct nfs4_state *state, struct dentry *dentry)
291{ 476{
292 struct nfs_server *server = NFS_SERVER(state->inode); 477 struct nfs_server *server = NFS_SERVER(state->inode);
293 struct nfs4_exception exception = { }; 478 struct nfs4_exception exception = { };
294 int err; 479 int err;
295 do { 480 do {
296 err = _nfs4_open_reclaim(sp, state); 481 err = _nfs4_do_open_reclaim(sp, state, dentry);
297 if (err != -NFS4ERR_DELAY) 482 if (err != -NFS4ERR_DELAY)
298 break; 483 break;
299 nfs4_handle_exception(server, err, &exception); 484 nfs4_handle_exception(server, err, &exception);
@@ -301,63 +486,36 @@ static int nfs4_open_reclaim(struct nfs4_state_owner *sp, struct nfs4_state *sta
301 return err; 486 return err;
302} 487}
303 488
489static int nfs4_open_reclaim(struct nfs4_state_owner *sp, struct nfs4_state *state)
490{
491 struct nfs_open_context *ctx;
492 int ret;
493
494 ctx = nfs4_state_find_open_context(state);
495 if (IS_ERR(ctx))
496 return PTR_ERR(ctx);
497 ret = nfs4_do_open_reclaim(sp, state, ctx->dentry);
498 put_nfs_open_context(ctx);
499 return ret;
500}
501
304static int _nfs4_open_delegation_recall(struct dentry *dentry, struct nfs4_state *state) 502static int _nfs4_open_delegation_recall(struct dentry *dentry, struct nfs4_state *state)
305{ 503{
306 struct nfs4_state_owner *sp = state->owner; 504 struct nfs4_state_owner *sp = state->owner;
307 struct inode *inode = dentry->d_inode; 505 struct nfs4_opendata *opendata;
308 struct nfs_server *server = NFS_SERVER(inode); 506 int ret;
309 struct dentry *parent = dget_parent(dentry);
310 struct nfs_openargs arg = {
311 .fh = NFS_FH(parent->d_inode),
312 .clientid = server->nfs4_state->cl_clientid,
313 .name = &dentry->d_name,
314 .id = sp->so_id,
315 .server = server,
316 .bitmask = server->attr_bitmask,
317 .claim = NFS4_OPEN_CLAIM_DELEGATE_CUR,
318 };
319 struct nfs_openres res = {
320 .server = server,
321 };
322 struct rpc_message msg = {
323 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_OPEN_NOATTR],
324 .rpc_argp = &arg,
325 .rpc_resp = &res,
326 .rpc_cred = sp->so_cred,
327 };
328 int status = 0;
329 507
330 if (!test_bit(NFS_DELEGATED_STATE, &state->flags)) 508 if (!test_bit(NFS_DELEGATED_STATE, &state->flags))
331 goto out; 509 return 0;
332 if (state->state == 0) 510 opendata = nfs4_opendata_alloc(dentry, sp, 0, NULL);
333 goto out; 511 if (opendata == NULL)
334 arg.seqid = nfs_alloc_seqid(&sp->so_seqid); 512 return -ENOMEM;
335 status = -ENOMEM; 513 opendata->o_arg.claim = NFS4_OPEN_CLAIM_DELEGATE_CUR;
336 if (arg.seqid == NULL) 514 memcpy(opendata->o_arg.u.delegation.data, state->stateid.data,
337 goto out; 515 sizeof(opendata->o_arg.u.delegation.data));
338 arg.open_flags = state->state; 516 ret = nfs4_open_recover(opendata, state);
339 memcpy(arg.u.delegation.data, state->stateid.data, sizeof(arg.u.delegation.data)); 517 nfs4_opendata_free(opendata);
340 status = rpc_call_sync(server->client, &msg, RPC_TASK_NOINTR); 518 return ret;
341 nfs_increment_open_seqid(status, arg.seqid);
342 if (status != 0)
343 goto out_free;
344 if(res.rflags & NFS4_OPEN_RESULT_CONFIRM) {
345 status = _nfs4_proc_open_confirm(server->client, NFS_FH(inode),
346 sp, &res.stateid, arg.seqid);
347 if (status != 0)
348 goto out_free;
349 }
350 nfs_confirm_seqid(&sp->so_seqid, 0);
351 if (status >= 0) {
352 memcpy(state->stateid.data, res.stateid.data,
353 sizeof(state->stateid.data));
354 clear_bit(NFS_DELEGATED_STATE, &state->flags);
355 }
356out_free:
357 nfs_free_seqid(arg.seqid);
358out:
359 dput(parent);
360 return status;
361} 519}
362 520
363int nfs4_open_delegation_recall(struct dentry *dentry, struct nfs4_state *state) 521int nfs4_open_delegation_recall(struct dentry *dentry, struct nfs4_state *state)
@@ -382,82 +540,202 @@ int nfs4_open_delegation_recall(struct dentry *dentry, struct nfs4_state *state)
382 return err; 540 return err;
383} 541}
384 542
385static int _nfs4_proc_open_confirm(struct rpc_clnt *clnt, const struct nfs_fh *fh, struct nfs4_state_owner *sp, nfs4_stateid *stateid, struct nfs_seqid *seqid) 543static void nfs4_open_confirm_prepare(struct rpc_task *task, void *calldata)
386{ 544{
387 struct nfs_open_confirmargs arg = { 545 struct nfs4_opendata *data = calldata;
388 .fh = fh, 546 struct rpc_message msg = {
389 .seqid = seqid, 547 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_OPEN_CONFIRM],
390 .stateid = *stateid, 548 .rpc_argp = &data->c_arg,
391 }; 549 .rpc_resp = &data->c_res,
392 struct nfs_open_confirmres res; 550 .rpc_cred = data->owner->so_cred,
393 struct rpc_message msg = {
394 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_OPEN_CONFIRM],
395 .rpc_argp = &arg,
396 .rpc_resp = &res,
397 .rpc_cred = sp->so_cred,
398 }; 551 };
552 data->timestamp = jiffies;
553 rpc_call_setup(task, &msg, 0);
554}
555
556static void nfs4_open_confirm_done(struct rpc_task *task, void *calldata)
557{
558 struct nfs4_opendata *data = calldata;
559
560 data->rpc_status = task->tk_status;
561 if (RPC_ASSASSINATED(task))
562 return;
563 if (data->rpc_status == 0) {
564 memcpy(data->o_res.stateid.data, data->c_res.stateid.data,
565 sizeof(data->o_res.stateid.data));
566 renew_lease(data->o_res.server, data->timestamp);
567 }
568 nfs_increment_open_seqid(data->rpc_status, data->c_arg.seqid);
569 nfs_confirm_seqid(&data->owner->so_seqid, data->rpc_status);
570}
571
572static void nfs4_open_confirm_release(void *calldata)
573{
574 struct nfs4_opendata *data = calldata;
575 struct nfs4_state *state = NULL;
576
577 /* If this request hasn't been cancelled, do nothing */
578 if (data->cancelled == 0)
579 goto out_free;
580 /* In case of error, no cleanup! */
581 if (data->rpc_status != 0)
582 goto out_free;
583 nfs_confirm_seqid(&data->owner->so_seqid, 0);
584 state = nfs4_opendata_to_nfs4_state(data);
585 if (state != NULL)
586 nfs4_close_state(state, data->o_arg.open_flags);
587out_free:
588 nfs4_opendata_free(data);
589}
590
591static const struct rpc_call_ops nfs4_open_confirm_ops = {
592 .rpc_call_prepare = nfs4_open_confirm_prepare,
593 .rpc_call_done = nfs4_open_confirm_done,
594 .rpc_release = nfs4_open_confirm_release,
595};
596
597/*
598 * Note: On error, nfs4_proc_open_confirm will free the struct nfs4_opendata
599 */
600static int _nfs4_proc_open_confirm(struct nfs4_opendata *data)
601{
602 struct nfs_server *server = NFS_SERVER(data->dir->d_inode);
603 struct rpc_task *task;
399 int status; 604 int status;
400 605
401 status = rpc_call_sync(clnt, &msg, RPC_TASK_NOINTR); 606 atomic_inc(&data->count);
402 /* Confirm the sequence as being established */ 607 task = rpc_run_task(server->client, RPC_TASK_ASYNC, &nfs4_open_confirm_ops, data);
403 nfs_confirm_seqid(&sp->so_seqid, status); 608 if (IS_ERR(task)) {
404 nfs_increment_open_seqid(status, seqid); 609 nfs4_opendata_free(data);
405 if (status >= 0) 610 return PTR_ERR(task);
406 memcpy(stateid, &res.stateid, sizeof(*stateid)); 611 }
612 status = nfs4_wait_for_completion_rpc_task(task);
613 if (status != 0) {
614 data->cancelled = 1;
615 smp_wmb();
616 } else
617 status = data->rpc_status;
618 rpc_release_task(task);
407 return status; 619 return status;
408} 620}
409 621
410static int _nfs4_proc_open(struct inode *dir, struct nfs4_state_owner *sp, struct nfs_openargs *o_arg, struct nfs_openres *o_res) 622static void nfs4_open_prepare(struct rpc_task *task, void *calldata)
411{ 623{
412 struct nfs_server *server = NFS_SERVER(dir); 624 struct nfs4_opendata *data = calldata;
625 struct nfs4_state_owner *sp = data->owner;
413 struct rpc_message msg = { 626 struct rpc_message msg = {
414 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_OPEN], 627 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_OPEN],
415 .rpc_argp = o_arg, 628 .rpc_argp = &data->o_arg,
416 .rpc_resp = o_res, 629 .rpc_resp = &data->o_res,
417 .rpc_cred = sp->so_cred, 630 .rpc_cred = sp->so_cred,
418 }; 631 };
419 int status; 632
633 if (nfs_wait_on_sequence(data->o_arg.seqid, task) != 0)
634 return;
635 /* Update sequence id. */
636 data->o_arg.id = sp->so_id;
637 data->o_arg.clientid = sp->so_client->cl_clientid;
638 if (data->o_arg.claim == NFS4_OPEN_CLAIM_PREVIOUS)
639 msg.rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_OPEN_NOATTR];
640 data->timestamp = jiffies;
641 rpc_call_setup(task, &msg, 0);
642}
420 643
421 /* Update sequence id. The caller must serialize! */ 644static void nfs4_open_done(struct rpc_task *task, void *calldata)
422 o_arg->id = sp->so_id; 645{
423 o_arg->clientid = sp->so_client->cl_clientid; 646 struct nfs4_opendata *data = calldata;
424 647
425 status = rpc_call_sync(server->client, &msg, RPC_TASK_NOINTR); 648 data->rpc_status = task->tk_status;
426 if (status == 0) { 649 if (RPC_ASSASSINATED(task))
427 /* OPEN on anything except a regular file is disallowed in NFSv4 */ 650 return;
428 switch (o_res->f_attr->mode & S_IFMT) { 651 if (task->tk_status == 0) {
652 switch (data->o_res.f_attr->mode & S_IFMT) {
429 case S_IFREG: 653 case S_IFREG:
430 break; 654 break;
431 case S_IFLNK: 655 case S_IFLNK:
432 status = -ELOOP; 656 data->rpc_status = -ELOOP;
433 break; 657 break;
434 case S_IFDIR: 658 case S_IFDIR:
435 status = -EISDIR; 659 data->rpc_status = -EISDIR;
436 break; 660 break;
437 default: 661 default:
438 status = -ENOTDIR; 662 data->rpc_status = -ENOTDIR;
439 } 663 }
664 renew_lease(data->o_res.server, data->timestamp);
440 } 665 }
666 nfs_increment_open_seqid(data->rpc_status, data->o_arg.seqid);
667}
668
669static void nfs4_open_release(void *calldata)
670{
671 struct nfs4_opendata *data = calldata;
672 struct nfs4_state *state = NULL;
441 673
442 nfs_increment_open_seqid(status, o_arg->seqid); 674 /* If this request hasn't been cancelled, do nothing */
675 if (data->cancelled == 0)
676 goto out_free;
677 /* In case of error, no cleanup! */
678 if (data->rpc_status != 0)
679 goto out_free;
680 /* In case we need an open_confirm, no cleanup! */
681 if (data->o_res.rflags & NFS4_OPEN_RESULT_CONFIRM)
682 goto out_free;
683 nfs_confirm_seqid(&data->owner->so_seqid, 0);
684 state = nfs4_opendata_to_nfs4_state(data);
685 if (state != NULL)
686 nfs4_close_state(state, data->o_arg.open_flags);
687out_free:
688 nfs4_opendata_free(data);
689}
690
691static const struct rpc_call_ops nfs4_open_ops = {
692 .rpc_call_prepare = nfs4_open_prepare,
693 .rpc_call_done = nfs4_open_done,
694 .rpc_release = nfs4_open_release,
695};
696
697/*
698 * Note: On error, nfs4_proc_open will free the struct nfs4_opendata
699 */
700static int _nfs4_proc_open(struct nfs4_opendata *data)
701{
702 struct inode *dir = data->dir->d_inode;
703 struct nfs_server *server = NFS_SERVER(dir);
704 struct nfs_openargs *o_arg = &data->o_arg;
705 struct nfs_openres *o_res = &data->o_res;
706 struct rpc_task *task;
707 int status;
708
709 atomic_inc(&data->count);
710 task = rpc_run_task(server->client, RPC_TASK_ASYNC, &nfs4_open_ops, data);
711 if (IS_ERR(task)) {
712 nfs4_opendata_free(data);
713 return PTR_ERR(task);
714 }
715 status = nfs4_wait_for_completion_rpc_task(task);
716 if (status != 0) {
717 data->cancelled = 1;
718 smp_wmb();
719 } else
720 status = data->rpc_status;
721 rpc_release_task(task);
443 if (status != 0) 722 if (status != 0)
444 goto out; 723 return status;
724
445 if (o_arg->open_flags & O_CREAT) { 725 if (o_arg->open_flags & O_CREAT) {
446 update_changeattr(dir, &o_res->cinfo); 726 update_changeattr(dir, &o_res->cinfo);
447 nfs_post_op_update_inode(dir, o_res->dir_attr); 727 nfs_post_op_update_inode(dir, o_res->dir_attr);
448 } else 728 } else
449 nfs_refresh_inode(dir, o_res->dir_attr); 729 nfs_refresh_inode(dir, o_res->dir_attr);
450 if(o_res->rflags & NFS4_OPEN_RESULT_CONFIRM) { 730 if(o_res->rflags & NFS4_OPEN_RESULT_CONFIRM) {
451 status = _nfs4_proc_open_confirm(server->client, &o_res->fh, 731 status = _nfs4_proc_open_confirm(data);
452 sp, &o_res->stateid, o_arg->seqid);
453 if (status != 0) 732 if (status != 0)
454 goto out; 733 return status;
455 } 734 }
456 nfs_confirm_seqid(&sp->so_seqid, 0); 735 nfs_confirm_seqid(&data->owner->so_seqid, 0);
457 if (!(o_res->f_attr->valid & NFS_ATTR_FATTR)) 736 if (!(o_res->f_attr->valid & NFS_ATTR_FATTR))
458 status = server->rpc_ops->getattr(server, &o_res->fh, o_res->f_attr); 737 return server->rpc_ops->getattr(server, &o_res->fh, o_res->f_attr);
459out: 738 return 0;
460 return status;
461} 739}
462 740
463static int _nfs4_do_access(struct inode *inode, struct rpc_cred *cred, int openflags) 741static int _nfs4_do_access(struct inode *inode, struct rpc_cred *cred, int openflags)
@@ -488,6 +766,15 @@ out:
488 return -EACCES; 766 return -EACCES;
489} 767}
490 768
769int nfs4_recover_expired_lease(struct nfs_server *server)
770{
771 struct nfs4_client *clp = server->nfs4_state;
772
773 if (test_and_clear_bit(NFS4CLNT_LEASE_EXPIRED, &clp->cl_state))
774 nfs4_schedule_state_recovery(clp);
775 return nfs4_wait_clnt_recover(server->client, clp);
776}
777
491/* 778/*
492 * OPEN_EXPIRED: 779 * OPEN_EXPIRED:
493 * reclaim state on the server after a network partition. 780 * reclaim state on the server after a network partition.
@@ -495,77 +782,31 @@ out:
495 */ 782 */
496static int _nfs4_open_expired(struct nfs4_state_owner *sp, struct nfs4_state *state, struct dentry *dentry) 783static int _nfs4_open_expired(struct nfs4_state_owner *sp, struct nfs4_state *state, struct dentry *dentry)
497{ 784{
498 struct dentry *parent = dget_parent(dentry);
499 struct inode *dir = parent->d_inode;
500 struct inode *inode = state->inode; 785 struct inode *inode = state->inode;
501 struct nfs_server *server = NFS_SERVER(dir);
502 struct nfs_delegation *delegation = NFS_I(inode)->delegation; 786 struct nfs_delegation *delegation = NFS_I(inode)->delegation;
503 struct nfs_fattr f_attr, dir_attr; 787 struct nfs4_opendata *opendata;
504 struct nfs_openargs o_arg = { 788 int openflags = state->state & (FMODE_READ|FMODE_WRITE);
505 .fh = NFS_FH(dir), 789 int ret;
506 .open_flags = state->state,
507 .name = &dentry->d_name,
508 .bitmask = server->attr_bitmask,
509 .claim = NFS4_OPEN_CLAIM_NULL,
510 };
511 struct nfs_openres o_res = {
512 .f_attr = &f_attr,
513 .dir_attr = &dir_attr,
514 .server = server,
515 };
516 int status = 0;
517 790
518 if (delegation != NULL && !(delegation->flags & NFS_DELEGATION_NEED_RECLAIM)) { 791 if (delegation != NULL && !(delegation->flags & NFS_DELEGATION_NEED_RECLAIM)) {
519 status = _nfs4_do_access(inode, sp->so_cred, state->state); 792 ret = _nfs4_do_access(inode, sp->so_cred, openflags);
520 if (status < 0) 793 if (ret < 0)
521 goto out; 794 return ret;
522 memcpy(&state->stateid, &delegation->stateid, sizeof(state->stateid)); 795 memcpy(&state->stateid, &delegation->stateid, sizeof(state->stateid));
523 set_bit(NFS_DELEGATED_STATE, &state->flags); 796 set_bit(NFS_DELEGATED_STATE, &state->flags);
524 goto out; 797 return 0;
525 } 798 }
526 o_arg.seqid = nfs_alloc_seqid(&sp->so_seqid); 799 opendata = nfs4_opendata_alloc(dentry, sp, openflags, NULL);
527 status = -ENOMEM; 800 if (opendata == NULL)
528 if (o_arg.seqid == NULL) 801 return -ENOMEM;
529 goto out; 802 ret = nfs4_open_recover(opendata, state);
530 nfs_fattr_init(&f_attr); 803 if (ret == -ESTALE) {
531 nfs_fattr_init(&dir_attr); 804 /* Invalidate the state owner so we don't ever use it again */
532 status = _nfs4_proc_open(dir, sp, &o_arg, &o_res); 805 nfs4_drop_state_owner(sp);
533 if (status != 0) 806 d_drop(dentry);
534 goto out_nodeleg;
535 /* Check if files differ */
536 if ((f_attr.mode & S_IFMT) != (inode->i_mode & S_IFMT))
537 goto out_stale;
538 /* Has the file handle changed? */
539 if (nfs_compare_fh(&o_res.fh, NFS_FH(inode)) != 0) {
540 /* Verify if the change attributes are the same */
541 if (f_attr.change_attr != NFS_I(inode)->change_attr)
542 goto out_stale;
543 if (nfs_size_to_loff_t(f_attr.size) != inode->i_size)
544 goto out_stale;
545 /* Lets just pretend that this is the same file */
546 nfs_copy_fh(NFS_FH(inode), &o_res.fh);
547 NFS_I(inode)->fileid = f_attr.fileid;
548 }
549 memcpy(&state->stateid, &o_res.stateid, sizeof(state->stateid));
550 if (o_res.delegation_type != 0) {
551 if (!(delegation->flags & NFS_DELEGATION_NEED_RECLAIM))
552 nfs_inode_set_delegation(inode, sp->so_cred, &o_res);
553 else
554 nfs_inode_reclaim_delegation(inode, sp->so_cred, &o_res);
555 } 807 }
556out_nodeleg: 808 nfs4_opendata_free(opendata);
557 nfs_free_seqid(o_arg.seqid); 809 return ret;
558 clear_bit(NFS_DELEGATED_STATE, &state->flags);
559out:
560 dput(parent);
561 return status;
562out_stale:
563 status = -ESTALE;
564 /* Invalidate the state owner so we don't ever use it again */
565 nfs4_drop_state_owner(sp);
566 d_drop(dentry);
567 /* Should we be trying to close that stateid? */
568 goto out_nodeleg;
569} 810}
570 811
571static inline int nfs4_do_open_expired(struct nfs4_state_owner *sp, struct nfs4_state *state, struct dentry *dentry) 812static inline int nfs4_do_open_expired(struct nfs4_state_owner *sp, struct nfs4_state *state, struct dentry *dentry)
@@ -584,26 +825,19 @@ static inline int nfs4_do_open_expired(struct nfs4_state_owner *sp, struct nfs4_
584 825
585static int nfs4_open_expired(struct nfs4_state_owner *sp, struct nfs4_state *state) 826static int nfs4_open_expired(struct nfs4_state_owner *sp, struct nfs4_state *state)
586{ 827{
587 struct nfs_inode *nfsi = NFS_I(state->inode);
588 struct nfs_open_context *ctx; 828 struct nfs_open_context *ctx;
589 int status; 829 int ret;
590 830
591 spin_lock(&state->inode->i_lock); 831 ctx = nfs4_state_find_open_context(state);
592 list_for_each_entry(ctx, &nfsi->open_files, list) { 832 if (IS_ERR(ctx))
593 if (ctx->state != state) 833 return PTR_ERR(ctx);
594 continue; 834 ret = nfs4_do_open_expired(sp, state, ctx->dentry);
595 get_nfs_open_context(ctx); 835 put_nfs_open_context(ctx);
596 spin_unlock(&state->inode->i_lock); 836 return ret;
597 status = nfs4_do_open_expired(sp, state, ctx->dentry);
598 put_nfs_open_context(ctx);
599 return status;
600 }
601 spin_unlock(&state->inode->i_lock);
602 return -ENOENT;
603} 837}
604 838
605/* 839/*
606 * Returns an nfs4_state + an extra reference to the inode 840 * Returns a referenced nfs4_state if there is an open delegation on the file
607 */ 841 */
608static int _nfs4_open_delegated(struct inode *inode, int flags, struct rpc_cred *cred, struct nfs4_state **res) 842static int _nfs4_open_delegated(struct inode *inode, int flags, struct rpc_cred *cred, struct nfs4_state **res)
609{ 843{
@@ -616,6 +850,14 @@ static int _nfs4_open_delegated(struct inode *inode, int flags, struct rpc_cred
616 int open_flags = flags & (FMODE_READ|FMODE_WRITE); 850 int open_flags = flags & (FMODE_READ|FMODE_WRITE);
617 int err; 851 int err;
618 852
853 err = -ENOMEM;
854 if (!(sp = nfs4_get_state_owner(server, cred))) {
855 dprintk("%s: nfs4_get_state_owner failed!\n", __FUNCTION__);
856 return err;
857 }
858 err = nfs4_recover_expired_lease(server);
859 if (err != 0)
860 goto out_put_state_owner;
619 /* Protect against reboot recovery - NOTE ORDER! */ 861 /* Protect against reboot recovery - NOTE ORDER! */
620 down_read(&clp->cl_sem); 862 down_read(&clp->cl_sem);
621 /* Protect against delegation recall */ 863 /* Protect against delegation recall */
@@ -625,10 +867,6 @@ static int _nfs4_open_delegated(struct inode *inode, int flags, struct rpc_cred
625 if (delegation == NULL || (delegation->type & open_flags) != open_flags) 867 if (delegation == NULL || (delegation->type & open_flags) != open_flags)
626 goto out_err; 868 goto out_err;
627 err = -ENOMEM; 869 err = -ENOMEM;
628 if (!(sp = nfs4_get_state_owner(server, cred))) {
629 dprintk("%s: nfs4_get_state_owner failed!\n", __FUNCTION__);
630 goto out_err;
631 }
632 state = nfs4_get_open_state(inode, sp); 870 state = nfs4_get_open_state(inode, sp);
633 if (state == NULL) 871 if (state == NULL)
634 goto out_err; 872 goto out_err;
@@ -636,39 +874,34 @@ static int _nfs4_open_delegated(struct inode *inode, int flags, struct rpc_cred
636 err = -ENOENT; 874 err = -ENOENT;
637 if ((state->state & open_flags) == open_flags) { 875 if ((state->state & open_flags) == open_flags) {
638 spin_lock(&inode->i_lock); 876 spin_lock(&inode->i_lock);
639 if (open_flags & FMODE_READ) 877 update_open_stateflags(state, open_flags);
640 state->nreaders++;
641 if (open_flags & FMODE_WRITE)
642 state->nwriters++;
643 spin_unlock(&inode->i_lock); 878 spin_unlock(&inode->i_lock);
644 goto out_ok; 879 goto out_ok;
645 } else if (state->state != 0) 880 } else if (state->state != 0)
646 goto out_err; 881 goto out_put_open_state;
647 882
648 lock_kernel(); 883 lock_kernel();
649 err = _nfs4_do_access(inode, cred, open_flags); 884 err = _nfs4_do_access(inode, cred, open_flags);
650 unlock_kernel(); 885 unlock_kernel();
651 if (err != 0) 886 if (err != 0)
652 goto out_err; 887 goto out_put_open_state;
653 set_bit(NFS_DELEGATED_STATE, &state->flags); 888 set_bit(NFS_DELEGATED_STATE, &state->flags);
654 update_open_stateid(state, &delegation->stateid, open_flags); 889 update_open_stateid(state, &delegation->stateid, open_flags);
655out_ok: 890out_ok:
656 nfs4_put_state_owner(sp); 891 nfs4_put_state_owner(sp);
657 up_read(&nfsi->rwsem); 892 up_read(&nfsi->rwsem);
658 up_read(&clp->cl_sem); 893 up_read(&clp->cl_sem);
659 igrab(inode);
660 *res = state; 894 *res = state;
661 return 0; 895 return 0;
896out_put_open_state:
897 nfs4_put_open_state(state);
662out_err: 898out_err:
663 if (sp != NULL) {
664 if (state != NULL)
665 nfs4_put_open_state(state);
666 nfs4_put_state_owner(sp);
667 }
668 up_read(&nfsi->rwsem); 899 up_read(&nfsi->rwsem);
669 up_read(&clp->cl_sem); 900 up_read(&clp->cl_sem);
670 if (err != -EACCES) 901 if (err != -EACCES)
671 nfs_inode_return_delegation(inode); 902 nfs_inode_return_delegation(inode);
903out_put_state_owner:
904 nfs4_put_state_owner(sp);
672 return err; 905 return err;
673} 906}
674 907
@@ -689,7 +922,7 @@ static struct nfs4_state *nfs4_open_delegated(struct inode *inode, int flags, st
689} 922}
690 923
691/* 924/*
692 * Returns an nfs4_state + an referenced inode 925 * Returns a referenced nfs4_state
693 */ 926 */
694static int _nfs4_do_open(struct inode *dir, struct dentry *dentry, int flags, struct iattr *sattr, struct rpc_cred *cred, struct nfs4_state **res) 927static int _nfs4_do_open(struct inode *dir, struct dentry *dentry, int flags, struct iattr *sattr, struct rpc_cred *cred, struct nfs4_state **res)
695{ 928{
@@ -697,73 +930,46 @@ static int _nfs4_do_open(struct inode *dir, struct dentry *dentry, int flags, st
697 struct nfs4_state *state = NULL; 930 struct nfs4_state *state = NULL;
698 struct nfs_server *server = NFS_SERVER(dir); 931 struct nfs_server *server = NFS_SERVER(dir);
699 struct nfs4_client *clp = server->nfs4_state; 932 struct nfs4_client *clp = server->nfs4_state;
700 struct inode *inode = NULL; 933 struct nfs4_opendata *opendata;
701 int status; 934 int status;
702 struct nfs_fattr f_attr, dir_attr;
703 struct nfs_openargs o_arg = {
704 .fh = NFS_FH(dir),
705 .open_flags = flags,
706 .name = &dentry->d_name,
707 .server = server,
708 .bitmask = server->attr_bitmask,
709 .claim = NFS4_OPEN_CLAIM_NULL,
710 };
711 struct nfs_openres o_res = {
712 .f_attr = &f_attr,
713 .dir_attr = &dir_attr,
714 .server = server,
715 };
716 935
717 /* Protect against reboot recovery conflicts */ 936 /* Protect against reboot recovery conflicts */
718 down_read(&clp->cl_sem);
719 status = -ENOMEM; 937 status = -ENOMEM;
720 if (!(sp = nfs4_get_state_owner(server, cred))) { 938 if (!(sp = nfs4_get_state_owner(server, cred))) {
721 dprintk("nfs4_do_open: nfs4_get_state_owner failed!\n"); 939 dprintk("nfs4_do_open: nfs4_get_state_owner failed!\n");
722 goto out_err; 940 goto out_err;
723 } 941 }
724 if (flags & O_EXCL) { 942 status = nfs4_recover_expired_lease(server);
725 u32 *p = (u32 *) o_arg.u.verifier.data; 943 if (status != 0)
726 p[0] = jiffies; 944 goto err_put_state_owner;
727 p[1] = current->pid; 945 down_read(&clp->cl_sem);
728 } else 946 status = -ENOMEM;
729 o_arg.u.attrs = sattr; 947 opendata = nfs4_opendata_alloc(dentry, sp, flags, sattr);
730 /* Serialization for the sequence id */ 948 if (opendata == NULL)
949 goto err_put_state_owner;
731 950
732 o_arg.seqid = nfs_alloc_seqid(&sp->so_seqid); 951 status = _nfs4_proc_open(opendata);
733 if (o_arg.seqid == NULL)
734 return -ENOMEM;
735 nfs_fattr_init(&f_attr);
736 nfs_fattr_init(&dir_attr);
737 status = _nfs4_proc_open(dir, sp, &o_arg, &o_res);
738 if (status != 0) 952 if (status != 0)
739 goto out_err; 953 goto err_opendata_free;
740 954
741 status = -ENOMEM; 955 status = -ENOMEM;
742 inode = nfs_fhget(dir->i_sb, &o_res.fh, &f_attr); 956 state = nfs4_opendata_to_nfs4_state(opendata);
743 if (!inode) 957 if (state == NULL)
744 goto out_err; 958 goto err_opendata_free;
745 state = nfs4_get_open_state(inode, sp); 959 if (opendata->o_res.delegation_type != 0)
746 if (!state) 960 nfs_inode_set_delegation(state->inode, cred, &opendata->o_res);
747 goto out_err; 961 nfs4_opendata_free(opendata);
748 update_open_stateid(state, &o_res.stateid, flags);
749 if (o_res.delegation_type != 0)
750 nfs_inode_set_delegation(inode, cred, &o_res);
751 nfs_free_seqid(o_arg.seqid);
752 nfs4_put_state_owner(sp); 962 nfs4_put_state_owner(sp);
753 up_read(&clp->cl_sem); 963 up_read(&clp->cl_sem);
754 *res = state; 964 *res = state;
755 return 0; 965 return 0;
966err_opendata_free:
967 nfs4_opendata_free(opendata);
968err_put_state_owner:
969 nfs4_put_state_owner(sp);
756out_err: 970out_err:
757 if (sp != NULL) {
758 if (state != NULL)
759 nfs4_put_open_state(state);
760 nfs_free_seqid(o_arg.seqid);
761 nfs4_put_state_owner(sp);
762 }
763 /* Note: clp->cl_sem must be released before nfs4_put_open_state()! */ 971 /* Note: clp->cl_sem must be released before nfs4_put_open_state()! */
764 up_read(&clp->cl_sem); 972 up_read(&clp->cl_sem);
765 if (inode != NULL)
766 iput(inode);
767 *res = NULL; 973 *res = NULL;
768 return status; 974 return status;
769} 975}
@@ -830,6 +1036,7 @@ static int _nfs4_do_setattr(struct nfs_server *server, struct nfs_fattr *fattr,
830 .rpc_argp = &arg, 1036 .rpc_argp = &arg,
831 .rpc_resp = &res, 1037 .rpc_resp = &res,
832 }; 1038 };
1039 unsigned long timestamp = jiffies;
833 int status; 1040 int status;
834 1041
835 nfs_fattr_init(fattr); 1042 nfs_fattr_init(fattr);
@@ -841,6 +1048,8 @@ static int _nfs4_do_setattr(struct nfs_server *server, struct nfs_fattr *fattr,
841 memcpy(&arg.stateid, &zero_stateid, sizeof(arg.stateid)); 1048 memcpy(&arg.stateid, &zero_stateid, sizeof(arg.stateid));
842 1049
843 status = rpc_call_sync(server->client, &msg, 0); 1050 status = rpc_call_sync(server->client, &msg, 0);
1051 if (status == 0 && state != NULL)
1052 renew_lease(server, timestamp);
844 return status; 1053 return status;
845} 1054}
846 1055
@@ -865,12 +1074,13 @@ struct nfs4_closedata {
865 struct nfs_closeargs arg; 1074 struct nfs_closeargs arg;
866 struct nfs_closeres res; 1075 struct nfs_closeres res;
867 struct nfs_fattr fattr; 1076 struct nfs_fattr fattr;
1077 unsigned long timestamp;
868}; 1078};
869 1079
870static void nfs4_free_closedata(struct nfs4_closedata *calldata) 1080static void nfs4_free_closedata(void *data)
871{ 1081{
872 struct nfs4_state *state = calldata->state; 1082 struct nfs4_closedata *calldata = data;
873 struct nfs4_state_owner *sp = state->owner; 1083 struct nfs4_state_owner *sp = calldata->state->owner;
874 1084
875 nfs4_put_open_state(calldata->state); 1085 nfs4_put_open_state(calldata->state);
876 nfs_free_seqid(calldata->arg.seqid); 1086 nfs_free_seqid(calldata->arg.seqid);
@@ -878,12 +1088,14 @@ static void nfs4_free_closedata(struct nfs4_closedata *calldata)
878 kfree(calldata); 1088 kfree(calldata);
879} 1089}
880 1090
881static void nfs4_close_done(struct rpc_task *task) 1091static void nfs4_close_done(struct rpc_task *task, void *data)
882{ 1092{
883 struct nfs4_closedata *calldata = (struct nfs4_closedata *)task->tk_calldata; 1093 struct nfs4_closedata *calldata = data;
884 struct nfs4_state *state = calldata->state; 1094 struct nfs4_state *state = calldata->state;
885 struct nfs_server *server = NFS_SERVER(calldata->inode); 1095 struct nfs_server *server = NFS_SERVER(calldata->inode);
886 1096
1097 if (RPC_ASSASSINATED(task))
1098 return;
887 /* hmm. we are done with the inode, and in the process of freeing 1099 /* hmm. we are done with the inode, and in the process of freeing
888 * the state_owner. we keep this around to process errors 1100 * the state_owner. we keep this around to process errors
889 */ 1101 */
@@ -892,6 +1104,7 @@ static void nfs4_close_done(struct rpc_task *task)
892 case 0: 1104 case 0:
893 memcpy(&state->stateid, &calldata->res.stateid, 1105 memcpy(&state->stateid, &calldata->res.stateid,
894 sizeof(state->stateid)); 1106 sizeof(state->stateid));
1107 renew_lease(server, calldata->timestamp);
895 break; 1108 break;
896 case -NFS4ERR_STALE_STATEID: 1109 case -NFS4ERR_STALE_STATEID:
897 case -NFS4ERR_EXPIRED: 1110 case -NFS4ERR_EXPIRED:
@@ -904,12 +1117,11 @@ static void nfs4_close_done(struct rpc_task *task)
904 } 1117 }
905 } 1118 }
906 nfs_refresh_inode(calldata->inode, calldata->res.fattr); 1119 nfs_refresh_inode(calldata->inode, calldata->res.fattr);
907 nfs4_free_closedata(calldata);
908} 1120}
909 1121
910static void nfs4_close_begin(struct rpc_task *task) 1122static void nfs4_close_prepare(struct rpc_task *task, void *data)
911{ 1123{
912 struct nfs4_closedata *calldata = (struct nfs4_closedata *)task->tk_calldata; 1124 struct nfs4_closedata *calldata = data;
913 struct nfs4_state *state = calldata->state; 1125 struct nfs4_state *state = calldata->state;
914 struct rpc_message msg = { 1126 struct rpc_message msg = {
915 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_CLOSE], 1127 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_CLOSE],
@@ -918,10 +1130,8 @@ static void nfs4_close_begin(struct rpc_task *task)
918 .rpc_cred = state->owner->so_cred, 1130 .rpc_cred = state->owner->so_cred,
919 }; 1131 };
920 int mode = 0, old_mode; 1132 int mode = 0, old_mode;
921 int status;
922 1133
923 status = nfs_wait_on_sequence(calldata->arg.seqid, task); 1134 if (nfs_wait_on_sequence(calldata->arg.seqid, task) != 0)
924 if (status != 0)
925 return; 1135 return;
926 /* Recalculate the new open mode in case someone reopened the file 1136 /* Recalculate the new open mode in case someone reopened the file
927 * while we were waiting in line to be scheduled. 1137 * while we were waiting in line to be scheduled.
@@ -929,26 +1139,34 @@ static void nfs4_close_begin(struct rpc_task *task)
929 spin_lock(&state->owner->so_lock); 1139 spin_lock(&state->owner->so_lock);
930 spin_lock(&calldata->inode->i_lock); 1140 spin_lock(&calldata->inode->i_lock);
931 mode = old_mode = state->state; 1141 mode = old_mode = state->state;
932 if (state->nreaders == 0) 1142 if (state->n_rdwr == 0) {
933 mode &= ~FMODE_READ; 1143 if (state->n_rdonly == 0)
934 if (state->nwriters == 0) 1144 mode &= ~FMODE_READ;
935 mode &= ~FMODE_WRITE; 1145 if (state->n_wronly == 0)
1146 mode &= ~FMODE_WRITE;
1147 }
936 nfs4_state_set_mode_locked(state, mode); 1148 nfs4_state_set_mode_locked(state, mode);
937 spin_unlock(&calldata->inode->i_lock); 1149 spin_unlock(&calldata->inode->i_lock);
938 spin_unlock(&state->owner->so_lock); 1150 spin_unlock(&state->owner->so_lock);
939 if (mode == old_mode || test_bit(NFS_DELEGATED_STATE, &state->flags)) { 1151 if (mode == old_mode || test_bit(NFS_DELEGATED_STATE, &state->flags)) {
940 nfs4_free_closedata(calldata); 1152 /* Note: exit _without_ calling nfs4_close_done */
941 task->tk_exit = NULL; 1153 task->tk_action = NULL;
942 rpc_exit(task, 0);
943 return; 1154 return;
944 } 1155 }
945 nfs_fattr_init(calldata->res.fattr); 1156 nfs_fattr_init(calldata->res.fattr);
946 if (mode != 0) 1157 if (mode != 0)
947 msg.rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_OPEN_DOWNGRADE]; 1158 msg.rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_OPEN_DOWNGRADE];
948 calldata->arg.open_flags = mode; 1159 calldata->arg.open_flags = mode;
1160 calldata->timestamp = jiffies;
949 rpc_call_setup(task, &msg, 0); 1161 rpc_call_setup(task, &msg, 0);
950} 1162}
951 1163
1164static const struct rpc_call_ops nfs4_close_ops = {
1165 .rpc_call_prepare = nfs4_close_prepare,
1166 .rpc_call_done = nfs4_close_done,
1167 .rpc_release = nfs4_free_closedata,
1168};
1169
952/* 1170/*
953 * It is possible for data to be read/written from a mem-mapped file 1171 * It is possible for data to be read/written from a mem-mapped file
954 * after the sys_close call (which hits the vfs layer as a flush). 1172 * after the sys_close call (which hits the vfs layer as a flush).
@@ -981,8 +1199,7 @@ int nfs4_do_close(struct inode *inode, struct nfs4_state *state)
981 calldata->res.fattr = &calldata->fattr; 1199 calldata->res.fattr = &calldata->fattr;
982 calldata->res.server = server; 1200 calldata->res.server = server;
983 1201
984 status = nfs4_call_async(server->client, nfs4_close_begin, 1202 status = nfs4_call_async(server->client, &nfs4_close_ops, calldata);
985 nfs4_close_done, calldata);
986 if (status == 0) 1203 if (status == 0)
987 goto out; 1204 goto out;
988 1205
@@ -1034,7 +1251,7 @@ nfs4_atomic_open(struct inode *dir, struct dentry *dentry, struct nameidata *nd)
1034 d_add(dentry, NULL); 1251 d_add(dentry, NULL);
1035 return (struct dentry *)state; 1252 return (struct dentry *)state;
1036 } 1253 }
1037 res = d_add_unique(dentry, state->inode); 1254 res = d_add_unique(dentry, igrab(state->inode));
1038 if (res != NULL) 1255 if (res != NULL)
1039 dentry = res; 1256 dentry = res;
1040 nfs4_intent_set_file(nd, dentry, state); 1257 nfs4_intent_set_file(nd, dentry, state);
@@ -1046,7 +1263,6 @@ nfs4_open_revalidate(struct inode *dir, struct dentry *dentry, int openflags, st
1046{ 1263{
1047 struct rpc_cred *cred; 1264 struct rpc_cred *cred;
1048 struct nfs4_state *state; 1265 struct nfs4_state *state;
1049 struct inode *inode;
1050 1266
1051 cred = rpcauth_lookupcred(NFS_SERVER(dir)->client->cl_auth, 0); 1267 cred = rpcauth_lookupcred(NFS_SERVER(dir)->client->cl_auth, 0);
1052 if (IS_ERR(cred)) 1268 if (IS_ERR(cred))
@@ -1070,9 +1286,7 @@ nfs4_open_revalidate(struct inode *dir, struct dentry *dentry, int openflags, st
1070 } 1286 }
1071 goto out_drop; 1287 goto out_drop;
1072 } 1288 }
1073 inode = state->inode; 1289 if (state->inode == dentry->d_inode) {
1074 iput(inode);
1075 if (inode == dentry->d_inode) {
1076 nfs4_intent_set_file(nd, dentry, state); 1290 nfs4_intent_set_file(nd, dentry, state);
1077 return 1; 1291 return 1;
1078 } 1292 }
@@ -1508,11 +1722,13 @@ static int _nfs4_proc_write(struct nfs_write_data *wdata)
1508 1722
1509 wdata->args.bitmask = server->attr_bitmask; 1723 wdata->args.bitmask = server->attr_bitmask;
1510 wdata->res.server = server; 1724 wdata->res.server = server;
1725 wdata->timestamp = jiffies;
1511 nfs_fattr_init(fattr); 1726 nfs_fattr_init(fattr);
1512 status = rpc_call_sync(server->client, &msg, rpcflags); 1727 status = rpc_call_sync(server->client, &msg, rpcflags);
1513 dprintk("NFS reply write: %d\n", status); 1728 dprintk("NFS reply write: %d\n", status);
1514 if (status < 0) 1729 if (status < 0)
1515 return status; 1730 return status;
1731 renew_lease(server, wdata->timestamp);
1516 nfs_post_op_update_inode(inode, fattr); 1732 nfs_post_op_update_inode(inode, fattr);
1517 return wdata->res.count; 1733 return wdata->res.count;
1518} 1734}
@@ -1547,8 +1763,11 @@ static int _nfs4_proc_commit(struct nfs_write_data *cdata)
1547 1763
1548 cdata->args.bitmask = server->attr_bitmask; 1764 cdata->args.bitmask = server->attr_bitmask;
1549 cdata->res.server = server; 1765 cdata->res.server = server;
1766 cdata->timestamp = jiffies;
1550 nfs_fattr_init(fattr); 1767 nfs_fattr_init(fattr);
1551 status = rpc_call_sync(server->client, &msg, 0); 1768 status = rpc_call_sync(server->client, &msg, 0);
1769 if (status >= 0)
1770 renew_lease(server, cdata->timestamp);
1552 dprintk("NFS reply commit: %d\n", status); 1771 dprintk("NFS reply commit: %d\n", status);
1553 if (status >= 0) 1772 if (status >= 0)
1554 nfs_post_op_update_inode(inode, fattr); 1773 nfs_post_op_update_inode(inode, fattr);
@@ -1601,7 +1820,7 @@ nfs4_proc_create(struct inode *dir, struct dentry *dentry, struct iattr *sattr,
1601 status = PTR_ERR(state); 1820 status = PTR_ERR(state);
1602 goto out; 1821 goto out;
1603 } 1822 }
1604 d_instantiate(dentry, state->inode); 1823 d_instantiate(dentry, igrab(state->inode));
1605 if (flags & O_EXCL) { 1824 if (flags & O_EXCL) {
1606 struct nfs_fattr fattr; 1825 struct nfs_fattr fattr;
1607 status = nfs4_do_setattr(NFS_SERVER(dir), &fattr, 1826 status = nfs4_do_setattr(NFS_SERVER(dir), &fattr,
@@ -2125,10 +2344,9 @@ static int nfs4_proc_pathconf(struct nfs_server *server, struct nfs_fh *fhandle,
2125 return err; 2344 return err;
2126} 2345}
2127 2346
2128static void 2347static void nfs4_read_done(struct rpc_task *task, void *calldata)
2129nfs4_read_done(struct rpc_task *task)
2130{ 2348{
2131 struct nfs_read_data *data = (struct nfs_read_data *) task->tk_calldata; 2349 struct nfs_read_data *data = calldata;
2132 struct inode *inode = data->inode; 2350 struct inode *inode = data->inode;
2133 2351
2134 if (nfs4_async_handle_error(task, NFS_SERVER(inode)) == -EAGAIN) { 2352 if (nfs4_async_handle_error(task, NFS_SERVER(inode)) == -EAGAIN) {
@@ -2138,9 +2356,14 @@ nfs4_read_done(struct rpc_task *task)
2138 if (task->tk_status > 0) 2356 if (task->tk_status > 0)
2139 renew_lease(NFS_SERVER(inode), data->timestamp); 2357 renew_lease(NFS_SERVER(inode), data->timestamp);
2140 /* Call back common NFS readpage processing */ 2358 /* Call back common NFS readpage processing */
2141 nfs_readpage_result(task); 2359 nfs_readpage_result(task, calldata);
2142} 2360}
2143 2361
2362static const struct rpc_call_ops nfs4_read_ops = {
2363 .rpc_call_done = nfs4_read_done,
2364 .rpc_release = nfs_readdata_release,
2365};
2366
2144static void 2367static void
2145nfs4_proc_read_setup(struct nfs_read_data *data) 2368nfs4_proc_read_setup(struct nfs_read_data *data)
2146{ 2369{
@@ -2160,14 +2383,13 @@ nfs4_proc_read_setup(struct nfs_read_data *data)
2160 flags = RPC_TASK_ASYNC | (IS_SWAPFILE(inode)? NFS_RPC_SWAPFLAGS : 0); 2383 flags = RPC_TASK_ASYNC | (IS_SWAPFILE(inode)? NFS_RPC_SWAPFLAGS : 0);
2161 2384
2162 /* Finalize the task. */ 2385 /* Finalize the task. */
2163 rpc_init_task(task, NFS_CLIENT(inode), nfs4_read_done, flags); 2386 rpc_init_task(task, NFS_CLIENT(inode), flags, &nfs4_read_ops, data);
2164 rpc_call_setup(task, &msg, 0); 2387 rpc_call_setup(task, &msg, 0);
2165} 2388}
2166 2389
2167static void 2390static void nfs4_write_done(struct rpc_task *task, void *calldata)
2168nfs4_write_done(struct rpc_task *task)
2169{ 2391{
2170 struct nfs_write_data *data = (struct nfs_write_data *) task->tk_calldata; 2392 struct nfs_write_data *data = calldata;
2171 struct inode *inode = data->inode; 2393 struct inode *inode = data->inode;
2172 2394
2173 if (nfs4_async_handle_error(task, NFS_SERVER(inode)) == -EAGAIN) { 2395 if (nfs4_async_handle_error(task, NFS_SERVER(inode)) == -EAGAIN) {
@@ -2179,9 +2401,14 @@ nfs4_write_done(struct rpc_task *task)
2179 nfs_post_op_update_inode(inode, data->res.fattr); 2401 nfs_post_op_update_inode(inode, data->res.fattr);
2180 } 2402 }
2181 /* Call back common NFS writeback processing */ 2403 /* Call back common NFS writeback processing */
2182 nfs_writeback_done(task); 2404 nfs_writeback_done(task, calldata);
2183} 2405}
2184 2406
2407static const struct rpc_call_ops nfs4_write_ops = {
2408 .rpc_call_done = nfs4_write_done,
2409 .rpc_release = nfs_writedata_release,
2410};
2411
2185static void 2412static void
2186nfs4_proc_write_setup(struct nfs_write_data *data, int how) 2413nfs4_proc_write_setup(struct nfs_write_data *data, int how)
2187{ 2414{
@@ -2214,14 +2441,13 @@ nfs4_proc_write_setup(struct nfs_write_data *data, int how)
2214 flags = (how & FLUSH_SYNC) ? 0 : RPC_TASK_ASYNC; 2441 flags = (how & FLUSH_SYNC) ? 0 : RPC_TASK_ASYNC;
2215 2442
2216 /* Finalize the task. */ 2443 /* Finalize the task. */
2217 rpc_init_task(task, NFS_CLIENT(inode), nfs4_write_done, flags); 2444 rpc_init_task(task, NFS_CLIENT(inode), flags, &nfs4_write_ops, data);
2218 rpc_call_setup(task, &msg, 0); 2445 rpc_call_setup(task, &msg, 0);
2219} 2446}
2220 2447
2221static void 2448static void nfs4_commit_done(struct rpc_task *task, void *calldata)
2222nfs4_commit_done(struct rpc_task *task)
2223{ 2449{
2224 struct nfs_write_data *data = (struct nfs_write_data *) task->tk_calldata; 2450 struct nfs_write_data *data = calldata;
2225 struct inode *inode = data->inode; 2451 struct inode *inode = data->inode;
2226 2452
2227 if (nfs4_async_handle_error(task, NFS_SERVER(inode)) == -EAGAIN) { 2453 if (nfs4_async_handle_error(task, NFS_SERVER(inode)) == -EAGAIN) {
@@ -2231,9 +2457,14 @@ nfs4_commit_done(struct rpc_task *task)
2231 if (task->tk_status >= 0) 2457 if (task->tk_status >= 0)
2232 nfs_post_op_update_inode(inode, data->res.fattr); 2458 nfs_post_op_update_inode(inode, data->res.fattr);
2233 /* Call back common NFS writeback processing */ 2459 /* Call back common NFS writeback processing */
2234 nfs_commit_done(task); 2460 nfs_commit_done(task, calldata);
2235} 2461}
2236 2462
2463static const struct rpc_call_ops nfs4_commit_ops = {
2464 .rpc_call_done = nfs4_commit_done,
2465 .rpc_release = nfs_commit_release,
2466};
2467
2237static void 2468static void
2238nfs4_proc_commit_setup(struct nfs_write_data *data, int how) 2469nfs4_proc_commit_setup(struct nfs_write_data *data, int how)
2239{ 2470{
@@ -2255,7 +2486,7 @@ nfs4_proc_commit_setup(struct nfs_write_data *data, int how)
2255 flags = (how & FLUSH_SYNC) ? 0 : RPC_TASK_ASYNC; 2486 flags = (how & FLUSH_SYNC) ? 0 : RPC_TASK_ASYNC;
2256 2487
2257 /* Finalize the task. */ 2488 /* Finalize the task. */
2258 rpc_init_task(task, NFS_CLIENT(inode), nfs4_commit_done, flags); 2489 rpc_init_task(task, NFS_CLIENT(inode), flags, &nfs4_commit_ops, data);
2259 rpc_call_setup(task, &msg, 0); 2490 rpc_call_setup(task, &msg, 0);
2260} 2491}
2261 2492
@@ -2263,11 +2494,10 @@ nfs4_proc_commit_setup(struct nfs_write_data *data, int how)
2263 * nfs4_proc_async_renew(): This is not one of the nfs_rpc_ops; it is a special 2494 * nfs4_proc_async_renew(): This is not one of the nfs_rpc_ops; it is a special
2264 * standalone procedure for queueing an asynchronous RENEW. 2495 * standalone procedure for queueing an asynchronous RENEW.
2265 */ 2496 */
2266static void 2497static void nfs4_renew_done(struct rpc_task *task, void *data)
2267renew_done(struct rpc_task *task)
2268{ 2498{
2269 struct nfs4_client *clp = (struct nfs4_client *)task->tk_msg.rpc_argp; 2499 struct nfs4_client *clp = (struct nfs4_client *)task->tk_msg.rpc_argp;
2270 unsigned long timestamp = (unsigned long)task->tk_calldata; 2500 unsigned long timestamp = (unsigned long)data;
2271 2501
2272 if (task->tk_status < 0) { 2502 if (task->tk_status < 0) {
2273 switch (task->tk_status) { 2503 switch (task->tk_status) {
@@ -2284,26 +2514,28 @@ renew_done(struct rpc_task *task)
2284 spin_unlock(&clp->cl_lock); 2514 spin_unlock(&clp->cl_lock);
2285} 2515}
2286 2516
2287int 2517static const struct rpc_call_ops nfs4_renew_ops = {
2288nfs4_proc_async_renew(struct nfs4_client *clp) 2518 .rpc_call_done = nfs4_renew_done,
2519};
2520
2521int nfs4_proc_async_renew(struct nfs4_client *clp, struct rpc_cred *cred)
2289{ 2522{
2290 struct rpc_message msg = { 2523 struct rpc_message msg = {
2291 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_RENEW], 2524 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_RENEW],
2292 .rpc_argp = clp, 2525 .rpc_argp = clp,
2293 .rpc_cred = clp->cl_cred, 2526 .rpc_cred = cred,
2294 }; 2527 };
2295 2528
2296 return rpc_call_async(clp->cl_rpcclient, &msg, RPC_TASK_SOFT, 2529 return rpc_call_async(clp->cl_rpcclient, &msg, RPC_TASK_SOFT,
2297 renew_done, (void *)jiffies); 2530 &nfs4_renew_ops, (void *)jiffies);
2298} 2531}
2299 2532
2300int 2533int nfs4_proc_renew(struct nfs4_client *clp, struct rpc_cred *cred)
2301nfs4_proc_renew(struct nfs4_client *clp)
2302{ 2534{
2303 struct rpc_message msg = { 2535 struct rpc_message msg = {
2304 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_RENEW], 2536 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_RENEW],
2305 .rpc_argp = clp, 2537 .rpc_argp = clp,
2306 .rpc_cred = clp->cl_cred, 2538 .rpc_cred = cred,
2307 }; 2539 };
2308 unsigned long now = jiffies; 2540 unsigned long now = jiffies;
2309 int status; 2541 int status;
@@ -2519,7 +2751,7 @@ nfs4_async_handle_error(struct rpc_task *task, const struct nfs_server *server)
2519 case -NFS4ERR_EXPIRED: 2751 case -NFS4ERR_EXPIRED:
2520 rpc_sleep_on(&clp->cl_rpcwaitq, task, NULL, NULL); 2752 rpc_sleep_on(&clp->cl_rpcwaitq, task, NULL, NULL);
2521 nfs4_schedule_state_recovery(clp); 2753 nfs4_schedule_state_recovery(clp);
2522 if (test_bit(NFS4CLNT_OK, &clp->cl_state)) 2754 if (test_bit(NFS4CLNT_STATE_RECOVER, &clp->cl_state) == 0)
2523 rpc_wake_up_task(task); 2755 rpc_wake_up_task(task);
2524 task->tk_status = 0; 2756 task->tk_status = 0;
2525 return -EAGAIN; 2757 return -EAGAIN;
@@ -2536,25 +2768,25 @@ nfs4_async_handle_error(struct rpc_task *task, const struct nfs_server *server)
2536 return 0; 2768 return 0;
2537} 2769}
2538 2770
2771static int nfs4_wait_bit_interruptible(void *word)
2772{
2773 if (signal_pending(current))
2774 return -ERESTARTSYS;
2775 schedule();
2776 return 0;
2777}
2778
2539static int nfs4_wait_clnt_recover(struct rpc_clnt *clnt, struct nfs4_client *clp) 2779static int nfs4_wait_clnt_recover(struct rpc_clnt *clnt, struct nfs4_client *clp)
2540{ 2780{
2541 DEFINE_WAIT(wait);
2542 sigset_t oldset; 2781 sigset_t oldset;
2543 int interruptible, res = 0; 2782 int res;
2544 2783
2545 might_sleep(); 2784 might_sleep();
2546 2785
2547 rpc_clnt_sigmask(clnt, &oldset); 2786 rpc_clnt_sigmask(clnt, &oldset);
2548 interruptible = TASK_UNINTERRUPTIBLE; 2787 res = wait_on_bit(&clp->cl_state, NFS4CLNT_STATE_RECOVER,
2549 if (clnt->cl_intr) 2788 nfs4_wait_bit_interruptible,
2550 interruptible = TASK_INTERRUPTIBLE; 2789 TASK_INTERRUPTIBLE);
2551 prepare_to_wait(&clp->cl_waitq, &wait, interruptible);
2552 nfs4_schedule_state_recovery(clp);
2553 if (clnt->cl_intr && signalled())
2554 res = -ERESTARTSYS;
2555 else if (!test_bit(NFS4CLNT_OK, &clp->cl_state))
2556 schedule();
2557 finish_wait(&clp->cl_waitq, &wait);
2558 rpc_clnt_sigunmask(clnt, &oldset); 2790 rpc_clnt_sigunmask(clnt, &oldset);
2559 return res; 2791 return res;
2560} 2792}
@@ -2597,6 +2829,7 @@ int nfs4_handle_exception(const struct nfs_server *server, int errorcode, struct
2597 case -NFS4ERR_STALE_CLIENTID: 2829 case -NFS4ERR_STALE_CLIENTID:
2598 case -NFS4ERR_STALE_STATEID: 2830 case -NFS4ERR_STALE_STATEID:
2599 case -NFS4ERR_EXPIRED: 2831 case -NFS4ERR_EXPIRED:
2832 nfs4_schedule_state_recovery(clp);
2600 ret = nfs4_wait_clnt_recover(server->client, clp); 2833 ret = nfs4_wait_clnt_recover(server->client, clp);
2601 if (ret == 0) 2834 if (ret == 0)
2602 exception->retry = 1; 2835 exception->retry = 1;
@@ -2613,7 +2846,7 @@ int nfs4_handle_exception(const struct nfs_server *server, int errorcode, struct
2613 return nfs4_map_errors(ret); 2846 return nfs4_map_errors(ret);
2614} 2847}
2615 2848
2616int nfs4_proc_setclientid(struct nfs4_client *clp, u32 program, unsigned short port) 2849int nfs4_proc_setclientid(struct nfs4_client *clp, u32 program, unsigned short port, struct rpc_cred *cred)
2617{ 2850{
2618 nfs4_verifier sc_verifier; 2851 nfs4_verifier sc_verifier;
2619 struct nfs4_setclientid setclientid = { 2852 struct nfs4_setclientid setclientid = {
@@ -2624,7 +2857,7 @@ int nfs4_proc_setclientid(struct nfs4_client *clp, u32 program, unsigned short p
2624 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_SETCLIENTID], 2857 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_SETCLIENTID],
2625 .rpc_argp = &setclientid, 2858 .rpc_argp = &setclientid,
2626 .rpc_resp = clp, 2859 .rpc_resp = clp,
2627 .rpc_cred = clp->cl_cred, 2860 .rpc_cred = cred,
2628 }; 2861 };
2629 u32 *p; 2862 u32 *p;
2630 int loop = 0; 2863 int loop = 0;
@@ -2638,7 +2871,7 @@ int nfs4_proc_setclientid(struct nfs4_client *clp, u32 program, unsigned short p
2638 setclientid.sc_name_len = scnprintf(setclientid.sc_name, 2871 setclientid.sc_name_len = scnprintf(setclientid.sc_name,
2639 sizeof(setclientid.sc_name), "%s/%u.%u.%u.%u %s %u", 2872 sizeof(setclientid.sc_name), "%s/%u.%u.%u.%u %s %u",
2640 clp->cl_ipaddr, NIPQUAD(clp->cl_addr.s_addr), 2873 clp->cl_ipaddr, NIPQUAD(clp->cl_addr.s_addr),
2641 clp->cl_cred->cr_ops->cr_name, 2874 cred->cr_ops->cr_name,
2642 clp->cl_id_uniquifier); 2875 clp->cl_id_uniquifier);
2643 setclientid.sc_netid_len = scnprintf(setclientid.sc_netid, 2876 setclientid.sc_netid_len = scnprintf(setclientid.sc_netid,
2644 sizeof(setclientid.sc_netid), "tcp"); 2877 sizeof(setclientid.sc_netid), "tcp");
@@ -2661,14 +2894,14 @@ int nfs4_proc_setclientid(struct nfs4_client *clp, u32 program, unsigned short p
2661} 2894}
2662 2895
2663int 2896int
2664nfs4_proc_setclientid_confirm(struct nfs4_client *clp) 2897nfs4_proc_setclientid_confirm(struct nfs4_client *clp, struct rpc_cred *cred)
2665{ 2898{
2666 struct nfs_fsinfo fsinfo; 2899 struct nfs_fsinfo fsinfo;
2667 struct rpc_message msg = { 2900 struct rpc_message msg = {
2668 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_SETCLIENTID_CONFIRM], 2901 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_SETCLIENTID_CONFIRM],
2669 .rpc_argp = clp, 2902 .rpc_argp = clp,
2670 .rpc_resp = &fsinfo, 2903 .rpc_resp = &fsinfo,
2671 .rpc_cred = clp->cl_cred, 2904 .rpc_cred = cred,
2672 }; 2905 };
2673 unsigned long now; 2906 unsigned long now;
2674 int status; 2907 int status;
@@ -2679,24 +2912,92 @@ nfs4_proc_setclientid_confirm(struct nfs4_client *clp)
2679 spin_lock(&clp->cl_lock); 2912 spin_lock(&clp->cl_lock);
2680 clp->cl_lease_time = fsinfo.lease_time * HZ; 2913 clp->cl_lease_time = fsinfo.lease_time * HZ;
2681 clp->cl_last_renewal = now; 2914 clp->cl_last_renewal = now;
2915 clear_bit(NFS4CLNT_LEASE_EXPIRED, &clp->cl_state);
2682 spin_unlock(&clp->cl_lock); 2916 spin_unlock(&clp->cl_lock);
2683 } 2917 }
2684 return status; 2918 return status;
2685} 2919}
2686 2920
2687static int _nfs4_proc_delegreturn(struct inode *inode, struct rpc_cred *cred, const nfs4_stateid *stateid) 2921struct nfs4_delegreturndata {
2922 struct nfs4_delegreturnargs args;
2923 struct nfs4_delegreturnres res;
2924 struct nfs_fh fh;
2925 nfs4_stateid stateid;
2926 struct rpc_cred *cred;
2927 unsigned long timestamp;
2928 struct nfs_fattr fattr;
2929 int rpc_status;
2930};
2931
2932static void nfs4_delegreturn_prepare(struct rpc_task *task, void *calldata)
2688{ 2933{
2689 struct nfs4_delegreturnargs args = { 2934 struct nfs4_delegreturndata *data = calldata;
2690 .fhandle = NFS_FH(inode),
2691 .stateid = stateid,
2692 };
2693 struct rpc_message msg = { 2935 struct rpc_message msg = {
2694 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_DELEGRETURN], 2936 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_DELEGRETURN],
2695 .rpc_argp = &args, 2937 .rpc_argp = &data->args,
2696 .rpc_cred = cred, 2938 .rpc_resp = &data->res,
2939 .rpc_cred = data->cred,
2697 }; 2940 };
2941 nfs_fattr_init(data->res.fattr);
2942 rpc_call_setup(task, &msg, 0);
2943}
2698 2944
2699 return rpc_call_sync(NFS_CLIENT(inode), &msg, 0); 2945static void nfs4_delegreturn_done(struct rpc_task *task, void *calldata)
2946{
2947 struct nfs4_delegreturndata *data = calldata;
2948 data->rpc_status = task->tk_status;
2949 if (data->rpc_status == 0)
2950 renew_lease(data->res.server, data->timestamp);
2951}
2952
2953static void nfs4_delegreturn_release(void *calldata)
2954{
2955 struct nfs4_delegreturndata *data = calldata;
2956
2957 put_rpccred(data->cred);
2958 kfree(calldata);
2959}
2960
2961const static struct rpc_call_ops nfs4_delegreturn_ops = {
2962 .rpc_call_prepare = nfs4_delegreturn_prepare,
2963 .rpc_call_done = nfs4_delegreturn_done,
2964 .rpc_release = nfs4_delegreturn_release,
2965};
2966
2967static int _nfs4_proc_delegreturn(struct inode *inode, struct rpc_cred *cred, const nfs4_stateid *stateid)
2968{
2969 struct nfs4_delegreturndata *data;
2970 struct nfs_server *server = NFS_SERVER(inode);
2971 struct rpc_task *task;
2972 int status;
2973
2974 data = kmalloc(sizeof(*data), GFP_KERNEL);
2975 if (data == NULL)
2976 return -ENOMEM;
2977 data->args.fhandle = &data->fh;
2978 data->args.stateid = &data->stateid;
2979 data->args.bitmask = server->attr_bitmask;
2980 nfs_copy_fh(&data->fh, NFS_FH(inode));
2981 memcpy(&data->stateid, stateid, sizeof(data->stateid));
2982 data->res.fattr = &data->fattr;
2983 data->res.server = server;
2984 data->cred = get_rpccred(cred);
2985 data->timestamp = jiffies;
2986 data->rpc_status = 0;
2987
2988 task = rpc_run_task(NFS_CLIENT(inode), RPC_TASK_ASYNC, &nfs4_delegreturn_ops, data);
2989 if (IS_ERR(task)) {
2990 nfs4_delegreturn_release(data);
2991 return PTR_ERR(task);
2992 }
2993 status = nfs4_wait_for_completion_rpc_task(task);
2994 if (status == 0) {
2995 status = data->rpc_status;
2996 if (status == 0)
2997 nfs_post_op_update_inode(inode, &data->fattr);
2998 }
2999 rpc_release_task(task);
3000 return status;
2700} 3001}
2701 3002
2702int nfs4_proc_delegreturn(struct inode *inode, struct rpc_cred *cred, const nfs4_stateid *stateid) 3003int nfs4_proc_delegreturn(struct inode *inode, struct rpc_cred *cred, const nfs4_stateid *stateid)
@@ -2734,43 +3035,17 @@ nfs4_set_lock_task_retry(unsigned long timeout)
2734 return timeout; 3035 return timeout;
2735} 3036}
2736 3037
2737static inline int
2738nfs4_lck_type(int cmd, struct file_lock *request)
2739{
2740 /* set lock type */
2741 switch (request->fl_type) {
2742 case F_RDLCK:
2743 return IS_SETLKW(cmd) ? NFS4_READW_LT : NFS4_READ_LT;
2744 case F_WRLCK:
2745 return IS_SETLKW(cmd) ? NFS4_WRITEW_LT : NFS4_WRITE_LT;
2746 case F_UNLCK:
2747 return NFS4_WRITE_LT;
2748 }
2749 BUG();
2750 return 0;
2751}
2752
2753static inline uint64_t
2754nfs4_lck_length(struct file_lock *request)
2755{
2756 if (request->fl_end == OFFSET_MAX)
2757 return ~(uint64_t)0;
2758 return request->fl_end - request->fl_start + 1;
2759}
2760
2761static int _nfs4_proc_getlk(struct nfs4_state *state, int cmd, struct file_lock *request) 3038static int _nfs4_proc_getlk(struct nfs4_state *state, int cmd, struct file_lock *request)
2762{ 3039{
2763 struct inode *inode = state->inode; 3040 struct inode *inode = state->inode;
2764 struct nfs_server *server = NFS_SERVER(inode); 3041 struct nfs_server *server = NFS_SERVER(inode);
2765 struct nfs4_client *clp = server->nfs4_state; 3042 struct nfs4_client *clp = server->nfs4_state;
2766 struct nfs_lockargs arg = { 3043 struct nfs_lockt_args arg = {
2767 .fh = NFS_FH(inode), 3044 .fh = NFS_FH(inode),
2768 .type = nfs4_lck_type(cmd, request), 3045 .fl = request,
2769 .offset = request->fl_start,
2770 .length = nfs4_lck_length(request),
2771 }; 3046 };
2772 struct nfs_lockres res = { 3047 struct nfs_lockt_res res = {
2773 .server = server, 3048 .denied = request,
2774 }; 3049 };
2775 struct rpc_message msg = { 3050 struct rpc_message msg = {
2776 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_LOCKT], 3051 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_LOCKT],
@@ -2778,36 +3053,23 @@ static int _nfs4_proc_getlk(struct nfs4_state *state, int cmd, struct file_lock
2778 .rpc_resp = &res, 3053 .rpc_resp = &res,
2779 .rpc_cred = state->owner->so_cred, 3054 .rpc_cred = state->owner->so_cred,
2780 }; 3055 };
2781 struct nfs_lowner nlo;
2782 struct nfs4_lock_state *lsp; 3056 struct nfs4_lock_state *lsp;
2783 int status; 3057 int status;
2784 3058
2785 down_read(&clp->cl_sem); 3059 down_read(&clp->cl_sem);
2786 nlo.clientid = clp->cl_clientid; 3060 arg.lock_owner.clientid = clp->cl_clientid;
2787 status = nfs4_set_lock_state(state, request); 3061 status = nfs4_set_lock_state(state, request);
2788 if (status != 0) 3062 if (status != 0)
2789 goto out; 3063 goto out;
2790 lsp = request->fl_u.nfs4_fl.owner; 3064 lsp = request->fl_u.nfs4_fl.owner;
2791 nlo.id = lsp->ls_id; 3065 arg.lock_owner.id = lsp->ls_id;
2792 arg.u.lockt = &nlo;
2793 status = rpc_call_sync(server->client, &msg, 0); 3066 status = rpc_call_sync(server->client, &msg, 0);
2794 if (!status) { 3067 switch (status) {
2795 request->fl_type = F_UNLCK; 3068 case 0:
2796 } else if (status == -NFS4ERR_DENIED) { 3069 request->fl_type = F_UNLCK;
2797 int64_t len, start, end; 3070 break;
2798 start = res.u.denied.offset; 3071 case -NFS4ERR_DENIED:
2799 len = res.u.denied.length; 3072 status = 0;
2800 end = start + len - 1;
2801 if (end < 0 || len == 0)
2802 request->fl_end = OFFSET_MAX;
2803 else
2804 request->fl_end = (loff_t)end;
2805 request->fl_start = (loff_t)start;
2806 request->fl_type = F_WRLCK;
2807 if (res.u.denied.type & 1)
2808 request->fl_type = F_RDLCK;
2809 request->fl_pid = 0;
2810 status = 0;
2811 } 3073 }
2812out: 3074out:
2813 up_read(&clp->cl_sem); 3075 up_read(&clp->cl_sem);
@@ -2847,196 +3109,314 @@ static int do_vfs_lock(struct file *file, struct file_lock *fl)
2847} 3109}
2848 3110
2849struct nfs4_unlockdata { 3111struct nfs4_unlockdata {
2850 struct nfs_lockargs arg; 3112 struct nfs_locku_args arg;
2851 struct nfs_locku_opargs luargs; 3113 struct nfs_locku_res res;
2852 struct nfs_lockres res;
2853 struct nfs4_lock_state *lsp; 3114 struct nfs4_lock_state *lsp;
2854 struct nfs_open_context *ctx; 3115 struct nfs_open_context *ctx;
2855 atomic_t refcount; 3116 struct file_lock fl;
2856 struct completion completion; 3117 const struct nfs_server *server;
3118 unsigned long timestamp;
2857}; 3119};
2858 3120
2859static void nfs4_locku_release_calldata(struct nfs4_unlockdata *calldata) 3121static struct nfs4_unlockdata *nfs4_alloc_unlockdata(struct file_lock *fl,
2860{ 3122 struct nfs_open_context *ctx,
2861 if (atomic_dec_and_test(&calldata->refcount)) { 3123 struct nfs4_lock_state *lsp,
2862 nfs_free_seqid(calldata->luargs.seqid); 3124 struct nfs_seqid *seqid)
2863 nfs4_put_lock_state(calldata->lsp); 3125{
2864 put_nfs_open_context(calldata->ctx); 3126 struct nfs4_unlockdata *p;
2865 kfree(calldata); 3127 struct inode *inode = lsp->ls_state->inode;
2866 } 3128
3129 p = kmalloc(sizeof(*p), GFP_KERNEL);
3130 if (p == NULL)
3131 return NULL;
3132 p->arg.fh = NFS_FH(inode);
3133 p->arg.fl = &p->fl;
3134 p->arg.seqid = seqid;
3135 p->arg.stateid = &lsp->ls_stateid;
3136 p->lsp = lsp;
3137 atomic_inc(&lsp->ls_count);
3138 /* Ensure we don't close file until we're done freeing locks! */
3139 p->ctx = get_nfs_open_context(ctx);
3140 memcpy(&p->fl, fl, sizeof(p->fl));
3141 p->server = NFS_SERVER(inode);
3142 return p;
2867} 3143}
2868 3144
2869static void nfs4_locku_complete(struct nfs4_unlockdata *calldata) 3145static void nfs4_locku_release_calldata(void *data)
2870{ 3146{
2871 complete(&calldata->completion); 3147 struct nfs4_unlockdata *calldata = data;
2872 nfs4_locku_release_calldata(calldata); 3148 nfs_free_seqid(calldata->arg.seqid);
3149 nfs4_put_lock_state(calldata->lsp);
3150 put_nfs_open_context(calldata->ctx);
3151 kfree(calldata);
2873} 3152}
2874 3153
2875static void nfs4_locku_done(struct rpc_task *task) 3154static void nfs4_locku_done(struct rpc_task *task, void *data)
2876{ 3155{
2877 struct nfs4_unlockdata *calldata = (struct nfs4_unlockdata *)task->tk_calldata; 3156 struct nfs4_unlockdata *calldata = data;
2878 3157
2879 nfs_increment_lock_seqid(task->tk_status, calldata->luargs.seqid); 3158 if (RPC_ASSASSINATED(task))
3159 return;
3160 nfs_increment_lock_seqid(task->tk_status, calldata->arg.seqid);
2880 switch (task->tk_status) { 3161 switch (task->tk_status) {
2881 case 0: 3162 case 0:
2882 memcpy(calldata->lsp->ls_stateid.data, 3163 memcpy(calldata->lsp->ls_stateid.data,
2883 calldata->res.u.stateid.data, 3164 calldata->res.stateid.data,
2884 sizeof(calldata->lsp->ls_stateid.data)); 3165 sizeof(calldata->lsp->ls_stateid.data));
3166 renew_lease(calldata->server, calldata->timestamp);
2885 break; 3167 break;
2886 case -NFS4ERR_STALE_STATEID: 3168 case -NFS4ERR_STALE_STATEID:
2887 case -NFS4ERR_EXPIRED: 3169 case -NFS4ERR_EXPIRED:
2888 nfs4_schedule_state_recovery(calldata->res.server->nfs4_state); 3170 nfs4_schedule_state_recovery(calldata->server->nfs4_state);
2889 break; 3171 break;
2890 default: 3172 default:
2891 if (nfs4_async_handle_error(task, calldata->res.server) == -EAGAIN) { 3173 if (nfs4_async_handle_error(task, calldata->server) == -EAGAIN) {
2892 rpc_restart_call(task); 3174 rpc_restart_call(task);
2893 return;
2894 } 3175 }
2895 } 3176 }
2896 nfs4_locku_complete(calldata);
2897} 3177}
2898 3178
2899static void nfs4_locku_begin(struct rpc_task *task) 3179static void nfs4_locku_prepare(struct rpc_task *task, void *data)
2900{ 3180{
2901 struct nfs4_unlockdata *calldata = (struct nfs4_unlockdata *)task->tk_calldata; 3181 struct nfs4_unlockdata *calldata = data;
2902 struct rpc_message msg = { 3182 struct rpc_message msg = {
2903 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_LOCKU], 3183 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_LOCKU],
2904 .rpc_argp = &calldata->arg, 3184 .rpc_argp = &calldata->arg,
2905 .rpc_resp = &calldata->res, 3185 .rpc_resp = &calldata->res,
2906 .rpc_cred = calldata->lsp->ls_state->owner->so_cred, 3186 .rpc_cred = calldata->lsp->ls_state->owner->so_cred,
2907 }; 3187 };
2908 int status;
2909 3188
2910 status = nfs_wait_on_sequence(calldata->luargs.seqid, task); 3189 if (nfs_wait_on_sequence(calldata->arg.seqid, task) != 0)
2911 if (status != 0)
2912 return; 3190 return;
2913 if ((calldata->lsp->ls_flags & NFS_LOCK_INITIALIZED) == 0) { 3191 if ((calldata->lsp->ls_flags & NFS_LOCK_INITIALIZED) == 0) {
2914 nfs4_locku_complete(calldata); 3192 /* Note: exit _without_ running nfs4_locku_done */
2915 task->tk_exit = NULL; 3193 task->tk_action = NULL;
2916 rpc_exit(task, 0);
2917 return; 3194 return;
2918 } 3195 }
3196 calldata->timestamp = jiffies;
2919 rpc_call_setup(task, &msg, 0); 3197 rpc_call_setup(task, &msg, 0);
2920} 3198}
2921 3199
3200static const struct rpc_call_ops nfs4_locku_ops = {
3201 .rpc_call_prepare = nfs4_locku_prepare,
3202 .rpc_call_done = nfs4_locku_done,
3203 .rpc_release = nfs4_locku_release_calldata,
3204};
3205
3206static struct rpc_task *nfs4_do_unlck(struct file_lock *fl,
3207 struct nfs_open_context *ctx,
3208 struct nfs4_lock_state *lsp,
3209 struct nfs_seqid *seqid)
3210{
3211 struct nfs4_unlockdata *data;
3212 struct rpc_task *task;
3213
3214 data = nfs4_alloc_unlockdata(fl, ctx, lsp, seqid);
3215 if (data == NULL) {
3216 nfs_free_seqid(seqid);
3217 return ERR_PTR(-ENOMEM);
3218 }
3219
3220 /* Unlock _before_ we do the RPC call */
3221 do_vfs_lock(fl->fl_file, fl);
3222 task = rpc_run_task(NFS_CLIENT(lsp->ls_state->inode), RPC_TASK_ASYNC, &nfs4_locku_ops, data);
3223 if (IS_ERR(task))
3224 nfs4_locku_release_calldata(data);
3225 return task;
3226}
3227
2922static int nfs4_proc_unlck(struct nfs4_state *state, int cmd, struct file_lock *request) 3228static int nfs4_proc_unlck(struct nfs4_state *state, int cmd, struct file_lock *request)
2923{ 3229{
2924 struct nfs4_unlockdata *calldata; 3230 struct nfs_seqid *seqid;
2925 struct inode *inode = state->inode;
2926 struct nfs_server *server = NFS_SERVER(inode);
2927 struct nfs4_lock_state *lsp; 3231 struct nfs4_lock_state *lsp;
2928 int status; 3232 struct rpc_task *task;
3233 int status = 0;
2929 3234
2930 /* Is this a delegated lock? */ 3235 /* Is this a delegated lock? */
2931 if (test_bit(NFS_DELEGATED_STATE, &state->flags)) 3236 if (test_bit(NFS_DELEGATED_STATE, &state->flags))
2932 return do_vfs_lock(request->fl_file, request); 3237 goto out_unlock;
3238 /* Is this open_owner holding any locks on the server? */
3239 if (test_bit(LK_STATE_IN_USE, &state->flags) == 0)
3240 goto out_unlock;
2933 3241
2934 status = nfs4_set_lock_state(state, request); 3242 status = nfs4_set_lock_state(state, request);
2935 if (status != 0) 3243 if (status != 0)
2936 return status; 3244 goto out_unlock;
2937 lsp = request->fl_u.nfs4_fl.owner; 3245 lsp = request->fl_u.nfs4_fl.owner;
2938 /* We might have lost the locks! */ 3246 status = -ENOMEM;
2939 if ((lsp->ls_flags & NFS_LOCK_INITIALIZED) == 0) 3247 seqid = nfs_alloc_seqid(&lsp->ls_seqid);
2940 return 0; 3248 if (seqid == NULL)
2941 calldata = kmalloc(sizeof(*calldata), GFP_KERNEL); 3249 goto out_unlock;
2942 if (calldata == NULL) 3250 task = nfs4_do_unlck(request, request->fl_file->private_data, lsp, seqid);
2943 return -ENOMEM; 3251 status = PTR_ERR(task);
2944 calldata->luargs.seqid = nfs_alloc_seqid(&lsp->ls_seqid); 3252 if (IS_ERR(task))
2945 if (calldata->luargs.seqid == NULL) { 3253 goto out_unlock;
2946 kfree(calldata); 3254 status = nfs4_wait_for_completion_rpc_task(task);
2947 return -ENOMEM; 3255 rpc_release_task(task);
2948 } 3256 return status;
2949 calldata->luargs.stateid = &lsp->ls_stateid; 3257out_unlock:
2950 calldata->arg.fh = NFS_FH(inode);
2951 calldata->arg.type = nfs4_lck_type(cmd, request);
2952 calldata->arg.offset = request->fl_start;
2953 calldata->arg.length = nfs4_lck_length(request);
2954 calldata->arg.u.locku = &calldata->luargs;
2955 calldata->res.server = server;
2956 calldata->lsp = lsp;
2957 atomic_inc(&lsp->ls_count);
2958
2959 /* Ensure we don't close file until we're done freeing locks! */
2960 calldata->ctx = get_nfs_open_context((struct nfs_open_context*)request->fl_file->private_data);
2961
2962 atomic_set(&calldata->refcount, 2);
2963 init_completion(&calldata->completion);
2964
2965 status = nfs4_call_async(NFS_SERVER(inode)->client, nfs4_locku_begin,
2966 nfs4_locku_done, calldata);
2967 if (status == 0)
2968 wait_for_completion_interruptible(&calldata->completion);
2969 do_vfs_lock(request->fl_file, request); 3258 do_vfs_lock(request->fl_file, request);
2970 nfs4_locku_release_calldata(calldata);
2971 return status; 3259 return status;
2972} 3260}
2973 3261
2974static int _nfs4_do_setlk(struct nfs4_state *state, int cmd, struct file_lock *request, int reclaim) 3262struct nfs4_lockdata {
3263 struct nfs_lock_args arg;
3264 struct nfs_lock_res res;
3265 struct nfs4_lock_state *lsp;
3266 struct nfs_open_context *ctx;
3267 struct file_lock fl;
3268 unsigned long timestamp;
3269 int rpc_status;
3270 int cancelled;
3271};
3272
3273static struct nfs4_lockdata *nfs4_alloc_lockdata(struct file_lock *fl,
3274 struct nfs_open_context *ctx, struct nfs4_lock_state *lsp)
2975{ 3275{
2976 struct inode *inode = state->inode; 3276 struct nfs4_lockdata *p;
3277 struct inode *inode = lsp->ls_state->inode;
2977 struct nfs_server *server = NFS_SERVER(inode); 3278 struct nfs_server *server = NFS_SERVER(inode);
2978 struct nfs4_lock_state *lsp = request->fl_u.nfs4_fl.owner; 3279
2979 struct nfs_lock_opargs largs = { 3280 p = kzalloc(sizeof(*p), GFP_KERNEL);
2980 .lock_stateid = &lsp->ls_stateid, 3281 if (p == NULL)
2981 .open_stateid = &state->stateid, 3282 return NULL;
2982 .lock_owner = { 3283
2983 .clientid = server->nfs4_state->cl_clientid, 3284 p->arg.fh = NFS_FH(inode);
2984 .id = lsp->ls_id, 3285 p->arg.fl = &p->fl;
2985 }, 3286 p->arg.lock_seqid = nfs_alloc_seqid(&lsp->ls_seqid);
2986 .reclaim = reclaim, 3287 if (p->arg.lock_seqid == NULL)
2987 }; 3288 goto out_free;
2988 struct nfs_lockargs arg = { 3289 p->arg.lock_stateid = &lsp->ls_stateid;
2989 .fh = NFS_FH(inode), 3290 p->arg.lock_owner.clientid = server->nfs4_state->cl_clientid;
2990 .type = nfs4_lck_type(cmd, request), 3291 p->arg.lock_owner.id = lsp->ls_id;
2991 .offset = request->fl_start, 3292 p->lsp = lsp;
2992 .length = nfs4_lck_length(request), 3293 atomic_inc(&lsp->ls_count);
2993 .u = { 3294 p->ctx = get_nfs_open_context(ctx);
2994 .lock = &largs, 3295 memcpy(&p->fl, fl, sizeof(p->fl));
2995 }, 3296 return p;
2996 }; 3297out_free:
2997 struct nfs_lockres res = { 3298 kfree(p);
2998 .server = server, 3299 return NULL;
2999 }; 3300}
3301
3302static void nfs4_lock_prepare(struct rpc_task *task, void *calldata)
3303{
3304 struct nfs4_lockdata *data = calldata;
3305 struct nfs4_state *state = data->lsp->ls_state;
3306 struct nfs4_state_owner *sp = state->owner;
3000 struct rpc_message msg = { 3307 struct rpc_message msg = {
3001 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_LOCK], 3308 .rpc_proc = &nfs4_procedures[NFSPROC4_CLNT_LOCK],
3002 .rpc_argp = &arg, 3309 .rpc_argp = &data->arg,
3003 .rpc_resp = &res, 3310 .rpc_resp = &data->res,
3004 .rpc_cred = state->owner->so_cred, 3311 .rpc_cred = sp->so_cred,
3005 }; 3312 };
3006 int status = -ENOMEM;
3007
3008 largs.lock_seqid = nfs_alloc_seqid(&lsp->ls_seqid);
3009 if (largs.lock_seqid == NULL)
3010 return -ENOMEM;
3011 if (!(lsp->ls_seqid.flags & NFS_SEQID_CONFIRMED)) {
3012 struct nfs4_state_owner *owner = state->owner;
3013 3313
3014 largs.open_seqid = nfs_alloc_seqid(&owner->so_seqid); 3314 if (nfs_wait_on_sequence(data->arg.lock_seqid, task) != 0)
3015 if (largs.open_seqid == NULL) 3315 return;
3316 dprintk("%s: begin!\n", __FUNCTION__);
3317 /* Do we need to do an open_to_lock_owner? */
3318 if (!(data->arg.lock_seqid->sequence->flags & NFS_SEQID_CONFIRMED)) {
3319 data->arg.open_seqid = nfs_alloc_seqid(&sp->so_seqid);
3320 if (data->arg.open_seqid == NULL) {
3321 data->rpc_status = -ENOMEM;
3322 task->tk_action = NULL;
3016 goto out; 3323 goto out;
3017 largs.new_lock_owner = 1;
3018 status = rpc_call_sync(server->client, &msg, RPC_TASK_NOINTR);
3019 /* increment open seqid on success, and seqid mutating errors */
3020 if (largs.new_lock_owner != 0) {
3021 nfs_increment_open_seqid(status, largs.open_seqid);
3022 if (status == 0)
3023 nfs_confirm_seqid(&lsp->ls_seqid, 0);
3024 } 3324 }
3025 nfs_free_seqid(largs.open_seqid); 3325 data->arg.open_stateid = &state->stateid;
3026 } else 3326 data->arg.new_lock_owner = 1;
3027 status = rpc_call_sync(server->client, &msg, RPC_TASK_NOINTR); 3327 }
3028 /* increment lock seqid on success, and seqid mutating errors*/ 3328 data->timestamp = jiffies;
3029 nfs_increment_lock_seqid(status, largs.lock_seqid); 3329 rpc_call_setup(task, &msg, 0);
3030 /* save the returned stateid. */
3031 if (status == 0) {
3032 memcpy(lsp->ls_stateid.data, res.u.stateid.data,
3033 sizeof(lsp->ls_stateid.data));
3034 lsp->ls_flags |= NFS_LOCK_INITIALIZED;
3035 } else if (status == -NFS4ERR_DENIED)
3036 status = -EAGAIN;
3037out: 3330out:
3038 nfs_free_seqid(largs.lock_seqid); 3331 dprintk("%s: done!, ret = %d\n", __FUNCTION__, data->rpc_status);
3039 return status; 3332}
3333
3334static void nfs4_lock_done(struct rpc_task *task, void *calldata)
3335{
3336 struct nfs4_lockdata *data = calldata;
3337
3338 dprintk("%s: begin!\n", __FUNCTION__);
3339
3340 data->rpc_status = task->tk_status;
3341 if (RPC_ASSASSINATED(task))
3342 goto out;
3343 if (data->arg.new_lock_owner != 0) {
3344 nfs_increment_open_seqid(data->rpc_status, data->arg.open_seqid);
3345 if (data->rpc_status == 0)
3346 nfs_confirm_seqid(&data->lsp->ls_seqid, 0);
3347 else
3348 goto out;
3349 }
3350 if (data->rpc_status == 0) {
3351 memcpy(data->lsp->ls_stateid.data, data->res.stateid.data,
3352 sizeof(data->lsp->ls_stateid.data));
3353 data->lsp->ls_flags |= NFS_LOCK_INITIALIZED;
3354 renew_lease(NFS_SERVER(data->ctx->dentry->d_inode), data->timestamp);
3355 }
3356 nfs_increment_lock_seqid(data->rpc_status, data->arg.lock_seqid);
3357out:
3358 dprintk("%s: done, ret = %d!\n", __FUNCTION__, data->rpc_status);
3359}
3360
3361static void nfs4_lock_release(void *calldata)
3362{
3363 struct nfs4_lockdata *data = calldata;
3364
3365 dprintk("%s: begin!\n", __FUNCTION__);
3366 if (data->arg.open_seqid != NULL)
3367 nfs_free_seqid(data->arg.open_seqid);
3368 if (data->cancelled != 0) {
3369 struct rpc_task *task;
3370 task = nfs4_do_unlck(&data->fl, data->ctx, data->lsp,
3371 data->arg.lock_seqid);
3372 if (!IS_ERR(task))
3373 rpc_release_task(task);
3374 dprintk("%s: cancelling lock!\n", __FUNCTION__);
3375 } else
3376 nfs_free_seqid(data->arg.lock_seqid);
3377 nfs4_put_lock_state(data->lsp);
3378 put_nfs_open_context(data->ctx);
3379 kfree(data);
3380 dprintk("%s: done!\n", __FUNCTION__);
3381}
3382
3383static const struct rpc_call_ops nfs4_lock_ops = {
3384 .rpc_call_prepare = nfs4_lock_prepare,
3385 .rpc_call_done = nfs4_lock_done,
3386 .rpc_release = nfs4_lock_release,
3387};
3388
3389static int _nfs4_do_setlk(struct nfs4_state *state, int cmd, struct file_lock *fl, int reclaim)
3390{
3391 struct nfs4_lockdata *data;
3392 struct rpc_task *task;
3393 int ret;
3394
3395 dprintk("%s: begin!\n", __FUNCTION__);
3396 data = nfs4_alloc_lockdata(fl, fl->fl_file->private_data,
3397 fl->fl_u.nfs4_fl.owner);
3398 if (data == NULL)
3399 return -ENOMEM;
3400 if (IS_SETLKW(cmd))
3401 data->arg.block = 1;
3402 if (reclaim != 0)
3403 data->arg.reclaim = 1;
3404 task = rpc_run_task(NFS_CLIENT(state->inode), RPC_TASK_ASYNC,
3405 &nfs4_lock_ops, data);
3406 if (IS_ERR(task)) {
3407 nfs4_lock_release(data);
3408 return PTR_ERR(task);
3409 }
3410 ret = nfs4_wait_for_completion_rpc_task(task);
3411 if (ret == 0) {
3412 ret = data->rpc_status;
3413 if (ret == -NFS4ERR_DENIED)
3414 ret = -EAGAIN;
3415 } else
3416 data->cancelled = 1;
3417 rpc_release_task(task);
3418 dprintk("%s: done, ret = %d!\n", __FUNCTION__, ret);
3419 return ret;
3040} 3420}
3041 3421
3042static int nfs4_lock_reclaim(struct nfs4_state *state, struct file_lock *request) 3422static int nfs4_lock_reclaim(struct nfs4_state *state, struct file_lock *request)
diff --git a/fs/nfs/nfs4renewd.c b/fs/nfs/nfs4renewd.c
index a3001628ad32..5d764d8e6d8a 100644
--- a/fs/nfs/nfs4renewd.c
+++ b/fs/nfs/nfs4renewd.c
@@ -54,6 +54,7 @@
54#include <linux/nfs4.h> 54#include <linux/nfs4.h>
55#include <linux/nfs_fs.h> 55#include <linux/nfs_fs.h>
56#include "nfs4_fs.h" 56#include "nfs4_fs.h"
57#include "delegation.h"
57 58
58#define NFSDBG_FACILITY NFSDBG_PROC 59#define NFSDBG_FACILITY NFSDBG_PROC
59 60
@@ -61,6 +62,7 @@ void
61nfs4_renew_state(void *data) 62nfs4_renew_state(void *data)
62{ 63{
63 struct nfs4_client *clp = (struct nfs4_client *)data; 64 struct nfs4_client *clp = (struct nfs4_client *)data;
65 struct rpc_cred *cred;
64 long lease, timeout; 66 long lease, timeout;
65 unsigned long last, now; 67 unsigned long last, now;
66 68
@@ -68,7 +70,7 @@ nfs4_renew_state(void *data)
68 dprintk("%s: start\n", __FUNCTION__); 70 dprintk("%s: start\n", __FUNCTION__);
69 /* Are there any active superblocks? */ 71 /* Are there any active superblocks? */
70 if (list_empty(&clp->cl_superblocks)) 72 if (list_empty(&clp->cl_superblocks))
71 goto out; 73 goto out;
72 spin_lock(&clp->cl_lock); 74 spin_lock(&clp->cl_lock);
73 lease = clp->cl_lease_time; 75 lease = clp->cl_lease_time;
74 last = clp->cl_last_renewal; 76 last = clp->cl_last_renewal;
@@ -76,9 +78,17 @@ nfs4_renew_state(void *data)
76 timeout = (2 * lease) / 3 + (long)last - (long)now; 78 timeout = (2 * lease) / 3 + (long)last - (long)now;
77 /* Are we close to a lease timeout? */ 79 /* Are we close to a lease timeout? */
78 if (time_after(now, last + lease/3)) { 80 if (time_after(now, last + lease/3)) {
81 cred = nfs4_get_renew_cred(clp);
82 if (cred == NULL) {
83 set_bit(NFS4CLNT_LEASE_EXPIRED, &clp->cl_state);
84 spin_unlock(&clp->cl_lock);
85 nfs_expire_all_delegations(clp);
86 goto out;
87 }
79 spin_unlock(&clp->cl_lock); 88 spin_unlock(&clp->cl_lock);
80 /* Queue an asynchronous RENEW. */ 89 /* Queue an asynchronous RENEW. */
81 nfs4_proc_async_renew(clp); 90 nfs4_proc_async_renew(clp, cred);
91 put_rpccred(cred);
82 timeout = (2 * lease) / 3; 92 timeout = (2 * lease) / 3;
83 spin_lock(&clp->cl_lock); 93 spin_lock(&clp->cl_lock);
84 } else 94 } else
diff --git a/fs/nfs/nfs4state.c b/fs/nfs/nfs4state.c
index 5ef4c57618fe..afad0255e7db 100644
--- a/fs/nfs/nfs4state.c
+++ b/fs/nfs/nfs4state.c
@@ -43,6 +43,8 @@
43#include <linux/smp_lock.h> 43#include <linux/smp_lock.h>
44#include <linux/nfs_fs.h> 44#include <linux/nfs_fs.h>
45#include <linux/nfs_idmap.h> 45#include <linux/nfs_idmap.h>
46#include <linux/kthread.h>
47#include <linux/module.h>
46#include <linux/workqueue.h> 48#include <linux/workqueue.h>
47#include <linux/bitops.h> 49#include <linux/bitops.h>
48 50
@@ -57,8 +59,6 @@ const nfs4_stateid zero_stateid;
57static DEFINE_SPINLOCK(state_spinlock); 59static DEFINE_SPINLOCK(state_spinlock);
58static LIST_HEAD(nfs4_clientid_list); 60static LIST_HEAD(nfs4_clientid_list);
59 61
60static void nfs4_recover_state(void *);
61
62void 62void
63init_nfsv4_state(struct nfs_server *server) 63init_nfsv4_state(struct nfs_server *server)
64{ 64{
@@ -91,11 +91,10 @@ nfs4_alloc_client(struct in_addr *addr)
91 91
92 if (nfs_callback_up() < 0) 92 if (nfs_callback_up() < 0)
93 return NULL; 93 return NULL;
94 if ((clp = kmalloc(sizeof(*clp), GFP_KERNEL)) == NULL) { 94 if ((clp = kzalloc(sizeof(*clp), GFP_KERNEL)) == NULL) {
95 nfs_callback_down(); 95 nfs_callback_down();
96 return NULL; 96 return NULL;
97 } 97 }
98 memset(clp, 0, sizeof(*clp));
99 memcpy(&clp->cl_addr, addr, sizeof(clp->cl_addr)); 98 memcpy(&clp->cl_addr, addr, sizeof(clp->cl_addr));
100 init_rwsem(&clp->cl_sem); 99 init_rwsem(&clp->cl_sem);
101 INIT_LIST_HEAD(&clp->cl_delegations); 100 INIT_LIST_HEAD(&clp->cl_delegations);
@@ -103,14 +102,12 @@ nfs4_alloc_client(struct in_addr *addr)
103 INIT_LIST_HEAD(&clp->cl_unused); 102 INIT_LIST_HEAD(&clp->cl_unused);
104 spin_lock_init(&clp->cl_lock); 103 spin_lock_init(&clp->cl_lock);
105 atomic_set(&clp->cl_count, 1); 104 atomic_set(&clp->cl_count, 1);
106 INIT_WORK(&clp->cl_recoverd, nfs4_recover_state, clp);
107 INIT_WORK(&clp->cl_renewd, nfs4_renew_state, clp); 105 INIT_WORK(&clp->cl_renewd, nfs4_renew_state, clp);
108 INIT_LIST_HEAD(&clp->cl_superblocks); 106 INIT_LIST_HEAD(&clp->cl_superblocks);
109 init_waitqueue_head(&clp->cl_waitq);
110 rpc_init_wait_queue(&clp->cl_rpcwaitq, "NFS4 client"); 107 rpc_init_wait_queue(&clp->cl_rpcwaitq, "NFS4 client");
111 clp->cl_rpcclient = ERR_PTR(-EINVAL); 108 clp->cl_rpcclient = ERR_PTR(-EINVAL);
112 clp->cl_boot_time = CURRENT_TIME; 109 clp->cl_boot_time = CURRENT_TIME;
113 clp->cl_state = 1 << NFS4CLNT_OK; 110 clp->cl_state = 1 << NFS4CLNT_LEASE_EXPIRED;
114 return clp; 111 return clp;
115} 112}
116 113
@@ -127,8 +124,6 @@ nfs4_free_client(struct nfs4_client *clp)
127 kfree(sp); 124 kfree(sp);
128 } 125 }
129 BUG_ON(!list_empty(&clp->cl_state_owners)); 126 BUG_ON(!list_empty(&clp->cl_state_owners));
130 if (clp->cl_cred)
131 put_rpccred(clp->cl_cred);
132 nfs_idmap_delete(clp); 127 nfs_idmap_delete(clp);
133 if (!IS_ERR(clp->cl_rpcclient)) 128 if (!IS_ERR(clp->cl_rpcclient))
134 rpc_shutdown_client(clp->cl_rpcclient); 129 rpc_shutdown_client(clp->cl_rpcclient);
@@ -193,27 +188,22 @@ nfs4_put_client(struct nfs4_client *clp)
193 list_del(&clp->cl_servers); 188 list_del(&clp->cl_servers);
194 spin_unlock(&state_spinlock); 189 spin_unlock(&state_spinlock);
195 BUG_ON(!list_empty(&clp->cl_superblocks)); 190 BUG_ON(!list_empty(&clp->cl_superblocks));
196 wake_up_all(&clp->cl_waitq);
197 rpc_wake_up(&clp->cl_rpcwaitq); 191 rpc_wake_up(&clp->cl_rpcwaitq);
198 nfs4_kill_renewd(clp); 192 nfs4_kill_renewd(clp);
199 nfs4_free_client(clp); 193 nfs4_free_client(clp);
200} 194}
201 195
202static int __nfs4_init_client(struct nfs4_client *clp) 196static int nfs4_init_client(struct nfs4_client *clp, struct rpc_cred *cred)
203{ 197{
204 int status = nfs4_proc_setclientid(clp, NFS4_CALLBACK, nfs_callback_tcpport); 198 int status = nfs4_proc_setclientid(clp, NFS4_CALLBACK,
199 nfs_callback_tcpport, cred);
205 if (status == 0) 200 if (status == 0)
206 status = nfs4_proc_setclientid_confirm(clp); 201 status = nfs4_proc_setclientid_confirm(clp, cred);
207 if (status == 0) 202 if (status == 0)
208 nfs4_schedule_state_renewal(clp); 203 nfs4_schedule_state_renewal(clp);
209 return status; 204 return status;
210} 205}
211 206
212int nfs4_init_client(struct nfs4_client *clp)
213{
214 return nfs4_map_errors(__nfs4_init_client(clp));
215}
216
217u32 207u32
218nfs4_alloc_lockowner_id(struct nfs4_client *clp) 208nfs4_alloc_lockowner_id(struct nfs4_client *clp)
219{ 209{
@@ -235,6 +225,32 @@ nfs4_client_grab_unused(struct nfs4_client *clp, struct rpc_cred *cred)
235 return sp; 225 return sp;
236} 226}
237 227
228struct rpc_cred *nfs4_get_renew_cred(struct nfs4_client *clp)
229{
230 struct nfs4_state_owner *sp;
231 struct rpc_cred *cred = NULL;
232
233 list_for_each_entry(sp, &clp->cl_state_owners, so_list) {
234 if (list_empty(&sp->so_states))
235 continue;
236 cred = get_rpccred(sp->so_cred);
237 break;
238 }
239 return cred;
240}
241
242struct rpc_cred *nfs4_get_setclientid_cred(struct nfs4_client *clp)
243{
244 struct nfs4_state_owner *sp;
245
246 if (!list_empty(&clp->cl_state_owners)) {
247 sp = list_entry(clp->cl_state_owners.next,
248 struct nfs4_state_owner, so_list);
249 return get_rpccred(sp->so_cred);
250 }
251 return NULL;
252}
253
238static struct nfs4_state_owner * 254static struct nfs4_state_owner *
239nfs4_find_state_owner(struct nfs4_client *clp, struct rpc_cred *cred) 255nfs4_find_state_owner(struct nfs4_client *clp, struct rpc_cred *cred)
240{ 256{
@@ -349,14 +365,9 @@ nfs4_alloc_open_state(void)
349{ 365{
350 struct nfs4_state *state; 366 struct nfs4_state *state;
351 367
352 state = kmalloc(sizeof(*state), GFP_KERNEL); 368 state = kzalloc(sizeof(*state), GFP_KERNEL);
353 if (!state) 369 if (!state)
354 return NULL; 370 return NULL;
355 state->state = 0;
356 state->nreaders = 0;
357 state->nwriters = 0;
358 state->flags = 0;
359 memset(state->stateid.data, 0, sizeof(state->stateid.data));
360 atomic_set(&state->count, 1); 371 atomic_set(&state->count, 1);
361 INIT_LIST_HEAD(&state->lock_states); 372 INIT_LIST_HEAD(&state->lock_states);
362 spin_lock_init(&state->state_lock); 373 spin_lock_init(&state->state_lock);
@@ -475,15 +486,23 @@ void nfs4_close_state(struct nfs4_state *state, mode_t mode)
475 /* Protect against nfs4_find_state() */ 486 /* Protect against nfs4_find_state() */
476 spin_lock(&owner->so_lock); 487 spin_lock(&owner->so_lock);
477 spin_lock(&inode->i_lock); 488 spin_lock(&inode->i_lock);
478 if (mode & FMODE_READ) 489 switch (mode & (FMODE_READ | FMODE_WRITE)) {
479 state->nreaders--; 490 case FMODE_READ:
480 if (mode & FMODE_WRITE) 491 state->n_rdonly--;
481 state->nwriters--; 492 break;
493 case FMODE_WRITE:
494 state->n_wronly--;
495 break;
496 case FMODE_READ|FMODE_WRITE:
497 state->n_rdwr--;
498 }
482 oldstate = newstate = state->state; 499 oldstate = newstate = state->state;
483 if (state->nreaders == 0) 500 if (state->n_rdwr == 0) {
484 newstate &= ~FMODE_READ; 501 if (state->n_rdonly == 0)
485 if (state->nwriters == 0) 502 newstate &= ~FMODE_READ;
486 newstate &= ~FMODE_WRITE; 503 if (state->n_wronly == 0)
504 newstate &= ~FMODE_WRITE;
505 }
487 if (test_bit(NFS_DELEGATED_STATE, &state->flags)) { 506 if (test_bit(NFS_DELEGATED_STATE, &state->flags)) {
488 nfs4_state_set_mode_locked(state, newstate); 507 nfs4_state_set_mode_locked(state, newstate);
489 oldstate = newstate; 508 oldstate = newstate;
@@ -733,45 +752,43 @@ out:
733} 752}
734 753
735static int reclaimer(void *); 754static int reclaimer(void *);
736struct reclaimer_args { 755
737 struct nfs4_client *clp; 756static inline void nfs4_clear_recover_bit(struct nfs4_client *clp)
738 struct completion complete; 757{
739}; 758 smp_mb__before_clear_bit();
759 clear_bit(NFS4CLNT_STATE_RECOVER, &clp->cl_state);
760 smp_mb__after_clear_bit();
761 wake_up_bit(&clp->cl_state, NFS4CLNT_STATE_RECOVER);
762 rpc_wake_up(&clp->cl_rpcwaitq);
763}
740 764
741/* 765/*
742 * State recovery routine 766 * State recovery routine
743 */ 767 */
744void 768static void nfs4_recover_state(struct nfs4_client *clp)
745nfs4_recover_state(void *data)
746{ 769{
747 struct nfs4_client *clp = (struct nfs4_client *)data; 770 struct task_struct *task;
748 struct reclaimer_args args = {
749 .clp = clp,
750 };
751 might_sleep();
752
753 init_completion(&args.complete);
754 771
755 if (kernel_thread(reclaimer, &args, CLONE_KERNEL) < 0) 772 __module_get(THIS_MODULE);
756 goto out_failed_clear; 773 atomic_inc(&clp->cl_count);
757 wait_for_completion(&args.complete); 774 task = kthread_run(reclaimer, clp, "%u.%u.%u.%u-reclaim",
758 return; 775 NIPQUAD(clp->cl_addr));
759out_failed_clear: 776 if (!IS_ERR(task))
760 set_bit(NFS4CLNT_OK, &clp->cl_state); 777 return;
761 wake_up_all(&clp->cl_waitq); 778 nfs4_clear_recover_bit(clp);
762 rpc_wake_up(&clp->cl_rpcwaitq); 779 nfs4_put_client(clp);
780 module_put(THIS_MODULE);
763} 781}
764 782
765/* 783/*
766 * Schedule a state recovery attempt 784 * Schedule a state recovery attempt
767 */ 785 */
768void 786void nfs4_schedule_state_recovery(struct nfs4_client *clp)
769nfs4_schedule_state_recovery(struct nfs4_client *clp)
770{ 787{
771 if (!clp) 788 if (!clp)
772 return; 789 return;
773 if (test_and_clear_bit(NFS4CLNT_OK, &clp->cl_state)) 790 if (test_and_set_bit(NFS4CLNT_STATE_RECOVER, &clp->cl_state) == 0)
774 schedule_work(&clp->cl_recoverd); 791 nfs4_recover_state(clp);
775} 792}
776 793
777static int nfs4_reclaim_locks(struct nfs4_state_recovery_ops *ops, struct nfs4_state *state) 794static int nfs4_reclaim_locks(struct nfs4_state_recovery_ops *ops, struct nfs4_state *state)
@@ -887,18 +904,14 @@ static void nfs4_state_mark_reclaim(struct nfs4_client *clp)
887 904
888static int reclaimer(void *ptr) 905static int reclaimer(void *ptr)
889{ 906{
890 struct reclaimer_args *args = (struct reclaimer_args *)ptr; 907 struct nfs4_client *clp = ptr;
891 struct nfs4_client *clp = args->clp;
892 struct nfs4_state_owner *sp; 908 struct nfs4_state_owner *sp;
893 struct nfs4_state_recovery_ops *ops; 909 struct nfs4_state_recovery_ops *ops;
910 struct rpc_cred *cred;
894 int status = 0; 911 int status = 0;
895 912
896 daemonize("%u.%u.%u.%u-reclaim", NIPQUAD(clp->cl_addr));
897 allow_signal(SIGKILL); 913 allow_signal(SIGKILL);
898 914
899 atomic_inc(&clp->cl_count);
900 complete(&args->complete);
901
902 /* Ensure exclusive access to NFSv4 state */ 915 /* Ensure exclusive access to NFSv4 state */
903 lock_kernel(); 916 lock_kernel();
904 down_write(&clp->cl_sem); 917 down_write(&clp->cl_sem);
@@ -906,20 +919,33 @@ static int reclaimer(void *ptr)
906 if (list_empty(&clp->cl_superblocks)) 919 if (list_empty(&clp->cl_superblocks))
907 goto out; 920 goto out;
908restart_loop: 921restart_loop:
909 status = nfs4_proc_renew(clp); 922 ops = &nfs4_network_partition_recovery_ops;
910 switch (status) { 923 /* Are there any open files on this volume? */
911 case 0: 924 cred = nfs4_get_renew_cred(clp);
912 case -NFS4ERR_CB_PATH_DOWN: 925 if (cred != NULL) {
913 goto out; 926 /* Yes there are: try to renew the old lease */
914 case -NFS4ERR_STALE_CLIENTID: 927 status = nfs4_proc_renew(clp, cred);
915 case -NFS4ERR_LEASE_MOVED: 928 switch (status) {
916 ops = &nfs4_reboot_recovery_ops; 929 case 0:
917 break; 930 case -NFS4ERR_CB_PATH_DOWN:
918 default: 931 put_rpccred(cred);
919 ops = &nfs4_network_partition_recovery_ops; 932 goto out;
920 }; 933 case -NFS4ERR_STALE_CLIENTID:
934 case -NFS4ERR_LEASE_MOVED:
935 ops = &nfs4_reboot_recovery_ops;
936 }
937 } else {
938 /* "reboot" to ensure we clear all state on the server */
939 clp->cl_boot_time = CURRENT_TIME;
940 cred = nfs4_get_setclientid_cred(clp);
941 }
942 /* We're going to have to re-establish a clientid */
921 nfs4_state_mark_reclaim(clp); 943 nfs4_state_mark_reclaim(clp);
922 status = __nfs4_init_client(clp); 944 status = -ENOENT;
945 if (cred != NULL) {
946 status = nfs4_init_client(clp, cred);
947 put_rpccred(cred);
948 }
923 if (status) 949 if (status)
924 goto out_error; 950 goto out_error;
925 /* Mark all delegations for reclaim */ 951 /* Mark all delegations for reclaim */
@@ -940,14 +966,13 @@ restart_loop:
940 } 966 }
941 nfs_delegation_reap_unclaimed(clp); 967 nfs_delegation_reap_unclaimed(clp);
942out: 968out:
943 set_bit(NFS4CLNT_OK, &clp->cl_state);
944 up_write(&clp->cl_sem); 969 up_write(&clp->cl_sem);
945 unlock_kernel(); 970 unlock_kernel();
946 wake_up_all(&clp->cl_waitq);
947 rpc_wake_up(&clp->cl_rpcwaitq);
948 if (status == -NFS4ERR_CB_PATH_DOWN) 971 if (status == -NFS4ERR_CB_PATH_DOWN)
949 nfs_handle_cb_pathdown(clp); 972 nfs_handle_cb_pathdown(clp);
973 nfs4_clear_recover_bit(clp);
950 nfs4_put_client(clp); 974 nfs4_put_client(clp);
975 module_put_and_exit(0);
951 return 0; 976 return 0;
952out_error: 977out_error:
953 printk(KERN_WARNING "Error: state recovery failed on NFSv4 server %u.%u.%u.%u with error %d\n", 978 printk(KERN_WARNING "Error: state recovery failed on NFSv4 server %u.%u.%u.%u with error %d\n",
diff --git a/fs/nfs/nfs4xdr.c b/fs/nfs/nfs4xdr.c
index fbbace8a30c4..4bbf5ef57785 100644
--- a/fs/nfs/nfs4xdr.c
+++ b/fs/nfs/nfs4xdr.c
@@ -392,9 +392,11 @@ static int nfs_stat_to_errno(int);
392 decode_getattr_maxsz) 392 decode_getattr_maxsz)
393#define NFS4_enc_delegreturn_sz (compound_encode_hdr_maxsz + \ 393#define NFS4_enc_delegreturn_sz (compound_encode_hdr_maxsz + \
394 encode_putfh_maxsz + \ 394 encode_putfh_maxsz + \
395 encode_delegreturn_maxsz) 395 encode_delegreturn_maxsz + \
396 encode_getattr_maxsz)
396#define NFS4_dec_delegreturn_sz (compound_decode_hdr_maxsz + \ 397#define NFS4_dec_delegreturn_sz (compound_decode_hdr_maxsz + \
397 decode_delegreturn_maxsz) 398 decode_delegreturn_maxsz + \
399 decode_getattr_maxsz)
398#define NFS4_enc_getacl_sz (compound_encode_hdr_maxsz + \ 400#define NFS4_enc_getacl_sz (compound_encode_hdr_maxsz + \
399 encode_putfh_maxsz + \ 401 encode_putfh_maxsz + \
400 encode_getattr_maxsz) 402 encode_getattr_maxsz)
@@ -564,7 +566,7 @@ static int encode_attrs(struct xdr_stream *xdr, const struct iattr *iap, const s
564 } 566 }
565 if (iap->ia_valid & ATTR_MODE) { 567 if (iap->ia_valid & ATTR_MODE) {
566 bmval1 |= FATTR4_WORD1_MODE; 568 bmval1 |= FATTR4_WORD1_MODE;
567 WRITE32(iap->ia_mode); 569 WRITE32(iap->ia_mode & S_IALLUGO);
568 } 570 }
569 if (iap->ia_valid & ATTR_UID) { 571 if (iap->ia_valid & ATTR_UID) {
570 bmval1 |= FATTR4_WORD1_OWNER; 572 bmval1 |= FATTR4_WORD1_OWNER;
@@ -742,69 +744,80 @@ static int encode_link(struct xdr_stream *xdr, const struct qstr *name)
742 return 0; 744 return 0;
743} 745}
744 746
747static inline int nfs4_lock_type(struct file_lock *fl, int block)
748{
749 if ((fl->fl_type & (F_RDLCK|F_WRLCK|F_UNLCK)) == F_RDLCK)
750 return block ? NFS4_READW_LT : NFS4_READ_LT;
751 return block ? NFS4_WRITEW_LT : NFS4_WRITE_LT;
752}
753
754static inline uint64_t nfs4_lock_length(struct file_lock *fl)
755{
756 if (fl->fl_end == OFFSET_MAX)
757 return ~(uint64_t)0;
758 return fl->fl_end - fl->fl_start + 1;
759}
760
745/* 761/*
746 * opcode,type,reclaim,offset,length,new_lock_owner = 32 762 * opcode,type,reclaim,offset,length,new_lock_owner = 32
747 * open_seqid,open_stateid,lock_seqid,lock_owner.clientid, lock_owner.id = 40 763 * open_seqid,open_stateid,lock_seqid,lock_owner.clientid, lock_owner.id = 40
748 */ 764 */
749static int encode_lock(struct xdr_stream *xdr, const struct nfs_lockargs *arg) 765static int encode_lock(struct xdr_stream *xdr, const struct nfs_lock_args *args)
750{ 766{
751 uint32_t *p; 767 uint32_t *p;
752 struct nfs_lock_opargs *opargs = arg->u.lock;
753 768
754 RESERVE_SPACE(32); 769 RESERVE_SPACE(32);
755 WRITE32(OP_LOCK); 770 WRITE32(OP_LOCK);
756 WRITE32(arg->type); 771 WRITE32(nfs4_lock_type(args->fl, args->block));
757 WRITE32(opargs->reclaim); 772 WRITE32(args->reclaim);
758 WRITE64(arg->offset); 773 WRITE64(args->fl->fl_start);
759 WRITE64(arg->length); 774 WRITE64(nfs4_lock_length(args->fl));
760 WRITE32(opargs->new_lock_owner); 775 WRITE32(args->new_lock_owner);
761 if (opargs->new_lock_owner){ 776 if (args->new_lock_owner){
762 RESERVE_SPACE(40); 777 RESERVE_SPACE(40);
763 WRITE32(opargs->open_seqid->sequence->counter); 778 WRITE32(args->open_seqid->sequence->counter);
764 WRITEMEM(opargs->open_stateid->data, sizeof(opargs->open_stateid->data)); 779 WRITEMEM(args->open_stateid->data, sizeof(args->open_stateid->data));
765 WRITE32(opargs->lock_seqid->sequence->counter); 780 WRITE32(args->lock_seqid->sequence->counter);
766 WRITE64(opargs->lock_owner.clientid); 781 WRITE64(args->lock_owner.clientid);
767 WRITE32(4); 782 WRITE32(4);
768 WRITE32(opargs->lock_owner.id); 783 WRITE32(args->lock_owner.id);
769 } 784 }
770 else { 785 else {
771 RESERVE_SPACE(20); 786 RESERVE_SPACE(20);
772 WRITEMEM(opargs->lock_stateid->data, sizeof(opargs->lock_stateid->data)); 787 WRITEMEM(args->lock_stateid->data, sizeof(args->lock_stateid->data));
773 WRITE32(opargs->lock_seqid->sequence->counter); 788 WRITE32(args->lock_seqid->sequence->counter);
774 } 789 }
775 790
776 return 0; 791 return 0;
777} 792}
778 793
779static int encode_lockt(struct xdr_stream *xdr, const struct nfs_lockargs *arg) 794static int encode_lockt(struct xdr_stream *xdr, const struct nfs_lockt_args *args)
780{ 795{
781 uint32_t *p; 796 uint32_t *p;
782 struct nfs_lowner *opargs = arg->u.lockt;
783 797
784 RESERVE_SPACE(40); 798 RESERVE_SPACE(40);
785 WRITE32(OP_LOCKT); 799 WRITE32(OP_LOCKT);
786 WRITE32(arg->type); 800 WRITE32(nfs4_lock_type(args->fl, 0));
787 WRITE64(arg->offset); 801 WRITE64(args->fl->fl_start);
788 WRITE64(arg->length); 802 WRITE64(nfs4_lock_length(args->fl));
789 WRITE64(opargs->clientid); 803 WRITE64(args->lock_owner.clientid);
790 WRITE32(4); 804 WRITE32(4);
791 WRITE32(opargs->id); 805 WRITE32(args->lock_owner.id);
792 806
793 return 0; 807 return 0;
794} 808}
795 809
796static int encode_locku(struct xdr_stream *xdr, const struct nfs_lockargs *arg) 810static int encode_locku(struct xdr_stream *xdr, const struct nfs_locku_args *args)
797{ 811{
798 uint32_t *p; 812 uint32_t *p;
799 struct nfs_locku_opargs *opargs = arg->u.locku;
800 813
801 RESERVE_SPACE(44); 814 RESERVE_SPACE(44);
802 WRITE32(OP_LOCKU); 815 WRITE32(OP_LOCKU);
803 WRITE32(arg->type); 816 WRITE32(nfs4_lock_type(args->fl, 0));
804 WRITE32(opargs->seqid->sequence->counter); 817 WRITE32(args->seqid->sequence->counter);
805 WRITEMEM(opargs->stateid->data, sizeof(opargs->stateid->data)); 818 WRITEMEM(args->stateid->data, sizeof(args->stateid->data));
806 WRITE64(arg->offset); 819 WRITE64(args->fl->fl_start);
807 WRITE64(arg->length); 820 WRITE64(nfs4_lock_length(args->fl));
808 821
809 return 0; 822 return 0;
810} 823}
@@ -964,9 +977,9 @@ static int encode_open_confirm(struct xdr_stream *xdr, const struct nfs_open_con
964{ 977{
965 uint32_t *p; 978 uint32_t *p;
966 979
967 RESERVE_SPACE(8+sizeof(arg->stateid.data)); 980 RESERVE_SPACE(8+sizeof(arg->stateid->data));
968 WRITE32(OP_OPEN_CONFIRM); 981 WRITE32(OP_OPEN_CONFIRM);
969 WRITEMEM(arg->stateid.data, sizeof(arg->stateid.data)); 982 WRITEMEM(arg->stateid->data, sizeof(arg->stateid->data));
970 WRITE32(arg->seqid->sequence->counter); 983 WRITE32(arg->seqid->sequence->counter);
971 984
972 return 0; 985 return 0;
@@ -1499,9 +1512,6 @@ static int nfs4_xdr_enc_open(struct rpc_rqst *req, uint32_t *p, struct nfs_opena
1499 }; 1512 };
1500 int status; 1513 int status;
1501 1514
1502 status = nfs_wait_on_sequence(args->seqid, req->rq_task);
1503 if (status != 0)
1504 goto out;
1505 xdr_init_encode(&xdr, &req->rq_snd_buf, p); 1515 xdr_init_encode(&xdr, &req->rq_snd_buf, p);
1506 encode_compound_hdr(&xdr, &hdr); 1516 encode_compound_hdr(&xdr, &hdr);
1507 status = encode_putfh(&xdr, args->fh); 1517 status = encode_putfh(&xdr, args->fh);
@@ -1538,9 +1548,6 @@ static int nfs4_xdr_enc_open_confirm(struct rpc_rqst *req, uint32_t *p, struct n
1538 }; 1548 };
1539 int status; 1549 int status;
1540 1550
1541 status = nfs_wait_on_sequence(args->seqid, req->rq_task);
1542 if (status != 0)
1543 goto out;
1544 xdr_init_encode(&xdr, &req->rq_snd_buf, p); 1551 xdr_init_encode(&xdr, &req->rq_snd_buf, p);
1545 encode_compound_hdr(&xdr, &hdr); 1552 encode_compound_hdr(&xdr, &hdr);
1546 status = encode_putfh(&xdr, args->fh); 1553 status = encode_putfh(&xdr, args->fh);
@@ -1558,19 +1565,19 @@ static int nfs4_xdr_enc_open_noattr(struct rpc_rqst *req, uint32_t *p, struct nf
1558{ 1565{
1559 struct xdr_stream xdr; 1566 struct xdr_stream xdr;
1560 struct compound_hdr hdr = { 1567 struct compound_hdr hdr = {
1561 .nops = 2, 1568 .nops = 3,
1562 }; 1569 };
1563 int status; 1570 int status;
1564 1571
1565 status = nfs_wait_on_sequence(args->seqid, req->rq_task);
1566 if (status != 0)
1567 goto out;
1568 xdr_init_encode(&xdr, &req->rq_snd_buf, p); 1572 xdr_init_encode(&xdr, &req->rq_snd_buf, p);
1569 encode_compound_hdr(&xdr, &hdr); 1573 encode_compound_hdr(&xdr, &hdr);
1570 status = encode_putfh(&xdr, args->fh); 1574 status = encode_putfh(&xdr, args->fh);
1571 if (status) 1575 if (status)
1572 goto out; 1576 goto out;
1573 status = encode_open(&xdr, args); 1577 status = encode_open(&xdr, args);
1578 if (status)
1579 goto out;
1580 status = encode_getfattr(&xdr, args->bitmask);
1574out: 1581out:
1575 return status; 1582 return status;
1576} 1583}
@@ -1602,21 +1609,14 @@ out:
1602/* 1609/*
1603 * Encode a LOCK request 1610 * Encode a LOCK request
1604 */ 1611 */
1605static int nfs4_xdr_enc_lock(struct rpc_rqst *req, uint32_t *p, struct nfs_lockargs *args) 1612static int nfs4_xdr_enc_lock(struct rpc_rqst *req, uint32_t *p, struct nfs_lock_args *args)
1606{ 1613{
1607 struct xdr_stream xdr; 1614 struct xdr_stream xdr;
1608 struct compound_hdr hdr = { 1615 struct compound_hdr hdr = {
1609 .nops = 2, 1616 .nops = 2,
1610 }; 1617 };
1611 struct nfs_lock_opargs *opargs = args->u.lock;
1612 int status; 1618 int status;
1613 1619
1614 status = nfs_wait_on_sequence(opargs->lock_seqid, req->rq_task);
1615 if (status != 0)
1616 goto out;
1617 /* Do we need to do an open_to_lock_owner? */
1618 if (opargs->lock_seqid->sequence->flags & NFS_SEQID_CONFIRMED)
1619 opargs->new_lock_owner = 0;
1620 xdr_init_encode(&xdr, &req->rq_snd_buf, p); 1620 xdr_init_encode(&xdr, &req->rq_snd_buf, p);
1621 encode_compound_hdr(&xdr, &hdr); 1621 encode_compound_hdr(&xdr, &hdr);
1622 status = encode_putfh(&xdr, args->fh); 1622 status = encode_putfh(&xdr, args->fh);
@@ -1630,7 +1630,7 @@ out:
1630/* 1630/*
1631 * Encode a LOCKT request 1631 * Encode a LOCKT request
1632 */ 1632 */
1633static int nfs4_xdr_enc_lockt(struct rpc_rqst *req, uint32_t *p, struct nfs_lockargs *args) 1633static int nfs4_xdr_enc_lockt(struct rpc_rqst *req, uint32_t *p, struct nfs_lockt_args *args)
1634{ 1634{
1635 struct xdr_stream xdr; 1635 struct xdr_stream xdr;
1636 struct compound_hdr hdr = { 1636 struct compound_hdr hdr = {
@@ -1651,7 +1651,7 @@ out:
1651/* 1651/*
1652 * Encode a LOCKU request 1652 * Encode a LOCKU request
1653 */ 1653 */
1654static int nfs4_xdr_enc_locku(struct rpc_rqst *req, uint32_t *p, struct nfs_lockargs *args) 1654static int nfs4_xdr_enc_locku(struct rpc_rqst *req, uint32_t *p, struct nfs_locku_args *args)
1655{ 1655{
1656 struct xdr_stream xdr; 1656 struct xdr_stream xdr;
1657 struct compound_hdr hdr = { 1657 struct compound_hdr hdr = {
@@ -1985,14 +1985,20 @@ static int nfs4_xdr_enc_delegreturn(struct rpc_rqst *req, uint32_t *p, const str
1985{ 1985{
1986 struct xdr_stream xdr; 1986 struct xdr_stream xdr;
1987 struct compound_hdr hdr = { 1987 struct compound_hdr hdr = {
1988 .nops = 2, 1988 .nops = 3,
1989 }; 1989 };
1990 int status; 1990 int status;
1991 1991
1992 xdr_init_encode(&xdr, &req->rq_snd_buf, p); 1992 xdr_init_encode(&xdr, &req->rq_snd_buf, p);
1993 encode_compound_hdr(&xdr, &hdr); 1993 encode_compound_hdr(&xdr, &hdr);
1994 if ((status = encode_putfh(&xdr, args->fhandle)) == 0) 1994 status = encode_putfh(&xdr, args->fhandle);
1995 status = encode_delegreturn(&xdr, args->stateid); 1995 if (status != 0)
1996 goto out;
1997 status = encode_delegreturn(&xdr, args->stateid);
1998 if (status != 0)
1999 goto out;
2000 status = encode_getfattr(&xdr, args->bitmask);
2001out:
1996 return status; 2002 return status;
1997} 2003}
1998 2004
@@ -2955,55 +2961,64 @@ static int decode_link(struct xdr_stream *xdr, struct nfs4_change_info *cinfo)
2955/* 2961/*
2956 * We create the owner, so we know a proper owner.id length is 4. 2962 * We create the owner, so we know a proper owner.id length is 4.
2957 */ 2963 */
2958static int decode_lock_denied (struct xdr_stream *xdr, struct nfs_lock_denied *denied) 2964static int decode_lock_denied (struct xdr_stream *xdr, struct file_lock *fl)
2959{ 2965{
2966 uint64_t offset, length, clientid;
2960 uint32_t *p; 2967 uint32_t *p;
2961 uint32_t namelen; 2968 uint32_t namelen, type;
2962 2969
2963 READ_BUF(32); 2970 READ_BUF(32);
2964 READ64(denied->offset); 2971 READ64(offset);
2965 READ64(denied->length); 2972 READ64(length);
2966 READ32(denied->type); 2973 READ32(type);
2967 READ64(denied->owner.clientid); 2974 if (fl != NULL) {
2975 fl->fl_start = (loff_t)offset;
2976 fl->fl_end = fl->fl_start + (loff_t)length - 1;
2977 if (length == ~(uint64_t)0)
2978 fl->fl_end = OFFSET_MAX;
2979 fl->fl_type = F_WRLCK;
2980 if (type & 1)
2981 fl->fl_type = F_RDLCK;
2982 fl->fl_pid = 0;
2983 }
2984 READ64(clientid);
2968 READ32(namelen); 2985 READ32(namelen);
2969 READ_BUF(namelen); 2986 READ_BUF(namelen);
2970 if (namelen == 4)
2971 READ32(denied->owner.id);
2972 return -NFS4ERR_DENIED; 2987 return -NFS4ERR_DENIED;
2973} 2988}
2974 2989
2975static int decode_lock(struct xdr_stream *xdr, struct nfs_lockres *res) 2990static int decode_lock(struct xdr_stream *xdr, struct nfs_lock_res *res)
2976{ 2991{
2977 uint32_t *p; 2992 uint32_t *p;
2978 int status; 2993 int status;
2979 2994
2980 status = decode_op_hdr(xdr, OP_LOCK); 2995 status = decode_op_hdr(xdr, OP_LOCK);
2981 if (status == 0) { 2996 if (status == 0) {
2982 READ_BUF(sizeof(res->u.stateid.data)); 2997 READ_BUF(sizeof(res->stateid.data));
2983 COPYMEM(res->u.stateid.data, sizeof(res->u.stateid.data)); 2998 COPYMEM(res->stateid.data, sizeof(res->stateid.data));
2984 } else if (status == -NFS4ERR_DENIED) 2999 } else if (status == -NFS4ERR_DENIED)
2985 return decode_lock_denied(xdr, &res->u.denied); 3000 return decode_lock_denied(xdr, NULL);
2986 return status; 3001 return status;
2987} 3002}
2988 3003
2989static int decode_lockt(struct xdr_stream *xdr, struct nfs_lockres *res) 3004static int decode_lockt(struct xdr_stream *xdr, struct nfs_lockt_res *res)
2990{ 3005{
2991 int status; 3006 int status;
2992 status = decode_op_hdr(xdr, OP_LOCKT); 3007 status = decode_op_hdr(xdr, OP_LOCKT);
2993 if (status == -NFS4ERR_DENIED) 3008 if (status == -NFS4ERR_DENIED)
2994 return decode_lock_denied(xdr, &res->u.denied); 3009 return decode_lock_denied(xdr, res->denied);
2995 return status; 3010 return status;
2996} 3011}
2997 3012
2998static int decode_locku(struct xdr_stream *xdr, struct nfs_lockres *res) 3013static int decode_locku(struct xdr_stream *xdr, struct nfs_locku_res *res)
2999{ 3014{
3000 uint32_t *p; 3015 uint32_t *p;
3001 int status; 3016 int status;
3002 3017
3003 status = decode_op_hdr(xdr, OP_LOCKU); 3018 status = decode_op_hdr(xdr, OP_LOCKU);
3004 if (status == 0) { 3019 if (status == 0) {
3005 READ_BUF(sizeof(res->u.stateid.data)); 3020 READ_BUF(sizeof(res->stateid.data));
3006 COPYMEM(res->u.stateid.data, sizeof(res->u.stateid.data)); 3021 COPYMEM(res->stateid.data, sizeof(res->stateid.data));
3007 } 3022 }
3008 return status; 3023 return status;
3009} 3024}
@@ -3831,6 +3846,9 @@ static int nfs4_xdr_dec_open_noattr(struct rpc_rqst *rqstp, uint32_t *p, struct
3831 if (status) 3846 if (status)
3832 goto out; 3847 goto out;
3833 status = decode_open(&xdr, res); 3848 status = decode_open(&xdr, res);
3849 if (status)
3850 goto out;
3851 decode_getfattr(&xdr, res->f_attr, res->server);
3834out: 3852out:
3835 return status; 3853 return status;
3836} 3854}
@@ -3864,7 +3882,7 @@ out:
3864/* 3882/*
3865 * Decode LOCK response 3883 * Decode LOCK response
3866 */ 3884 */
3867static int nfs4_xdr_dec_lock(struct rpc_rqst *rqstp, uint32_t *p, struct nfs_lockres *res) 3885static int nfs4_xdr_dec_lock(struct rpc_rqst *rqstp, uint32_t *p, struct nfs_lock_res *res)
3868{ 3886{
3869 struct xdr_stream xdr; 3887 struct xdr_stream xdr;
3870 struct compound_hdr hdr; 3888 struct compound_hdr hdr;
@@ -3885,7 +3903,7 @@ out:
3885/* 3903/*
3886 * Decode LOCKT response 3904 * Decode LOCKT response
3887 */ 3905 */
3888static int nfs4_xdr_dec_lockt(struct rpc_rqst *rqstp, uint32_t *p, struct nfs_lockres *res) 3906static int nfs4_xdr_dec_lockt(struct rpc_rqst *rqstp, uint32_t *p, struct nfs_lockt_res *res)
3889{ 3907{
3890 struct xdr_stream xdr; 3908 struct xdr_stream xdr;
3891 struct compound_hdr hdr; 3909 struct compound_hdr hdr;
@@ -3906,7 +3924,7 @@ out:
3906/* 3924/*
3907 * Decode LOCKU response 3925 * Decode LOCKU response
3908 */ 3926 */
3909static int nfs4_xdr_dec_locku(struct rpc_rqst *rqstp, uint32_t *p, struct nfs_lockres *res) 3927static int nfs4_xdr_dec_locku(struct rpc_rqst *rqstp, uint32_t *p, struct nfs_locku_res *res)
3910{ 3928{
3911 struct xdr_stream xdr; 3929 struct xdr_stream xdr;
3912 struct compound_hdr hdr; 3930 struct compound_hdr hdr;
@@ -4174,7 +4192,7 @@ static int nfs4_xdr_dec_setclientid_confirm(struct rpc_rqst *req, uint32_t *p, s
4174/* 4192/*
4175 * DELEGRETURN request 4193 * DELEGRETURN request
4176 */ 4194 */
4177static int nfs4_xdr_dec_delegreturn(struct rpc_rqst *rqstp, uint32_t *p, void *dummy) 4195static int nfs4_xdr_dec_delegreturn(struct rpc_rqst *rqstp, uint32_t *p, struct nfs4_delegreturnres *res)
4178{ 4196{
4179 struct xdr_stream xdr; 4197 struct xdr_stream xdr;
4180 struct compound_hdr hdr; 4198 struct compound_hdr hdr;
@@ -4182,11 +4200,14 @@ static int nfs4_xdr_dec_delegreturn(struct rpc_rqst *rqstp, uint32_t *p, void *d
4182 4200
4183 xdr_init_decode(&xdr, &rqstp->rq_rcv_buf, p); 4201 xdr_init_decode(&xdr, &rqstp->rq_rcv_buf, p);
4184 status = decode_compound_hdr(&xdr, &hdr); 4202 status = decode_compound_hdr(&xdr, &hdr);
4185 if (status == 0) { 4203 if (status != 0)
4186 status = decode_putfh(&xdr); 4204 goto out;
4187 if (status == 0) 4205 status = decode_putfh(&xdr);
4188 status = decode_delegreturn(&xdr); 4206 if (status != 0)
4189 } 4207 goto out;
4208 status = decode_delegreturn(&xdr);
4209 decode_getfattr(&xdr, res->fattr, res->server);
4210out:
4190 return status; 4211 return status;
4191} 4212}
4192 4213
diff --git a/fs/nfs/nfsroot.c b/fs/nfs/nfsroot.c
index 1b272a135a31..985cc53b8dd5 100644
--- a/fs/nfs/nfsroot.c
+++ b/fs/nfs/nfsroot.c
@@ -296,8 +296,8 @@ static int __init root_nfs_name(char *name)
296 nfs_port = -1; 296 nfs_port = -1;
297 nfs_data.version = NFS_MOUNT_VERSION; 297 nfs_data.version = NFS_MOUNT_VERSION;
298 nfs_data.flags = NFS_MOUNT_NONLM; /* No lockd in nfs root yet */ 298 nfs_data.flags = NFS_MOUNT_NONLM; /* No lockd in nfs root yet */
299 nfs_data.rsize = NFS_DEF_FILE_IO_BUFFER_SIZE; 299 nfs_data.rsize = NFS_DEF_FILE_IO_SIZE;
300 nfs_data.wsize = NFS_DEF_FILE_IO_BUFFER_SIZE; 300 nfs_data.wsize = NFS_DEF_FILE_IO_SIZE;
301 nfs_data.acregmin = 3; 301 nfs_data.acregmin = 3;
302 nfs_data.acregmax = 60; 302 nfs_data.acregmax = 60;
303 nfs_data.acdirmin = 30; 303 nfs_data.acdirmin = 30;
diff --git a/fs/nfs/proc.c b/fs/nfs/proc.c
index e1e3ca5d746b..f5150d71c03d 100644
--- a/fs/nfs/proc.c
+++ b/fs/nfs/proc.c
@@ -111,6 +111,9 @@ nfs_proc_setattr(struct dentry *dentry, struct nfs_fattr *fattr,
111 }; 111 };
112 int status; 112 int status;
113 113
114 /* Mask out the non-modebit related stuff from attr->ia_mode */
115 sattr->ia_mode &= S_IALLUGO;
116
114 dprintk("NFS call setattr\n"); 117 dprintk("NFS call setattr\n");
115 nfs_fattr_init(fattr); 118 nfs_fattr_init(fattr);
116 status = rpc_call(NFS_CLIENT(inode), NFSPROC_SETATTR, &arg, fattr, 0); 119 status = rpc_call(NFS_CLIENT(inode), NFSPROC_SETATTR, &arg, fattr, 0);
@@ -547,10 +550,9 @@ nfs_proc_pathconf(struct nfs_server *server, struct nfs_fh *fhandle,
547 550
548extern u32 * nfs_decode_dirent(u32 *, struct nfs_entry *, int); 551extern u32 * nfs_decode_dirent(u32 *, struct nfs_entry *, int);
549 552
550static void 553static void nfs_read_done(struct rpc_task *task, void *calldata)
551nfs_read_done(struct rpc_task *task)
552{ 554{
553 struct nfs_read_data *data = (struct nfs_read_data *) task->tk_calldata; 555 struct nfs_read_data *data = calldata;
554 556
555 if (task->tk_status >= 0) { 557 if (task->tk_status >= 0) {
556 nfs_refresh_inode(data->inode, data->res.fattr); 558 nfs_refresh_inode(data->inode, data->res.fattr);
@@ -560,9 +562,14 @@ nfs_read_done(struct rpc_task *task)
560 if (data->args.offset + data->args.count >= data->res.fattr->size) 562 if (data->args.offset + data->args.count >= data->res.fattr->size)
561 data->res.eof = 1; 563 data->res.eof = 1;
562 } 564 }
563 nfs_readpage_result(task); 565 nfs_readpage_result(task, calldata);
564} 566}
565 567
568static const struct rpc_call_ops nfs_read_ops = {
569 .rpc_call_done = nfs_read_done,
570 .rpc_release = nfs_readdata_release,
571};
572
566static void 573static void
567nfs_proc_read_setup(struct nfs_read_data *data) 574nfs_proc_read_setup(struct nfs_read_data *data)
568{ 575{
@@ -580,20 +587,24 @@ nfs_proc_read_setup(struct nfs_read_data *data)
580 flags = RPC_TASK_ASYNC | (IS_SWAPFILE(inode)? NFS_RPC_SWAPFLAGS : 0); 587 flags = RPC_TASK_ASYNC | (IS_SWAPFILE(inode)? NFS_RPC_SWAPFLAGS : 0);
581 588
582 /* Finalize the task. */ 589 /* Finalize the task. */
583 rpc_init_task(task, NFS_CLIENT(inode), nfs_read_done, flags); 590 rpc_init_task(task, NFS_CLIENT(inode), flags, &nfs_read_ops, data);
584 rpc_call_setup(task, &msg, 0); 591 rpc_call_setup(task, &msg, 0);
585} 592}
586 593
587static void 594static void nfs_write_done(struct rpc_task *task, void *calldata)
588nfs_write_done(struct rpc_task *task)
589{ 595{
590 struct nfs_write_data *data = (struct nfs_write_data *) task->tk_calldata; 596 struct nfs_write_data *data = calldata;
591 597
592 if (task->tk_status >= 0) 598 if (task->tk_status >= 0)
593 nfs_post_op_update_inode(data->inode, data->res.fattr); 599 nfs_post_op_update_inode(data->inode, data->res.fattr);
594 nfs_writeback_done(task); 600 nfs_writeback_done(task, calldata);
595} 601}
596 602
603static const struct rpc_call_ops nfs_write_ops = {
604 .rpc_call_done = nfs_write_done,
605 .rpc_release = nfs_writedata_release,
606};
607
597static void 608static void
598nfs_proc_write_setup(struct nfs_write_data *data, int how) 609nfs_proc_write_setup(struct nfs_write_data *data, int how)
599{ 610{
@@ -614,7 +625,7 @@ nfs_proc_write_setup(struct nfs_write_data *data, int how)
614 flags = (how & FLUSH_SYNC) ? 0 : RPC_TASK_ASYNC; 625 flags = (how & FLUSH_SYNC) ? 0 : RPC_TASK_ASYNC;
615 626
616 /* Finalize the task. */ 627 /* Finalize the task. */
617 rpc_init_task(task, NFS_CLIENT(inode), nfs_write_done, flags); 628 rpc_init_task(task, NFS_CLIENT(inode), flags, &nfs_write_ops, data);
618 rpc_call_setup(task, &msg, 0); 629 rpc_call_setup(task, &msg, 0);
619} 630}
620 631
diff --git a/fs/nfs/read.c b/fs/nfs/read.c
index 5f20eafba8ec..05eb43fadf8e 100644
--- a/fs/nfs/read.c
+++ b/fs/nfs/read.c
@@ -42,9 +42,8 @@ mempool_t *nfs_rdata_mempool;
42 42
43#define MIN_POOL_READ (32) 43#define MIN_POOL_READ (32)
44 44
45void nfs_readdata_release(struct rpc_task *task) 45void nfs_readdata_release(void *data)
46{ 46{
47 struct nfs_read_data *data = (struct nfs_read_data *)task->tk_calldata;
48 nfs_readdata_free(data); 47 nfs_readdata_free(data);
49} 48}
50 49
@@ -84,7 +83,7 @@ static int nfs_readpage_sync(struct nfs_open_context *ctx, struct inode *inode,
84 int result; 83 int result;
85 struct nfs_read_data *rdata; 84 struct nfs_read_data *rdata;
86 85
87 rdata = nfs_readdata_alloc(); 86 rdata = nfs_readdata_alloc(1);
88 if (!rdata) 87 if (!rdata)
89 return -ENOMEM; 88 return -ENOMEM;
90 89
@@ -220,9 +219,6 @@ static void nfs_read_rpcsetup(struct nfs_page *req, struct nfs_read_data *data,
220 NFS_PROTO(inode)->read_setup(data); 219 NFS_PROTO(inode)->read_setup(data);
221 220
222 data->task.tk_cookie = (unsigned long)inode; 221 data->task.tk_cookie = (unsigned long)inode;
223 data->task.tk_calldata = data;
224 /* Release requests */
225 data->task.tk_release = nfs_readdata_release;
226 222
227 dprintk("NFS: %4d initiated read call (req %s/%Ld, %u bytes @ offset %Lu)\n", 223 dprintk("NFS: %4d initiated read call (req %s/%Ld, %u bytes @ offset %Lu)\n",
228 data->task.tk_pid, 224 data->task.tk_pid,
@@ -287,7 +283,7 @@ static int nfs_pagein_multi(struct list_head *head, struct inode *inode)
287 283
288 nbytes = req->wb_bytes; 284 nbytes = req->wb_bytes;
289 for(;;) { 285 for(;;) {
290 data = nfs_readdata_alloc(); 286 data = nfs_readdata_alloc(1);
291 if (!data) 287 if (!data)
292 goto out_bad; 288 goto out_bad;
293 INIT_LIST_HEAD(&data->pages); 289 INIT_LIST_HEAD(&data->pages);
@@ -343,7 +339,7 @@ static int nfs_pagein_one(struct list_head *head, struct inode *inode)
343 if (NFS_SERVER(inode)->rsize < PAGE_CACHE_SIZE) 339 if (NFS_SERVER(inode)->rsize < PAGE_CACHE_SIZE)
344 return nfs_pagein_multi(head, inode); 340 return nfs_pagein_multi(head, inode);
345 341
346 data = nfs_readdata_alloc(); 342 data = nfs_readdata_alloc(NFS_SERVER(inode)->rpages);
347 if (!data) 343 if (!data)
348 goto out_bad; 344 goto out_bad;
349 345
@@ -452,9 +448,9 @@ static void nfs_readpage_result_full(struct nfs_read_data *data, int status)
452 * This is the callback from RPC telling us whether a reply was 448 * This is the callback from RPC telling us whether a reply was
453 * received or some error occurred (timeout or socket shutdown). 449 * received or some error occurred (timeout or socket shutdown).
454 */ 450 */
455void nfs_readpage_result(struct rpc_task *task) 451void nfs_readpage_result(struct rpc_task *task, void *calldata)
456{ 452{
457 struct nfs_read_data *data = (struct nfs_read_data *)task->tk_calldata; 453 struct nfs_read_data *data = calldata;
458 struct nfs_readargs *argp = &data->args; 454 struct nfs_readargs *argp = &data->args;
459 struct nfs_readres *resp = &data->res; 455 struct nfs_readres *resp = &data->res;
460 int status = task->tk_status; 456 int status = task->tk_status;
diff --git a/fs/nfs/sysctl.c b/fs/nfs/sysctl.c
new file mode 100644
index 000000000000..4c486eb867ca
--- /dev/null
+++ b/fs/nfs/sysctl.c
@@ -0,0 +1,84 @@
1/*
2 * linux/fs/nfs/sysctl.c
3 *
4 * Sysctl interface to NFS parameters
5 */
6#include <linux/config.h>
7#include <linux/types.h>
8#include <linux/linkage.h>
9#include <linux/ctype.h>
10#include <linux/fs.h>
11#include <linux/sysctl.h>
12#include <linux/module.h>
13#include <linux/nfs4.h>
14#include <linux/nfs_idmap.h>
15
16#include "callback.h"
17
18static const int nfs_set_port_min = 0;
19static const int nfs_set_port_max = 65535;
20static struct ctl_table_header *nfs_callback_sysctl_table;
21/*
22 * Something that isn't CTL_ANY, CTL_NONE or a value that may clash.
23 * Use the same values as fs/lockd/svc.c
24 */
25#define CTL_UNNUMBERED -2
26
27static ctl_table nfs_cb_sysctls[] = {
28#ifdef CONFIG_NFS_V4
29 {
30 .ctl_name = CTL_UNNUMBERED,
31 .procname = "nfs_callback_tcpport",
32 .data = &nfs_callback_set_tcpport,
33 .maxlen = sizeof(int),
34 .mode = 0644,
35 .proc_handler = &proc_dointvec_minmax,
36 .extra1 = (int *)&nfs_set_port_min,
37 .extra2 = (int *)&nfs_set_port_max,
38 },
39 {
40 .ctl_name = CTL_UNNUMBERED,
41 .procname = "idmap_cache_timeout",
42 .data = &nfs_idmap_cache_timeout,
43 .maxlen = sizeof(int),
44 .mode = 0644,
45 .proc_handler = &proc_dointvec_jiffies,
46 .strategy = &sysctl_jiffies,
47 },
48#endif
49 { .ctl_name = 0 }
50};
51
52static ctl_table nfs_cb_sysctl_dir[] = {
53 {
54 .ctl_name = CTL_UNNUMBERED,
55 .procname = "nfs",
56 .mode = 0555,
57 .child = nfs_cb_sysctls,
58 },
59 { .ctl_name = 0 }
60};
61
62static ctl_table nfs_cb_sysctl_root[] = {
63 {
64 .ctl_name = CTL_FS,
65 .procname = "fs",
66 .mode = 0555,
67 .child = nfs_cb_sysctl_dir,
68 },
69 { .ctl_name = 0 }
70};
71
72int nfs_register_sysctl(void)
73{
74 nfs_callback_sysctl_table = register_sysctl_table(nfs_cb_sysctl_root, 0);
75 if (nfs_callback_sysctl_table == NULL)
76 return -ENOMEM;
77 return 0;
78}
79
80void nfs_unregister_sysctl(void)
81{
82 unregister_sysctl_table(nfs_callback_sysctl_table);
83 nfs_callback_sysctl_table = NULL;
84}
diff --git a/fs/nfs/unlink.c b/fs/nfs/unlink.c
index d639d172d568..a65c7b53d558 100644
--- a/fs/nfs/unlink.c
+++ b/fs/nfs/unlink.c
@@ -87,10 +87,9 @@ nfs_copy_dname(struct dentry *dentry, struct nfs_unlinkdata *data)
87 * We delay initializing RPC info until after the call to dentry_iput() 87 * We delay initializing RPC info until after the call to dentry_iput()
88 * in order to minimize races against rename(). 88 * in order to minimize races against rename().
89 */ 89 */
90static void 90static void nfs_async_unlink_init(struct rpc_task *task, void *calldata)
91nfs_async_unlink_init(struct rpc_task *task)
92{ 91{
93 struct nfs_unlinkdata *data = (struct nfs_unlinkdata *)task->tk_calldata; 92 struct nfs_unlinkdata *data = calldata;
94 struct dentry *dir = data->dir; 93 struct dentry *dir = data->dir;
95 struct rpc_message msg = { 94 struct rpc_message msg = {
96 .rpc_cred = data->cred, 95 .rpc_cred = data->cred,
@@ -116,10 +115,9 @@ nfs_async_unlink_init(struct rpc_task *task)
116 * 115 *
117 * Do the directory attribute update. 116 * Do the directory attribute update.
118 */ 117 */
119static void 118static void nfs_async_unlink_done(struct rpc_task *task, void *calldata)
120nfs_async_unlink_done(struct rpc_task *task)
121{ 119{
122 struct nfs_unlinkdata *data = (struct nfs_unlinkdata *)task->tk_calldata; 120 struct nfs_unlinkdata *data = calldata;
123 struct dentry *dir = data->dir; 121 struct dentry *dir = data->dir;
124 struct inode *dir_i; 122 struct inode *dir_i;
125 123
@@ -141,13 +139,18 @@ nfs_async_unlink_done(struct rpc_task *task)
141 * We need to call nfs_put_unlinkdata as a 'tk_release' task since the 139 * We need to call nfs_put_unlinkdata as a 'tk_release' task since the
142 * rpc_task would be freed too. 140 * rpc_task would be freed too.
143 */ 141 */
144static void 142static void nfs_async_unlink_release(void *calldata)
145nfs_async_unlink_release(struct rpc_task *task)
146{ 143{
147 struct nfs_unlinkdata *data = (struct nfs_unlinkdata *)task->tk_calldata; 144 struct nfs_unlinkdata *data = calldata;
148 nfs_put_unlinkdata(data); 145 nfs_put_unlinkdata(data);
149} 146}
150 147
148static const struct rpc_call_ops nfs_unlink_ops = {
149 .rpc_call_prepare = nfs_async_unlink_init,
150 .rpc_call_done = nfs_async_unlink_done,
151 .rpc_release = nfs_async_unlink_release,
152};
153
151/** 154/**
152 * nfs_async_unlink - asynchronous unlinking of a file 155 * nfs_async_unlink - asynchronous unlinking of a file
153 * @dentry: dentry to unlink 156 * @dentry: dentry to unlink
@@ -157,7 +160,6 @@ nfs_async_unlink(struct dentry *dentry)
157{ 160{
158 struct dentry *dir = dentry->d_parent; 161 struct dentry *dir = dentry->d_parent;
159 struct nfs_unlinkdata *data; 162 struct nfs_unlinkdata *data;
160 struct rpc_task *task;
161 struct rpc_clnt *clnt = NFS_CLIENT(dir->d_inode); 163 struct rpc_clnt *clnt = NFS_CLIENT(dir->d_inode);
162 int status = -ENOMEM; 164 int status = -ENOMEM;
163 165
@@ -178,17 +180,13 @@ nfs_async_unlink(struct dentry *dentry)
178 nfs_deletes = data; 180 nfs_deletes = data;
179 data->count = 1; 181 data->count = 1;
180 182
181 task = &data->task; 183 rpc_init_task(&data->task, clnt, RPC_TASK_ASYNC, &nfs_unlink_ops, data);
182 rpc_init_task(task, clnt, nfs_async_unlink_done , RPC_TASK_ASYNC);
183 task->tk_calldata = data;
184 task->tk_action = nfs_async_unlink_init;
185 task->tk_release = nfs_async_unlink_release;
186 184
187 spin_lock(&dentry->d_lock); 185 spin_lock(&dentry->d_lock);
188 dentry->d_flags |= DCACHE_NFSFS_RENAMED; 186 dentry->d_flags |= DCACHE_NFSFS_RENAMED;
189 spin_unlock(&dentry->d_lock); 187 spin_unlock(&dentry->d_lock);
190 188
191 rpc_sleep_on(&nfs_delete_queue, task, NULL, NULL); 189 rpc_sleep_on(&nfs_delete_queue, &data->task, NULL, NULL);
192 status = 0; 190 status = 0;
193 out: 191 out:
194 return status; 192 return status;
diff --git a/fs/nfs/write.c b/fs/nfs/write.c
index 3107908e5f3f..9449b6835509 100644
--- a/fs/nfs/write.c
+++ b/fs/nfs/write.c
@@ -89,24 +89,38 @@ static mempool_t *nfs_commit_mempool;
89 89
90static DECLARE_WAIT_QUEUE_HEAD(nfs_write_congestion); 90static DECLARE_WAIT_QUEUE_HEAD(nfs_write_congestion);
91 91
92static inline struct nfs_write_data *nfs_commit_alloc(void) 92static inline struct nfs_write_data *nfs_commit_alloc(unsigned int pagecount)
93{ 93{
94 struct nfs_write_data *p = mempool_alloc(nfs_commit_mempool, SLAB_NOFS); 94 struct nfs_write_data *p = mempool_alloc(nfs_commit_mempool, SLAB_NOFS);
95
95 if (p) { 96 if (p) {
96 memset(p, 0, sizeof(*p)); 97 memset(p, 0, sizeof(*p));
97 INIT_LIST_HEAD(&p->pages); 98 INIT_LIST_HEAD(&p->pages);
99 if (pagecount < NFS_PAGEVEC_SIZE)
100 p->pagevec = &p->page_array[0];
101 else {
102 size_t size = ++pagecount * sizeof(struct page *);
103 p->pagevec = kmalloc(size, GFP_NOFS);
104 if (p->pagevec) {
105 memset(p->pagevec, 0, size);
106 } else {
107 mempool_free(p, nfs_commit_mempool);
108 p = NULL;
109 }
110 }
98 } 111 }
99 return p; 112 return p;
100} 113}
101 114
102static inline void nfs_commit_free(struct nfs_write_data *p) 115static inline void nfs_commit_free(struct nfs_write_data *p)
103{ 116{
117 if (p && (p->pagevec != &p->page_array[0]))
118 kfree(p->pagevec);
104 mempool_free(p, nfs_commit_mempool); 119 mempool_free(p, nfs_commit_mempool);
105} 120}
106 121
107static void nfs_writedata_release(struct rpc_task *task) 122void nfs_writedata_release(void *wdata)
108{ 123{
109 struct nfs_write_data *wdata = (struct nfs_write_data *)task->tk_calldata;
110 nfs_writedata_free(wdata); 124 nfs_writedata_free(wdata);
111} 125}
112 126
@@ -168,7 +182,7 @@ static int nfs_writepage_sync(struct nfs_open_context *ctx, struct inode *inode,
168 int result, written = 0; 182 int result, written = 0;
169 struct nfs_write_data *wdata; 183 struct nfs_write_data *wdata;
170 184
171 wdata = nfs_writedata_alloc(); 185 wdata = nfs_writedata_alloc(1);
172 if (!wdata) 186 if (!wdata)
173 return -ENOMEM; 187 return -ENOMEM;
174 188
@@ -232,19 +246,16 @@ static int nfs_writepage_async(struct nfs_open_context *ctx,
232 unsigned int offset, unsigned int count) 246 unsigned int offset, unsigned int count)
233{ 247{
234 struct nfs_page *req; 248 struct nfs_page *req;
235 int status;
236 249
237 req = nfs_update_request(ctx, inode, page, offset, count); 250 req = nfs_update_request(ctx, inode, page, offset, count);
238 status = (IS_ERR(req)) ? PTR_ERR(req) : 0; 251 if (IS_ERR(req))
239 if (status < 0) 252 return PTR_ERR(req);
240 goto out;
241 /* Update file length */ 253 /* Update file length */
242 nfs_grow_file(page, offset, count); 254 nfs_grow_file(page, offset, count);
243 /* Set the PG_uptodate flag? */ 255 /* Set the PG_uptodate flag? */
244 nfs_mark_uptodate(page, offset, count); 256 nfs_mark_uptodate(page, offset, count);
245 nfs_unlock_request(req); 257 nfs_unlock_request(req);
246 out: 258 return 0;
247 return status;
248} 259}
249 260
250static int wb_priority(struct writeback_control *wbc) 261static int wb_priority(struct writeback_control *wbc)
@@ -304,11 +315,8 @@ do_it:
304 lock_kernel(); 315 lock_kernel();
305 if (!IS_SYNC(inode) && inode_referenced) { 316 if (!IS_SYNC(inode) && inode_referenced) {
306 err = nfs_writepage_async(ctx, inode, page, 0, offset); 317 err = nfs_writepage_async(ctx, inode, page, 0, offset);
307 if (err >= 0) { 318 if (!wbc->for_writepages)
308 err = 0; 319 nfs_flush_inode(inode, 0, 0, wb_priority(wbc));
309 if (wbc->for_reclaim)
310 nfs_flush_inode(inode, 0, 0, FLUSH_STABLE);
311 }
312 } else { 320 } else {
313 err = nfs_writepage_sync(ctx, inode, page, 0, 321 err = nfs_writepage_sync(ctx, inode, page, 0,
314 offset, priority); 322 offset, priority);
@@ -877,9 +885,6 @@ static void nfs_write_rpcsetup(struct nfs_page *req,
877 885
878 data->task.tk_priority = flush_task_priority(how); 886 data->task.tk_priority = flush_task_priority(how);
879 data->task.tk_cookie = (unsigned long)inode; 887 data->task.tk_cookie = (unsigned long)inode;
880 data->task.tk_calldata = data;
881 /* Release requests */
882 data->task.tk_release = nfs_writedata_release;
883 888
884 dprintk("NFS: %4d initiated write call (req %s/%Ld, %u bytes @ offset %Lu)\n", 889 dprintk("NFS: %4d initiated write call (req %s/%Ld, %u bytes @ offset %Lu)\n",
885 data->task.tk_pid, 890 data->task.tk_pid,
@@ -919,7 +924,7 @@ static int nfs_flush_multi(struct list_head *head, struct inode *inode, int how)
919 924
920 nbytes = req->wb_bytes; 925 nbytes = req->wb_bytes;
921 for (;;) { 926 for (;;) {
922 data = nfs_writedata_alloc(); 927 data = nfs_writedata_alloc(1);
923 if (!data) 928 if (!data)
924 goto out_bad; 929 goto out_bad;
925 list_add(&data->pages, &list); 930 list_add(&data->pages, &list);
@@ -983,7 +988,7 @@ static int nfs_flush_one(struct list_head *head, struct inode *inode, int how)
983 if (NFS_SERVER(inode)->wsize < PAGE_CACHE_SIZE) 988 if (NFS_SERVER(inode)->wsize < PAGE_CACHE_SIZE)
984 return nfs_flush_multi(head, inode, how); 989 return nfs_flush_multi(head, inode, how);
985 990
986 data = nfs_writedata_alloc(); 991 data = nfs_writedata_alloc(NFS_SERVER(inode)->wpages);
987 if (!data) 992 if (!data)
988 goto out_bad; 993 goto out_bad;
989 994
@@ -1137,9 +1142,9 @@ static void nfs_writeback_done_full(struct nfs_write_data *data, int status)
1137/* 1142/*
1138 * This function is called when the WRITE call is complete. 1143 * This function is called when the WRITE call is complete.
1139 */ 1144 */
1140void nfs_writeback_done(struct rpc_task *task) 1145void nfs_writeback_done(struct rpc_task *task, void *calldata)
1141{ 1146{
1142 struct nfs_write_data *data = (struct nfs_write_data *) task->tk_calldata; 1147 struct nfs_write_data *data = calldata;
1143 struct nfs_writeargs *argp = &data->args; 1148 struct nfs_writeargs *argp = &data->args;
1144 struct nfs_writeres *resp = &data->res; 1149 struct nfs_writeres *resp = &data->res;
1145 1150
@@ -1206,9 +1211,8 @@ void nfs_writeback_done(struct rpc_task *task)
1206 1211
1207 1212
1208#if defined(CONFIG_NFS_V3) || defined(CONFIG_NFS_V4) 1213#if defined(CONFIG_NFS_V3) || defined(CONFIG_NFS_V4)
1209static void nfs_commit_release(struct rpc_task *task) 1214void nfs_commit_release(void *wdata)
1210{ 1215{
1211 struct nfs_write_data *wdata = (struct nfs_write_data *)task->tk_calldata;
1212 nfs_commit_free(wdata); 1216 nfs_commit_free(wdata);
1213} 1217}
1214 1218
@@ -1244,9 +1248,6 @@ static void nfs_commit_rpcsetup(struct list_head *head,
1244 1248
1245 data->task.tk_priority = flush_task_priority(how); 1249 data->task.tk_priority = flush_task_priority(how);
1246 data->task.tk_cookie = (unsigned long)inode; 1250 data->task.tk_cookie = (unsigned long)inode;
1247 data->task.tk_calldata = data;
1248 /* Release requests */
1249 data->task.tk_release = nfs_commit_release;
1250 1251
1251 dprintk("NFS: %4d initiated commit call\n", data->task.tk_pid); 1252 dprintk("NFS: %4d initiated commit call\n", data->task.tk_pid);
1252} 1253}
@@ -1255,12 +1256,12 @@ static void nfs_commit_rpcsetup(struct list_head *head,
1255 * Commit dirty pages 1256 * Commit dirty pages
1256 */ 1257 */
1257static int 1258static int
1258nfs_commit_list(struct list_head *head, int how) 1259nfs_commit_list(struct inode *inode, struct list_head *head, int how)
1259{ 1260{
1260 struct nfs_write_data *data; 1261 struct nfs_write_data *data;
1261 struct nfs_page *req; 1262 struct nfs_page *req;
1262 1263
1263 data = nfs_commit_alloc(); 1264 data = nfs_commit_alloc(NFS_SERVER(inode)->wpages);
1264 1265
1265 if (!data) 1266 if (!data)
1266 goto out_bad; 1267 goto out_bad;
@@ -1283,10 +1284,9 @@ nfs_commit_list(struct list_head *head, int how)
1283/* 1284/*
1284 * COMMIT call returned 1285 * COMMIT call returned
1285 */ 1286 */
1286void 1287void nfs_commit_done(struct rpc_task *task, void *calldata)
1287nfs_commit_done(struct rpc_task *task)
1288{ 1288{
1289 struct nfs_write_data *data = (struct nfs_write_data *)task->tk_calldata; 1289 struct nfs_write_data *data = calldata;
1290 struct nfs_page *req; 1290 struct nfs_page *req;
1291 int res = 0; 1291 int res = 0;
1292 1292
@@ -1366,7 +1366,7 @@ int nfs_commit_inode(struct inode *inode, int how)
1366 res = nfs_scan_commit(inode, &head, 0, 0); 1366 res = nfs_scan_commit(inode, &head, 0, 0);
1367 spin_unlock(&nfsi->req_lock); 1367 spin_unlock(&nfsi->req_lock);
1368 if (res) { 1368 if (res) {
1369 error = nfs_commit_list(&head, how); 1369 error = nfs_commit_list(inode, &head, how);
1370 if (error < 0) 1370 if (error < 0)
1371 return error; 1371 return error;
1372 } 1372 }
@@ -1377,22 +1377,23 @@ int nfs_commit_inode(struct inode *inode, int how)
1377int nfs_sync_inode(struct inode *inode, unsigned long idx_start, 1377int nfs_sync_inode(struct inode *inode, unsigned long idx_start,
1378 unsigned int npages, int how) 1378 unsigned int npages, int how)
1379{ 1379{
1380 int error, 1380 int nocommit = how & FLUSH_NOCOMMIT;
1381 wait; 1381 int wait = how & FLUSH_WAIT;
1382 int error;
1382 1383
1383 wait = how & FLUSH_WAIT; 1384 how &= ~(FLUSH_WAIT|FLUSH_NOCOMMIT);
1384 how &= ~FLUSH_WAIT;
1385 1385
1386 do { 1386 do {
1387 error = 0; 1387 if (wait) {
1388 if (wait)
1389 error = nfs_wait_on_requests(inode, idx_start, npages); 1388 error = nfs_wait_on_requests(inode, idx_start, npages);
1390 if (error == 0) 1389 if (error != 0)
1391 error = nfs_flush_inode(inode, idx_start, npages, how); 1390 continue;
1392#if defined(CONFIG_NFS_V3) || defined(CONFIG_NFS_V4) 1391 }
1393 if (error == 0) 1392 error = nfs_flush_inode(inode, idx_start, npages, how);
1393 if (error != 0)
1394 continue;
1395 if (!nocommit)
1394 error = nfs_commit_inode(inode, how); 1396 error = nfs_commit_inode(inode, how);
1395#endif
1396 } while (error > 0); 1397 } while (error > 0);
1397 return error; 1398 return error;
1398} 1399}
diff --git a/fs/nfsd/nfs4callback.c b/fs/nfsd/nfs4callback.c
index 583c0710e45e..d828662d737d 100644
--- a/fs/nfsd/nfs4callback.c
+++ b/fs/nfsd/nfs4callback.c
@@ -53,7 +53,7 @@
53#define NFSPROC4_CB_COMPOUND 1 53#define NFSPROC4_CB_COMPOUND 1
54 54
55/* declarations */ 55/* declarations */
56static void nfs4_cb_null(struct rpc_task *task); 56static const struct rpc_call_ops nfs4_cb_null_ops;
57 57
58/* Index of predefined Linux callback client operations */ 58/* Index of predefined Linux callback client operations */
59 59
@@ -431,7 +431,6 @@ nfsd4_probe_callback(struct nfs4_client *clp)
431 } 431 }
432 clnt->cl_intr = 0; 432 clnt->cl_intr = 0;
433 clnt->cl_softrtry = 1; 433 clnt->cl_softrtry = 1;
434 clnt->cl_chatty = 1;
435 434
436 /* Kick rpciod, put the call on the wire. */ 435 /* Kick rpciod, put the call on the wire. */
437 436
@@ -447,7 +446,7 @@ nfsd4_probe_callback(struct nfs4_client *clp)
447 msg.rpc_cred = nfsd4_lookupcred(clp,0); 446 msg.rpc_cred = nfsd4_lookupcred(clp,0);
448 if (IS_ERR(msg.rpc_cred)) 447 if (IS_ERR(msg.rpc_cred))
449 goto out_rpciod; 448 goto out_rpciod;
450 status = rpc_call_async(clnt, &msg, RPC_TASK_ASYNC, nfs4_cb_null, NULL); 449 status = rpc_call_async(clnt, &msg, RPC_TASK_ASYNC, &nfs4_cb_null_ops, NULL);
451 put_rpccred(msg.rpc_cred); 450 put_rpccred(msg.rpc_cred);
452 451
453 if (status != 0) { 452 if (status != 0) {
@@ -469,7 +468,7 @@ out_err:
469} 468}
470 469
471static void 470static void
472nfs4_cb_null(struct rpc_task *task) 471nfs4_cb_null(struct rpc_task *task, void *dummy)
473{ 472{
474 struct nfs4_client *clp = (struct nfs4_client *)task->tk_msg.rpc_argp; 473 struct nfs4_client *clp = (struct nfs4_client *)task->tk_msg.rpc_argp;
475 struct nfs4_callback *cb = &clp->cl_callback; 474 struct nfs4_callback *cb = &clp->cl_callback;
@@ -488,6 +487,10 @@ out:
488 put_nfs4_client(clp); 487 put_nfs4_client(clp);
489} 488}
490 489
490static const struct rpc_call_ops nfs4_cb_null_ops = {
491 .rpc_call_done = nfs4_cb_null,
492};
493
491/* 494/*
492 * called with dp->dl_count inc'ed. 495 * called with dp->dl_count inc'ed.
493 * nfs4_lock_state() may or may not have been called. 496 * nfs4_lock_state() may or may not have been called.
diff --git a/include/linux/fs.h b/include/linux/fs.h
index 115e72be25d0..2c9c48d65630 100644
--- a/include/linux/fs.h
+++ b/include/linux/fs.h
@@ -760,7 +760,7 @@ extern struct file_lock *posix_test_lock(struct file *, struct file_lock *);
760extern int posix_lock_file(struct file *, struct file_lock *); 760extern int posix_lock_file(struct file *, struct file_lock *);
761extern int posix_lock_file_wait(struct file *, struct file_lock *); 761extern int posix_lock_file_wait(struct file *, struct file_lock *);
762extern void posix_block_lock(struct file_lock *, struct file_lock *); 762extern void posix_block_lock(struct file_lock *, struct file_lock *);
763extern void posix_unblock_lock(struct file *, struct file_lock *); 763extern int posix_unblock_lock(struct file *, struct file_lock *);
764extern int posix_locks_deadlock(struct file_lock *, struct file_lock *); 764extern int posix_locks_deadlock(struct file_lock *, struct file_lock *);
765extern int flock_lock_file_wait(struct file *filp, struct file_lock *fl); 765extern int flock_lock_file_wait(struct file *filp, struct file_lock *fl);
766extern int __break_lease(struct inode *inode, unsigned int flags); 766extern int __break_lease(struct inode *inode, unsigned int flags);
diff --git a/include/linux/lockd/lockd.h b/include/linux/lockd/lockd.h
index 16d4e5a08e1d..95c8fea293ba 100644
--- a/include/linux/lockd/lockd.h
+++ b/include/linux/lockd/lockd.h
@@ -172,7 +172,7 @@ extern struct nlm_host *nlm_find_client(void);
172/* 172/*
173 * Server-side lock handling 173 * Server-side lock handling
174 */ 174 */
175int nlmsvc_async_call(struct nlm_rqst *, u32, rpc_action); 175int nlmsvc_async_call(struct nlm_rqst *, u32, const struct rpc_call_ops *);
176u32 nlmsvc_lock(struct svc_rqst *, struct nlm_file *, 176u32 nlmsvc_lock(struct svc_rqst *, struct nlm_file *,
177 struct nlm_lock *, int, struct nlm_cookie *); 177 struct nlm_lock *, int, struct nlm_cookie *);
178u32 nlmsvc_unlock(struct nlm_file *, struct nlm_lock *); 178u32 nlmsvc_unlock(struct nlm_file *, struct nlm_lock *);
diff --git a/include/linux/nfs_fs.h b/include/linux/nfs_fs.h
index 2516adeccecf..547d649b274e 100644
--- a/include/linux/nfs_fs.h
+++ b/include/linux/nfs_fs.h
@@ -38,9 +38,6 @@
38# define NFS_DEBUG 38# define NFS_DEBUG
39#endif 39#endif
40 40
41#define NFS_MAX_FILE_IO_BUFFER_SIZE 32768
42#define NFS_DEF_FILE_IO_BUFFER_SIZE 4096
43
44/* Default timeout values */ 41/* Default timeout values */
45#define NFS_MAX_UDP_TIMEOUT (60*HZ) 42#define NFS_MAX_UDP_TIMEOUT (60*HZ)
46#define NFS_MAX_TCP_TIMEOUT (600*HZ) 43#define NFS_MAX_TCP_TIMEOUT (600*HZ)
@@ -65,6 +62,7 @@
65#define FLUSH_STABLE 4 /* commit to stable storage */ 62#define FLUSH_STABLE 4 /* commit to stable storage */
66#define FLUSH_LOWPRI 8 /* low priority background flush */ 63#define FLUSH_LOWPRI 8 /* low priority background flush */
67#define FLUSH_HIGHPRI 16 /* high priority memory reclaim flush */ 64#define FLUSH_HIGHPRI 16 /* high priority memory reclaim flush */
65#define FLUSH_NOCOMMIT 32 /* Don't send the NFSv3/v4 COMMIT */
68 66
69#ifdef __KERNEL__ 67#ifdef __KERNEL__
70 68
@@ -394,6 +392,17 @@ extern int nfs_instantiate(struct dentry *dentry, struct nfs_fh *fh, struct nfs_
394extern struct inode_operations nfs_symlink_inode_operations; 392extern struct inode_operations nfs_symlink_inode_operations;
395 393
396/* 394/*
395 * linux/fs/nfs/sysctl.c
396 */
397#ifdef CONFIG_SYSCTL
398extern int nfs_register_sysctl(void);
399extern void nfs_unregister_sysctl(void);
400#else
401#define nfs_register_sysctl() do { } while(0)
402#define nfs_unregister_sysctl() do { } while(0)
403#endif
404
405/*
397 * linux/fs/nfs/unlink.c 406 * linux/fs/nfs/unlink.c
398 */ 407 */
399extern int nfs_async_unlink(struct dentry *); 408extern int nfs_async_unlink(struct dentry *);
@@ -406,10 +415,12 @@ extern int nfs_writepage(struct page *page, struct writeback_control *wbc);
406extern int nfs_writepages(struct address_space *, struct writeback_control *); 415extern int nfs_writepages(struct address_space *, struct writeback_control *);
407extern int nfs_flush_incompatible(struct file *file, struct page *page); 416extern int nfs_flush_incompatible(struct file *file, struct page *page);
408extern int nfs_updatepage(struct file *, struct page *, unsigned int, unsigned int); 417extern int nfs_updatepage(struct file *, struct page *, unsigned int, unsigned int);
409extern void nfs_writeback_done(struct rpc_task *task); 418extern void nfs_writeback_done(struct rpc_task *task, void *data);
419extern void nfs_writedata_release(void *data);
410 420
411#if defined(CONFIG_NFS_V3) || defined(CONFIG_NFS_V4) 421#if defined(CONFIG_NFS_V3) || defined(CONFIG_NFS_V4)
412extern void nfs_commit_done(struct rpc_task *); 422extern void nfs_commit_done(struct rpc_task *, void *data);
423extern void nfs_commit_release(void *data);
413#endif 424#endif
414 425
415/* 426/*
@@ -460,18 +471,33 @@ static inline int nfs_wb_page(struct inode *inode, struct page* page)
460 */ 471 */
461extern mempool_t *nfs_wdata_mempool; 472extern mempool_t *nfs_wdata_mempool;
462 473
463static inline struct nfs_write_data *nfs_writedata_alloc(void) 474static inline struct nfs_write_data *nfs_writedata_alloc(unsigned int pagecount)
464{ 475{
465 struct nfs_write_data *p = mempool_alloc(nfs_wdata_mempool, SLAB_NOFS); 476 struct nfs_write_data *p = mempool_alloc(nfs_wdata_mempool, SLAB_NOFS);
477
466 if (p) { 478 if (p) {
467 memset(p, 0, sizeof(*p)); 479 memset(p, 0, sizeof(*p));
468 INIT_LIST_HEAD(&p->pages); 480 INIT_LIST_HEAD(&p->pages);
481 if (pagecount < NFS_PAGEVEC_SIZE)
482 p->pagevec = &p->page_array[0];
483 else {
484 size_t size = ++pagecount * sizeof(struct page *);
485 p->pagevec = kmalloc(size, GFP_NOFS);
486 if (p->pagevec) {
487 memset(p->pagevec, 0, size);
488 } else {
489 mempool_free(p, nfs_wdata_mempool);
490 p = NULL;
491 }
492 }
469 } 493 }
470 return p; 494 return p;
471} 495}
472 496
473static inline void nfs_writedata_free(struct nfs_write_data *p) 497static inline void nfs_writedata_free(struct nfs_write_data *p)
474{ 498{
499 if (p && (p->pagevec != &p->page_array[0]))
500 kfree(p->pagevec);
475 mempool_free(p, nfs_wdata_mempool); 501 mempool_free(p, nfs_wdata_mempool);
476} 502}
477 503
@@ -481,28 +507,45 @@ static inline void nfs_writedata_free(struct nfs_write_data *p)
481extern int nfs_readpage(struct file *, struct page *); 507extern int nfs_readpage(struct file *, struct page *);
482extern int nfs_readpages(struct file *, struct address_space *, 508extern int nfs_readpages(struct file *, struct address_space *,
483 struct list_head *, unsigned); 509 struct list_head *, unsigned);
484extern void nfs_readpage_result(struct rpc_task *); 510extern void nfs_readpage_result(struct rpc_task *, void *);
511extern void nfs_readdata_release(void *data);
512
485 513
486/* 514/*
487 * Allocate and free nfs_read_data structures 515 * Allocate and free nfs_read_data structures
488 */ 516 */
489extern mempool_t *nfs_rdata_mempool; 517extern mempool_t *nfs_rdata_mempool;
490 518
491static inline struct nfs_read_data *nfs_readdata_alloc(void) 519static inline struct nfs_read_data *nfs_readdata_alloc(unsigned int pagecount)
492{ 520{
493 struct nfs_read_data *p = mempool_alloc(nfs_rdata_mempool, SLAB_NOFS); 521 struct nfs_read_data *p = mempool_alloc(nfs_rdata_mempool, SLAB_NOFS);
494 if (p) 522
523 if (p) {
495 memset(p, 0, sizeof(*p)); 524 memset(p, 0, sizeof(*p));
525 INIT_LIST_HEAD(&p->pages);
526 if (pagecount < NFS_PAGEVEC_SIZE)
527 p->pagevec = &p->page_array[0];
528 else {
529 size_t size = ++pagecount * sizeof(struct page *);
530 p->pagevec = kmalloc(size, GFP_NOFS);
531 if (p->pagevec) {
532 memset(p->pagevec, 0, size);
533 } else {
534 mempool_free(p, nfs_rdata_mempool);
535 p = NULL;
536 }
537 }
538 }
496 return p; 539 return p;
497} 540}
498 541
499static inline void nfs_readdata_free(struct nfs_read_data *p) 542static inline void nfs_readdata_free(struct nfs_read_data *p)
500{ 543{
544 if (p && (p->pagevec != &p->page_array[0]))
545 kfree(p->pagevec);
501 mempool_free(p, nfs_rdata_mempool); 546 mempool_free(p, nfs_rdata_mempool);
502} 547}
503 548
504extern void nfs_readdata_release(struct rpc_task *task);
505
506/* 549/*
507 * linux/fs/nfs3proc.c 550 * linux/fs/nfs3proc.c
508 */ 551 */
diff --git a/include/linux/nfs_idmap.h b/include/linux/nfs_idmap.h
index a0f1f25e0ead..102e56094296 100644
--- a/include/linux/nfs_idmap.h
+++ b/include/linux/nfs_idmap.h
@@ -71,6 +71,8 @@ int nfs_map_name_to_uid(struct nfs4_client *, const char *, size_t, __u32 *);
71int nfs_map_group_to_gid(struct nfs4_client *, const char *, size_t, __u32 *); 71int nfs_map_group_to_gid(struct nfs4_client *, const char *, size_t, __u32 *);
72int nfs_map_uid_to_name(struct nfs4_client *, __u32, char *); 72int nfs_map_uid_to_name(struct nfs4_client *, __u32, char *);
73int nfs_map_gid_to_group(struct nfs4_client *, __u32, char *); 73int nfs_map_gid_to_group(struct nfs4_client *, __u32, char *);
74
75extern unsigned int nfs_idmap_cache_timeout;
74#endif /* __KERNEL__ */ 76#endif /* __KERNEL__ */
75 77
76#endif /* NFS_IDMAP_H */ 78#endif /* NFS_IDMAP_H */
diff --git a/include/linux/nfs_page.h b/include/linux/nfs_page.h
index da2e077b65e2..66e2ed658527 100644
--- a/include/linux/nfs_page.h
+++ b/include/linux/nfs_page.h
@@ -79,9 +79,7 @@ extern void nfs_clear_page_writeback(struct nfs_page *req);
79static inline int 79static inline int
80nfs_lock_request_dontget(struct nfs_page *req) 80nfs_lock_request_dontget(struct nfs_page *req)
81{ 81{
82 if (test_and_set_bit(PG_BUSY, &req->wb_flags)) 82 return !test_and_set_bit(PG_BUSY, &req->wb_flags);
83 return 0;
84 return 1;
85} 83}
86 84
87/* 85/*
@@ -125,9 +123,7 @@ nfs_list_remove_request(struct nfs_page *req)
125static inline int 123static inline int
126nfs_defer_commit(struct nfs_page *req) 124nfs_defer_commit(struct nfs_page *req)
127{ 125{
128 if (test_and_set_bit(PG_NEED_COMMIT, &req->wb_flags)) 126 return !test_and_set_bit(PG_NEED_COMMIT, &req->wb_flags);
129 return 0;
130 return 1;
131} 127}
132 128
133static inline void 129static inline void
@@ -141,9 +137,7 @@ nfs_clear_commit(struct nfs_page *req)
141static inline int 137static inline int
142nfs_defer_reschedule(struct nfs_page *req) 138nfs_defer_reschedule(struct nfs_page *req)
143{ 139{
144 if (test_and_set_bit(PG_NEED_RESCHED, &req->wb_flags)) 140 return !test_and_set_bit(PG_NEED_RESCHED, &req->wb_flags);
145 return 0;
146 return 1;
147} 141}
148 142
149static inline void 143static inline void
diff --git a/include/linux/nfs_xdr.h b/include/linux/nfs_xdr.h
index 40718669b9c8..6d6f69ec5675 100644
--- a/include/linux/nfs_xdr.h
+++ b/include/linux/nfs_xdr.h
@@ -4,6 +4,16 @@
4#include <linux/sunrpc/xprt.h> 4#include <linux/sunrpc/xprt.h>
5#include <linux/nfsacl.h> 5#include <linux/nfsacl.h>
6 6
7/*
8 * To change the maximum rsize and wsize supported by the NFS client, adjust
9 * NFS_MAX_FILE_IO_SIZE. 64KB is a typical maximum, but some servers can
10 * support a megabyte or more. The default is left at 4096 bytes, which is
11 * reasonable for NFS over UDP.
12 */
13#define NFS_MAX_FILE_IO_SIZE (1048576U)
14#define NFS_DEF_FILE_IO_SIZE (4096U)
15#define NFS_MIN_FILE_IO_SIZE (1024U)
16
7struct nfs4_fsid { 17struct nfs4_fsid {
8 __u64 major; 18 __u64 major;
9 __u64 minor; 19 __u64 minor;
@@ -137,7 +147,7 @@ struct nfs_openres {
137 */ 147 */
138struct nfs_open_confirmargs { 148struct nfs_open_confirmargs {
139 const struct nfs_fh * fh; 149 const struct nfs_fh * fh;
140 nfs4_stateid stateid; 150 nfs4_stateid * stateid;
141 struct nfs_seqid * seqid; 151 struct nfs_seqid * seqid;
142}; 152};
143 153
@@ -165,66 +175,62 @@ struct nfs_closeres {
165 * * Arguments to the lock,lockt, and locku call. 175 * * Arguments to the lock,lockt, and locku call.
166 * */ 176 * */
167struct nfs_lowner { 177struct nfs_lowner {
168 __u64 clientid; 178 __u64 clientid;
169 u32 id; 179 u32 id;
170}; 180};
171 181
172struct nfs_lock_opargs { 182struct nfs_lock_args {
183 struct nfs_fh * fh;
184 struct file_lock * fl;
173 struct nfs_seqid * lock_seqid; 185 struct nfs_seqid * lock_seqid;
174 nfs4_stateid * lock_stateid; 186 nfs4_stateid * lock_stateid;
175 struct nfs_seqid * open_seqid; 187 struct nfs_seqid * open_seqid;
176 nfs4_stateid * open_stateid; 188 nfs4_stateid * open_stateid;
177 struct nfs_lowner lock_owner; 189 struct nfs_lowner lock_owner;
178 __u32 reclaim; 190 unsigned char block : 1;
179 __u32 new_lock_owner; 191 unsigned char reclaim : 1;
192 unsigned char new_lock_owner : 1;
180}; 193};
181 194
182struct nfs_locku_opargs { 195struct nfs_lock_res {
196 nfs4_stateid stateid;
197};
198
199struct nfs_locku_args {
200 struct nfs_fh * fh;
201 struct file_lock * fl;
183 struct nfs_seqid * seqid; 202 struct nfs_seqid * seqid;
184 nfs4_stateid * stateid; 203 nfs4_stateid * stateid;
185}; 204};
186 205
187struct nfs_lockargs { 206struct nfs_locku_res {
188 struct nfs_fh * fh; 207 nfs4_stateid stateid;
189 __u32 type;
190 __u64 offset;
191 __u64 length;
192 union {
193 struct nfs_lock_opargs *lock; /* LOCK */
194 struct nfs_lowner *lockt; /* LOCKT */
195 struct nfs_locku_opargs *locku; /* LOCKU */
196 } u;
197}; 208};
198 209
199struct nfs_lock_denied { 210struct nfs_lockt_args {
200 __u64 offset; 211 struct nfs_fh * fh;
201 __u64 length; 212 struct file_lock * fl;
202 __u32 type; 213 struct nfs_lowner lock_owner;
203 struct nfs_lowner owner;
204}; 214};
205 215
206struct nfs_lockres { 216struct nfs_lockt_res {
207 union { 217 struct file_lock * denied; /* LOCK, LOCKT failed */
208 nfs4_stateid stateid;/* LOCK success, LOCKU */
209 struct nfs_lock_denied denied; /* LOCK failed, LOCKT success */
210 } u;
211 const struct nfs_server * server;
212}; 218};
213 219
214struct nfs4_delegreturnargs { 220struct nfs4_delegreturnargs {
215 const struct nfs_fh *fhandle; 221 const struct nfs_fh *fhandle;
216 const nfs4_stateid *stateid; 222 const nfs4_stateid *stateid;
223 const u32 * bitmask;
224};
225
226struct nfs4_delegreturnres {
227 struct nfs_fattr * fattr;
228 const struct nfs_server *server;
217}; 229};
218 230
219/* 231/*
220 * Arguments to the read call. 232 * Arguments to the read call.
221 */ 233 */
222
223#define NFS_READ_MAXIOV (9U)
224#if (NFS_READ_MAXIOV > (MAX_IOVEC -2))
225#error "NFS_READ_MAXIOV is too large"
226#endif
227
228struct nfs_readargs { 234struct nfs_readargs {
229 struct nfs_fh * fh; 235 struct nfs_fh * fh;
230 struct nfs_open_context *context; 236 struct nfs_open_context *context;
@@ -243,11 +249,6 @@ struct nfs_readres {
243/* 249/*
244 * Arguments to the write call. 250 * Arguments to the write call.
245 */ 251 */
246#define NFS_WRITE_MAXIOV (9U)
247#if (NFS_WRITE_MAXIOV > (MAX_IOVEC -2))
248#error "NFS_WRITE_MAXIOV is too large"
249#endif
250
251struct nfs_writeargs { 252struct nfs_writeargs {
252 struct nfs_fh * fh; 253 struct nfs_fh * fh;
253 struct nfs_open_context *context; 254 struct nfs_open_context *context;
@@ -678,6 +679,8 @@ struct nfs4_server_caps_res {
678 679
679struct nfs_page; 680struct nfs_page;
680 681
682#define NFS_PAGEVEC_SIZE (8U)
683
681struct nfs_read_data { 684struct nfs_read_data {
682 int flags; 685 int flags;
683 struct rpc_task task; 686 struct rpc_task task;
@@ -686,13 +689,14 @@ struct nfs_read_data {
686 struct nfs_fattr fattr; /* fattr storage */ 689 struct nfs_fattr fattr; /* fattr storage */
687 struct list_head pages; /* Coalesced read requests */ 690 struct list_head pages; /* Coalesced read requests */
688 struct nfs_page *req; /* multi ops per nfs_page */ 691 struct nfs_page *req; /* multi ops per nfs_page */
689 struct page *pagevec[NFS_READ_MAXIOV]; 692 struct page **pagevec;
690 struct nfs_readargs args; 693 struct nfs_readargs args;
691 struct nfs_readres res; 694 struct nfs_readres res;
692#ifdef CONFIG_NFS_V4 695#ifdef CONFIG_NFS_V4
693 unsigned long timestamp; /* For lease renewal */ 696 unsigned long timestamp; /* For lease renewal */
694#endif 697#endif
695 void (*complete) (struct nfs_read_data *, int); 698 void (*complete) (struct nfs_read_data *, int);
699 struct page *page_array[NFS_PAGEVEC_SIZE + 1];
696}; 700};
697 701
698struct nfs_write_data { 702struct nfs_write_data {
@@ -704,13 +708,14 @@ struct nfs_write_data {
704 struct nfs_writeverf verf; 708 struct nfs_writeverf verf;
705 struct list_head pages; /* Coalesced requests we wish to flush */ 709 struct list_head pages; /* Coalesced requests we wish to flush */
706 struct nfs_page *req; /* multi ops per nfs_page */ 710 struct nfs_page *req; /* multi ops per nfs_page */
707 struct page *pagevec[NFS_WRITE_MAXIOV]; 711 struct page **pagevec;
708 struct nfs_writeargs args; /* argument struct */ 712 struct nfs_writeargs args; /* argument struct */
709 struct nfs_writeres res; /* result struct */ 713 struct nfs_writeres res; /* result struct */
710#ifdef CONFIG_NFS_V4 714#ifdef CONFIG_NFS_V4
711 unsigned long timestamp; /* For lease renewal */ 715 unsigned long timestamp; /* For lease renewal */
712#endif 716#endif
713 void (*complete) (struct nfs_write_data *, int); 717 void (*complete) (struct nfs_write_data *, int);
718 struct page *page_array[NFS_PAGEVEC_SIZE + 1];
714}; 719};
715 720
716struct nfs_access_entry; 721struct nfs_access_entry;
diff --git a/include/linux/sunrpc/clnt.h b/include/linux/sunrpc/clnt.h
index ab151bbb66df..f147e6b84332 100644
--- a/include/linux/sunrpc/clnt.h
+++ b/include/linux/sunrpc/clnt.h
@@ -49,7 +49,6 @@ struct rpc_clnt {
49 49
50 unsigned int cl_softrtry : 1,/* soft timeouts */ 50 unsigned int cl_softrtry : 1,/* soft timeouts */
51 cl_intr : 1,/* interruptible */ 51 cl_intr : 1,/* interruptible */
52 cl_chatty : 1,/* be verbose */
53 cl_autobind : 1,/* use getport() */ 52 cl_autobind : 1,/* use getport() */
54 cl_oneshot : 1,/* dispose after use */ 53 cl_oneshot : 1,/* dispose after use */
55 cl_dead : 1;/* abandoned */ 54 cl_dead : 1;/* abandoned */
@@ -126,7 +125,8 @@ int rpc_register(u32, u32, int, unsigned short, int *);
126void rpc_call_setup(struct rpc_task *, struct rpc_message *, int); 125void rpc_call_setup(struct rpc_task *, struct rpc_message *, int);
127 126
128int rpc_call_async(struct rpc_clnt *clnt, struct rpc_message *msg, 127int rpc_call_async(struct rpc_clnt *clnt, struct rpc_message *msg,
129 int flags, rpc_action callback, void *clntdata); 128 int flags, const struct rpc_call_ops *tk_ops,
129 void *calldata);
130int rpc_call_sync(struct rpc_clnt *clnt, struct rpc_message *msg, 130int rpc_call_sync(struct rpc_clnt *clnt, struct rpc_message *msg,
131 int flags); 131 int flags);
132void rpc_restart_call(struct rpc_task *); 132void rpc_restart_call(struct rpc_task *);
@@ -134,6 +134,7 @@ void rpc_clnt_sigmask(struct rpc_clnt *clnt, sigset_t *oldset);
134void rpc_clnt_sigunmask(struct rpc_clnt *clnt, sigset_t *oldset); 134void rpc_clnt_sigunmask(struct rpc_clnt *clnt, sigset_t *oldset);
135void rpc_setbufsize(struct rpc_clnt *, unsigned int, unsigned int); 135void rpc_setbufsize(struct rpc_clnt *, unsigned int, unsigned int);
136size_t rpc_max_payload(struct rpc_clnt *); 136size_t rpc_max_payload(struct rpc_clnt *);
137void rpc_force_rebind(struct rpc_clnt *);
137int rpc_ping(struct rpc_clnt *clnt, int flags); 138int rpc_ping(struct rpc_clnt *clnt, int flags);
138 139
139static __inline__ 140static __inline__
diff --git a/include/linux/sunrpc/gss_spkm3.h b/include/linux/sunrpc/gss_spkm3.h
index 0beb2cf00a84..336e218c2782 100644
--- a/include/linux/sunrpc/gss_spkm3.h
+++ b/include/linux/sunrpc/gss_spkm3.h
@@ -48,7 +48,7 @@ u32 spkm3_read_token(struct spkm3_ctx *ctx, struct xdr_netobj *read_token, struc
48#define CKSUMTYPE_RSA_MD5 0x0007 48#define CKSUMTYPE_RSA_MD5 0x0007
49 49
50s32 make_checksum(s32 cksumtype, char *header, int hdrlen, struct xdr_buf *body, 50s32 make_checksum(s32 cksumtype, char *header, int hdrlen, struct xdr_buf *body,
51 struct xdr_netobj *cksum); 51 int body_offset, struct xdr_netobj *cksum);
52void asn1_bitstring_len(struct xdr_netobj *in, int *enclen, int *zerobits); 52void asn1_bitstring_len(struct xdr_netobj *in, int *enclen, int *zerobits);
53int decode_asn1_bitstring(struct xdr_netobj *out, char *in, int enclen, 53int decode_asn1_bitstring(struct xdr_netobj *out, char *in, int enclen,
54 int explen); 54 int explen);
diff --git a/include/linux/sunrpc/sched.h b/include/linux/sunrpc/sched.h
index 4d77e90d0b30..8b25629accd8 100644
--- a/include/linux/sunrpc/sched.h
+++ b/include/linux/sunrpc/sched.h
@@ -27,6 +27,7 @@ struct rpc_message {
27 struct rpc_cred * rpc_cred; /* Credentials */ 27 struct rpc_cred * rpc_cred; /* Credentials */
28}; 28};
29 29
30struct rpc_call_ops;
30struct rpc_wait_queue; 31struct rpc_wait_queue;
31struct rpc_wait { 32struct rpc_wait {
32 struct list_head list; /* wait queue links */ 33 struct list_head list; /* wait queue links */
@@ -41,6 +42,7 @@ struct rpc_task {
41#ifdef RPC_DEBUG 42#ifdef RPC_DEBUG
42 unsigned long tk_magic; /* 0xf00baa */ 43 unsigned long tk_magic; /* 0xf00baa */
43#endif 44#endif
45 atomic_t tk_count; /* Reference count */
44 struct list_head tk_task; /* global list of tasks */ 46 struct list_head tk_task; /* global list of tasks */
45 struct rpc_clnt * tk_client; /* RPC client */ 47 struct rpc_clnt * tk_client; /* RPC client */
46 struct rpc_rqst * tk_rqstp; /* RPC request */ 48 struct rpc_rqst * tk_rqstp; /* RPC request */
@@ -50,8 +52,6 @@ struct rpc_task {
50 * RPC call state 52 * RPC call state
51 */ 53 */
52 struct rpc_message tk_msg; /* RPC call info */ 54 struct rpc_message tk_msg; /* RPC call info */
53 __u32 * tk_buffer; /* XDR buffer */
54 size_t tk_bufsize;
55 __u8 tk_garb_retry; 55 __u8 tk_garb_retry;
56 __u8 tk_cred_retry; 56 __u8 tk_cred_retry;
57 57
@@ -61,13 +61,12 @@ struct rpc_task {
61 * timeout_fn to be executed by timer bottom half 61 * timeout_fn to be executed by timer bottom half
62 * callback to be executed after waking up 62 * callback to be executed after waking up
63 * action next procedure for async tasks 63 * action next procedure for async tasks
64 * exit exit async task and report to caller 64 * tk_ops caller callbacks
65 */ 65 */
66 void (*tk_timeout_fn)(struct rpc_task *); 66 void (*tk_timeout_fn)(struct rpc_task *);
67 void (*tk_callback)(struct rpc_task *); 67 void (*tk_callback)(struct rpc_task *);
68 void (*tk_action)(struct rpc_task *); 68 void (*tk_action)(struct rpc_task *);
69 void (*tk_exit)(struct rpc_task *); 69 const struct rpc_call_ops *tk_ops;
70 void (*tk_release)(struct rpc_task *);
71 void * tk_calldata; 70 void * tk_calldata;
72 71
73 /* 72 /*
@@ -78,7 +77,6 @@ struct rpc_task {
78 struct timer_list tk_timer; /* kernel timer */ 77 struct timer_list tk_timer; /* kernel timer */
79 unsigned long tk_timeout; /* timeout for rpc_sleep() */ 78 unsigned long tk_timeout; /* timeout for rpc_sleep() */
80 unsigned short tk_flags; /* misc flags */ 79 unsigned short tk_flags; /* misc flags */
81 unsigned char tk_active : 1;/* Task has been activated */
82 unsigned char tk_priority : 2;/* Task priority */ 80 unsigned char tk_priority : 2;/* Task priority */
83 unsigned long tk_runstate; /* Task run status */ 81 unsigned long tk_runstate; /* Task run status */
84 struct workqueue_struct *tk_workqueue; /* Normally rpciod, but could 82 struct workqueue_struct *tk_workqueue; /* Normally rpciod, but could
@@ -111,6 +109,13 @@ struct rpc_task {
111 109
112typedef void (*rpc_action)(struct rpc_task *); 110typedef void (*rpc_action)(struct rpc_task *);
113 111
112struct rpc_call_ops {
113 void (*rpc_call_prepare)(struct rpc_task *, void *);
114 void (*rpc_call_done)(struct rpc_task *, void *);
115 void (*rpc_release)(void *);
116};
117
118
114/* 119/*
115 * RPC task flags 120 * RPC task flags
116 */ 121 */
@@ -129,7 +134,6 @@ typedef void (*rpc_action)(struct rpc_task *);
129#define RPC_IS_SWAPPER(t) ((t)->tk_flags & RPC_TASK_SWAPPER) 134#define RPC_IS_SWAPPER(t) ((t)->tk_flags & RPC_TASK_SWAPPER)
130#define RPC_DO_ROOTOVERRIDE(t) ((t)->tk_flags & RPC_TASK_ROOTCREDS) 135#define RPC_DO_ROOTOVERRIDE(t) ((t)->tk_flags & RPC_TASK_ROOTCREDS)
131#define RPC_ASSASSINATED(t) ((t)->tk_flags & RPC_TASK_KILLED) 136#define RPC_ASSASSINATED(t) ((t)->tk_flags & RPC_TASK_KILLED)
132#define RPC_IS_ACTIVATED(t) ((t)->tk_active)
133#define RPC_DO_CALLBACK(t) ((t)->tk_callback != NULL) 137#define RPC_DO_CALLBACK(t) ((t)->tk_callback != NULL)
134#define RPC_IS_SOFT(t) ((t)->tk_flags & RPC_TASK_SOFT) 138#define RPC_IS_SOFT(t) ((t)->tk_flags & RPC_TASK_SOFT)
135#define RPC_TASK_UNINTERRUPTIBLE(t) ((t)->tk_flags & RPC_TASK_NOINTR) 139#define RPC_TASK_UNINTERRUPTIBLE(t) ((t)->tk_flags & RPC_TASK_NOINTR)
@@ -138,6 +142,7 @@ typedef void (*rpc_action)(struct rpc_task *);
138#define RPC_TASK_QUEUED 1 142#define RPC_TASK_QUEUED 1
139#define RPC_TASK_WAKEUP 2 143#define RPC_TASK_WAKEUP 2
140#define RPC_TASK_HAS_TIMER 3 144#define RPC_TASK_HAS_TIMER 3
145#define RPC_TASK_ACTIVE 4
141 146
142#define RPC_IS_RUNNING(t) (test_bit(RPC_TASK_RUNNING, &(t)->tk_runstate)) 147#define RPC_IS_RUNNING(t) (test_bit(RPC_TASK_RUNNING, &(t)->tk_runstate))
143#define rpc_set_running(t) (set_bit(RPC_TASK_RUNNING, &(t)->tk_runstate)) 148#define rpc_set_running(t) (set_bit(RPC_TASK_RUNNING, &(t)->tk_runstate))
@@ -168,6 +173,15 @@ typedef void (*rpc_action)(struct rpc_task *);
168 smp_mb__after_clear_bit(); \ 173 smp_mb__after_clear_bit(); \
169 } while (0) 174 } while (0)
170 175
176#define RPC_IS_ACTIVATED(t) (test_bit(RPC_TASK_ACTIVE, &(t)->tk_runstate))
177#define rpc_set_active(t) (set_bit(RPC_TASK_ACTIVE, &(t)->tk_runstate))
178#define rpc_clear_active(t) \
179 do { \
180 smp_mb__before_clear_bit(); \
181 clear_bit(RPC_TASK_ACTIVE, &(t)->tk_runstate); \
182 smp_mb__after_clear_bit(); \
183 } while(0)
184
171/* 185/*
172 * Task priorities. 186 * Task priorities.
173 * Note: if you change these, you must also change 187 * Note: if you change these, you must also change
@@ -228,11 +242,16 @@ struct rpc_wait_queue {
228/* 242/*
229 * Function prototypes 243 * Function prototypes
230 */ 244 */
231struct rpc_task *rpc_new_task(struct rpc_clnt *, rpc_action, int flags); 245struct rpc_task *rpc_new_task(struct rpc_clnt *, int flags,
246 const struct rpc_call_ops *ops, void *data);
247struct rpc_task *rpc_run_task(struct rpc_clnt *clnt, int flags,
248 const struct rpc_call_ops *ops, void *data);
232struct rpc_task *rpc_new_child(struct rpc_clnt *, struct rpc_task *parent); 249struct rpc_task *rpc_new_child(struct rpc_clnt *, struct rpc_task *parent);
233void rpc_init_task(struct rpc_task *, struct rpc_clnt *, 250void rpc_init_task(struct rpc_task *task, struct rpc_clnt *clnt,
234 rpc_action exitfunc, int flags); 251 int flags, const struct rpc_call_ops *ops,
252 void *data);
235void rpc_release_task(struct rpc_task *); 253void rpc_release_task(struct rpc_task *);
254void rpc_exit_task(struct rpc_task *);
236void rpc_killall_tasks(struct rpc_clnt *); 255void rpc_killall_tasks(struct rpc_clnt *);
237int rpc_execute(struct rpc_task *); 256int rpc_execute(struct rpc_task *);
238void rpc_run_child(struct rpc_task *parent, struct rpc_task *child, 257void rpc_run_child(struct rpc_task *parent, struct rpc_task *child,
@@ -247,9 +266,11 @@ struct rpc_task *rpc_wake_up_next(struct rpc_wait_queue *);
247void rpc_wake_up_status(struct rpc_wait_queue *, int); 266void rpc_wake_up_status(struct rpc_wait_queue *, int);
248void rpc_delay(struct rpc_task *, unsigned long); 267void rpc_delay(struct rpc_task *, unsigned long);
249void * rpc_malloc(struct rpc_task *, size_t); 268void * rpc_malloc(struct rpc_task *, size_t);
269void rpc_free(struct rpc_task *);
250int rpciod_up(void); 270int rpciod_up(void);
251void rpciod_down(void); 271void rpciod_down(void);
252void rpciod_wake_up(void); 272void rpciod_wake_up(void);
273int __rpc_wait_for_completion_task(struct rpc_task *task, int (*)(void *));
253#ifdef RPC_DEBUG 274#ifdef RPC_DEBUG
254void rpc_show_tasks(void); 275void rpc_show_tasks(void);
255#endif 276#endif
@@ -259,7 +280,12 @@ void rpc_destroy_mempool(void);
259static inline void rpc_exit(struct rpc_task *task, int status) 280static inline void rpc_exit(struct rpc_task *task, int status)
260{ 281{
261 task->tk_status = status; 282 task->tk_status = status;
262 task->tk_action = NULL; 283 task->tk_action = rpc_exit_task;
284}
285
286static inline int rpc_wait_for_completion_task(struct rpc_task *task)
287{
288 return __rpc_wait_for_completion_task(task, NULL);
263} 289}
264 290
265#ifdef RPC_DEBUG 291#ifdef RPC_DEBUG
diff --git a/include/linux/sunrpc/xdr.h b/include/linux/sunrpc/xdr.h
index 5da968729cf8..84c35d42d250 100644
--- a/include/linux/sunrpc/xdr.h
+++ b/include/linux/sunrpc/xdr.h
@@ -91,7 +91,6 @@ struct xdr_buf {
91u32 * xdr_encode_opaque_fixed(u32 *p, const void *ptr, unsigned int len); 91u32 * xdr_encode_opaque_fixed(u32 *p, const void *ptr, unsigned int len);
92u32 * xdr_encode_opaque(u32 *p, const void *ptr, unsigned int len); 92u32 * xdr_encode_opaque(u32 *p, const void *ptr, unsigned int len);
93u32 * xdr_encode_string(u32 *p, const char *s); 93u32 * xdr_encode_string(u32 *p, const char *s);
94u32 * xdr_decode_string(u32 *p, char **sp, int *lenp, int maxlen);
95u32 * xdr_decode_string_inplace(u32 *p, char **sp, int *lenp, int maxlen); 94u32 * xdr_decode_string_inplace(u32 *p, char **sp, int *lenp, int maxlen);
96u32 * xdr_encode_netobj(u32 *p, const struct xdr_netobj *); 95u32 * xdr_encode_netobj(u32 *p, const struct xdr_netobj *);
97u32 * xdr_decode_netobj(u32 *p, struct xdr_netobj *); 96u32 * xdr_decode_netobj(u32 *p, struct xdr_netobj *);
@@ -135,11 +134,6 @@ xdr_adjust_iovec(struct kvec *iov, u32 *p)
135} 134}
136 135
137/* 136/*
138 * Maximum number of iov's we use.
139 */
140#define MAX_IOVEC (12)
141
142/*
143 * XDR buffer helper functions 137 * XDR buffer helper functions
144 */ 138 */
145extern void xdr_shift_buf(struct xdr_buf *, size_t); 139extern void xdr_shift_buf(struct xdr_buf *, size_t);
diff --git a/include/linux/sunrpc/xprt.h b/include/linux/sunrpc/xprt.h
index 3b8b6e823c70..6ef99b14ff09 100644
--- a/include/linux/sunrpc/xprt.h
+++ b/include/linux/sunrpc/xprt.h
@@ -79,21 +79,19 @@ struct rpc_rqst {
79 void (*rq_release_snd_buf)(struct rpc_rqst *); /* release rq_enc_pages */ 79 void (*rq_release_snd_buf)(struct rpc_rqst *); /* release rq_enc_pages */
80 struct list_head rq_list; 80 struct list_head rq_list;
81 81
82 __u32 * rq_buffer; /* XDR encode buffer */
83 size_t rq_bufsize;
84
82 struct xdr_buf rq_private_buf; /* The receive buffer 85 struct xdr_buf rq_private_buf; /* The receive buffer
83 * used in the softirq. 86 * used in the softirq.
84 */ 87 */
85 unsigned long rq_majortimeo; /* major timeout alarm */ 88 unsigned long rq_majortimeo; /* major timeout alarm */
86 unsigned long rq_timeout; /* Current timeout value */ 89 unsigned long rq_timeout; /* Current timeout value */
87 unsigned int rq_retries; /* # of retries */ 90 unsigned int rq_retries; /* # of retries */
88 /*
89 * For authentication (e.g. auth_des)
90 */
91 u32 rq_creddata[2];
92 91
93 /* 92 /*
94 * Partial send handling 93 * Partial send handling
95 */ 94 */
96
97 u32 rq_bytes_sent; /* Bytes we have sent */ 95 u32 rq_bytes_sent; /* Bytes we have sent */
98 96
99 unsigned long rq_xtime; /* when transmitted */ 97 unsigned long rq_xtime; /* when transmitted */
@@ -106,7 +104,10 @@ struct rpc_xprt_ops {
106 void (*set_buffer_size)(struct rpc_xprt *xprt, size_t sndsize, size_t rcvsize); 104 void (*set_buffer_size)(struct rpc_xprt *xprt, size_t sndsize, size_t rcvsize);
107 int (*reserve_xprt)(struct rpc_task *task); 105 int (*reserve_xprt)(struct rpc_task *task);
108 void (*release_xprt)(struct rpc_xprt *xprt, struct rpc_task *task); 106 void (*release_xprt)(struct rpc_xprt *xprt, struct rpc_task *task);
107 void (*set_port)(struct rpc_xprt *xprt, unsigned short port);
109 void (*connect)(struct rpc_task *task); 108 void (*connect)(struct rpc_task *task);
109 void * (*buf_alloc)(struct rpc_task *task, size_t size);
110 void (*buf_free)(struct rpc_task *task);
110 int (*send_request)(struct rpc_task *task); 111 int (*send_request)(struct rpc_task *task);
111 void (*set_retrans_timeout)(struct rpc_task *task); 112 void (*set_retrans_timeout)(struct rpc_task *task);
112 void (*timer)(struct rpc_task *task); 113 void (*timer)(struct rpc_task *task);
@@ -253,6 +254,7 @@ int xs_setup_tcp(struct rpc_xprt *xprt, struct rpc_timeout *to);
253#define XPRT_LOCKED (0) 254#define XPRT_LOCKED (0)
254#define XPRT_CONNECTED (1) 255#define XPRT_CONNECTED (1)
255#define XPRT_CONNECTING (2) 256#define XPRT_CONNECTING (2)
257#define XPRT_CLOSE_WAIT (3)
256 258
257static inline void xprt_set_connected(struct rpc_xprt *xprt) 259static inline void xprt_set_connected(struct rpc_xprt *xprt)
258{ 260{
diff --git a/include/linux/writeback.h b/include/linux/writeback.h
index 64a36ba43b2f..b096159086e8 100644
--- a/include/linux/writeback.h
+++ b/include/linux/writeback.h
@@ -53,10 +53,11 @@ struct writeback_control {
53 loff_t start; 53 loff_t start;
54 loff_t end; 54 loff_t end;
55 55
56 unsigned nonblocking:1; /* Don't get stuck on request queues */ 56 unsigned nonblocking:1; /* Don't get stuck on request queues */
57 unsigned encountered_congestion:1; /* An output: a queue is full */ 57 unsigned encountered_congestion:1; /* An output: a queue is full */
58 unsigned for_kupdate:1; /* A kupdate writeback */ 58 unsigned for_kupdate:1; /* A kupdate writeback */
59 unsigned for_reclaim:1; /* Invoked from the page allocator */ 59 unsigned for_reclaim:1; /* Invoked from the page allocator */
60 unsigned for_writepages:1; /* This is a writepages() call */
60}; 61};
61 62
62/* 63/*
diff --git a/mm/page-writeback.c b/mm/page-writeback.c
index 0166ea15c9ee..5240e426c1f7 100644
--- a/mm/page-writeback.c
+++ b/mm/page-writeback.c
@@ -550,11 +550,17 @@ void __init page_writeback_init(void)
550 550
551int do_writepages(struct address_space *mapping, struct writeback_control *wbc) 551int do_writepages(struct address_space *mapping, struct writeback_control *wbc)
552{ 552{
553 int ret;
554
553 if (wbc->nr_to_write <= 0) 555 if (wbc->nr_to_write <= 0)
554 return 0; 556 return 0;
557 wbc->for_writepages = 1;
555 if (mapping->a_ops->writepages) 558 if (mapping->a_ops->writepages)
556 return mapping->a_ops->writepages(mapping, wbc); 559 ret = mapping->a_ops->writepages(mapping, wbc);
557 return generic_writepages(mapping, wbc); 560 else
561 ret = generic_writepages(mapping, wbc);
562 wbc->for_writepages = 0;
563 return ret;
558} 564}
559 565
560/** 566/**
diff --git a/net/sunrpc/auth_gss/gss_krb5_mech.c b/net/sunrpc/auth_gss/gss_krb5_mech.c
index 5f1f806a0b11..129e2bd36aff 100644
--- a/net/sunrpc/auth_gss/gss_krb5_mech.c
+++ b/net/sunrpc/auth_gss/gss_krb5_mech.c
@@ -97,13 +97,17 @@ get_key(const void *p, const void *end, struct crypto_tfm **res)
97 alg_mode = CRYPTO_TFM_MODE_CBC; 97 alg_mode = CRYPTO_TFM_MODE_CBC;
98 break; 98 break;
99 default: 99 default:
100 dprintk("RPC: get_key: unsupported algorithm %d\n", alg); 100 printk("gss_kerberos_mech: unsupported algorithm %d\n", alg);
101 goto out_err_free_key; 101 goto out_err_free_key;
102 } 102 }
103 if (!(*res = crypto_alloc_tfm(alg_name, alg_mode))) 103 if (!(*res = crypto_alloc_tfm(alg_name, alg_mode))) {
104 printk("gss_kerberos_mech: unable to initialize crypto algorithm %s\n", alg_name);
104 goto out_err_free_key; 105 goto out_err_free_key;
105 if (crypto_cipher_setkey(*res, key.data, key.len)) 106 }
107 if (crypto_cipher_setkey(*res, key.data, key.len)) {
108 printk("gss_kerberos_mech: error setting key for crypto algorithm %s\n", alg_name);
106 goto out_err_free_tfm; 109 goto out_err_free_tfm;
110 }
107 111
108 kfree(key.data); 112 kfree(key.data);
109 return p; 113 return p;
diff --git a/net/sunrpc/auth_gss/gss_spkm3_mech.c b/net/sunrpc/auth_gss/gss_spkm3_mech.c
index 39b3edc14694..58400807d4df 100644
--- a/net/sunrpc/auth_gss/gss_spkm3_mech.c
+++ b/net/sunrpc/auth_gss/gss_spkm3_mech.c
@@ -111,14 +111,18 @@ get_key(const void *p, const void *end, struct crypto_tfm **res, int *resalg)
111 setkey = 0; 111 setkey = 0;
112 break; 112 break;
113 default: 113 default:
114 dprintk("RPC: SPKM3 get_key: unsupported algorithm %d", *resalg); 114 dprintk("gss_spkm3_mech: unsupported algorithm %d\n", *resalg);
115 goto out_err_free_key; 115 goto out_err_free_key;
116 } 116 }
117 if (!(*res = crypto_alloc_tfm(alg_name, alg_mode))) 117 if (!(*res = crypto_alloc_tfm(alg_name, alg_mode))) {
118 printk("gss_spkm3_mech: unable to initialize crypto algorthm %s\n", alg_name);
118 goto out_err_free_key; 119 goto out_err_free_key;
120 }
119 if (setkey) { 121 if (setkey) {
120 if (crypto_cipher_setkey(*res, key.data, key.len)) 122 if (crypto_cipher_setkey(*res, key.data, key.len)) {
123 printk("gss_spkm3_mech: error setting key for crypto algorthm %s\n", alg_name);
121 goto out_err_free_tfm; 124 goto out_err_free_tfm;
125 }
122 } 126 }
123 127
124 if(key.len > 0) 128 if(key.len > 0)
diff --git a/net/sunrpc/auth_gss/gss_spkm3_seal.c b/net/sunrpc/auth_gss/gss_spkm3_seal.c
index d1e12b25d6e2..86fbf7c3e39c 100644
--- a/net/sunrpc/auth_gss/gss_spkm3_seal.c
+++ b/net/sunrpc/auth_gss/gss_spkm3_seal.c
@@ -59,7 +59,7 @@ spkm3_make_token(struct spkm3_ctx *ctx,
59 char tokhdrbuf[25]; 59 char tokhdrbuf[25];
60 struct xdr_netobj md5cksum = {.len = 0, .data = NULL}; 60 struct xdr_netobj md5cksum = {.len = 0, .data = NULL};
61 struct xdr_netobj mic_hdr = {.len = 0, .data = tokhdrbuf}; 61 struct xdr_netobj mic_hdr = {.len = 0, .data = tokhdrbuf};
62 int tmsglen, tokenlen = 0; 62 int tokenlen = 0;
63 unsigned char *ptr; 63 unsigned char *ptr;
64 s32 now; 64 s32 now;
65 int ctxelen = 0, ctxzbit = 0; 65 int ctxelen = 0, ctxzbit = 0;
@@ -92,24 +92,23 @@ spkm3_make_token(struct spkm3_ctx *ctx,
92 } 92 }
93 93
94 if (toktype == SPKM_MIC_TOK) { 94 if (toktype == SPKM_MIC_TOK) {
95 tmsglen = 0;
96 /* Calculate checksum over the mic-header */ 95 /* Calculate checksum over the mic-header */
97 asn1_bitstring_len(&ctx->ctx_id, &ctxelen, &ctxzbit); 96 asn1_bitstring_len(&ctx->ctx_id, &ctxelen, &ctxzbit);
98 spkm3_mic_header(&mic_hdr.data, &mic_hdr.len, ctx->ctx_id.data, 97 spkm3_mic_header(&mic_hdr.data, &mic_hdr.len, ctx->ctx_id.data,
99 ctxelen, ctxzbit); 98 ctxelen, ctxzbit);
100 99
101 if (make_checksum(checksum_type, mic_hdr.data, mic_hdr.len, 100 if (make_checksum(checksum_type, mic_hdr.data, mic_hdr.len,
102 text, &md5cksum)) 101 text, 0, &md5cksum))
103 goto out_err; 102 goto out_err;
104 103
105 asn1_bitstring_len(&md5cksum, &md5elen, &md5zbit); 104 asn1_bitstring_len(&md5cksum, &md5elen, &md5zbit);
106 tokenlen = 10 + ctxelen + 1 + 2 + md5elen + 1; 105 tokenlen = 10 + ctxelen + 1 + md5elen + 1;
107 106
108 /* Create token header using generic routines */ 107 /* Create token header using generic routines */
109 token->len = g_token_size(&ctx->mech_used, tokenlen + tmsglen); 108 token->len = g_token_size(&ctx->mech_used, tokenlen);
110 109
111 ptr = token->data; 110 ptr = token->data;
112 g_make_token_header(&ctx->mech_used, tokenlen + tmsglen, &ptr); 111 g_make_token_header(&ctx->mech_used, tokenlen, &ptr);
113 112
114 spkm3_make_mic_token(&ptr, tokenlen, &mic_hdr, &md5cksum, md5elen, md5zbit); 113 spkm3_make_mic_token(&ptr, tokenlen, &mic_hdr, &md5cksum, md5elen, md5zbit);
115 } else if (toktype == SPKM_WRAP_TOK) { /* Not Supported */ 114 } else if (toktype == SPKM_WRAP_TOK) { /* Not Supported */
diff --git a/net/sunrpc/auth_gss/gss_spkm3_token.c b/net/sunrpc/auth_gss/gss_spkm3_token.c
index 1f824578d773..af0d7ce74686 100644
--- a/net/sunrpc/auth_gss/gss_spkm3_token.c
+++ b/net/sunrpc/auth_gss/gss_spkm3_token.c
@@ -182,6 +182,7 @@ spkm3_mic_header(unsigned char **hdrbuf, unsigned int *hdrlen, unsigned char *ct
182 * *tokp points to the beginning of the SPKM_MIC token described 182 * *tokp points to the beginning of the SPKM_MIC token described
183 * in rfc 2025, section 3.2.1: 183 * in rfc 2025, section 3.2.1:
184 * 184 *
185 * toklen is the inner token length
185 */ 186 */
186void 187void
187spkm3_make_mic_token(unsigned char **tokp, int toklen, struct xdr_netobj *mic_hdr, struct xdr_netobj *md5cksum, int md5elen, int md5zbit) 188spkm3_make_mic_token(unsigned char **tokp, int toklen, struct xdr_netobj *mic_hdr, struct xdr_netobj *md5cksum, int md5elen, int md5zbit)
@@ -189,7 +190,7 @@ spkm3_make_mic_token(unsigned char **tokp, int toklen, struct xdr_netobj *mic_hd
189 unsigned char *ict = *tokp; 190 unsigned char *ict = *tokp;
190 191
191 *(u8 *)ict++ = 0xa4; 192 *(u8 *)ict++ = 0xa4;
192 *(u8 *)ict++ = toklen - 2; 193 *(u8 *)ict++ = toklen;
193 memcpy(ict, mic_hdr->data, mic_hdr->len); 194 memcpy(ict, mic_hdr->data, mic_hdr->len);
194 ict += mic_hdr->len; 195 ict += mic_hdr->len;
195 196
diff --git a/net/sunrpc/auth_gss/gss_spkm3_unseal.c b/net/sunrpc/auth_gss/gss_spkm3_unseal.c
index 241d5b30dfcb..96851b0ba1ba 100644
--- a/net/sunrpc/auth_gss/gss_spkm3_unseal.c
+++ b/net/sunrpc/auth_gss/gss_spkm3_unseal.c
@@ -95,7 +95,7 @@ spkm3_read_token(struct spkm3_ctx *ctx,
95 ret = GSS_S_DEFECTIVE_TOKEN; 95 ret = GSS_S_DEFECTIVE_TOKEN;
96 code = make_checksum(CKSUMTYPE_RSA_MD5, ptr + 2, 96 code = make_checksum(CKSUMTYPE_RSA_MD5, ptr + 2,
97 mic_hdrlen + 2, 97 mic_hdrlen + 2,
98 message_buffer, &md5cksum); 98 message_buffer, 0, &md5cksum);
99 99
100 if (code) 100 if (code)
101 goto out; 101 goto out;
diff --git a/net/sunrpc/clnt.c b/net/sunrpc/clnt.c
index 61c3abeaccae..5530ac8c6df9 100644
--- a/net/sunrpc/clnt.c
+++ b/net/sunrpc/clnt.c
@@ -374,19 +374,23 @@ out:
374 * Default callback for async RPC calls 374 * Default callback for async RPC calls
375 */ 375 */
376static void 376static void
377rpc_default_callback(struct rpc_task *task) 377rpc_default_callback(struct rpc_task *task, void *data)
378{ 378{
379} 379}
380 380
381static const struct rpc_call_ops rpc_default_ops = {
382 .rpc_call_done = rpc_default_callback,
383};
384
381/* 385/*
382 * Export the signal mask handling for synchronous code that 386 * Export the signal mask handling for synchronous code that
383 * sleeps on RPC calls 387 * sleeps on RPC calls
384 */ 388 */
385#define RPC_INTR_SIGNALS (sigmask(SIGINT) | sigmask(SIGQUIT) | sigmask(SIGKILL)) 389#define RPC_INTR_SIGNALS (sigmask(SIGHUP) | sigmask(SIGINT) | sigmask(SIGQUIT) | sigmask(SIGTERM))
386 390
387static void rpc_save_sigmask(sigset_t *oldset, int intr) 391static void rpc_save_sigmask(sigset_t *oldset, int intr)
388{ 392{
389 unsigned long sigallow = 0; 393 unsigned long sigallow = sigmask(SIGKILL);
390 sigset_t sigmask; 394 sigset_t sigmask;
391 395
392 /* Block all signals except those listed in sigallow */ 396 /* Block all signals except those listed in sigallow */
@@ -432,7 +436,7 @@ int rpc_call_sync(struct rpc_clnt *clnt, struct rpc_message *msg, int flags)
432 BUG_ON(flags & RPC_TASK_ASYNC); 436 BUG_ON(flags & RPC_TASK_ASYNC);
433 437
434 status = -ENOMEM; 438 status = -ENOMEM;
435 task = rpc_new_task(clnt, NULL, flags); 439 task = rpc_new_task(clnt, flags, &rpc_default_ops, NULL);
436 if (task == NULL) 440 if (task == NULL)
437 goto out; 441 goto out;
438 442
@@ -442,14 +446,15 @@ int rpc_call_sync(struct rpc_clnt *clnt, struct rpc_message *msg, int flags)
442 rpc_call_setup(task, msg, 0); 446 rpc_call_setup(task, msg, 0);
443 447
444 /* Set up the call info struct and execute the task */ 448 /* Set up the call info struct and execute the task */
445 if (task->tk_status == 0) { 449 status = task->tk_status;
450 if (status == 0) {
451 atomic_inc(&task->tk_count);
446 status = rpc_execute(task); 452 status = rpc_execute(task);
447 } else { 453 if (status == 0)
448 status = task->tk_status; 454 status = task->tk_status;
449 rpc_release_task(task);
450 } 455 }
451
452 rpc_restore_sigmask(&oldset); 456 rpc_restore_sigmask(&oldset);
457 rpc_release_task(task);
453out: 458out:
454 return status; 459 return status;
455} 460}
@@ -459,7 +464,7 @@ out:
459 */ 464 */
460int 465int
461rpc_call_async(struct rpc_clnt *clnt, struct rpc_message *msg, int flags, 466rpc_call_async(struct rpc_clnt *clnt, struct rpc_message *msg, int flags,
462 rpc_action callback, void *data) 467 const struct rpc_call_ops *tk_ops, void *data)
463{ 468{
464 struct rpc_task *task; 469 struct rpc_task *task;
465 sigset_t oldset; 470 sigset_t oldset;
@@ -472,12 +477,9 @@ rpc_call_async(struct rpc_clnt *clnt, struct rpc_message *msg, int flags,
472 flags |= RPC_TASK_ASYNC; 477 flags |= RPC_TASK_ASYNC;
473 478
474 /* Create/initialize a new RPC task */ 479 /* Create/initialize a new RPC task */
475 if (!callback)
476 callback = rpc_default_callback;
477 status = -ENOMEM; 480 status = -ENOMEM;
478 if (!(task = rpc_new_task(clnt, callback, flags))) 481 if (!(task = rpc_new_task(clnt, flags, tk_ops, data)))
479 goto out; 482 goto out;
480 task->tk_calldata = data;
481 483
482 /* Mask signals on GSS_AUTH upcalls */ 484 /* Mask signals on GSS_AUTH upcalls */
483 rpc_task_sigmask(task, &oldset); 485 rpc_task_sigmask(task, &oldset);
@@ -511,7 +513,7 @@ rpc_call_setup(struct rpc_task *task, struct rpc_message *msg, int flags)
511 if (task->tk_status == 0) 513 if (task->tk_status == 0)
512 task->tk_action = call_start; 514 task->tk_action = call_start;
513 else 515 else
514 task->tk_action = NULL; 516 task->tk_action = rpc_exit_task;
515} 517}
516 518
517void 519void
@@ -536,6 +538,18 @@ size_t rpc_max_payload(struct rpc_clnt *clnt)
536} 538}
537EXPORT_SYMBOL(rpc_max_payload); 539EXPORT_SYMBOL(rpc_max_payload);
538 540
541/**
542 * rpc_force_rebind - force transport to check that remote port is unchanged
543 * @clnt: client to rebind
544 *
545 */
546void rpc_force_rebind(struct rpc_clnt *clnt)
547{
548 if (clnt->cl_autobind)
549 clnt->cl_port = 0;
550}
551EXPORT_SYMBOL(rpc_force_rebind);
552
539/* 553/*
540 * Restart an (async) RPC call. Usually called from within the 554 * Restart an (async) RPC call. Usually called from within the
541 * exit handler. 555 * exit handler.
@@ -642,24 +656,26 @@ call_reserveresult(struct rpc_task *task)
642 656
643/* 657/*
644 * 2. Allocate the buffer. For details, see sched.c:rpc_malloc. 658 * 2. Allocate the buffer. For details, see sched.c:rpc_malloc.
645 * (Note: buffer memory is freed in rpc_task_release). 659 * (Note: buffer memory is freed in xprt_release).
646 */ 660 */
647static void 661static void
648call_allocate(struct rpc_task *task) 662call_allocate(struct rpc_task *task)
649{ 663{
664 struct rpc_rqst *req = task->tk_rqstp;
665 struct rpc_xprt *xprt = task->tk_xprt;
650 unsigned int bufsiz; 666 unsigned int bufsiz;
651 667
652 dprintk("RPC: %4d call_allocate (status %d)\n", 668 dprintk("RPC: %4d call_allocate (status %d)\n",
653 task->tk_pid, task->tk_status); 669 task->tk_pid, task->tk_status);
654 task->tk_action = call_bind; 670 task->tk_action = call_bind;
655 if (task->tk_buffer) 671 if (req->rq_buffer)
656 return; 672 return;
657 673
658 /* FIXME: compute buffer requirements more exactly using 674 /* FIXME: compute buffer requirements more exactly using
659 * auth->au_wslack */ 675 * auth->au_wslack */
660 bufsiz = task->tk_msg.rpc_proc->p_bufsiz + RPC_SLACK_SPACE; 676 bufsiz = task->tk_msg.rpc_proc->p_bufsiz + RPC_SLACK_SPACE;
661 677
662 if (rpc_malloc(task, bufsiz << 1) != NULL) 678 if (xprt->ops->buf_alloc(task, bufsiz << 1) != NULL)
663 return; 679 return;
664 printk(KERN_INFO "RPC: buffer allocation failed for task %p\n", task); 680 printk(KERN_INFO "RPC: buffer allocation failed for task %p\n", task);
665 681
@@ -702,14 +718,14 @@ call_encode(struct rpc_task *task)
702 task->tk_pid, task->tk_status); 718 task->tk_pid, task->tk_status);
703 719
704 /* Default buffer setup */ 720 /* Default buffer setup */
705 bufsiz = task->tk_bufsize >> 1; 721 bufsiz = req->rq_bufsize >> 1;
706 sndbuf->head[0].iov_base = (void *)task->tk_buffer; 722 sndbuf->head[0].iov_base = (void *)req->rq_buffer;
707 sndbuf->head[0].iov_len = bufsiz; 723 sndbuf->head[0].iov_len = bufsiz;
708 sndbuf->tail[0].iov_len = 0; 724 sndbuf->tail[0].iov_len = 0;
709 sndbuf->page_len = 0; 725 sndbuf->page_len = 0;
710 sndbuf->len = 0; 726 sndbuf->len = 0;
711 sndbuf->buflen = bufsiz; 727 sndbuf->buflen = bufsiz;
712 rcvbuf->head[0].iov_base = (void *)((char *)task->tk_buffer + bufsiz); 728 rcvbuf->head[0].iov_base = (void *)((char *)req->rq_buffer + bufsiz);
713 rcvbuf->head[0].iov_len = bufsiz; 729 rcvbuf->head[0].iov_len = bufsiz;
714 rcvbuf->tail[0].iov_len = 0; 730 rcvbuf->tail[0].iov_len = 0;
715 rcvbuf->page_len = 0; 731 rcvbuf->page_len = 0;
@@ -849,8 +865,7 @@ call_connect_status(struct rpc_task *task)
849 } 865 }
850 866
851 /* Something failed: remote service port may have changed */ 867 /* Something failed: remote service port may have changed */
852 if (clnt->cl_autobind) 868 rpc_force_rebind(clnt);
853 clnt->cl_port = 0;
854 869
855 switch (status) { 870 switch (status) {
856 case -ENOTCONN: 871 case -ENOTCONN:
@@ -892,7 +907,7 @@ call_transmit(struct rpc_task *task)
892 if (task->tk_status < 0) 907 if (task->tk_status < 0)
893 return; 908 return;
894 if (!task->tk_msg.rpc_proc->p_decode) { 909 if (!task->tk_msg.rpc_proc->p_decode) {
895 task->tk_action = NULL; 910 task->tk_action = rpc_exit_task;
896 rpc_wake_up_task(task); 911 rpc_wake_up_task(task);
897 } 912 }
898 return; 913 return;
@@ -931,8 +946,7 @@ call_status(struct rpc_task *task)
931 break; 946 break;
932 case -ECONNREFUSED: 947 case -ECONNREFUSED:
933 case -ENOTCONN: 948 case -ENOTCONN:
934 if (clnt->cl_autobind) 949 rpc_force_rebind(clnt);
935 clnt->cl_port = 0;
936 task->tk_action = call_bind; 950 task->tk_action = call_bind;
937 break; 951 break;
938 case -EAGAIN: 952 case -EAGAIN:
@@ -943,8 +957,7 @@ call_status(struct rpc_task *task)
943 rpc_exit(task, status); 957 rpc_exit(task, status);
944 break; 958 break;
945 default: 959 default:
946 if (clnt->cl_chatty) 960 printk("%s: RPC call returned error %d\n",
947 printk("%s: RPC call returned error %d\n",
948 clnt->cl_protname, -status); 961 clnt->cl_protname, -status);
949 rpc_exit(task, status); 962 rpc_exit(task, status);
950 break; 963 break;
@@ -979,20 +992,18 @@ call_timeout(struct rpc_task *task)
979 992
980 dprintk("RPC: %4d call_timeout (major)\n", task->tk_pid); 993 dprintk("RPC: %4d call_timeout (major)\n", task->tk_pid);
981 if (RPC_IS_SOFT(task)) { 994 if (RPC_IS_SOFT(task)) {
982 if (clnt->cl_chatty) 995 printk(KERN_NOTICE "%s: server %s not responding, timed out\n",
983 printk(KERN_NOTICE "%s: server %s not responding, timed out\n",
984 clnt->cl_protname, clnt->cl_server); 996 clnt->cl_protname, clnt->cl_server);
985 rpc_exit(task, -EIO); 997 rpc_exit(task, -EIO);
986 return; 998 return;
987 } 999 }
988 1000
989 if (clnt->cl_chatty && !(task->tk_flags & RPC_CALL_MAJORSEEN)) { 1001 if (!(task->tk_flags & RPC_CALL_MAJORSEEN)) {
990 task->tk_flags |= RPC_CALL_MAJORSEEN; 1002 task->tk_flags |= RPC_CALL_MAJORSEEN;
991 printk(KERN_NOTICE "%s: server %s not responding, still trying\n", 1003 printk(KERN_NOTICE "%s: server %s not responding, still trying\n",
992 clnt->cl_protname, clnt->cl_server); 1004 clnt->cl_protname, clnt->cl_server);
993 } 1005 }
994 if (clnt->cl_autobind) 1006 rpc_force_rebind(clnt);
995 clnt->cl_port = 0;
996 1007
997retry: 1008retry:
998 clnt->cl_stats->rpcretrans++; 1009 clnt->cl_stats->rpcretrans++;
@@ -1014,7 +1025,7 @@ call_decode(struct rpc_task *task)
1014 dprintk("RPC: %4d call_decode (status %d)\n", 1025 dprintk("RPC: %4d call_decode (status %d)\n",
1015 task->tk_pid, task->tk_status); 1026 task->tk_pid, task->tk_status);
1016 1027
1017 if (clnt->cl_chatty && (task->tk_flags & RPC_CALL_MAJORSEEN)) { 1028 if (task->tk_flags & RPC_CALL_MAJORSEEN) {
1018 printk(KERN_NOTICE "%s: server %s OK\n", 1029 printk(KERN_NOTICE "%s: server %s OK\n",
1019 clnt->cl_protname, clnt->cl_server); 1030 clnt->cl_protname, clnt->cl_server);
1020 task->tk_flags &= ~RPC_CALL_MAJORSEEN; 1031 task->tk_flags &= ~RPC_CALL_MAJORSEEN;
@@ -1039,13 +1050,14 @@ call_decode(struct rpc_task *task)
1039 sizeof(req->rq_rcv_buf)) != 0); 1050 sizeof(req->rq_rcv_buf)) != 0);
1040 1051
1041 /* Verify the RPC header */ 1052 /* Verify the RPC header */
1042 if (!(p = call_verify(task))) { 1053 p = call_verify(task);
1043 if (task->tk_action == NULL) 1054 if (IS_ERR(p)) {
1044 return; 1055 if (p == ERR_PTR(-EAGAIN))
1045 goto out_retry; 1056 goto out_retry;
1057 return;
1046 } 1058 }
1047 1059
1048 task->tk_action = NULL; 1060 task->tk_action = rpc_exit_task;
1049 1061
1050 if (decode) 1062 if (decode)
1051 task->tk_status = rpcauth_unwrap_resp(task, decode, req, p, 1063 task->tk_status = rpcauth_unwrap_resp(task, decode, req, p,
@@ -1138,7 +1150,7 @@ call_verify(struct rpc_task *task)
1138 1150
1139 if ((n = ntohl(*p++)) != RPC_REPLY) { 1151 if ((n = ntohl(*p++)) != RPC_REPLY) {
1140 printk(KERN_WARNING "call_verify: not an RPC reply: %x\n", n); 1152 printk(KERN_WARNING "call_verify: not an RPC reply: %x\n", n);
1141 goto out_retry; 1153 goto out_garbage;
1142 } 1154 }
1143 if ((n = ntohl(*p++)) != RPC_MSG_ACCEPTED) { 1155 if ((n = ntohl(*p++)) != RPC_MSG_ACCEPTED) {
1144 if (--len < 0) 1156 if (--len < 0)
@@ -1168,7 +1180,7 @@ call_verify(struct rpc_task *task)
1168 task->tk_pid); 1180 task->tk_pid);
1169 rpcauth_invalcred(task); 1181 rpcauth_invalcred(task);
1170 task->tk_action = call_refresh; 1182 task->tk_action = call_refresh;
1171 return NULL; 1183 goto out_retry;
1172 case RPC_AUTH_BADCRED: 1184 case RPC_AUTH_BADCRED:
1173 case RPC_AUTH_BADVERF: 1185 case RPC_AUTH_BADVERF:
1174 /* possibly garbled cred/verf? */ 1186 /* possibly garbled cred/verf? */
@@ -1178,7 +1190,7 @@ call_verify(struct rpc_task *task)
1178 dprintk("RPC: %4d call_verify: retry garbled creds\n", 1190 dprintk("RPC: %4d call_verify: retry garbled creds\n",
1179 task->tk_pid); 1191 task->tk_pid);
1180 task->tk_action = call_bind; 1192 task->tk_action = call_bind;
1181 return NULL; 1193 goto out_retry;
1182 case RPC_AUTH_TOOWEAK: 1194 case RPC_AUTH_TOOWEAK:
1183 printk(KERN_NOTICE "call_verify: server requires stronger " 1195 printk(KERN_NOTICE "call_verify: server requires stronger "
1184 "authentication.\n"); 1196 "authentication.\n");
@@ -1193,7 +1205,7 @@ call_verify(struct rpc_task *task)
1193 } 1205 }
1194 if (!(p = rpcauth_checkverf(task, p))) { 1206 if (!(p = rpcauth_checkverf(task, p))) {
1195 printk(KERN_WARNING "call_verify: auth check failed\n"); 1207 printk(KERN_WARNING "call_verify: auth check failed\n");
1196 goto out_retry; /* bad verifier, retry */ 1208 goto out_garbage; /* bad verifier, retry */
1197 } 1209 }
1198 len = p - (u32 *)iov->iov_base - 1; 1210 len = p - (u32 *)iov->iov_base - 1;
1199 if (len < 0) 1211 if (len < 0)
@@ -1230,23 +1242,24 @@ call_verify(struct rpc_task *task)
1230 /* Also retry */ 1242 /* Also retry */
1231 } 1243 }
1232 1244
1233out_retry: 1245out_garbage:
1234 task->tk_client->cl_stats->rpcgarbage++; 1246 task->tk_client->cl_stats->rpcgarbage++;
1235 if (task->tk_garb_retry) { 1247 if (task->tk_garb_retry) {
1236 task->tk_garb_retry--; 1248 task->tk_garb_retry--;
1237 dprintk("RPC %s: retrying %4d\n", __FUNCTION__, task->tk_pid); 1249 dprintk("RPC %s: retrying %4d\n", __FUNCTION__, task->tk_pid);
1238 task->tk_action = call_bind; 1250 task->tk_action = call_bind;
1239 return NULL; 1251out_retry:
1252 return ERR_PTR(-EAGAIN);
1240 } 1253 }
1241 printk(KERN_WARNING "RPC %s: retry failed, exit EIO\n", __FUNCTION__); 1254 printk(KERN_WARNING "RPC %s: retry failed, exit EIO\n", __FUNCTION__);
1242out_eio: 1255out_eio:
1243 error = -EIO; 1256 error = -EIO;
1244out_err: 1257out_err:
1245 rpc_exit(task, error); 1258 rpc_exit(task, error);
1246 return NULL; 1259 return ERR_PTR(error);
1247out_overflow: 1260out_overflow:
1248 printk(KERN_WARNING "RPC %s: server reply was truncated.\n", __FUNCTION__); 1261 printk(KERN_WARNING "RPC %s: server reply was truncated.\n", __FUNCTION__);
1249 goto out_retry; 1262 goto out_garbage;
1250} 1263}
1251 1264
1252static int rpcproc_encode_null(void *rqstp, u32 *data, void *obj) 1265static int rpcproc_encode_null(void *rqstp, u32 *data, void *obj)
diff --git a/net/sunrpc/pmap_clnt.c b/net/sunrpc/pmap_clnt.c
index a398575f94b8..8139ce68e915 100644
--- a/net/sunrpc/pmap_clnt.c
+++ b/net/sunrpc/pmap_clnt.c
@@ -90,8 +90,7 @@ bailout:
90 map->pm_binding = 0; 90 map->pm_binding = 0;
91 rpc_wake_up(&map->pm_bindwait); 91 rpc_wake_up(&map->pm_bindwait);
92 spin_unlock(&pmap_lock); 92 spin_unlock(&pmap_lock);
93 task->tk_status = -EIO; 93 rpc_exit(task, -EIO);
94 task->tk_action = NULL;
95} 94}
96 95
97#ifdef CONFIG_ROOT_NFS 96#ifdef CONFIG_ROOT_NFS
@@ -132,21 +131,22 @@ static void
132pmap_getport_done(struct rpc_task *task) 131pmap_getport_done(struct rpc_task *task)
133{ 132{
134 struct rpc_clnt *clnt = task->tk_client; 133 struct rpc_clnt *clnt = task->tk_client;
134 struct rpc_xprt *xprt = task->tk_xprt;
135 struct rpc_portmap *map = clnt->cl_pmap; 135 struct rpc_portmap *map = clnt->cl_pmap;
136 136
137 dprintk("RPC: %4d pmap_getport_done(status %d, port %d)\n", 137 dprintk("RPC: %4d pmap_getport_done(status %d, port %d)\n",
138 task->tk_pid, task->tk_status, clnt->cl_port); 138 task->tk_pid, task->tk_status, clnt->cl_port);
139
140 xprt->ops->set_port(xprt, 0);
139 if (task->tk_status < 0) { 141 if (task->tk_status < 0) {
140 /* Make the calling task exit with an error */ 142 /* Make the calling task exit with an error */
141 task->tk_action = NULL; 143 task->tk_action = rpc_exit_task;
142 } else if (clnt->cl_port == 0) { 144 } else if (clnt->cl_port == 0) {
143 /* Program not registered */ 145 /* Program not registered */
144 task->tk_status = -EACCES; 146 rpc_exit(task, -EACCES);
145 task->tk_action = NULL;
146 } else { 147 } else {
147 /* byte-swap port number first */ 148 xprt->ops->set_port(xprt, clnt->cl_port);
148 clnt->cl_port = htons(clnt->cl_port); 149 clnt->cl_port = htons(clnt->cl_port);
149 clnt->cl_xprt->addr.sin_port = clnt->cl_port;
150 } 150 }
151 spin_lock(&pmap_lock); 151 spin_lock(&pmap_lock);
152 map->pm_binding = 0; 152 map->pm_binding = 0;
@@ -207,7 +207,7 @@ pmap_create(char *hostname, struct sockaddr_in *srvaddr, int proto, int privileg
207 xprt = xprt_create_proto(proto, srvaddr, NULL); 207 xprt = xprt_create_proto(proto, srvaddr, NULL);
208 if (IS_ERR(xprt)) 208 if (IS_ERR(xprt))
209 return (struct rpc_clnt *)xprt; 209 return (struct rpc_clnt *)xprt;
210 xprt->addr.sin_port = htons(RPC_PMAP_PORT); 210 xprt->ops->set_port(xprt, RPC_PMAP_PORT);
211 if (!privileged) 211 if (!privileged)
212 xprt->resvport = 0; 212 xprt->resvport = 0;
213 213
@@ -217,7 +217,6 @@ pmap_create(char *hostname, struct sockaddr_in *srvaddr, int proto, int privileg
217 RPC_AUTH_UNIX); 217 RPC_AUTH_UNIX);
218 if (!IS_ERR(clnt)) { 218 if (!IS_ERR(clnt)) {
219 clnt->cl_softrtry = 1; 219 clnt->cl_softrtry = 1;
220 clnt->cl_chatty = 1;
221 clnt->cl_oneshot = 1; 220 clnt->cl_oneshot = 1;
222 } 221 }
223 return clnt; 222 return clnt;
diff --git a/net/sunrpc/rpc_pipe.c b/net/sunrpc/rpc_pipe.c
index 16a2458f38f7..24cc23af9b95 100644
--- a/net/sunrpc/rpc_pipe.c
+++ b/net/sunrpc/rpc_pipe.c
@@ -70,8 +70,11 @@ rpc_timeout_upcall_queue(void *data)
70 struct inode *inode = &rpci->vfs_inode; 70 struct inode *inode = &rpci->vfs_inode;
71 71
72 down(&inode->i_sem); 72 down(&inode->i_sem);
73 if (rpci->ops == NULL)
74 goto out;
73 if (rpci->nreaders == 0 && !list_empty(&rpci->pipe)) 75 if (rpci->nreaders == 0 && !list_empty(&rpci->pipe))
74 __rpc_purge_upcall(inode, -ETIMEDOUT); 76 __rpc_purge_upcall(inode, -ETIMEDOUT);
77out:
75 up(&inode->i_sem); 78 up(&inode->i_sem);
76} 79}
77 80
@@ -113,8 +116,6 @@ rpc_close_pipes(struct inode *inode)
113{ 116{
114 struct rpc_inode *rpci = RPC_I(inode); 117 struct rpc_inode *rpci = RPC_I(inode);
115 118
116 cancel_delayed_work(&rpci->queue_timeout);
117 flush_scheduled_work();
118 down(&inode->i_sem); 119 down(&inode->i_sem);
119 if (rpci->ops != NULL) { 120 if (rpci->ops != NULL) {
120 rpci->nreaders = 0; 121 rpci->nreaders = 0;
@@ -127,6 +128,8 @@ rpc_close_pipes(struct inode *inode)
127 } 128 }
128 rpc_inode_setowner(inode, NULL); 129 rpc_inode_setowner(inode, NULL);
129 up(&inode->i_sem); 130 up(&inode->i_sem);
131 cancel_delayed_work(&rpci->queue_timeout);
132 flush_scheduled_work();
130} 133}
131 134
132static struct inode * 135static struct inode *
@@ -166,7 +169,7 @@ rpc_pipe_open(struct inode *inode, struct file *filp)
166static int 169static int
167rpc_pipe_release(struct inode *inode, struct file *filp) 170rpc_pipe_release(struct inode *inode, struct file *filp)
168{ 171{
169 struct rpc_inode *rpci = RPC_I(filp->f_dentry->d_inode); 172 struct rpc_inode *rpci = RPC_I(inode);
170 struct rpc_pipe_msg *msg; 173 struct rpc_pipe_msg *msg;
171 174
172 down(&inode->i_sem); 175 down(&inode->i_sem);
diff --git a/net/sunrpc/sched.c b/net/sunrpc/sched.c
index 54e60a657500..7415406aa1ae 100644
--- a/net/sunrpc/sched.c
+++ b/net/sunrpc/sched.c
@@ -41,8 +41,6 @@ static mempool_t *rpc_buffer_mempool __read_mostly;
41 41
42static void __rpc_default_timer(struct rpc_task *task); 42static void __rpc_default_timer(struct rpc_task *task);
43static void rpciod_killall(void); 43static void rpciod_killall(void);
44static void rpc_free(struct rpc_task *task);
45
46static void rpc_async_schedule(void *); 44static void rpc_async_schedule(void *);
47 45
48/* 46/*
@@ -264,6 +262,35 @@ void rpc_init_wait_queue(struct rpc_wait_queue *queue, const char *qname)
264} 262}
265EXPORT_SYMBOL(rpc_init_wait_queue); 263EXPORT_SYMBOL(rpc_init_wait_queue);
266 264
265static int rpc_wait_bit_interruptible(void *word)
266{
267 if (signal_pending(current))
268 return -ERESTARTSYS;
269 schedule();
270 return 0;
271}
272
273/*
274 * Mark an RPC call as having completed by clearing the 'active' bit
275 */
276static inline void rpc_mark_complete_task(struct rpc_task *task)
277{
278 rpc_clear_active(task);
279 wake_up_bit(&task->tk_runstate, RPC_TASK_ACTIVE);
280}
281
282/*
283 * Allow callers to wait for completion of an RPC call
284 */
285int __rpc_wait_for_completion_task(struct rpc_task *task, int (*action)(void *))
286{
287 if (action == NULL)
288 action = rpc_wait_bit_interruptible;
289 return wait_on_bit(&task->tk_runstate, RPC_TASK_ACTIVE,
290 action, TASK_INTERRUPTIBLE);
291}
292EXPORT_SYMBOL(__rpc_wait_for_completion_task);
293
267/* 294/*
268 * Make an RPC task runnable. 295 * Make an RPC task runnable.
269 * 296 *
@@ -299,10 +326,7 @@ static void rpc_make_runnable(struct rpc_task *task)
299static inline void 326static inline void
300rpc_schedule_run(struct rpc_task *task) 327rpc_schedule_run(struct rpc_task *task)
301{ 328{
302 /* Don't run a child twice! */ 329 rpc_set_active(task);
303 if (RPC_IS_ACTIVATED(task))
304 return;
305 task->tk_active = 1;
306 rpc_make_runnable(task); 330 rpc_make_runnable(task);
307} 331}
308 332
@@ -324,8 +348,7 @@ static void __rpc_sleep_on(struct rpc_wait_queue *q, struct rpc_task *task,
324 } 348 }
325 349
326 /* Mark the task as being activated if so needed */ 350 /* Mark the task as being activated if so needed */
327 if (!RPC_IS_ACTIVATED(task)) 351 rpc_set_active(task);
328 task->tk_active = 1;
329 352
330 __rpc_add_wait_queue(q, task); 353 __rpc_add_wait_queue(q, task);
331 354
@@ -555,36 +578,29 @@ __rpc_atrun(struct rpc_task *task)
555} 578}
556 579
557/* 580/*
558 * Helper that calls task->tk_exit if it exists and then returns 581 * Helper to call task->tk_ops->rpc_call_prepare
559 * true if we should exit __rpc_execute.
560 */ 582 */
561static inline int __rpc_do_exit(struct rpc_task *task) 583static void rpc_prepare_task(struct rpc_task *task)
562{ 584{
563 if (task->tk_exit != NULL) { 585 task->tk_ops->rpc_call_prepare(task, task->tk_calldata);
564 lock_kernel();
565 task->tk_exit(task);
566 unlock_kernel();
567 /* If tk_action is non-null, we should restart the call */
568 if (task->tk_action != NULL) {
569 if (!RPC_ASSASSINATED(task)) {
570 /* Release RPC slot and buffer memory */
571 xprt_release(task);
572 rpc_free(task);
573 return 0;
574 }
575 printk(KERN_ERR "RPC: dead task tried to walk away.\n");
576 }
577 }
578 return 1;
579} 586}
580 587
581static int rpc_wait_bit_interruptible(void *word) 588/*
589 * Helper that calls task->tk_ops->rpc_call_done if it exists
590 */
591void rpc_exit_task(struct rpc_task *task)
582{ 592{
583 if (signal_pending(current)) 593 task->tk_action = NULL;
584 return -ERESTARTSYS; 594 if (task->tk_ops->rpc_call_done != NULL) {
585 schedule(); 595 task->tk_ops->rpc_call_done(task, task->tk_calldata);
586 return 0; 596 if (task->tk_action != NULL) {
597 WARN_ON(RPC_ASSASSINATED(task));
598 /* Always release the RPC slot and buffer memory */
599 xprt_release(task);
600 }
601 }
587} 602}
603EXPORT_SYMBOL(rpc_exit_task);
588 604
589/* 605/*
590 * This is the RPC `scheduler' (or rather, the finite state machine). 606 * This is the RPC `scheduler' (or rather, the finite state machine).
@@ -631,12 +647,11 @@ static int __rpc_execute(struct rpc_task *task)
631 * by someone else. 647 * by someone else.
632 */ 648 */
633 if (!RPC_IS_QUEUED(task)) { 649 if (!RPC_IS_QUEUED(task)) {
634 if (task->tk_action != NULL) { 650 if (task->tk_action == NULL)
635 lock_kernel();
636 task->tk_action(task);
637 unlock_kernel();
638 } else if (__rpc_do_exit(task))
639 break; 651 break;
652 lock_kernel();
653 task->tk_action(task);
654 unlock_kernel();
640 } 655 }
641 656
642 /* 657 /*
@@ -676,9 +691,9 @@ static int __rpc_execute(struct rpc_task *task)
676 dprintk("RPC: %4d sync task resuming\n", task->tk_pid); 691 dprintk("RPC: %4d sync task resuming\n", task->tk_pid);
677 } 692 }
678 693
679 dprintk("RPC: %4d exit() = %d\n", task->tk_pid, task->tk_status); 694 dprintk("RPC: %4d, return %d, status %d\n", task->tk_pid, status, task->tk_status);
680 status = task->tk_status; 695 /* Wake up anyone who is waiting for task completion */
681 696 rpc_mark_complete_task(task);
682 /* Release all resources associated with the task */ 697 /* Release all resources associated with the task */
683 rpc_release_task(task); 698 rpc_release_task(task);
684 return status; 699 return status;
@@ -696,9 +711,7 @@ static int __rpc_execute(struct rpc_task *task)
696int 711int
697rpc_execute(struct rpc_task *task) 712rpc_execute(struct rpc_task *task)
698{ 713{
699 BUG_ON(task->tk_active); 714 rpc_set_active(task);
700
701 task->tk_active = 1;
702 rpc_set_running(task); 715 rpc_set_running(task);
703 return __rpc_execute(task); 716 return __rpc_execute(task);
704} 717}
@@ -708,17 +721,19 @@ static void rpc_async_schedule(void *arg)
708 __rpc_execute((struct rpc_task *)arg); 721 __rpc_execute((struct rpc_task *)arg);
709} 722}
710 723
711/* 724/**
712 * Allocate memory for RPC purposes. 725 * rpc_malloc - allocate an RPC buffer
726 * @task: RPC task that will use this buffer
727 * @size: requested byte size
713 * 728 *
714 * We try to ensure that some NFS reads and writes can always proceed 729 * We try to ensure that some NFS reads and writes can always proceed
715 * by using a mempool when allocating 'small' buffers. 730 * by using a mempool when allocating 'small' buffers.
716 * In order to avoid memory starvation triggering more writebacks of 731 * In order to avoid memory starvation triggering more writebacks of
717 * NFS requests, we use GFP_NOFS rather than GFP_KERNEL. 732 * NFS requests, we use GFP_NOFS rather than GFP_KERNEL.
718 */ 733 */
719void * 734void * rpc_malloc(struct rpc_task *task, size_t size)
720rpc_malloc(struct rpc_task *task, size_t size)
721{ 735{
736 struct rpc_rqst *req = task->tk_rqstp;
722 gfp_t gfp; 737 gfp_t gfp;
723 738
724 if (task->tk_flags & RPC_TASK_SWAPPER) 739 if (task->tk_flags & RPC_TASK_SWAPPER)
@@ -727,42 +742,52 @@ rpc_malloc(struct rpc_task *task, size_t size)
727 gfp = GFP_NOFS; 742 gfp = GFP_NOFS;
728 743
729 if (size > RPC_BUFFER_MAXSIZE) { 744 if (size > RPC_BUFFER_MAXSIZE) {
730 task->tk_buffer = kmalloc(size, gfp); 745 req->rq_buffer = kmalloc(size, gfp);
731 if (task->tk_buffer) 746 if (req->rq_buffer)
732 task->tk_bufsize = size; 747 req->rq_bufsize = size;
733 } else { 748 } else {
734 task->tk_buffer = mempool_alloc(rpc_buffer_mempool, gfp); 749 req->rq_buffer = mempool_alloc(rpc_buffer_mempool, gfp);
735 if (task->tk_buffer) 750 if (req->rq_buffer)
736 task->tk_bufsize = RPC_BUFFER_MAXSIZE; 751 req->rq_bufsize = RPC_BUFFER_MAXSIZE;
737 } 752 }
738 return task->tk_buffer; 753 return req->rq_buffer;
739} 754}
740 755
741static void 756/**
742rpc_free(struct rpc_task *task) 757 * rpc_free - free buffer allocated via rpc_malloc
758 * @task: RPC task with a buffer to be freed
759 *
760 */
761void rpc_free(struct rpc_task *task)
743{ 762{
744 if (task->tk_buffer) { 763 struct rpc_rqst *req = task->tk_rqstp;
745 if (task->tk_bufsize == RPC_BUFFER_MAXSIZE) 764
746 mempool_free(task->tk_buffer, rpc_buffer_mempool); 765 if (req->rq_buffer) {
766 if (req->rq_bufsize == RPC_BUFFER_MAXSIZE)
767 mempool_free(req->rq_buffer, rpc_buffer_mempool);
747 else 768 else
748 kfree(task->tk_buffer); 769 kfree(req->rq_buffer);
749 task->tk_buffer = NULL; 770 req->rq_buffer = NULL;
750 task->tk_bufsize = 0; 771 req->rq_bufsize = 0;
751 } 772 }
752} 773}
753 774
754/* 775/*
755 * Creation and deletion of RPC task structures 776 * Creation and deletion of RPC task structures
756 */ 777 */
757void rpc_init_task(struct rpc_task *task, struct rpc_clnt *clnt, rpc_action callback, int flags) 778void rpc_init_task(struct rpc_task *task, struct rpc_clnt *clnt, int flags, const struct rpc_call_ops *tk_ops, void *calldata)
758{ 779{
759 memset(task, 0, sizeof(*task)); 780 memset(task, 0, sizeof(*task));
760 init_timer(&task->tk_timer); 781 init_timer(&task->tk_timer);
761 task->tk_timer.data = (unsigned long) task; 782 task->tk_timer.data = (unsigned long) task;
762 task->tk_timer.function = (void (*)(unsigned long)) rpc_run_timer; 783 task->tk_timer.function = (void (*)(unsigned long)) rpc_run_timer;
784 atomic_set(&task->tk_count, 1);
763 task->tk_client = clnt; 785 task->tk_client = clnt;
764 task->tk_flags = flags; 786 task->tk_flags = flags;
765 task->tk_exit = callback; 787 task->tk_ops = tk_ops;
788 if (tk_ops->rpc_call_prepare != NULL)
789 task->tk_action = rpc_prepare_task;
790 task->tk_calldata = calldata;
766 791
767 /* Initialize retry counters */ 792 /* Initialize retry counters */
768 task->tk_garb_retry = 2; 793 task->tk_garb_retry = 2;
@@ -791,6 +816,8 @@ void rpc_init_task(struct rpc_task *task, struct rpc_clnt *clnt, rpc_action call
791 list_add_tail(&task->tk_task, &all_tasks); 816 list_add_tail(&task->tk_task, &all_tasks);
792 spin_unlock(&rpc_sched_lock); 817 spin_unlock(&rpc_sched_lock);
793 818
819 BUG_ON(task->tk_ops == NULL);
820
794 dprintk("RPC: %4d new task procpid %d\n", task->tk_pid, 821 dprintk("RPC: %4d new task procpid %d\n", task->tk_pid,
795 current->pid); 822 current->pid);
796} 823}
@@ -801,8 +828,7 @@ rpc_alloc_task(void)
801 return (struct rpc_task *)mempool_alloc(rpc_task_mempool, GFP_NOFS); 828 return (struct rpc_task *)mempool_alloc(rpc_task_mempool, GFP_NOFS);
802} 829}
803 830
804static void 831static void rpc_free_task(struct rpc_task *task)
805rpc_default_free_task(struct rpc_task *task)
806{ 832{
807 dprintk("RPC: %4d freeing task\n", task->tk_pid); 833 dprintk("RPC: %4d freeing task\n", task->tk_pid);
808 mempool_free(task, rpc_task_mempool); 834 mempool_free(task, rpc_task_mempool);
@@ -813,8 +839,7 @@ rpc_default_free_task(struct rpc_task *task)
813 * clean up after an allocation failure, as the client may 839 * clean up after an allocation failure, as the client may
814 * have specified "oneshot". 840 * have specified "oneshot".
815 */ 841 */
816struct rpc_task * 842struct rpc_task *rpc_new_task(struct rpc_clnt *clnt, int flags, const struct rpc_call_ops *tk_ops, void *calldata)
817rpc_new_task(struct rpc_clnt *clnt, rpc_action callback, int flags)
818{ 843{
819 struct rpc_task *task; 844 struct rpc_task *task;
820 845
@@ -822,10 +847,7 @@ rpc_new_task(struct rpc_clnt *clnt, rpc_action callback, int flags)
822 if (!task) 847 if (!task)
823 goto cleanup; 848 goto cleanup;
824 849
825 rpc_init_task(task, clnt, callback, flags); 850 rpc_init_task(task, clnt, flags, tk_ops, calldata);
826
827 /* Replace tk_release */
828 task->tk_release = rpc_default_free_task;
829 851
830 dprintk("RPC: %4d allocated task\n", task->tk_pid); 852 dprintk("RPC: %4d allocated task\n", task->tk_pid);
831 task->tk_flags |= RPC_TASK_DYNAMIC; 853 task->tk_flags |= RPC_TASK_DYNAMIC;
@@ -845,11 +867,15 @@ cleanup:
845 867
846void rpc_release_task(struct rpc_task *task) 868void rpc_release_task(struct rpc_task *task)
847{ 869{
848 dprintk("RPC: %4d release task\n", task->tk_pid); 870 const struct rpc_call_ops *tk_ops = task->tk_ops;
871 void *calldata = task->tk_calldata;
849 872
850#ifdef RPC_DEBUG 873#ifdef RPC_DEBUG
851 BUG_ON(task->tk_magic != RPC_TASK_MAGIC_ID); 874 BUG_ON(task->tk_magic != RPC_TASK_MAGIC_ID);
852#endif 875#endif
876 if (!atomic_dec_and_test(&task->tk_count))
877 return;
878 dprintk("RPC: %4d release task\n", task->tk_pid);
853 879
854 /* Remove from global task list */ 880 /* Remove from global task list */
855 spin_lock(&rpc_sched_lock); 881 spin_lock(&rpc_sched_lock);
@@ -857,7 +883,6 @@ void rpc_release_task(struct rpc_task *task)
857 spin_unlock(&rpc_sched_lock); 883 spin_unlock(&rpc_sched_lock);
858 884
859 BUG_ON (RPC_IS_QUEUED(task)); 885 BUG_ON (RPC_IS_QUEUED(task));
860 task->tk_active = 0;
861 886
862 /* Synchronously delete any running timer */ 887 /* Synchronously delete any running timer */
863 rpc_delete_timer(task); 888 rpc_delete_timer(task);
@@ -867,7 +892,6 @@ void rpc_release_task(struct rpc_task *task)
867 xprt_release(task); 892 xprt_release(task);
868 if (task->tk_msg.rpc_cred) 893 if (task->tk_msg.rpc_cred)
869 rpcauth_unbindcred(task); 894 rpcauth_unbindcred(task);
870 rpc_free(task);
871 if (task->tk_client) { 895 if (task->tk_client) {
872 rpc_release_client(task->tk_client); 896 rpc_release_client(task->tk_client);
873 task->tk_client = NULL; 897 task->tk_client = NULL;
@@ -876,11 +900,34 @@ void rpc_release_task(struct rpc_task *task)
876#ifdef RPC_DEBUG 900#ifdef RPC_DEBUG
877 task->tk_magic = 0; 901 task->tk_magic = 0;
878#endif 902#endif
879 if (task->tk_release) 903 if (task->tk_flags & RPC_TASK_DYNAMIC)
880 task->tk_release(task); 904 rpc_free_task(task);
905 if (tk_ops->rpc_release)
906 tk_ops->rpc_release(calldata);
881} 907}
882 908
883/** 909/**
910 * rpc_run_task - Allocate a new RPC task, then run rpc_execute against it
911 * @clnt - pointer to RPC client
912 * @flags - RPC flags
913 * @ops - RPC call ops
914 * @data - user call data
915 */
916struct rpc_task *rpc_run_task(struct rpc_clnt *clnt, int flags,
917 const struct rpc_call_ops *ops,
918 void *data)
919{
920 struct rpc_task *task;
921 task = rpc_new_task(clnt, flags, ops, data);
922 if (task == NULL)
923 return ERR_PTR(-ENOMEM);
924 atomic_inc(&task->tk_count);
925 rpc_execute(task);
926 return task;
927}
928EXPORT_SYMBOL(rpc_run_task);
929
930/**
884 * rpc_find_parent - find the parent of a child task. 931 * rpc_find_parent - find the parent of a child task.
885 * @child: child task 932 * @child: child task
886 * 933 *
@@ -890,12 +937,11 @@ void rpc_release_task(struct rpc_task *task)
890 * 937 *
891 * Caller must hold childq.lock 938 * Caller must hold childq.lock
892 */ 939 */
893static inline struct rpc_task *rpc_find_parent(struct rpc_task *child) 940static inline struct rpc_task *rpc_find_parent(struct rpc_task *child, struct rpc_task *parent)
894{ 941{
895 struct rpc_task *task, *parent; 942 struct rpc_task *task;
896 struct list_head *le; 943 struct list_head *le;
897 944
898 parent = (struct rpc_task *) child->tk_calldata;
899 task_for_each(task, le, &childq.tasks[0]) 945 task_for_each(task, le, &childq.tasks[0])
900 if (task == parent) 946 if (task == parent)
901 return parent; 947 return parent;
@@ -903,18 +949,22 @@ static inline struct rpc_task *rpc_find_parent(struct rpc_task *child)
903 return NULL; 949 return NULL;
904} 950}
905 951
906static void rpc_child_exit(struct rpc_task *child) 952static void rpc_child_exit(struct rpc_task *child, void *calldata)
907{ 953{
908 struct rpc_task *parent; 954 struct rpc_task *parent;
909 955
910 spin_lock_bh(&childq.lock); 956 spin_lock_bh(&childq.lock);
911 if ((parent = rpc_find_parent(child)) != NULL) { 957 if ((parent = rpc_find_parent(child, calldata)) != NULL) {
912 parent->tk_status = child->tk_status; 958 parent->tk_status = child->tk_status;
913 __rpc_wake_up_task(parent); 959 __rpc_wake_up_task(parent);
914 } 960 }
915 spin_unlock_bh(&childq.lock); 961 spin_unlock_bh(&childq.lock);
916} 962}
917 963
964static const struct rpc_call_ops rpc_child_ops = {
965 .rpc_call_done = rpc_child_exit,
966};
967
918/* 968/*
919 * Note: rpc_new_task releases the client after a failure. 969 * Note: rpc_new_task releases the client after a failure.
920 */ 970 */
@@ -923,11 +973,9 @@ rpc_new_child(struct rpc_clnt *clnt, struct rpc_task *parent)
923{ 973{
924 struct rpc_task *task; 974 struct rpc_task *task;
925 975
926 task = rpc_new_task(clnt, NULL, RPC_TASK_ASYNC | RPC_TASK_CHILD); 976 task = rpc_new_task(clnt, RPC_TASK_ASYNC | RPC_TASK_CHILD, &rpc_child_ops, parent);
927 if (!task) 977 if (!task)
928 goto fail; 978 goto fail;
929 task->tk_exit = rpc_child_exit;
930 task->tk_calldata = parent;
931 return task; 979 return task;
932 980
933fail: 981fail:
@@ -1063,7 +1111,7 @@ void rpc_show_tasks(void)
1063 return; 1111 return;
1064 } 1112 }
1065 printk("-pid- proc flgs status -client- -prog- --rqstp- -timeout " 1113 printk("-pid- proc flgs status -client- -prog- --rqstp- -timeout "
1066 "-rpcwait -action- --exit--\n"); 1114 "-rpcwait -action- ---ops--\n");
1067 alltask_for_each(t, le, &all_tasks) { 1115 alltask_for_each(t, le, &all_tasks) {
1068 const char *rpc_waitq = "none"; 1116 const char *rpc_waitq = "none";
1069 1117
@@ -1078,7 +1126,7 @@ void rpc_show_tasks(void)
1078 (t->tk_client ? t->tk_client->cl_prog : 0), 1126 (t->tk_client ? t->tk_client->cl_prog : 0),
1079 t->tk_rqstp, t->tk_timeout, 1127 t->tk_rqstp, t->tk_timeout,
1080 rpc_waitq, 1128 rpc_waitq,
1081 t->tk_action, t->tk_exit); 1129 t->tk_action, t->tk_ops);
1082 } 1130 }
1083 spin_unlock(&rpc_sched_lock); 1131 spin_unlock(&rpc_sched_lock);
1084} 1132}
diff --git a/net/sunrpc/sunrpc_syms.c b/net/sunrpc/sunrpc_syms.c
index a03d4b600c92..9f7373203592 100644
--- a/net/sunrpc/sunrpc_syms.c
+++ b/net/sunrpc/sunrpc_syms.c
@@ -30,8 +30,6 @@ EXPORT_SYMBOL(rpc_init_task);
30EXPORT_SYMBOL(rpc_sleep_on); 30EXPORT_SYMBOL(rpc_sleep_on);
31EXPORT_SYMBOL(rpc_wake_up_next); 31EXPORT_SYMBOL(rpc_wake_up_next);
32EXPORT_SYMBOL(rpc_wake_up_task); 32EXPORT_SYMBOL(rpc_wake_up_task);
33EXPORT_SYMBOL(rpc_new_child);
34EXPORT_SYMBOL(rpc_run_child);
35EXPORT_SYMBOL(rpciod_down); 33EXPORT_SYMBOL(rpciod_down);
36EXPORT_SYMBOL(rpciod_up); 34EXPORT_SYMBOL(rpciod_up);
37EXPORT_SYMBOL(rpc_new_task); 35EXPORT_SYMBOL(rpc_new_task);
@@ -45,7 +43,6 @@ EXPORT_SYMBOL(rpc_clone_client);
45EXPORT_SYMBOL(rpc_bind_new_program); 43EXPORT_SYMBOL(rpc_bind_new_program);
46EXPORT_SYMBOL(rpc_destroy_client); 44EXPORT_SYMBOL(rpc_destroy_client);
47EXPORT_SYMBOL(rpc_shutdown_client); 45EXPORT_SYMBOL(rpc_shutdown_client);
48EXPORT_SYMBOL(rpc_release_client);
49EXPORT_SYMBOL(rpc_killall_tasks); 46EXPORT_SYMBOL(rpc_killall_tasks);
50EXPORT_SYMBOL(rpc_call_sync); 47EXPORT_SYMBOL(rpc_call_sync);
51EXPORT_SYMBOL(rpc_call_async); 48EXPORT_SYMBOL(rpc_call_async);
@@ -120,7 +117,6 @@ EXPORT_SYMBOL(unix_domain_find);
120 117
121/* Generic XDR */ 118/* Generic XDR */
122EXPORT_SYMBOL(xdr_encode_string); 119EXPORT_SYMBOL(xdr_encode_string);
123EXPORT_SYMBOL(xdr_decode_string);
124EXPORT_SYMBOL(xdr_decode_string_inplace); 120EXPORT_SYMBOL(xdr_decode_string_inplace);
125EXPORT_SYMBOL(xdr_decode_netobj); 121EXPORT_SYMBOL(xdr_decode_netobj);
126EXPORT_SYMBOL(xdr_encode_netobj); 122EXPORT_SYMBOL(xdr_encode_netobj);
diff --git a/net/sunrpc/xdr.c b/net/sunrpc/xdr.c
index aaf08cdd19f0..ca4bfa57e116 100644
--- a/net/sunrpc/xdr.c
+++ b/net/sunrpc/xdr.c
@@ -93,27 +93,6 @@ xdr_encode_string(u32 *p, const char *string)
93} 93}
94 94
95u32 * 95u32 *
96xdr_decode_string(u32 *p, char **sp, int *lenp, int maxlen)
97{
98 unsigned int len;
99 char *string;
100
101 if ((len = ntohl(*p++)) > maxlen)
102 return NULL;
103 if (lenp)
104 *lenp = len;
105 if ((len % 4) != 0) {
106 string = (char *) p;
107 } else {
108 string = (char *) (p - 1);
109 memmove(string, p, len);
110 }
111 string[len] = '\0';
112 *sp = string;
113 return p + XDR_QUADLEN(len);
114}
115
116u32 *
117xdr_decode_string_inplace(u32 *p, char **sp, int *lenp, int maxlen) 96xdr_decode_string_inplace(u32 *p, char **sp, int *lenp, int maxlen)
118{ 97{
119 unsigned int len; 98 unsigned int len;
diff --git a/net/sunrpc/xprt.c b/net/sunrpc/xprt.c
index 6dda3860351f..8ff2c8acb223 100644
--- a/net/sunrpc/xprt.c
+++ b/net/sunrpc/xprt.c
@@ -119,6 +119,17 @@ out_sleep:
119 return 0; 119 return 0;
120} 120}
121 121
122static void xprt_clear_locked(struct rpc_xprt *xprt)
123{
124 xprt->snd_task = NULL;
125 if (!test_bit(XPRT_CLOSE_WAIT, &xprt->state) || xprt->shutdown) {
126 smp_mb__before_clear_bit();
127 clear_bit(XPRT_LOCKED, &xprt->state);
128 smp_mb__after_clear_bit();
129 } else
130 schedule_work(&xprt->task_cleanup);
131}
132
122/* 133/*
123 * xprt_reserve_xprt_cong - serialize write access to transports 134 * xprt_reserve_xprt_cong - serialize write access to transports
124 * @task: task that is requesting access to the transport 135 * @task: task that is requesting access to the transport
@@ -145,9 +156,7 @@ int xprt_reserve_xprt_cong(struct rpc_task *task)
145 } 156 }
146 return 1; 157 return 1;
147 } 158 }
148 smp_mb__before_clear_bit(); 159 xprt_clear_locked(xprt);
149 clear_bit(XPRT_LOCKED, &xprt->state);
150 smp_mb__after_clear_bit();
151out_sleep: 160out_sleep:
152 dprintk("RPC: %4d failed to lock transport %p\n", task->tk_pid, xprt); 161 dprintk("RPC: %4d failed to lock transport %p\n", task->tk_pid, xprt);
153 task->tk_timeout = 0; 162 task->tk_timeout = 0;
@@ -193,9 +202,7 @@ static void __xprt_lock_write_next(struct rpc_xprt *xprt)
193 return; 202 return;
194 203
195out_unlock: 204out_unlock:
196 smp_mb__before_clear_bit(); 205 xprt_clear_locked(xprt);
197 clear_bit(XPRT_LOCKED, &xprt->state);
198 smp_mb__after_clear_bit();
199} 206}
200 207
201static void __xprt_lock_write_next_cong(struct rpc_xprt *xprt) 208static void __xprt_lock_write_next_cong(struct rpc_xprt *xprt)
@@ -222,9 +229,7 @@ static void __xprt_lock_write_next_cong(struct rpc_xprt *xprt)
222 return; 229 return;
223 } 230 }
224out_unlock: 231out_unlock:
225 smp_mb__before_clear_bit(); 232 xprt_clear_locked(xprt);
226 clear_bit(XPRT_LOCKED, &xprt->state);
227 smp_mb__after_clear_bit();
228} 233}
229 234
230/** 235/**
@@ -237,10 +242,7 @@ out_unlock:
237void xprt_release_xprt(struct rpc_xprt *xprt, struct rpc_task *task) 242void xprt_release_xprt(struct rpc_xprt *xprt, struct rpc_task *task)
238{ 243{
239 if (xprt->snd_task == task) { 244 if (xprt->snd_task == task) {
240 xprt->snd_task = NULL; 245 xprt_clear_locked(xprt);
241 smp_mb__before_clear_bit();
242 clear_bit(XPRT_LOCKED, &xprt->state);
243 smp_mb__after_clear_bit();
244 __xprt_lock_write_next(xprt); 246 __xprt_lock_write_next(xprt);
245 } 247 }
246} 248}
@@ -256,10 +258,7 @@ void xprt_release_xprt(struct rpc_xprt *xprt, struct rpc_task *task)
256void xprt_release_xprt_cong(struct rpc_xprt *xprt, struct rpc_task *task) 258void xprt_release_xprt_cong(struct rpc_xprt *xprt, struct rpc_task *task)
257{ 259{
258 if (xprt->snd_task == task) { 260 if (xprt->snd_task == task) {
259 xprt->snd_task = NULL; 261 xprt_clear_locked(xprt);
260 smp_mb__before_clear_bit();
261 clear_bit(XPRT_LOCKED, &xprt->state);
262 smp_mb__after_clear_bit();
263 __xprt_lock_write_next_cong(xprt); 262 __xprt_lock_write_next_cong(xprt);
264 } 263 }
265} 264}
@@ -535,10 +534,6 @@ void xprt_connect(struct rpc_task *task)
535 dprintk("RPC: %4d xprt_connect xprt %p %s connected\n", task->tk_pid, 534 dprintk("RPC: %4d xprt_connect xprt %p %s connected\n", task->tk_pid,
536 xprt, (xprt_connected(xprt) ? "is" : "is not")); 535 xprt, (xprt_connected(xprt) ? "is" : "is not"));
537 536
538 if (xprt->shutdown) {
539 task->tk_status = -EIO;
540 return;
541 }
542 if (!xprt->addr.sin_port) { 537 if (!xprt->addr.sin_port) {
543 task->tk_status = -EIO; 538 task->tk_status = -EIO;
544 return; 539 return;
@@ -687,9 +682,6 @@ int xprt_prepare_transmit(struct rpc_task *task)
687 682
688 dprintk("RPC: %4d xprt_prepare_transmit\n", task->tk_pid); 683 dprintk("RPC: %4d xprt_prepare_transmit\n", task->tk_pid);
689 684
690 if (xprt->shutdown)
691 return -EIO;
692
693 spin_lock_bh(&xprt->transport_lock); 685 spin_lock_bh(&xprt->transport_lock);
694 if (req->rq_received && !req->rq_bytes_sent) { 686 if (req->rq_received && !req->rq_bytes_sent) {
695 err = req->rq_received; 687 err = req->rq_received;
@@ -814,11 +806,9 @@ void xprt_reserve(struct rpc_task *task)
814 struct rpc_xprt *xprt = task->tk_xprt; 806 struct rpc_xprt *xprt = task->tk_xprt;
815 807
816 task->tk_status = -EIO; 808 task->tk_status = -EIO;
817 if (!xprt->shutdown) { 809 spin_lock(&xprt->reserve_lock);
818 spin_lock(&xprt->reserve_lock); 810 do_xprt_reserve(task);
819 do_xprt_reserve(task); 811 spin_unlock(&xprt->reserve_lock);
820 spin_unlock(&xprt->reserve_lock);
821 }
822} 812}
823 813
824static inline u32 xprt_alloc_xid(struct rpc_xprt *xprt) 814static inline u32 xprt_alloc_xid(struct rpc_xprt *xprt)
@@ -838,6 +828,8 @@ static void xprt_request_init(struct rpc_task *task, struct rpc_xprt *xprt)
838 req->rq_timeout = xprt->timeout.to_initval; 828 req->rq_timeout = xprt->timeout.to_initval;
839 req->rq_task = task; 829 req->rq_task = task;
840 req->rq_xprt = xprt; 830 req->rq_xprt = xprt;
831 req->rq_buffer = NULL;
832 req->rq_bufsize = 0;
841 req->rq_xid = xprt_alloc_xid(xprt); 833 req->rq_xid = xprt_alloc_xid(xprt);
842 req->rq_release_snd_buf = NULL; 834 req->rq_release_snd_buf = NULL;
843 dprintk("RPC: %4d reserved req %p xid %08x\n", task->tk_pid, 835 dprintk("RPC: %4d reserved req %p xid %08x\n", task->tk_pid,
@@ -863,10 +855,11 @@ void xprt_release(struct rpc_task *task)
863 if (!list_empty(&req->rq_list)) 855 if (!list_empty(&req->rq_list))
864 list_del(&req->rq_list); 856 list_del(&req->rq_list);
865 xprt->last_used = jiffies; 857 xprt->last_used = jiffies;
866 if (list_empty(&xprt->recv) && !xprt->shutdown) 858 if (list_empty(&xprt->recv))
867 mod_timer(&xprt->timer, 859 mod_timer(&xprt->timer,
868 xprt->last_used + xprt->idle_timeout); 860 xprt->last_used + xprt->idle_timeout);
869 spin_unlock_bh(&xprt->transport_lock); 861 spin_unlock_bh(&xprt->transport_lock);
862 xprt->ops->buf_free(task);
870 task->tk_rqstp = NULL; 863 task->tk_rqstp = NULL;
871 if (req->rq_release_snd_buf) 864 if (req->rq_release_snd_buf)
872 req->rq_release_snd_buf(req); 865 req->rq_release_snd_buf(req);
@@ -974,16 +967,6 @@ struct rpc_xprt *xprt_create_proto(int proto, struct sockaddr_in *sap, struct rp
974 return xprt; 967 return xprt;
975} 968}
976 969
977static void xprt_shutdown(struct rpc_xprt *xprt)
978{
979 xprt->shutdown = 1;
980 rpc_wake_up(&xprt->sending);
981 rpc_wake_up(&xprt->resend);
982 xprt_wake_pending_tasks(xprt, -EIO);
983 rpc_wake_up(&xprt->backlog);
984 del_timer_sync(&xprt->timer);
985}
986
987/** 970/**
988 * xprt_destroy - destroy an RPC transport, killing off all requests. 971 * xprt_destroy - destroy an RPC transport, killing off all requests.
989 * @xprt: transport to destroy 972 * @xprt: transport to destroy
@@ -992,7 +975,8 @@ static void xprt_shutdown(struct rpc_xprt *xprt)
992int xprt_destroy(struct rpc_xprt *xprt) 975int xprt_destroy(struct rpc_xprt *xprt)
993{ 976{
994 dprintk("RPC: destroying transport %p\n", xprt); 977 dprintk("RPC: destroying transport %p\n", xprt);
995 xprt_shutdown(xprt); 978 xprt->shutdown = 1;
979 del_timer_sync(&xprt->timer);
996 xprt->ops->destroy(xprt); 980 xprt->ops->destroy(xprt);
997 kfree(xprt); 981 kfree(xprt);
998 982
diff --git a/net/sunrpc/xprtsock.c b/net/sunrpc/xprtsock.c
index 77e8800d4127..c458f8d1d6d1 100644
--- a/net/sunrpc/xprtsock.c
+++ b/net/sunrpc/xprtsock.c
@@ -28,6 +28,7 @@
28#include <linux/udp.h> 28#include <linux/udp.h>
29#include <linux/tcp.h> 29#include <linux/tcp.h>
30#include <linux/sunrpc/clnt.h> 30#include <linux/sunrpc/clnt.h>
31#include <linux/sunrpc/sched.h>
31#include <linux/file.h> 32#include <linux/file.h>
32 33
33#include <net/sock.h> 34#include <net/sock.h>
@@ -424,7 +425,7 @@ static void xs_close(struct rpc_xprt *xprt)
424 struct sock *sk = xprt->inet; 425 struct sock *sk = xprt->inet;
425 426
426 if (!sk) 427 if (!sk)
427 return; 428 goto clear_close_wait;
428 429
429 dprintk("RPC: xs_close xprt %p\n", xprt); 430 dprintk("RPC: xs_close xprt %p\n", xprt);
430 431
@@ -441,6 +442,10 @@ static void xs_close(struct rpc_xprt *xprt)
441 sk->sk_no_check = 0; 442 sk->sk_no_check = 0;
442 443
443 sock_release(sock); 444 sock_release(sock);
445clear_close_wait:
446 smp_mb__before_clear_bit();
447 clear_bit(XPRT_CLOSE_WAIT, &xprt->state);
448 smp_mb__after_clear_bit();
444} 449}
445 450
446/** 451/**
@@ -800,9 +805,13 @@ static void xs_tcp_state_change(struct sock *sk)
800 case TCP_SYN_SENT: 805 case TCP_SYN_SENT:
801 case TCP_SYN_RECV: 806 case TCP_SYN_RECV:
802 break; 807 break;
808 case TCP_CLOSE_WAIT:
809 /* Try to schedule an autoclose RPC calls */
810 set_bit(XPRT_CLOSE_WAIT, &xprt->state);
811 if (test_and_set_bit(XPRT_LOCKED, &xprt->state) == 0)
812 schedule_work(&xprt->task_cleanup);
803 default: 813 default:
804 xprt_disconnect(xprt); 814 xprt_disconnect(xprt);
805 break;
806 } 815 }
807 out: 816 out:
808 read_unlock(&sk->sk_callback_lock); 817 read_unlock(&sk->sk_callback_lock);
@@ -920,6 +929,18 @@ static void xs_udp_timer(struct rpc_task *task)
920 xprt_adjust_cwnd(task, -ETIMEDOUT); 929 xprt_adjust_cwnd(task, -ETIMEDOUT);
921} 930}
922 931
932/**
933 * xs_set_port - reset the port number in the remote endpoint address
934 * @xprt: generic transport
935 * @port: new port number
936 *
937 */
938static void xs_set_port(struct rpc_xprt *xprt, unsigned short port)
939{
940 dprintk("RPC: setting port for xprt %p to %u\n", xprt, port);
941 xprt->addr.sin_port = htons(port);
942}
943
923static int xs_bindresvport(struct rpc_xprt *xprt, struct socket *sock) 944static int xs_bindresvport(struct rpc_xprt *xprt, struct socket *sock)
924{ 945{
925 struct sockaddr_in myaddr = { 946 struct sockaddr_in myaddr = {
@@ -1160,7 +1181,10 @@ static struct rpc_xprt_ops xs_udp_ops = {
1160 .set_buffer_size = xs_udp_set_buffer_size, 1181 .set_buffer_size = xs_udp_set_buffer_size,
1161 .reserve_xprt = xprt_reserve_xprt_cong, 1182 .reserve_xprt = xprt_reserve_xprt_cong,
1162 .release_xprt = xprt_release_xprt_cong, 1183 .release_xprt = xprt_release_xprt_cong,
1184 .set_port = xs_set_port,
1163 .connect = xs_connect, 1185 .connect = xs_connect,
1186 .buf_alloc = rpc_malloc,
1187 .buf_free = rpc_free,
1164 .send_request = xs_udp_send_request, 1188 .send_request = xs_udp_send_request,
1165 .set_retrans_timeout = xprt_set_retrans_timeout_rtt, 1189 .set_retrans_timeout = xprt_set_retrans_timeout_rtt,
1166 .timer = xs_udp_timer, 1190 .timer = xs_udp_timer,
@@ -1172,7 +1196,10 @@ static struct rpc_xprt_ops xs_udp_ops = {
1172static struct rpc_xprt_ops xs_tcp_ops = { 1196static struct rpc_xprt_ops xs_tcp_ops = {
1173 .reserve_xprt = xprt_reserve_xprt, 1197 .reserve_xprt = xprt_reserve_xprt,
1174 .release_xprt = xprt_release_xprt, 1198 .release_xprt = xprt_release_xprt,
1199 .set_port = xs_set_port,
1175 .connect = xs_connect, 1200 .connect = xs_connect,
1201 .buf_alloc = rpc_malloc,
1202 .buf_free = rpc_free,
1176 .send_request = xs_tcp_send_request, 1203 .send_request = xs_tcp_send_request,
1177 .set_retrans_timeout = xprt_set_retrans_timeout_def, 1204 .set_retrans_timeout = xprt_set_retrans_timeout_def,
1178 .close = xs_close, 1205 .close = xs_close,