[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Qemu-devel] [PATCH 2/2] virtio-net: do not expose a larger config size
From: |
Anthony Liguori |
Subject: |
[Qemu-devel] [PATCH 2/2] virtio-net: do not expose a larger config size if multiqueue isn't enabled |
Date: |
Sat, 2 Feb 2013 17:06:23 -0600 |
The windows PV drivers seem to get very upset if the config size changes.
Even when we disable features, we don't change the config size today which
is a bug.
This patch is a pretty rough way to solve this problem and it only handles
the multiqueue case specifically.
Cc: Michael Tokarev <address@hidden>
Reported-by: Michael Tokarev <address@hidden>
Signed-off-by: Anthony Liguori <address@hidden>
---
hw/virtio-net.c | 20 ++++++++++++++------
1 file changed, 14 insertions(+), 6 deletions(-)
diff --git a/hw/virtio-net.c b/hw/virtio-net.c
index e37358a..8d15813 100644
--- a/hw/virtio-net.c
+++ b/hw/virtio-net.c
@@ -73,6 +73,7 @@ typedef struct VirtIONet
int multiqueue;
uint16_t max_queues;
uint16_t curr_queues;
+ int config_size;
} VirtIONet;
static VirtIONetQueue *virtio_net_get_subqueue(NetClientState *nc)
@@ -99,20 +100,20 @@ static VirtIONet *to_virtio_net(VirtIODevice *vdev)
static void virtio_net_get_config(VirtIODevice *vdev, uint8_t *config)
{
VirtIONet *n = to_virtio_net(vdev);
- struct virtio_net_config netcfg;
+ struct virtio_net_config netcfg = {};
stw_p(&netcfg.status, n->status);
stw_p(&netcfg.max_virtqueue_pairs, n->max_queues);
memcpy(netcfg.mac, n->mac, ETH_ALEN);
- memcpy(config, &netcfg, sizeof(netcfg));
+ memcpy(config, &netcfg, n->config_size);
}
static void virtio_net_set_config(VirtIODevice *vdev, const uint8_t *config)
{
VirtIONet *n = to_virtio_net(vdev);
- struct virtio_net_config netcfg;
+ struct virtio_net_config netcfg = {};
- memcpy(&netcfg, config, sizeof(netcfg));
+ memcpy(&netcfg, config, n->config_size);
if (!(n->vdev.guest_features >> VIRTIO_NET_F_CTRL_MAC_ADDR & 1) &&
memcmp(netcfg.mac, n->mac, ETH_ALEN)) {
@@ -1279,14 +1280,21 @@ static void virtio_net_guest_notifier_mask(VirtIODevice
*vdev, int idx,
}
VirtIODevice *virtio_net_init(DeviceState *dev, NICConf *conf,
- virtio_net_conf *net)
+ virtio_net_conf *net, uint32_t host_features)
{
VirtIONet *n;
int i;
+ int config_size;
+ if (host_features & VIRTIO_NET_F_MQ) {
+ config_size = sizeof(struct virtio_net_config);
+ } else {
+ config_size = 8;
+ }
n = (VirtIONet *)virtio_common_init("virtio-net", VIRTIO_ID_NET,
- sizeof(struct virtio_net_config),
+ config_size,
sizeof(VirtIONet));
+ n->config_size = config_size;
n->vdev.get_config = virtio_net_get_config;
n->vdev.set_config = virtio_net_set_config;
--
1.8.0