aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/linux/sunrpc/xprt.h1
-rw-r--r--net/sunrpc/xprt.c18
-rw-r--r--net/sunrpc/xprtsock.c7
3 files changed, 19 insertions, 7 deletions
diff --git a/include/linux/sunrpc/xprt.h b/include/linux/sunrpc/xprt.h
index 009a3bb4f99..d5223993fca 100644
--- a/include/linux/sunrpc/xprt.h
+++ b/include/linux/sunrpc/xprt.h
@@ -232,6 +232,7 @@ void xprt_reserve(struct rpc_task *);
int xprt_prepare_transmit(struct rpc_task *);
void xprt_transmit(struct rpc_task *);
void xprt_receive(struct rpc_task *);
+void xprt_wake_pending_tasks(struct rpc_xprt *, int);
int xprt_adjust_timeout(struct rpc_rqst *req);
void xprt_release(struct rpc_task *);
void xprt_connect(struct rpc_task *);
diff --git a/net/sunrpc/xprt.c b/net/sunrpc/xprt.c
index 57c5e77b155..2f9cd468b95 100644
--- a/net/sunrpc/xprt.c
+++ b/net/sunrpc/xprt.c
@@ -227,6 +227,20 @@ xprt_adjust_cwnd(struct rpc_xprt *xprt, int result)
xprt->cwnd = cwnd;
}
+/**
+ * xprt_wake_pending_tasks - wake all tasks on a transport's pending queue
+ * @xprt: transport with waiting tasks
+ * @status: result code to plant in each task before waking it
+ *
+ */
+void xprt_wake_pending_tasks(struct rpc_xprt *xprt, int status)
+{
+ if (status < 0)
+ rpc_wake_up_status(&xprt->pending, status);
+ else
+ rpc_wake_up(&xprt->pending);
+}
+
static void xprt_reset_majortimeo(struct rpc_rqst *req)
{
struct rpc_timeout *to = &req->rq_xprt->timeout;
@@ -300,7 +314,7 @@ void xprt_disconnect(struct rpc_xprt *xprt)
dprintk("RPC: disconnected transport %p\n", xprt);
spin_lock_bh(&xprt->transport_lock);
xprt_clear_connected(xprt);
- rpc_wake_up_status(&xprt->pending, -ENOTCONN);
+ xprt_wake_pending_tasks(xprt, -ENOTCONN);
spin_unlock_bh(&xprt->transport_lock);
}
@@ -803,7 +817,7 @@ static void xprt_shutdown(struct rpc_xprt *xprt)
xprt->shutdown = 1;
rpc_wake_up(&xprt->sending);
rpc_wake_up(&xprt->resend);
- rpc_wake_up(&xprt->pending);
+ xprt_wake_pending_tasks(xprt, -EIO);
rpc_wake_up(&xprt->backlog);
wake_up(&xprt->cong_wait);
del_timer_sync(&xprt->timer);
diff --git a/net/sunrpc/xprtsock.c b/net/sunrpc/xprtsock.c
index 76a33b54f43..182da2edf61 100644
--- a/net/sunrpc/xprtsock.c
+++ b/net/sunrpc/xprtsock.c
@@ -703,7 +703,7 @@ static void xs_tcp_state_change(struct sock *sk)
xprt->tcp_reclen = 0;
xprt->tcp_copied = 0;
xprt->tcp_flags = XPRT_COPY_RECM | XPRT_COPY_XID;
- rpc_wake_up(&xprt->pending);
+ xprt_wake_pending_tasks(xprt, 0);
}
spin_unlock_bh(&xprt->transport_lock);
break;
@@ -920,10 +920,7 @@ static void xs_connect_worker(void *args)
}
}
out:
- if (status < 0)
- rpc_wake_up_status(&xprt->pending, status);
- else
- rpc_wake_up(&xprt->pending);
+ xprt_wake_pending_tasks(xprt, status);
out_clear:
xprt_clear_connecting(xprt);
}