aboutsummaryrefslogtreecommitdiffstats
path: root/net/sunrpc/xprt.c
diff options
context:
space:
mode:
authorTrond Myklebust <Trond.Myklebust@netapp.com>2009-03-11 14:38:00 -0400
committerTrond Myklebust <Trond.Myklebust@netapp.com>2009-03-11 14:38:00 -0400
commit2a4919919a97911b0aa4b9f5ac1eab90ba87652b (patch)
treec12eb42c34f0d0b79130ae93ebd56159e8366ee8 /net/sunrpc/xprt.c
parent482f32e65d31cbf88d08306fa5d397cc945c3c26 (diff)
SUNRPC: Return EAGAIN instead of ENOTCONN when waking up xprt->pending
While we should definitely return socket errors to the task that is currently trying to send data, there is no need to propagate the same error to all the other tasks on xprt->pending. Doing so actually slows down recovery, since it causes more than one tasks to attempt socket recovery. Signed-off-by: Trond Myklebust <Trond.Myklebust@netapp.com>
Diffstat (limited to 'net/sunrpc/xprt.c')
-rw-r--r--net/sunrpc/xprt.c20
1 files changed, 6 insertions, 14 deletions
diff --git a/net/sunrpc/xprt.c b/net/sunrpc/xprt.c
index d588e755e107..a0bfe53f1621 100644
--- a/net/sunrpc/xprt.c
+++ b/net/sunrpc/xprt.c
@@ -611,7 +611,7 @@ void xprt_disconnect_done(struct rpc_xprt *xprt)
611 dprintk("RPC: disconnected transport %p\n", xprt); 611 dprintk("RPC: disconnected transport %p\n", xprt);
612 spin_lock_bh(&xprt->transport_lock); 612 spin_lock_bh(&xprt->transport_lock);
613 xprt_clear_connected(xprt); 613 xprt_clear_connected(xprt);
614 xprt_wake_pending_tasks(xprt, -ENOTCONN); 614 xprt_wake_pending_tasks(xprt, -EAGAIN);
615 spin_unlock_bh(&xprt->transport_lock); 615 spin_unlock_bh(&xprt->transport_lock);
616} 616}
617EXPORT_SYMBOL_GPL(xprt_disconnect_done); 617EXPORT_SYMBOL_GPL(xprt_disconnect_done);
@@ -629,7 +629,7 @@ void xprt_force_disconnect(struct rpc_xprt *xprt)
629 /* Try to schedule an autoclose RPC call */ 629 /* Try to schedule an autoclose RPC call */
630 if (test_and_set_bit(XPRT_LOCKED, &xprt->state) == 0) 630 if (test_and_set_bit(XPRT_LOCKED, &xprt->state) == 0)
631 queue_work(rpciod_workqueue, &xprt->task_cleanup); 631 queue_work(rpciod_workqueue, &xprt->task_cleanup);
632 xprt_wake_pending_tasks(xprt, -ENOTCONN); 632 xprt_wake_pending_tasks(xprt, -EAGAIN);
633 spin_unlock_bh(&xprt->transport_lock); 633 spin_unlock_bh(&xprt->transport_lock);
634} 634}
635 635
@@ -656,7 +656,7 @@ void xprt_conditional_disconnect(struct rpc_xprt *xprt, unsigned int cookie)
656 /* Try to schedule an autoclose RPC call */ 656 /* Try to schedule an autoclose RPC call */
657 if (test_and_set_bit(XPRT_LOCKED, &xprt->state) == 0) 657 if (test_and_set_bit(XPRT_LOCKED, &xprt->state) == 0)
658 queue_work(rpciod_workqueue, &xprt->task_cleanup); 658 queue_work(rpciod_workqueue, &xprt->task_cleanup);
659 xprt_wake_pending_tasks(xprt, -ENOTCONN); 659 xprt_wake_pending_tasks(xprt, -EAGAIN);
660out: 660out:
661 spin_unlock_bh(&xprt->transport_lock); 661 spin_unlock_bh(&xprt->transport_lock);
662} 662}
@@ -726,9 +726,8 @@ static void xprt_connect_status(struct rpc_task *task)
726 } 726 }
727 727
728 switch (task->tk_status) { 728 switch (task->tk_status) {
729 case -ENOTCONN: 729 case -EAGAIN:
730 dprintk("RPC: %5u xprt_connect_status: connection broken\n", 730 dprintk("RPC: %5u xprt_connect_status: retrying\n", task->tk_pid);
731 task->tk_pid);
732 break; 731 break;
733 case -ETIMEDOUT: 732 case -ETIMEDOUT:
734 dprintk("RPC: %5u xprt_connect_status: connect attempt timed " 733 dprintk("RPC: %5u xprt_connect_status: connect attempt timed "
@@ -849,15 +848,8 @@ int xprt_prepare_transmit(struct rpc_task *task)
849 err = req->rq_received; 848 err = req->rq_received;
850 goto out_unlock; 849 goto out_unlock;
851 } 850 }
852 if (!xprt->ops->reserve_xprt(task)) { 851 if (!xprt->ops->reserve_xprt(task))
853 err = -EAGAIN; 852 err = -EAGAIN;
854 goto out_unlock;
855 }
856
857 if (!xprt_connected(xprt)) {
858 err = -ENOTCONN;
859 goto out_unlock;
860 }
861out_unlock: 853out_unlock:
862 spin_unlock_bh(&xprt->transport_lock); 854 spin_unlock_bh(&xprt->transport_lock);
863 return err; 855 return err;