|
Hans de Goede |
56753f |
From 0386bf2be16745ce87f35ce65153ef4e11f93b22 Mon Sep 17 00:00:00 2001
|
|
Hans de Goede |
56753f |
From: Yonit Halperin <yhalperi@redhat.com>
|
|
Hans de Goede |
56753f |
Date: Wed, 15 Feb 2012 11:22:15 +0200
|
|
Hans de Goede |
56753f |
Subject: [PATCH 405/434] qxl: set only off-screen surfaces dirty instead of
|
|
Hans de Goede |
56753f |
the whole vram
|
|
Hans de Goede |
56753f |
|
|
Hans de Goede |
56753f |
We used to assure the guest surfaces were saved before migration by
|
|
Hans de Goede |
56753f |
setting the whole vram dirty. This patch sets dirty only the areas
|
|
Hans de Goede |
56753f |
that are actually used in the vram.
|
|
Hans de Goede |
56753f |
|
|
Hans de Goede |
56753f |
Signed-off-by: Yonit Halperin <yhalperi@redhat.com>
|
|
Hans de Goede |
56753f |
Signed-off-by: Gerd Hoffmann <kraxel@redhat.com>
|
|
Hans de Goede |
56753f |
---
|
|
Hans de Goede |
56753f |
hw/qxl.c | 53 ++++++++++++++++++++++++++++++++++++++++++++---------
|
|
Hans de Goede |
56753f |
1 file changed, 44 insertions(+), 9 deletions(-)
|
|
Hans de Goede |
56753f |
|
|
Hans de Goede |
56753f |
diff --git a/hw/qxl.c b/hw/qxl.c
|
|
Hans de Goede |
56753f |
index 4fd5e4e..3d9b1b3 100644
|
|
Hans de Goede |
56753f |
--- a/hw/qxl.c
|
|
Hans de Goede |
56753f |
+++ b/hw/qxl.c
|
|
Hans de Goede |
56753f |
@@ -1010,7 +1010,7 @@ static void qxl_reset_surfaces(PCIQXLDevice *d)
|
|
Hans de Goede |
56753f |
qxl_spice_destroy_surfaces(d, QXL_SYNC);
|
|
Hans de Goede |
56753f |
}
|
|
Hans de Goede |
56753f |
|
|
Hans de Goede |
56753f |
-/* called from spice server thread context only */
|
|
Hans de Goede |
56753f |
+/* can be also called from spice server thread context */
|
|
Hans de Goede |
56753f |
void *qxl_phys2virt(PCIQXLDevice *qxl, QXLPHYSICAL pqxl, int group_id)
|
|
Hans de Goede |
56753f |
{
|
|
Hans de Goede |
56753f |
uint64_t phys = le64_to_cpu(pqxl);
|
|
Hans de Goede |
56753f |
@@ -1469,6 +1469,46 @@ static void qxl_hw_text_update(void *opaque, console_ch_t *chardata)
|
|
Hans de Goede |
56753f |
}
|
|
Hans de Goede |
56753f |
}
|
|
Hans de Goede |
56753f |
|
|
Hans de Goede |
56753f |
+static void qxl_dirty_surfaces(PCIQXLDevice *qxl)
|
|
Hans de Goede |
56753f |
+{
|
|
Hans de Goede |
56753f |
+ intptr_t vram_start;
|
|
Hans de Goede |
56753f |
+ int i;
|
|
Hans de Goede |
56753f |
+
|
|
Hans de Goede |
56753f |
+ if (qxl->mode != QXL_MODE_NATIVE) {
|
|
Hans de Goede |
56753f |
+ return;
|
|
Hans de Goede |
56753f |
+ }
|
|
Hans de Goede |
56753f |
+
|
|
Hans de Goede |
56753f |
+ /* dirty the primary surface */
|
|
Hans de Goede |
56753f |
+ qxl_set_dirty(&qxl->vga.vram, qxl->shadow_rom.draw_area_offset,
|
|
Hans de Goede |
56753f |
+ qxl->shadow_rom.surface0_area_size);
|
|
Hans de Goede |
56753f |
+
|
|
Hans de Goede |
56753f |
+ vram_start = (intptr_t)memory_region_get_ram_ptr(&qxl->vram_bar);
|
|
Hans de Goede |
56753f |
+
|
|
Hans de Goede |
56753f |
+ /* dirty the off-screen surfaces */
|
|
Hans de Goede |
56753f |
+ for (i = 0; i < NUM_SURFACES; i++) {
|
|
Hans de Goede |
56753f |
+ QXLSurfaceCmd *cmd;
|
|
Hans de Goede |
56753f |
+ intptr_t surface_offset;
|
|
Hans de Goede |
56753f |
+ int surface_size;
|
|
Hans de Goede |
56753f |
+
|
|
Hans de Goede |
56753f |
+ if (qxl->guest_surfaces.cmds[i] == 0) {
|
|
Hans de Goede |
56753f |
+ continue;
|
|
Hans de Goede |
56753f |
+ }
|
|
Hans de Goede |
56753f |
+
|
|
Hans de Goede |
56753f |
+ cmd = qxl_phys2virt(qxl, qxl->guest_surfaces.cmds[i],
|
|
Hans de Goede |
56753f |
+ MEMSLOT_GROUP_GUEST);
|
|
Hans de Goede |
56753f |
+ assert(cmd->type == QXL_SURFACE_CMD_CREATE);
|
|
Hans de Goede |
56753f |
+ surface_offset = (intptr_t)qxl_phys2virt(qxl,
|
|
Hans de Goede |
56753f |
+ cmd->u.surface_create.data,
|
|
Hans de Goede |
56753f |
+ MEMSLOT_GROUP_GUEST);
|
|
Hans de Goede |
56753f |
+ surface_offset -= vram_start;
|
|
Hans de Goede |
56753f |
+ surface_size = cmd->u.surface_create.height *
|
|
Hans de Goede |
56753f |
+ abs(cmd->u.surface_create.stride);
|
|
Hans de Goede |
56753f |
+ dprint(qxl, 3, "%s: dirty surface %d, offset %d, size %d\n", __func__,
|
|
Hans de Goede |
56753f |
+ i, (int)surface_offset, surface_size);
|
|
Hans de Goede |
56753f |
+ qxl_set_dirty(&qxl->vram_bar, surface_offset, surface_size);
|
|
Hans de Goede |
56753f |
+ }
|
|
Hans de Goede |
56753f |
+}
|
|
Hans de Goede |
56753f |
+
|
|
Hans de Goede |
56753f |
static void qxl_vm_change_state_handler(void *opaque, int running,
|
|
Hans de Goede |
56753f |
RunState state)
|
|
Hans de Goede |
56753f |
{
|
|
Hans de Goede |
56753f |
@@ -1482,14 +1522,9 @@ static void qxl_vm_change_state_handler(void *opaque, int running,
|
|
Hans de Goede |
56753f |
* called
|
|
Hans de Goede |
56753f |
*/
|
|
Hans de Goede |
56753f |
qxl_update_irq(qxl);
|
|
Hans de Goede |
56753f |
- } else if (qxl->mode == QXL_MODE_NATIVE) {
|
|
Hans de Goede |
56753f |
- /* dirty all vram (which holds surfaces) and devram (primary surface)
|
|
Hans de Goede |
56753f |
- * to make sure they are saved */
|
|
Hans de Goede |
56753f |
- /* FIXME #1: should go out during "live" stage */
|
|
Hans de Goede |
56753f |
- /* FIXME #2: we only need to save the areas which are actually used */
|
|
Hans de Goede |
56753f |
- qxl_set_dirty(&qxl->vram_bar, 0, qxl->vram_size);
|
|
Hans de Goede |
56753f |
- qxl_set_dirty(&qxl->vga.vram, qxl->shadow_rom.draw_area_offset,
|
|
Hans de Goede |
56753f |
- qxl->shadow_rom.surface0_area_size);
|
|
Hans de Goede |
56753f |
+ } else {
|
|
Hans de Goede |
56753f |
+ /* make sure surfaces are saved before migration */
|
|
Hans de Goede |
56753f |
+ qxl_dirty_surfaces(qxl);
|
|
Hans de Goede |
56753f |
}
|
|
Hans de Goede |
56753f |
}
|
|
Hans de Goede |
56753f |
|
|
Hans de Goede |
56753f |
--
|
|
Hans de Goede |
56753f |
1.7.10
|
|
Hans de Goede |
56753f |
|