aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGreg Kurz <groug@kaod.org>2020-10-07 18:30:34 +0200
committerMichael S. Tsirkin <mst@redhat.com>2020-10-30 04:29:13 -0400
commit170a6794efde98fb1ad70f59d4cd9af7decf279d (patch)
treebf3813cac319cbebd7e57a7a85e00c803c88db95
parent459ca8bfa41b42b9d80739929f09f792207f15f3 (diff)
downloadqemu-170a6794efde98fb1ad70f59d4cd9af7decf279d.zip
qemu-170a6794efde98fb1ad70f59d4cd9af7decf279d.tar.gz
qemu-170a6794efde98fb1ad70f59d4cd9af7decf279d.tar.bz2
vhost: Don't special case vq->used_phys in vhost_get_log_size()
The first loop in vhost_get_log_size() computes the size of the dirty log bitmap so that it allows to track changes in the entire guest memory, in terms of GPA. When not using a vIOMMU, the address of the vring's used structure, vq->used_phys, is a GPA. It is thus already covered by the first loop. When using a vIOMMU, vq->used_phys is a GIOVA that will be translated to an HVA when the vhost backend needs to update the used structure. It will log the corresponding GPAs into the bitmap but it certainly won't log the GIOVA. So in any case, vq->used_phys shouldn't be explicitly used to size the bitmap. Drop the second loop. This fixes a crash of the source when migrating a guest using in-kernel vhost-net and iommu_platform=on on POWER, because DMA regions are put over 0x800000000000000ULL. The resulting insanely huge log size causes g_malloc0() to abort. BugLink: https://bugzilla.redhat.com/show_bug.cgi?id=1879349 Signed-off-by: Greg Kurz <groug@kaod.org> Message-Id: <160208823418.29027.15172801181796272300.stgit@bahia.lan> Acked-by: Jason Wang <jasowang@redhat.com> Reviewed-by: Michael S. Tsirkin <mst@redhat.com> Signed-off-by: Michael S. Tsirkin <mst@redhat.com>
-rw-r--r--hw/virtio/vhost.c10
1 files changed, 0 insertions, 10 deletions
diff --git a/hw/virtio/vhost.c b/hw/virtio/vhost.c
index 3077fa6..79b2be2 100644
--- a/hw/virtio/vhost.c
+++ b/hw/virtio/vhost.c
@@ -172,16 +172,6 @@ static uint64_t vhost_get_log_size(struct vhost_dev *dev)
reg->memory_size);
log_size = MAX(log_size, last / VHOST_LOG_CHUNK + 1);
}
- for (i = 0; i < dev->nvqs; ++i) {
- struct vhost_virtqueue *vq = dev->vqs + i;
-
- if (!vq->used_phys && !vq->used_size) {
- continue;
- }
-
- uint64_t last = vq->used_phys + vq->used_size - 1;
- log_size = MAX(log_size, last / VHOST_LOG_CHUNK + 1);
- }
return log_size;
}