[PATCH 3.16.y-ckt 009/104] kvm: fix zero length mmio searching

Luis Henriques luis.henriques at canonical.com
Mon Oct 26 13:41:51 UTC 2015


3.16.7-ckt19 -stable review patch.  If anyone has any objections, please let me know.

------------------

From: Jason Wang <jasowang at redhat.com>

commit 8f4216c7d28976f7ec1b2bcbfa0a9f787133c45e upstream.

Currently, if we had a zero length mmio eventfd assigned on
KVM_MMIO_BUS. It will never be found by kvm_io_bus_cmp() since it
always compares the kvm_io_range() with the length that guest
wrote. This will cause e.g for vhost, kick will be trapped by qemu
userspace instead of vhost. Fixing this by using zero length if an
iodevice is zero length.

Cc: Gleb Natapov <gleb at kernel.org>
Cc: Paolo Bonzini <pbonzini at redhat.com>
Signed-off-by: Jason Wang <jasowang at redhat.com>
Reviewed-by: Cornelia Huck <cornelia.huck at de.ibm.com>
Signed-off-by: Paolo Bonzini <pbonzini at redhat.com>
Signed-off-by: Luis Henriques <luis.henriques at canonical.com>
---
 virt/kvm/kvm_main.c | 19 +++++++++++++++++--
 1 file changed, 17 insertions(+), 2 deletions(-)

diff --git a/virt/kvm/kvm_main.c b/virt/kvm/kvm_main.c
index 032150ca597d..12f7bd58da37 100644
--- a/virt/kvm/kvm_main.c
+++ b/virt/kvm/kvm_main.c
@@ -2803,10 +2803,25 @@ static void kvm_io_bus_destroy(struct kvm_io_bus *bus)
 static inline int kvm_io_bus_cmp(const struct kvm_io_range *r1,
                                  const struct kvm_io_range *r2)
 {
-	if (r1->addr < r2->addr)
+	gpa_t addr1 = r1->addr;
+	gpa_t addr2 = r2->addr;
+
+	if (addr1 < addr2)
 		return -1;
-	if (r1->addr + r1->len > r2->addr + r2->len)
+
+	/* If r2->len == 0, match the exact address.  If r2->len != 0,
+	 * accept any overlapping write.  Any order is acceptable for
+	 * overlapping ranges, because kvm_io_bus_get_first_dev ensures
+	 * we process all of them.
+	 */
+	if (r2->len) {
+		addr1 += r1->len;
+		addr2 += r2->len;
+	}
+
+	if (addr1 > addr2)
 		return 1;
+
 	return 0;
 }
 




More information about the kernel-team mailing list