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

[Xen-devel] [PATCH] qemu-xen-traditionnal, Fix dirty logging during migration.



This moves the xen_modified_memory call from cpu_physical_memory_map to
cpu_physical_memory_unmap because the memory could be migrated before the
device model have written to it.

The xen_ram_addr_from_mapcache function is imported from QEMU.

Signed-off-by: Anthony PERARD <anthony.perard@xxxxxxxxxx>

---
 hw/xen_machine_fv.c |   39 +++++++++++++++++++++++++++++++++++++++
 i386-dm/exec-dm.c   |   10 ++++++----
 qemu-xen.h          |    1 +
 3 files changed, 46 insertions(+), 4 deletions(-)

diff --git a/hw/xen_machine_fv.c b/hw/xen_machine_fv.c
index fdad42a..c358944 100644
--- a/hw/xen_machine_fv.c
+++ b/hw/xen_machine_fv.c
@@ -223,6 +223,45 @@ void qemu_invalidate_entry(uint8_t *buffer)
     qemu_free(entry);
 }
 
+target_phys_addr_t xen_ram_addr_from_mapcache(void *ptr)
+{
+    struct map_cache *entry = NULL;
+    struct map_cache_rev *reventry;
+    target_phys_addr_t paddr_index;
+    int found = 0;
+
+    TAILQ_FOREACH(reventry, &locked_entries, next) {
+        if (reventry->vaddr_req == ptr) {
+            paddr_index = reventry->paddr_index;
+            found = 1;
+            break;
+        }
+    }
+    if (!found) {
+        fprintf(stderr, "%s, could not find %p\n", __func__, ptr);
+        TAILQ_FOREACH(reventry, &locked_entries, next) {
+            fprintf(stderr, "   %#10lx -> %p is present\n",
+                    reventry->paddr_index,
+                    reventry->vaddr_req);
+        }
+        abort();
+        return 0;
+    }
+
+    entry = &mapcache_entry[paddr_index % nr_buckets];
+    while (entry && (entry->paddr_index != paddr_index)) {
+        entry = entry->next;
+    }
+    if (!entry) {
+        fprintf(stderr,
+                "Trying to find address %p that is not in the mapcache!\n",
+                ptr);
+        return 0;
+    }
+    return (reventry->paddr_index << MCACHE_BUCKET_SHIFT) +
+        ((unsigned long) ptr - (unsigned long) entry->vaddr_base);
+}
+
 void qemu_invalidate_map_cache(void)
 {
     unsigned long i;
diff --git a/i386-dm/exec-dm.c b/i386-dm/exec-dm.c
index 96274d9..bf27a6a 100644
--- a/i386-dm/exec-dm.c
+++ b/i386-dm/exec-dm.c
@@ -820,10 +820,6 @@ void *cpu_physical_memory_map(target_phys_addr_t addr,
     if ((*plen) > l)
         *plen = l;
 #endif
-    if (xen_logdirty_enable)
-        xc_hvm_modified_memory(xc_handle, domid, addr >> TARGET_PAGE_BITS,
-                ((addr + l + TARGET_PAGE_SIZE - 1) >> TARGET_PAGE_BITS)
-                    - (addr >> TARGET_PAGE_BITS));
 
     return qemu_map_cache(addr, 1);
 }
@@ -835,6 +831,12 @@ void *cpu_physical_memory_map(target_phys_addr_t addr,
 void cpu_physical_memory_unmap(void *buffer, target_phys_addr_t len,
                                int is_write, target_phys_addr_t access_len)
 {
+    if (xen_logdirty_enable && is_write) {
+        target_phys_addr_t addr = xen_ram_addr_from_mapcache(buffer);
+        xc_hvm_modified_memory(xc_handle, domid, addr >> TARGET_PAGE_BITS,
+            ((addr + access_len + TARGET_PAGE_SIZE - 1) >> TARGET_PAGE_BITS)
+                - (addr >> TARGET_PAGE_BITS));
+    }
     qemu_invalidate_entry(buffer);
     cpu_notify_map_clients();
 }
diff --git a/qemu-xen.h b/qemu-xen.h
index d50c89f..6f72db6 100644
--- a/qemu-xen.h
+++ b/qemu-xen.h
@@ -28,6 +28,7 @@ extern int vga_ram_size;
 #endif
 
 uint8_t *qemu_map_cache(target_phys_addr_t phys_addr, uint8_t lock);
+target_phys_addr_t xen_ram_addr_from_mapcache(void *ptr);
 void     qemu_invalidate_entry(uint8_t *buffer);
 void     qemu_invalidate_map_cache(void);
 
-- 
Anthony PERARD

_______________________________________________
Xen-devel mailing list
Xen-devel@xxxxxxxxxxxxx
http://lists.xen.org/xen-devel


 


Rackspace

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