| From 451bad27ad7ce05114f03127a4ceca35d35d58a2 Mon Sep 17 00:00:00 2001 |
| From: Jason Wang <jasowang@redhat.com> |
| Date: Thu, 4 Jul 2013 11:22:57 +0930 |
| Subject: virtio-net: fix the race between channels setting and refill |
| |
| From: Jason Wang <jasowang@redhat.com> |
| |
| [ Upstream commit 9b9cd8024a2882e896c65222aa421d461354e3f2 ] |
| |
| Commit 55257d72bd1c51f25106350f4983ec19f62ed1fa (virtio-net: fill only rx queues |
| which are being used) tries to refill on demand when changing the number of |
| channels by call try_refill_recv() directly, this may race: |
| |
| - the refill work who may do the refill in the same time |
| - the try_refill_recv() called in bh since napi was not disabled |
| |
| Which may led guest complain during setting channels: |
| |
| virtio_net virtio0: input.1:id 0 is not a head! |
| |
| Solve this issue by scheduling a refill work which can guarantee the |
| serialization of refill. |
| |
| Signed-off-by: Jason Wang <jasowang@redhat.com> |
| Cc: Sasha Levin <sasha.levin@oracle.com> |
| Cc: Rusty Russell <rusty@rustcorp.com.au> |
| Cc: Michael S. Tsirkin <mst@redhat.com> |
| Signed-off-by: Rusty Russell <rusty@rustcorp.com.au> |
| Signed-off-by: Greg Kroah-Hartman <gregkh@linuxfoundation.org> |
| --- |
| drivers/net/virtio_net.c | 5 +---- |
| 1 file changed, 1 insertion(+), 4 deletions(-) |
| |
| --- a/drivers/net/virtio_net.c |
| +++ b/drivers/net/virtio_net.c |
| @@ -902,7 +902,6 @@ static int virtnet_set_queues(struct vir |
| struct scatterlist sg; |
| struct virtio_net_ctrl_mq s; |
| struct net_device *dev = vi->dev; |
| - int i; |
| |
| if (!vi->has_cvq || !virtio_has_feature(vi->vdev, VIRTIO_NET_F_MQ)) |
| return 0; |
| @@ -916,10 +915,8 @@ static int virtnet_set_queues(struct vir |
| queue_pairs); |
| return -EINVAL; |
| } else { |
| - for (i = vi->curr_queue_pairs; i < queue_pairs; i++) |
| - if (!try_fill_recv(&vi->rq[i], GFP_KERNEL)) |
| - schedule_delayed_work(&vi->refill, 0); |
| vi->curr_queue_pairs = queue_pairs; |
| + schedule_delayed_work(&vi->refill, 0); |
| } |
| |
| return 0; |