[PATCH net-next 2/3] vsock: fix vsock_dequeue/enqueue_accept race

Subsystems: networking [general], the rest, vm sockets (af_vsock)

STALE3347d

5 messages, 3 authors, 2017-08-18 · open the first message on its own page

[PATCH net-next 2/3] vsock: fix vsock_dequeue/enqueue_accept race

From: Dexuan Cui <decui@microsoft.com>
Date: 2017-08-15 22:16:01

With the current code, when vsock_dequeue_accept() is removing a sock
from the list, nothing prevents vsock_enqueue_accept() from adding a new
sock into the list concurrently. We should add a lock to protect the list.

Signed-off-by: Dexuan Cui <decui@microsoft.com>
Cc: Andy King <redacted>
Cc: Dmitry Torokhov <redacted>
Cc: George Zhang <redacted>
Cc: Jorgen Hansen <redacted>
Cc: Reilly Grant <redacted>
Cc: Asias He <redacted>
Cc: Stefan Hajnoczi <stefanha@redhat.com>
Cc: Vitaly Kuznetsov <vkuznets@redhat.com>
Cc: Cathy Avery <redacted>
Cc: K. Y. Srinivasan <redacted>
Cc: Haiyang Zhang <haiyangz@microsoft.com>
Cc: Stephen Hemminger <redacted>
---
 net/vmw_vsock/af_vsock.c | 7 +++++++
 1 file changed, 7 insertions(+)
diff --git a/net/vmw_vsock/af_vsock.c b/net/vmw_vsock/af_vsock.c
index dfc8c51e..b7b2c66 100644
--- a/net/vmw_vsock/af_vsock.c
+++ b/net/vmw_vsock/af_vsock.c
@@ -126,6 +126,7 @@ static struct proto vsock_proto = {
 
 static const struct vsock_transport *transport;
 static DEFINE_MUTEX(vsock_register_mutex);
+static DEFINE_SPINLOCK(vsock_accept_queue_lock);
 
 /**** EXPORTS ****/
 
@@ -406,7 +407,10 @@ void vsock_enqueue_accept(struct sock *listener, struct sock *connected)
 
 	sock_hold(connected);
 	sock_hold(listener);
+
+	spin_lock(&vsock_accept_queue_lock);
 	list_add_tail(&vconnected->accept_queue, &vlistener->accept_queue);
+	spin_unlock(&vsock_accept_queue_lock);
 }
 EXPORT_SYMBOL_GPL(vsock_enqueue_accept);
 
@@ -423,7 +427,10 @@ static struct sock *vsock_dequeue_accept(struct sock *listener)
 	vconnected = list_entry(vlistener->accept_queue.next,
 				struct vsock_sock, accept_queue);
 
+	spin_lock(&vsock_accept_queue_lock);
 	list_del_init(&vconnected->accept_queue);
+	spin_unlock(&vsock_accept_queue_lock);
+
 	sock_put(listener);
 	/* The caller will need a reference on the connected socket so we let
 	 * it call sock_put().
-- 
2.7.4

Re: [PATCH net-next 2/3] vsock: fix vsock_dequeue/enqueue_accept race

From: Jorgen S. Hansen <hidden>
Date: 2017-08-17 12:43:30

On Aug 16, 2017, at 12:15 AM, Dexuan Cui [off-list ref] wrote:


With the current code, when vsock_dequeue_accept() is removing a sock
from the list, nothing prevents vsock_enqueue_accept() from adding a new
sock into the list concurrently. We should add a lock to protect the list.
For the VMCI socket transport, we always lock the sockets before calling into vsock_enqueue_accept and af_vsock.c locks the socket before calling vsock_dequeue_accept, so from our point of view these operations are already protected, but with finer granularity than a single global lock. As far as I can see, the virtio transport also locks the socket before calling vsock_enqueue_accept, so they should be fine with the current version as well, but Stefan can comment on that.

Thanks,
Jorgen

RE: [PATCH net-next 2/3] vsock: fix vsock_dequeue/enqueue_accept race

From: Dexuan Cui <decui@microsoft.com>
Date: 2017-08-18 00:38:13

quoted
On Aug 16, 2017, at 12:15 AM, Dexuan Cui [off-list ref] wrote:
With the current code, when vsock_dequeue_accept() is removing a sock
from the list, nothing prevents vsock_enqueue_accept() from adding a new
sock into the list concurrently. We should add a lock to protect the list.
For the VMCI socket transport, we always lock the sockets before calling into
vsock_enqueue_accept and af_vsock.c locks the socket before calling
vsock_dequeue_accept, so from our point of view these operations are already
protected, but with finer granularity than a single global lock. As far as I can see,
the virtio transport also locks the socket before calling vsock_enqueue_accept,
so they should be fine with the current version as well, but Stefan can comment
on that.

Jorgen
Hi Jorgen,
Thanks, you're correct.
Please ignore this patch. I'll update the hv_sock driver to add proper 
lock_sock()/relesae_sock().

Thanks,
-- Dexuan

Re: [PATCH net-next 2/3] vsock: fix vsock_dequeue/enqueue_accept race

From: Stefan Hajnoczi <stefanha@redhat.com>
Date: 2017-08-18 15:50:26

On Tue, Aug 15, 2017 at 10:15:39PM +0000, Dexuan Cui wrote:
With the current code, when vsock_dequeue_accept() is removing a sock
from the list, nothing prevents vsock_enqueue_accept() from adding a new
sock into the list concurrently. We should add a lock to protect the list.
The listener sock is locked, preventing concurrent modification.  I have
checked both the virtio and vmci transports.  Can you post an example
where the listener sock isn't locked?

Stefan

RE: [PATCH net-next 2/3] vsock: fix vsock_dequeue/enqueue_accept race

From: Dexuan Cui <decui@microsoft.com>
Date: 2017-08-18 21:13:29

From: Stefan Hajnoczi [mailto:stefanha@redhat.com]
Sent: Thursday, August 17, 2017 07:06

On Tue, Aug 15, 2017 at 10:15:39PM +0000, Dexuan Cui wrote:
quoted
With the current code, when vsock_dequeue_accept() is removing a sock
from the list, nothing prevents vsock_enqueue_accept() from adding a new
sock into the list concurrently. We should add a lock to protect the list.
The listener sock is locked, preventing concurrent modification.  I have
checked both the virtio and vmci transports.  Can you post an example
where the listener sock isn't locked?

Stefan
Sorry, I was not careful when checking the vmci code. 
Please ignore the patch.

Now I realized the expectation is that the individual transport drivers should
do the locking for vsock_enqueue_accept(), but for vsock_dequeue_accept(),
the locking is done by the common vsock driver.

Thanks,
-- Dexuan
Keyboard shortcuts
hback out one level
jnext message in thread
kprevious message in thread
ldrill in
Escclose help / fold thread tree
?toggle this help