diff mbox series

[v3,03/16] libqos: extend feature bits to 64-bit

Message ID 20191019063810.6944-4-stefanha@redhat.com
State New
Headers show
Series libqos: add VIRTIO PCI 1.0 support | expand

Commit Message

Stefan Hajnoczi Oct. 19, 2019, 6:37 a.m. UTC
In VIRTIO 1.0 feature bits changed from 32-bit to 64-bit.  (In fact, the
transports allow even more feature bits but nothing uses more than 64
bits today.)

Add 64-bit feature bit support to virtio-mmio and virtio-pci.  This will
be necessary for VIRTIO 1.0 support.

Signed-off-by: Stefan Hajnoczi <stefanha@redhat.com>
---
 tests/libqos/virtio.h      | 12 ++++++------
 tests/libqos/virtio-mmio.c | 28 ++++++++++++++++++++++------
 tests/libqos/virtio-net.c  |  6 +++---
 tests/libqos/virtio-pci.c  | 12 ++++++------
 tests/libqos/virtio.c      |  4 ++--
 tests/virtio-blk-test.c    |  8 ++++----
 6 files changed, 43 insertions(+), 27 deletions(-)

Comments

Thomas Huth Oct. 21, 2019, 9:21 a.m. UTC | #1
On 19/10/2019 08.37, Stefan Hajnoczi wrote:
> In VIRTIO 1.0 feature bits changed from 32-bit to 64-bit.  (In fact, the
> transports allow even more feature bits but nothing uses more than 64
> bits today.)
> 
> Add 64-bit feature bit support to virtio-mmio and virtio-pci.  This will
> be necessary for VIRTIO 1.0 support.
> 
> Signed-off-by: Stefan Hajnoczi <stefanha@redhat.com>
> ---
>  tests/libqos/virtio.h      | 12 ++++++------
>  tests/libqos/virtio-mmio.c | 28 ++++++++++++++++++++++------
>  tests/libqos/virtio-net.c  |  6 +++---
>  tests/libqos/virtio-pci.c  | 12 ++++++------
>  tests/libqos/virtio.c      |  4 ++--
>  tests/virtio-blk-test.c    |  8 ++++----
>  6 files changed, 43 insertions(+), 27 deletions(-)

