9ae3a8
From 3fa0b44ff46eccd3c22729a6e5d4ed044d22ab8a Mon Sep 17 00:00:00 2001
9ae3a8
From: "Daniel P. Berrange" <berrange@redhat.com>
9ae3a8
Date: Thu, 8 Feb 2018 17:50:28 +0100
9ae3a8
Subject: [PATCH 14/27] ui: fix refresh of VNC server surface
9ae3a8
9ae3a8
RH-Author: Daniel P. Berrange <berrange@redhat.com>
9ae3a8
Message-id: <20180208175041.5634-15-berrange@redhat.com>
9ae3a8
Patchwork-id: 78948
9ae3a8
O-Subject: [RHEL-7.5 qemu-kvm PATCH v1 14/27] ui: fix refresh of VNC server surface
9ae3a8
Bugzilla: 1527405
9ae3a8
RH-Acked-by: Laszlo Ersek <lersek@redhat.com>
9ae3a8
RH-Acked-by: Gerd Hoffmann <kraxel@redhat.com>
9ae3a8
RH-Acked-by: Miroslav Rezanina <mrezanin@redhat.com>
9ae3a8
9ae3a8
From: "Daniel P. Berrange" <berrange@redhat.com>
9ae3a8
9ae3a8
In previous commit
9ae3a8
9ae3a8
  commit c7628bff4138ce906a3620d12e0820c1cf6c140d
9ae3a8
  Author: Gerd Hoffmann <kraxel@redhat.com>
9ae3a8
  Date:   Fri Oct 30 12:10:09 2015 +0100
9ae3a8
9ae3a8
    vnc: only alloc server surface with clients connected
9ae3a8
9ae3a8
the VNC server was changed so that the 'vd->server' pixman
9ae3a8
image was only allocated when a client is connected.
9ae3a8
9ae3a8
Since then if a client disconnects and then reconnects to
9ae3a8
the VNC server all they will see is a black screen until
9ae3a8
they do something that triggers a refresh. On a graphical
9ae3a8
desktop this is not often noticed since there's many things
9ae3a8
going on which cause a refresh. On a plain text console it
9ae3a8
is really obvious since nothing refreshes frequently.
9ae3a8
9ae3a8
The problem is that the VNC server didn't update the guest
9ae3a8
dirty bitmap, so still believes its server image is in sync
9ae3a8
with the guest contents.
9ae3a8
9ae3a8
To fix this we must explicitly mark the entire guest desktop
9ae3a8
as dirty after re-creating the server surface. Move this
9ae3a8
logic into vnc_update_server_surface() so it is guaranteed
9ae3a8
to be call in all code paths that re-create the surface
9ae3a8
instead of only in vnc_dpy_switch()
9ae3a8
9ae3a8
Signed-off-by: Daniel P. Berrange <berrange@redhat.com>
9ae3a8
Reviewed-by: Peter Lieven <pl@kamp.de>
9ae3a8
Tested-by: Peter Lieven <pl@kamp.de>
9ae3a8
Message-id: 1471365032-18096-1-git-send-email-berrange@redhat.com
9ae3a8
Signed-off-by: Peter Maydell <peter.maydell@linaro.org>
9ae3a8
(cherry picked from commit b69a553b4af9bc87a8b2e0a7b7a7de4cc7f0557e)
9ae3a8
Signed-off-by: Miroslav Rezanina <mrezanin@redhat.com>
9ae3a8
---
9ae3a8
 ui/vnc.c | 20 +++++++++++---------
9ae3a8
 1 file changed, 11 insertions(+), 9 deletions(-)
9ae3a8
9ae3a8
diff --git a/ui/vnc.c b/ui/vnc.c
9ae3a8
index dc09089..ec7bb0c 100644
9ae3a8
--- a/ui/vnc.c
9ae3a8
+++ b/ui/vnc.c
9ae3a8
@@ -617,6 +617,8 @@ void *vnc_server_fb_ptr(VncDisplay *vd, int x, int y)
9ae3a8
 
9ae3a8
 static void vnc_update_server_surface(VncDisplay *vd)
9ae3a8
 {
9ae3a8
+    int width, height;
9ae3a8
+
9ae3a8
     qemu_pixman_image_unref(vd->server);
9ae3a8
     vd->server = NULL;
9ae3a8
 
9ae3a8
@@ -624,10 +626,15 @@ static void vnc_update_server_surface(VncDisplay *vd)
9ae3a8
         return;
9ae3a8
     }
9ae3a8
 
9ae3a8
+    width = vnc_width(vd);
9ae3a8
+    height = vnc_height(vd);
9ae3a8
     vd->server = pixman_image_create_bits(VNC_SERVER_FB_FORMAT,
9ae3a8
-                                          vnc_width(vd),
9ae3a8
-                                          vnc_height(vd),
9ae3a8
+                                          width, height,
9ae3a8
                                           NULL, 0);
9ae3a8
+
9ae3a8
+    memset(vd->guest.dirty, 0x00, sizeof(vd->guest.dirty));
9ae3a8
+    vnc_set_area_dirty(vd->guest.dirty, vd, 0, 0,
9ae3a8
+                       width, height);
9ae3a8
 }
9ae3a8
 
9ae3a8
 static void vnc_dpy_switch(DisplayChangeListener *dcl,
9ae3a8
@@ -635,7 +642,6 @@ static void vnc_dpy_switch(DisplayChangeListener *dcl,
9ae3a8
 {
9ae3a8
     VncDisplay *vd = container_of(dcl, VncDisplay, dcl);
9ae3a8
     VncState *vs;
9ae3a8
-    int width, height;
9ae3a8
 
9ae3a8
     vnc_abort_display_jobs(vd);
9ae3a8
     vd->ds = surface;
9ae3a8
@@ -647,11 +653,6 @@ static void vnc_dpy_switch(DisplayChangeListener *dcl,
9ae3a8
     qemu_pixman_image_unref(vd->guest.fb);
9ae3a8
     vd->guest.fb = pixman_image_ref(surface->image);
9ae3a8
     vd->guest.format = surface->format;
9ae3a8
-    width = vnc_width(vd);
9ae3a8
-    height = vnc_height(vd);
9ae3a8
-    memset(vd->guest.dirty, 0x00, sizeof(vd->guest.dirty));
9ae3a8
-    vnc_set_area_dirty(vd->guest.dirty, vd, 0, 0,
9ae3a8
-                       width, height);
9ae3a8
 
9ae3a8
     QTAILQ_FOREACH(vs, &vd->clients, next) {
9ae3a8
         vnc_colordepth(vs);
9ae3a8
@@ -661,7 +662,8 @@ static void vnc_dpy_switch(DisplayChangeListener *dcl,
9ae3a8
         }
9ae3a8
         memset(vs->dirty, 0x00, sizeof(vs->dirty));
9ae3a8
         vnc_set_area_dirty(vs->dirty, vd, 0, 0,
9ae3a8
-                           width, height);
9ae3a8
+                           vnc_width(vd),
9ae3a8
+                           vnc_height(vd));
9ae3a8
     }
9ae3a8
 }
9ae3a8
 
9ae3a8
-- 
9ae3a8
1.8.3.1
9ae3a8