aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorYuri Benditovich <yuri.benditovich@daynix.com>2025-05-15 09:32:37 +0300
committerMichael S. Tsirkin <mst@redhat.com>2025-06-01 06:38:53 -0400
commitac8fc4ccacd8a77d8d56dc3990bfb221c1f48fcd (patch)
treea4a65ccb9b2f7f29ee1a267d5a207d8b66d42e10
parentd2e9b78162e31b1eaf20f3a4f563da82da56908d (diff)
downloadqemu-ac8fc4ccacd8a77d8d56dc3990bfb221c1f48fcd.zip
qemu-ac8fc4ccacd8a77d8d56dc3990bfb221c1f48fcd.tar.gz
qemu-ac8fc4ccacd8a77d8d56dc3990bfb221c1f48fcd.tar.bz2
virtio: check for validity of indirect descriptors
virtio processes indirect descriptors even if the respected feature VIRTIO_RING_F_INDIRECT_DESC was not negotiated. If qemu is used with reduced set of features to emulate the hardware device that does not support indirect descriptors, the will probably trigger problematic flows on the hardware setup but do not reveal the mistake on qemu. Add LOG_GUEST_ERROR for such case. This will issue logs with '-d guest_errors' in the command line Signed-off-by: Yuri Benditovich <yuri.benditovich@daynix.com> Message-Id: <20250515063237.808293-1-yuri.benditovich@daynix.com> Signed-off-by: Yuri Benditovich <yuri.benditovich@daynix.com>
-rw-r--r--hw/virtio/virtio.c11
1 files changed, 11 insertions, 0 deletions
diff --git a/hw/virtio/virtio.c b/hw/virtio/virtio.c
index 2e98cec..5534251 100644
--- a/hw/virtio/virtio.c
+++ b/hw/virtio/virtio.c
@@ -205,6 +205,15 @@ static const char *virtio_id_to_name(uint16_t device_id)
return name;
}
+static void virtio_check_indirect_feature(VirtIODevice *vdev)
+{
+ if (!virtio_vdev_has_feature(vdev, VIRTIO_RING_F_INDIRECT_DESC)) {
+ qemu_log_mask(LOG_GUEST_ERROR,
+ "Device %s: indirect_desc was not negotiated!\n",
+ vdev->name);
+ }
+}
+
/* Called within call_rcu(). */
static void virtio_free_region_cache(VRingMemoryRegionCaches *caches)
{
@@ -1733,6 +1742,7 @@ static void *virtqueue_split_pop(VirtQueue *vq, size_t sz)
virtio_error(vdev, "Invalid size for indirect buffer table");
goto done;
}
+ virtio_check_indirect_feature(vdev);
/* loop over the indirect descriptor table */
len = address_space_cache_init(&indirect_desc_cache, vdev->dma_as,
@@ -1870,6 +1880,7 @@ static void *virtqueue_packed_pop(VirtQueue *vq, size_t sz)
virtio_error(vdev, "Invalid size for indirect buffer table");
goto done;
}
+ virtio_check_indirect_feature(vdev);
/* loop over the indirect descriptor table */
len = address_space_cache_init(&indirect_desc_cache, vdev->dma_as,