Reviewed-by: Thomas Huth <thuth@redhat.com>
Philippe Mathieu-Daudé Oct. 21, 2019, 12:57 p.m. UTC | #2
On 10/19/19 8:37 AM, Stefan Hajnoczi wrote:
> In VIRTIO 1.0 feature bits changed from 32-bit to 64-bit.  (In fact, the
> transports allow even more feature bits but nothing uses more than 64
> bits today.)
> 
> Add 64-bit feature bit support to virtio-mmio and virtio-pci.  This will
> be necessary for VIRTIO 1.0 support.
> 
> Signed-off-by: Stefan Hajnoczi <stefanha@redhat.com>
> ---
>   tests/libqos/virtio.h      | 12 ++++++------
>   tests/libqos/virtio-mmio.c | 28 ++++++++++++++++++++++------
>   tests/libqos/virtio-net.c  |  6 +++---
>   tests/libqos/virtio-pci.c  | 12 ++++++------
>   tests/libqos/virtio.c      |  4 ++--
>   tests/virtio-blk-test.c    |  8 ++++----
>   6 files changed, 43 insertions(+), 27 deletions(-)
> 
> diff --git a/tests/libqos/virtio.h b/tests/libqos/virtio.h
> index 2cb2448f46..a5c99fb3c9 100644
> --- a/tests/libqos/virtio.h
> +++ b/tests/libqos/virtio.h
> @@ -13,7 +13,7 @@
>   #include "libqos/malloc.h"
>   #include "standard-headers/linux/virtio_ring.h"
>   
> -#define QVIRTIO_F_BAD_FEATURE           0x40000000
> +#define QVIRTIO_F_BAD_FEATURE           0x40000000ull
>   
>   typedef struct QVirtioBus QVirtioBus;
>   
> @@ -52,13 +52,13 @@ struct QVirtioBus {
>       uint64_t (*config_readq)(QVirtioDevice *d, uint64_t addr);
>   
>       /* Get features of the device */
> -    uint32_t (*get_features)(QVirtioDevice *d);
> +    uint64_t (*get_features)(QVirtioDevice *d);
>   
>       /* Set features of the device */
> -    void (*set_features)(QVirtioDevice *d, uint32_t features);
> +    void (*set_features)(QVirtioDevice *d, uint64_t features);
>   
>       /* Get features of the guest */
> -    uint32_t (*get_guest_features)(QVirtioDevice *d);
> +    uint64_t (*get_guest_features)(QVirtioDevice *d);
>   
>       /* Get status of the device */
>       uint8_t (*get_status)(QVirtioDevice *d);
> @@ -103,8 +103,8 @@ uint8_t qvirtio_config_readb(QVirtioDevice *d, uint64_t addr);
>   uint16_t qvirtio_config_readw(QVirtioDevice *d, uint64_t addr);
>   uint32_t qvirtio_config_readl(QVirtioDevice *d, uint64_t addr);
>   uint64_t qvirtio_config_readq(QVirtioDevice *d, uint64_t addr);
> -uint32_t qvirtio_get_features(QVirtioDevice *d);
> -void qvirtio_set_features(QVirtioDevice *d, uint32_t features);
> +uint64_t qvirtio_get_features(QVirtioDevice *d);
> +void qvirtio_set_features(QVirtioDevice *d, uint64_t features);
>   bool qvirtio_is_big_endian(QVirtioDevice *d);
>   
>   void qvirtio_reset(QVirtioDevice *d);
> diff --git a/tests/libqos/virtio-mmio.c b/tests/libqos/virtio-mmio.c
> index 7154b03c1d..78066e6e05 100644
> --- a/tests/libqos/virtio-mmio.c
> +++ b/tests/libqos/virtio-mmio.c
> @@ -40,22 +40,38 @@ static uint64_t qvirtio_mmio_config_readq(QVirtioDevice *d, uint64_t off)
>       return qtest_readq(dev->qts, dev->addr + QVIRTIO_MMIO_DEVICE_SPECIFIC + off);
>   }
>   
> -static uint32_t qvirtio_mmio_get_features(QVirtioDevice *d)
> +static uint64_t qvirtio_mmio_get_features(QVirtioDevice *d)
>   {
>       QVirtioMMIODevice *dev = container_of(d, QVirtioMMIODevice, vdev);
> +    uint64_t lo;
> +    uint64_t hi = 0;
> +
>       qtest_writel(dev->qts, dev->addr + QVIRTIO_MMIO_HOST_FEATURES_SEL, 0);
> -    return qtest_readl(dev->qts, dev->addr + QVIRTIO_MMIO_HOST_FEATURES);
> +    lo = qtest_readl(dev->qts, dev->addr + QVIRTIO_MMIO_HOST_FEATURES);
> +
> +    if (dev->version >= 2) {
> +        qtest_writel(dev->qts, dev->addr + QVIRTIO_MMIO_HOST_FEATURES_SEL, 1);
> +        hi = qtest_readl(dev->qts, dev->addr + QVIRTIO_MMIO_HOST_FEATURES);
> +    }
> +
> +    return (hi << 32) | lo;
>   }
>   
> -static void qvirtio_mmio_set_features(QVirtioDevice *d, uint32_t features)
> +static void qvirtio_mmio_set_features(QVirtioDevice *d, uint64_t features)
>   {
>       QVirtioMMIODevice *dev = container_of(d, QVirtioMMIODevice, vdev);
>       dev->features = features;
>       qtest_writel(dev->qts, dev->addr + QVIRTIO_MMIO_GUEST_FEATURES_SEL, 0);
>       qtest_writel(dev->qts, dev->addr + QVIRTIO_MMIO_GUEST_FEATURES, features);
> +
> +    if (dev->version >= 2) {
> +        qtest_writel(dev->qts, dev->addr + QVIRTIO_MMIO_GUEST_FEATURES_SEL, 1);
> +        qtest_writel(dev->qts, dev->addr + QVIRTIO_MMIO_GUEST_FEATURES,
> +                     features >> 32);
> +    }
>   }
>   
> -static uint32_t qvirtio_mmio_get_guest_features(QVirtioDevice *d)
> +static uint64_t qvirtio_mmio_get_guest_features(QVirtioDevice *d)
>   {
>       QVirtioMMIODevice *dev = container_of(d, QVirtioMMIODevice, vdev);
>       return dev->features;
> @@ -149,8 +165,8 @@ static QVirtQueue *qvirtio_mmio_virtqueue_setup(QVirtioDevice *d,
>       vq->free_head = 0;
>       vq->num_free = vq->size;
>       vq->align = dev->page_size;
> -    vq->indirect = (dev->features & (1u << VIRTIO_RING_F_INDIRECT_DESC)) != 0;
> -    vq->event = (dev->features & (1u << VIRTIO_RING_F_EVENT_IDX)) != 0;
> +    vq->indirect = dev->features & (1ull << VIRTIO_RING_F_INDIRECT_DESC);
> +    vq->event = dev->features & (1ull << VIRTIO_RING_F_EVENT_IDX);
>   
>       qtest_writel(dev->qts, dev->addr + QVIRTIO_MMIO_QUEUE_NUM, vq->size);
>   
> diff --git a/tests/libqos/virtio-net.c b/tests/libqos/virtio-net.c
> index 6567beb553..710d440c3d 100644
> --- a/tests/libqos/virtio-net.c
> +++ b/tests/libqos/virtio-net.c
> @@ -44,11 +44,11 @@ static void virtio_net_setup(QVirtioNet *interface)
>   
>       features = qvirtio_get_features(vdev);
>       features &= ~(QVIRTIO_F_BAD_FEATURE |
> -                  (1u << VIRTIO_RING_F_INDIRECT_DESC) |
> -                  (1u << VIRTIO_RING_F_EVENT_IDX));
> +                  (1ull << VIRTIO_RING_F_INDIRECT_DESC) |
> +                  (1ull << VIRTIO_RING_F_EVENT_IDX));
>       qvirtio_set_features(vdev, features);
>   
> -    if (features & (1u << VIRTIO_NET_F_MQ)) {
> +    if (features & (1ull << VIRTIO_NET_F_MQ)) {
>           interface->n_queues = qvirtio_config_readw(vdev, 8) * 2;
>       } else {
>           interface->n_queues = 2;
> diff --git a/tests/libqos/virtio-pci.c b/tests/libqos/virtio-pci.c
> index 50499e75ef..1b6b760fc6 100644
> --- a/tests/libqos/virtio-pci.c
> +++ b/tests/libqos/virtio-pci.c
> @@ -96,19 +96,19 @@ static uint64_t qvirtio_pci_config_readq(QVirtioDevice *d, uint64_t off)
>       return val;
>   }
>   
> -static uint32_t qvirtio_pci_get_features(QVirtioDevice *d)
> +static uint64_t qvirtio_pci_get_features(QVirtioDevice *d)
>   {
>       QVirtioPCIDevice *dev = container_of(d, QVirtioPCIDevice, vdev);
>       return qpci_io_readl(dev->pdev, dev->bar, VIRTIO_PCI_HOST_FEATURES);
>   }
>   
> -static void qvirtio_pci_set_features(QVirtioDevice *d, uint32_t features)
> +static void qvirtio_pci_set_features(QVirtioDevice *d, uint64_t features)
>   {
>       QVirtioPCIDevice *dev = container_of(d, QVirtioPCIDevice, vdev);
>       qpci_io_writel(dev->pdev, dev->bar, VIRTIO_PCI_GUEST_FEATURES, features);
>   }
>   
> -static uint32_t qvirtio_pci_get_guest_features(QVirtioDevice *d)
> +static uint64_t qvirtio_pci_get_guest_features(QVirtioDevice *d)
>   {
>       QVirtioPCIDevice *dev = container_of(d, QVirtioPCIDevice, vdev);
>       return qpci_io_readl(dev->pdev, dev->bar, VIRTIO_PCI_GUEST_FEATURES);
> @@ -208,7 +208,7 @@ static void qvirtio_pci_set_queue_address(QVirtioDevice *d, uint32_t pfn)
>   static QVirtQueue *qvirtio_pci_virtqueue_setup(QVirtioDevice *d,
>                                           QGuestAllocator *alloc, uint16_t index)
>   {
> -    uint32_t feat;
> +    uint64_t feat;
>       uint64_t addr;
>       QVirtQueuePCI *vqpci;
>       QVirtioPCIDevice *qvpcidev = container_of(d, QVirtioPCIDevice, vdev);
> @@ -222,8 +222,8 @@ static QVirtQueue *qvirtio_pci_virtqueue_setup(QVirtioDevice *d,
>       vqpci->vq.free_head = 0;
>       vqpci->vq.num_free = vqpci->vq.size;
>       vqpci->vq.align = VIRTIO_PCI_VRING_ALIGN;
> -    vqpci->vq.indirect = (feat & (1u << VIRTIO_RING_F_INDIRECT_DESC)) != 0;
> -    vqpci->vq.event = (feat & (1u << VIRTIO_RING_F_EVENT_IDX)) != 0;
> +    vqpci->vq.indirect = feat & (1ull << VIRTIO_RING_F_INDIRECT_DESC);
> +    vqpci->vq.event = feat & (1ull << VIRTIO_RING_F_EVENT_IDX);
>   
>       vqpci->msix_entry = -1;
>       vqpci->msix_addr = 0;
> diff --git a/tests/libqos/virtio.c b/tests/libqos/virtio.c
> index 0ae9956fc8..4f7e6bb8a1 100644
> --- a/tests/libqos/virtio.c
> +++ b/tests/libqos/virtio.c
> @@ -33,12 +33,12 @@ uint64_t qvirtio_config_readq(QVirtioDevice *d, uint64_t addr)
>       return d->bus->config_readq(d, addr);
>   }
>   
> -uint32_t qvirtio_get_features(QVirtioDevice *d)
> +uint64_t qvirtio_get_features(QVirtioDevice *d)
>   {
>       return d->bus->get_features(d);
>   }
>   
> -void qvirtio_set_features(QVirtioDevice *d, uint32_t features)
> +void qvirtio_set_features(QVirtioDevice *d, uint64_t features)
>   {
>       d->features = features;
>       d->bus->set_features(d, features);
> diff --git a/tests/virtio-blk-test.c b/tests/virtio-blk-test.c
> index f6674fb233..31680cc159 100644
> --- a/tests/virtio-blk-test.c
> +++ b/tests/virtio-blk-test.c
> @@ -119,7 +119,7 @@ static void test_basic(QVirtioDevice *dev, QGuestAllocator *alloc,
>       QVirtioBlkReq req;
>       uint64_t req_addr;
>       uint64_t capacity;
> -    uint32_t features;
> +    uint64_t features;
>       uint32_t free_head;
>       uint8_t status;
>       char *data;
> @@ -352,7 +352,7 @@ static void indirect(void *obj, void *u_data, QGuestAllocator *t_alloc)
>       QVRingIndirectDesc *indirect;
>       uint64_t req_addr;
>       uint64_t capacity;
> -    uint32_t features;
> +    uint64_t features;
>       uint32_t free_head;
>       uint8_t status;
>       char *data;
> @@ -467,7 +467,7 @@ static void msix(void *obj, void *u_data, QGuestAllocator *t_alloc)
>       int n_size = TEST_IMAGE_SIZE / 2;
>       uint64_t req_addr;
>       uint64_t capacity;
> -    uint32_t features;
> +    uint64_t features;
>       uint32_t free_head;
>       uint8_t status;
>       char *data;
> @@ -574,7 +574,7 @@ static void idx(void *obj, void *u_data, QGuestAllocator *t_alloc)
>       QVirtioBlkReq req;
>       uint64_t req_addr;
>       uint64_t capacity;
> -    uint32_t features;
> +    uint64_t features;
>       uint32_t free_head;
>       uint32_t write_head;
>       uint32_t desc_idx;
> 

Reviewed-by: Philippe Mathieu-Daudé <philmd@redhat.com>
diff mbox series

Patch

diff --git a/tests/libqos/virtio.h b/tests/libqos/virtio.h
index 2cb2448f46..a5c99fb3c9 100644
--- a/tests/libqos/virtio.h
+++ b/tests/libqos/virtio.h
@@ -13,7 +13,7 @@ 
 #include "libqos/malloc.h"
 #include "standard-headers/linux/virtio_ring.h"
 
-#define QVIRTIO_F_BAD_FEATURE           0x40000000
+#define QVIRTIO_F_BAD_FEATURE           0x40000000ull
 
 typedef struct QVirtioBus QVirtioBus;
 
@@ -52,13 +52,13 @@  struct QVirtioBus {
     uint64_t (*config_readq)(QVirtioDevice *d, uint64_t addr);
 
     /* Get features of the device */
-    uint32_t (*get_features)(QVirtioDevice *d);
+    uint64_t (*get_features)(QVirtioDevice *d);
 
     /* Set features of the device */
-    void (*set_features)(QVirtioDevice *d, uint32_t features);
+    void (*set_features)(QVirtioDevice *d, uint64_t features);
 
     /* Get features of the guest */
-    uint32_t (*get_guest_features)(QVirtioDevice *d);
+    uint64_t (*get_guest_features)(QVirtioDevice *d);
 
     /* Get status of the device */
     uint8_t (*get_status)(QVirtioDevice *d);
@@ -103,8 +103,8 @@  uint8_t qvirtio_config_readb(QVirtioDevice *d, uint64_t addr);
 uint16_t qvirtio_config_readw(QVirtioDevice *d, uint64_t addr);
 uint32_t qvirtio_config_readl(QVirtioDevice *d, uint64_t addr);
 uint64_t qvirtio_config_readq(QVirtioDevice *d, uint64_t addr);
-uint32_t qvirtio_get_features(QVirtioDevice *d);
-void qvirtio_set_features(QVirtioDevice *d, uint32_t features);
+uint64_t qvirtio_get_features(QVirtioDevice *d);
+void qvirtio_set_features(QVirtioDevice *d, uint64_t features);
 bool qvirtio_is_big_endian(QVirtioDevice *d);
 
 void qvirtio_reset(QVirtioDevice *d);
diff --git a/tests/libqos/virtio-mmio.c b/tests/libqos/virtio-mmio.c
index 7154b03c1d..78066e6e05 100644
--- a/tests/libqos/virtio-mmio.c
+++ b/tests/libqos/virtio-mmio.c
@@ -40,22 +40,38 @@  static uint64_t qvirtio_mmio_config_readq(QVirtioDevice *d, uint64_t off)
     return qtest_readq(dev->qts, dev->addr + QVIRTIO_MMIO_DEVICE_SPECIFIC + off);
 }
 
-static uint32_t qvirtio_mmio_get_features(QVirtioDevice *d)
+static uint64_t qvirtio_mmio_get_features(QVirtioDevice *d)
 {
     QVirtioMMIODevice *dev = container_of(d, QVirtioMMIODevice, vdev);
+    uint64_t lo;
+    uint64_t hi = 0;
+
     qtest_writel(dev->qts, dev->addr + QVIRTIO_MMIO_HOST_FEATURES_SEL, 0);
-    return qtest_readl(dev->qts, dev->addr + QVIRTIO_MMIO_HOST_FEATURES);
+    lo = qtest_readl(dev->qts, dev->addr + QVIRTIO_MMIO_HOST_FEATURES);
+
+    if (dev->version >= 2) {
+        qtest_writel(dev->qts, dev->addr + QVIRTIO_MMIO_HOST_FEATURES_SEL, 1);
+        hi = qtest_readl(dev->qts, dev->addr + QVIRTIO_MMIO_HOST_FEATURES);
+    }
+
+    return (hi << 32) | lo;
 }
 
-static void qvirtio_mmio_set_features(QVirtioDevice *d, uint32_t features)
+static void qvirtio_mmio_set_features(QVirtioDevice *d, uint64_t features)
 {
     QVirtioMMIODevice *dev = container_of(d, QVirtioMMIODevice, vdev);
     dev->features = features;
     qtest_writel(dev->qts, dev->addr + QVIRTIO_MMIO_GUEST_FEATURES_SEL, 0);
     qtest_writel(dev->qts, dev->addr + QVIRTIO_MMIO_GUEST_FEATURES, features);
+
+    if (dev->version >= 2) {
+        qtest_writel(dev->qts, dev->addr + QVIRTIO_MMIO_GUEST_FEATURES_SEL, 1);
+        qtest_writel(dev->qts, dev->addr + QVIRTIO_MMIO_GUEST_FEATURES,
+                     features >> 32);
+    }
 }
 
-static uint32_t qvirtio_mmio_get_guest_features(QVirtioDevice *d)
+static uint64_t qvirtio_mmio_get_guest_features(QVirtioDevice *d)
 {
     QVirtioMMIODevice *dev = container_of(d, QVirtioMMIODevice, vdev);
     return dev->features;
@@ -149,8 +165,8 @@  static QVirtQueue *qvirtio_mmio_virtqueue_setup(QVirtioDevice *d,
     vq->free_head = 0;
     vq->num_free = vq->size;
     vq->align = dev->page_size;
-    vq->indirect = (dev->features & (1u << VIRTIO_RING_F_INDIRECT_DESC)) != 0;
-    vq->event = (dev->features & (1u << VIRTIO_RING_F_EVENT_IDX)) != 0;
+    vq->indirect = dev->features & (1ull << VIRTIO_RING_F_INDIRECT_DESC);
+    vq->event = dev->features & (1ull << VIRTIO_RING_F_EVENT_IDX);
 
     qtest_writel(dev->qts, dev->addr + QVIRTIO_MMIO_QUEUE_NUM, vq->size);
 
diff --git a/tests/libqos/virtio-net.c b/tests/libqos/virtio-net.c
index 6567beb553..710d440c3d 100644
--- a/tests/libqos/virtio-net.c
+++ b/tests/libqos/virtio-net.c
@@ -44,11 +44,11 @@  static void virtio_net_setup(QVirtioNet *interface)
 
     features = qvirtio_get_features(vdev);
     features &= ~(QVIRTIO_F_BAD_FEATURE |
-                  (1u << VIRTIO_RING_F_INDIRECT_DESC) |
-                  (1u << VIRTIO_RING_F_EVENT_IDX));
+                  (1ull << VIRTIO_RING_F_INDIRECT_DESC) |
+                  (1ull << VIRTIO_RING_F_EVENT_IDX));
     qvirtio_set_features(vdev, features);
 
-    if (features & (1u << VIRTIO_NET_F_MQ)) {
+    if (features & (1ull << VIRTIO_NET_F_MQ)) {
         interface->n_queues = qvirtio_config_readw(vdev, 8) * 2;
     } else {
         interface->n_queues = 2;
diff --git a/tests/libqos/virtio-pci.c b/tests/libqos/virtio-pci.c
index 50499e75ef..1b6b760fc6 100644
--- a/tests/libqos/virtio-pci.c
+++ b/tests/libqos/virtio-pci.c
@@ -96,19 +96,19 @@  static uint64_t qvirtio_pci_config_readq(QVirtioDevice *d, uint64_t off)
     return val;
 }
 
-static uint32_t qvirtio_pci_get_features(QVirtioDevice *d)
+static uint64_t qvirtio_pci_get_features(QVirtioDevice *d)
 {
     QVirtioPCIDevice *dev = container_of(d, QVirtioPCIDevice, vdev);
     return qpci_io_readl(dev->pdev, dev->bar, VIRTIO_PCI_HOST_FEATURES);
 }
 
-static void qvirtio_pci_set_features(QVirtioDevice *d, uint32_t features)
+static void qvirtio_pci_set_features(QVirtioDevice *d, uint64_t features)
 {
     QVirtioPCIDevice *dev = container_of(d, QVirtioPCIDevice, vdev);
     qpci_io_writel(dev->pdev, dev->bar, VIRTIO_PCI_GUEST_FEATURES, features);
 }
 
-static uint32_t qvirtio_pci_get_guest_features(QVirtioDevice *d)
+static uint64_t qvirtio_pci_get_guest_features(QVirtioDevice *d)
 {
     QVirtioPCIDevice *dev = container_of(d, QVirtioPCIDevice, vdev);
     return qpci_io_readl(dev->pdev, dev->bar, VIRTIO_PCI_GUEST_FEATURES);
@@ -208,7 +208,7 @@  static void qvirtio_pci_set_queue_address(QVirtioDevice *d, uint32_t pfn)
 static QVirtQueue *qvirtio_pci_virtqueue_setup(QVirtioDevice *d,
                                         QGuestAllocator *alloc, uint16_t index)
 {
-    uint32_t feat;
+    uint64_t feat;
     uint64_t addr;
     QVirtQueuePCI *vqpci;
     QVirtioPCIDevice *qvpcidev = container_of(d, QVirtioPCIDevice, vdev);
@@ -222,8 +222,8 @@  static QVirtQueue *qvirtio_pci_virtqueue_setup(QVirtioDevice *d,
     vqpci->vq.free_head = 0;
     vqpci->vq.num_free = vqpci->vq.size;
     vqpci->vq.align = VIRTIO_PCI_VRING_ALIGN;
-    vqpci->vq.indirect = (feat & (1u << VIRTIO_RING_F_INDIRECT_DESC)) != 0;
-    vqpci->vq.event = (feat & (1u << VIRTIO_RING_F_EVENT_IDX)) != 0;
+    vqpci->vq.indirect = feat & (1ull << VIRTIO_RING_F_INDIRECT_DESC);
+    vqpci->vq.event = feat & (1ull << VIRTIO_RING_F_EVENT_IDX);
 
     vqpci->msix_entry = -1;
     vqpci->msix_addr = 0;
diff --git a/tests/libqos/virtio.c b/tests/libqos/virtio.c
index 0ae9956fc8..4f7e6bb8a1 100644
--- a/tests/libqos/virtio.c
+++ b/tests/libqos/virtio.c
@@ -33,12 +33,12 @@  uint64_t qvirtio_config_readq(QVirtioDevice *d, uint64_t addr)
     return d->bus->config_readq(d, addr);
 }
 
-uint32_t qvirtio_get_features(QVirtioDevice *d)
+uint64_t qvirtio_get_features(QVirtioDevice *d)
 {
     return d->bus->get_features(d);
 }
 
-void qvirtio_set_features(QVirtioDevice *d, uint32_t features)
+void qvirtio_set_features(QVirtioDevice *d, uint64_t features)
 {
     d->features = features;
     d->bus->set_features(d, features);
diff --git a/tests/virtio-blk-test.c b/tests/virtio-blk-test.c
index f6674fb233..31680cc159 100644
--- a/tests/virtio-blk-test.c
+++ b/tests/virtio-blk-test.c
@@ -119,7 +119,7 @@  static void test_basic(QVirtioDevice *dev, QGuestAllocator *alloc,
     QVirtioBlkReq req;
     uint64_t req_addr;
     uint64_t capacity;
-    uint32_t features;
+    uint64_t features;
     uint32_t free_head;
     uint8_t status;
     char *data;
@@ -352,7 +352,7 @@  static void indirect(void *obj, void *u_data, QGuestAllocator *t_alloc)
     QVRingIndirectDesc *indirect;
     uint64_t req_addr;
     uint64_t capacity;
-    uint32_t features;
+    uint64_t features;
     uint32_t free_head;
     uint8_t status;
     char *data;
@@ -467,7 +467,7 @@  static void msix(void *obj, void *u_data, QGuestAllocator *t_alloc)
     int n_size = TEST_IMAGE_SIZE / 2;
     uint64_t req_addr;
     uint64_t capacity;
-    uint32_t features;
+    uint64_t features;
     uint32_t free_head;
     uint8_t status;
     char *data;
@@ -574,7 +574,7 @@  static void idx(void *obj, void *u_data, QGuestAllocator *t_alloc)
     QVirtioBlkReq req;
     uint64_t req_addr;
     uint64_t capacity;
-    uint32_t features;
+    uint64_t features;
     uint32_t free_head;
     uint32_t write_head;
     uint32_t desc_idx;