summaryrefslogtreecommitdiffstats
path: root/net/9p/client.c
diff options
context:
space:
mode:
authorPaul Moore <pmoore@redhat.com>2014-06-17 17:30:23 -0400
committerPaul Moore <pmoore@redhat.com>2014-06-17 17:30:23 -0400
commit170b5910d9fbea79de1bb40df22eda5f98250c0c (patch)
treeca9560e878d2842d45c6f99077d0d8b8f8b0f9ba /net/9p/client.c
parent47dd0b76ace953bd2c0479076db0d3e3b9594003 (diff)
parent1860e379875dfe7271c649058aeddffe5afd9d0d (diff)
Merge tag 'v3.15' into next
Linux 3.15
Diffstat (limited to 'net/9p/client.c')
-rw-r--r--net/9p/client.c25
1 files changed, 18 insertions, 7 deletions
diff --git a/net/9p/client.c b/net/9p/client.c
index 9186550d77a..0004cbaac4a 100644
--- a/net/9p/client.c
+++ b/net/9p/client.c
@@ -415,9 +415,17 @@ static void p9_free_req(struct p9_client *c, struct p9_req_t *r)
* req: request received
*
*/
-void p9_client_cb(struct p9_client *c, struct p9_req_t *req)
+void p9_client_cb(struct p9_client *c, struct p9_req_t *req, int status)
{
p9_debug(P9_DEBUG_MUX, " tag %d\n", req->tc->tag);
+
+ /*
+ * This barrier is needed to make sure any change made to req before
+ * the other thread wakes up will indeed be seen by the waiting side.
+ */
+ smp_wmb();
+ req->status = status;
+
wake_up(req->wq);
p9_debug(P9_DEBUG_MUX, "wakeup: %d\n", req->tc->tag);
}
@@ -655,16 +663,13 @@ static int p9_client_flush(struct p9_client *c, struct p9_req_t *oldreq)
if (IS_ERR(req))
return PTR_ERR(req);
-
/*
* if we haven't received a response for oldreq,
* remove it from the list
*/
- if (oldreq->status == REQ_STATUS_FLSH) {
- spin_lock(&c->lock);
- list_del(&oldreq->req_list);
- spin_unlock(&c->lock);
- }
+ if (oldreq->status == REQ_STATUS_SENT)
+ if (c->trans_mod->cancelled)
+ c->trans_mod->cancelled(c, oldreq);
p9_free_req(c, req);
return 0;
@@ -751,6 +756,12 @@ again:
err = wait_event_interruptible(*req->wq,
req->status >= REQ_STATUS_RCVD);
+ /*
+ * Make sure our req is coherent with regard to updates in other
+ * threads - echoes to wmb() in the callback
+ */
+ smp_rmb();
+
if ((err == -ERESTARTSYS) && (c->status == Connected)
&& (type == P9_TFLUSH)) {
sigpending = 1;