aboutsummaryrefslogtreecommitdiff
path: root/hw/virtio/virtio-pci.c
diff options
context:
space:
mode:
authorGerd Hoffmann <kraxel@redhat.com>2015-06-04 12:34:26 +0200
committerMichael S. Tsirkin <mst@redhat.com>2015-06-10 18:15:05 +0200
commite266d421490e0ae83044bbebb209b2d3650c0ba6 (patch)
tree32f771aadda59b7cbe77b416a48261a6ec33bbd7 /hw/virtio/virtio-pci.c
parent54c720d49d3f9741b52ac95c65a5cc990254a5d8 (diff)
virtio-pci: add flags to enable/disable legacy/modern
Add VIRTIO_PCI_FLAG_DISABLE_LEGACY and VIRTIO_PCI_FLAG_DISABLE_MODERN for VirtIOPCIProxy->flags. Also add properties for them. They can be used to disable modern (virtio 1.0) or legacy (virtio 0.9) modes. By default only legacy is advertized, modern will be turned on by default once all remaining spec compilance issues are addressed. Signed-off-by: Gerd Hoffmann <kraxel@redhat.com> Acked-by: Michael S. Tsirkin <mst@redhat.com> Signed-off-by: Michael S. Tsirkin <mst@redhat.com> Reviewed-by: Michael S. Tsirkin <mst@redhat.com>
Diffstat (limited to 'hw/virtio/virtio-pci.c')
-rw-r--r--hw/virtio/virtio-pci.c46
1 files changed, 33 insertions, 13 deletions
diff --git a/hw/virtio/virtio-pci.c b/hw/virtio/virtio-pci.c
index d6d76684fc..37c45330b7 100644
--- a/hw/virtio/virtio-pci.c
+++ b/hw/virtio/virtio-pci.c
@@ -1197,6 +1197,8 @@ static void virtio_pci_device_plugged(DeviceState *d, Error **errp)
{
VirtIOPCIProxy *proxy = VIRTIO_PCI(d);
VirtioBusState *bus = &proxy->bus;
+ bool legacy = !(proxy->flags & VIRTIO_PCI_FLAG_DISABLE_LEGACY);
+ bool modern = !(proxy->flags & VIRTIO_PCI_FLAG_DISABLE_MODERN);
uint8_t *config;
uint32_t size;
VirtIODevice *vdev = virtio_bus_get_device(&proxy->bus);
@@ -1205,13 +1207,24 @@ static void virtio_pci_device_plugged(DeviceState *d, Error **errp)
if (proxy->class_code) {
pci_config_set_class(config, proxy->class_code);
}
- pci_set_word(config + PCI_SUBSYSTEM_VENDOR_ID,
- pci_get_word(config + PCI_VENDOR_ID));
- pci_set_word(config + PCI_SUBSYSTEM_ID, virtio_bus_get_vdev_id(bus));
+
+ if (legacy) {
+ /* legacy and transitional */
+ pci_set_word(config + PCI_SUBSYSTEM_VENDOR_ID,
+ pci_get_word(config + PCI_VENDOR_ID));
+ pci_set_word(config + PCI_SUBSYSTEM_ID, virtio_bus_get_vdev_id(bus));
+ } else {
+ /* pure virtio-1.0 */
+ pci_set_word(config + PCI_VENDOR_ID,
+ PCI_VENDOR_ID_REDHAT_QUMRANET);
+ pci_set_word(config + PCI_DEVICE_ID,
+ 0x1040 + virtio_bus_get_vdev_id(bus));
+ pci_config_set_revision(config, 1);
+ }
config[PCI_INTERRUPT_PIN] = 1;
- if (1) { /* TODO: Make this optional, dependent on virtio 1.0 */
+ if (modern) {
struct virtio_pci_cap common = {
.cfg_type = VIRTIO_PCI_CAP_COMMON_CFG,
.cap_len = sizeof common,
@@ -1325,17 +1338,20 @@ static void virtio_pci_device_plugged(DeviceState *d, Error **errp)
proxy->pci_dev.config_write = virtio_write_config;
- size = VIRTIO_PCI_REGION_SIZE(&proxy->pci_dev)
- + virtio_bus_get_vdev_config_len(bus);
- if (size & (size - 1)) {
- size = 1 << qemu_fls(size);
- }
+ if (legacy) {
+ size = VIRTIO_PCI_REGION_SIZE(&proxy->pci_dev)
+ + virtio_bus_get_vdev_config_len(bus);
+ if (size & (size - 1)) {
+ size = 1 << qemu_fls(size);
+ }
- memory_region_init_io(&proxy->bar, OBJECT(proxy), &virtio_pci_config_ops,
- proxy, "virtio-pci", size);
+ memory_region_init_io(&proxy->bar, OBJECT(proxy),
+ &virtio_pci_config_ops,
+ proxy, "virtio-pci", size);
- pci_register_bar(&proxy->pci_dev, 0, PCI_BASE_ADDRESS_SPACE_IO,
- &proxy->bar);
+ pci_register_bar(&proxy->pci_dev, 0, PCI_BASE_ADDRESS_SPACE_IO,
+ &proxy->bar);
+ }
if (!kvm_has_many_ioeventfds()) {
proxy->flags &= ~VIRTIO_PCI_FLAG_USE_IOEVENTFD;
@@ -1379,6 +1395,10 @@ static void virtio_pci_reset(DeviceState *qdev)
static Property virtio_pci_properties[] = {
DEFINE_PROP_BIT("virtio-pci-bus-master-bug-migration", VirtIOPCIProxy, flags,
VIRTIO_PCI_FLAG_BUS_MASTER_BUG_MIGRATION_BIT, false),
+ DEFINE_PROP_BIT("disable-legacy", VirtIOPCIProxy, flags,
+ VIRTIO_PCI_FLAG_DISABLE_LEGACY_BIT, false),
+ DEFINE_PROP_BIT("disable-modern", VirtIOPCIProxy, flags,
+ VIRTIO_PCI_FLAG_DISABLE_MODERN_BIT, true),
DEFINE_PROP_END_OF_LIST(),
};