[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Xen-changelog] [qemu-xen-3.4-testing] passthrough: fix segmentation fault after hotplug pass-through device



commit 62539a7d5974cdc0a448d469cda458761940cd33
Author: Ian Jackson <ian.jackson@xxxxxxxxxxxxx>
Date:   Tue Apr 13 12:07:33 2010 +0100

    passthrough: fix segmentation fault after hotplug pass-through device
    
    This patch fixed the QEMU segmentation fault after hotplug
    pass-through devices with MSI-X for many times.
    
    There is a wrong boundary check in cpu_register_io_memory that uses
    io_index rather than io_mem_nb. After many times of hotplug of MSI-X
    pass-through device, io_mem_read[] got extended to overwrite mmio_cnt,
    then cause QEMU segmentation fault.
    
    This fix sync with upstream QEMU code in exec.c, and free unused
    io_mem_XXX element after hot removal.
    
    Signed-off-by: Zhai Edwin <edwin.zhai@xxxxxxxxx>
    (cherry picked from commit b5160622517fb2d16d0836172a2e34633c9d94bf)
---
 hw/pt-msi.c       |    6 ++++++
 i386-dm/exec-dm.c |   23 +++++++++++++++++++----
 2 files changed, 25 insertions(+), 4 deletions(-)

diff --git a/hw/pt-msi.c b/hw/pt-msi.c
index 9f4a3b3..f6a1226 100644
--- a/hw/pt-msi.c
+++ b/hw/pt-msi.c
@@ -618,5 +618,11 @@ void pt_msix_delete(struct pt_dev *dev)
         munmap(dev->msix->phys_iomem_base, dev->msix->total_entries * 16);
     }
 
+    if (dev->msix->mmio_index > 0)
+    {
+        cpu_unregister_io_memory(dev->msix->mmio_index);
+    }
+
+
     free(dev->msix);
 }
diff --git a/i386-dm/exec-dm.c b/i386-dm/exec-dm.c
index 45fc8e5..12adede 100644
--- a/i386-dm/exec-dm.c
+++ b/i386-dm/exec-dm.c
@@ -125,7 +125,7 @@ unsigned long qemu_host_page_mask;
 CPUWriteMemoryFunc *io_mem_write[IO_MEM_NB_ENTRIES][4];
 CPUReadMemoryFunc *io_mem_read[IO_MEM_NB_ENTRIES][4];
 void *io_mem_opaque[IO_MEM_NB_ENTRIES];
-static int io_mem_nb = 1;
+char io_mem_used[IO_MEM_NB_ENTRIES];
 
 /* log support */
 FILE *logfile;
@@ -310,6 +310,20 @@ void cpu_register_physical_memory(target_phys_addr_t 
start_addr,
     mmio[mmio_cnt++].size = size;
 }
 
+static int get_free_io_mem_idx(void)
+{
+    int i;
+
+    /* Leave 1st element empty */
+    for (i = 1; i<IO_MEM_NB_ENTRIES; i++)
+        if (!io_mem_used[i]) {
+            io_mem_used[i] = 1;
+            return i;
+        }
+
+    return -1;
+}
+
 /* mem_read and mem_write are arrays of functions containing the
    function to access byte (index 0), word (index 1) and dword (index
    2). All functions must be supplied. If io_index is non zero, the
@@ -324,9 +338,9 @@ int cpu_register_io_memory(int io_index,
     int i;
 
     if (io_index <= 0) {
-        if (io_index >= IO_MEM_NB_ENTRIES)
-            return -1;
-        io_index = io_mem_nb++;
+        io_index = get_free_io_mem_idx();
+        if (io_index == -1)
+            return io_index;
     } else {
         if (io_index >= IO_MEM_NB_ENTRIES)
             return -1;
@@ -357,6 +371,7 @@ void cpu_unregister_io_memory(int io_table_address)
         io_mem_write[io_index][i] = NULL;
     }
     io_mem_opaque[io_index] = NULL;
+    io_mem_used[io_index] = 0;
 }
 
 CPUWriteMemoryFunc **cpu_get_io_memory_write(int io_index)
--
generated by git-patchbot for /home/xen/git/qemu-xen-3.4-testing.git

_______________________________________________
Xen-changelog mailing list
Xen-changelog@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-changelog


 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.