summaryrefslogtreecommitdiffstats
path: root/hw/display
diff options
context:
space:
mode:
authorMarc-André Lureau2021-02-04 11:52:30 +0100
committerGerd Hoffmann2021-02-04 15:58:54 +0100
commit3cddb8b9e0b58eea04e6eb908fc6a12d5af3d3cb (patch)
tree3c3aed83b87348628a62e8c5c719d087b21498e9 /hw/display
parentvirtio-gpu: avoid re-entering cmdq processing (diff)
downloadqemu-3cddb8b9e0b58eea04e6eb908fc6a12d5af3d3cb.tar.gz
qemu-3cddb8b9e0b58eea04e6eb908fc6a12d5af3d3cb.tar.xz
qemu-3cddb8b9e0b58eea04e6eb908fc6a12d5af3d3cb.zip
display/ui: add a callback to indicate GL state is flushed
Displaying rendered resources requires blocking qemu GPU to avoid extra framebuffer copies. For an external display, via Spice currently, there is a callback to block/unblock the rendering in the same thread. But with the vhost-user-gpu backend, the qemu process doesn't handle the rendering itself, and the blocking callback isn't effective. Instead, the backend must be notified when the display code is done. Fix this by adding a new GraphicHwOps callback to indicate the GL state is flushed, and we are done manipulating the shared GL resources. Call it from gtk and spice display. Signed-off-by: Marc-André Lureau <marcandre.lureau@redhat.com> Message-Id: <20210204105232.834642-19-marcandre.lureau@redhat.com> Signed-off-by: Gerd Hoffmann <kraxel@redhat.com>
Diffstat (limited to 'hw/display')
-rw-r--r--hw/display/vhost-user-gpu.c4
-rw-r--r--hw/display/virtio-gpu-base.c17
-rw-r--r--hw/display/virtio-gpu.c4
-rw-r--r--hw/display/virtio-vga.c11
4 files changed, 27 insertions, 9 deletions
diff --git a/hw/display/vhost-user-gpu.c b/hw/display/vhost-user-gpu.c
index b7bde9feb6..4d8cb3525b 100644
--- a/hw/display/vhost-user-gpu.c
+++ b/hw/display/vhost-user-gpu.c
@@ -360,7 +360,7 @@ vhost_user_gpu_update_blocked(VhostUserGPU *g, bool blocked)
}
static void
-vhost_user_gpu_gl_unblock(VirtIOGPUBase *b)
+vhost_user_gpu_gl_flushed(VirtIOGPUBase *b)
{
VhostUserGPU *g = VHOST_USER_GPU(b);
@@ -578,7 +578,7 @@ vhost_user_gpu_class_init(ObjectClass *klass, void *data)
VirtioDeviceClass *vdc = VIRTIO_DEVICE_CLASS(klass);
VirtIOGPUBaseClass *vgc = VIRTIO_GPU_BASE_CLASS(klass);
- vgc->gl_unblock = vhost_user_gpu_gl_unblock;
+ vgc->gl_flushed = vhost_user_gpu_gl_flushed;
vdc->realize = vhost_user_gpu_device_realize;
vdc->reset = vhost_user_gpu_reset;
diff --git a/hw/display/virtio-gpu-base.c b/hw/display/virtio-gpu-base.c
index f27a6fbe75..4a57350917 100644
--- a/hw/display/virtio-gpu-base.c
+++ b/hw/display/virtio-gpu-base.c
@@ -97,21 +97,27 @@ static int virtio_gpu_ui_info(void *opaque, uint32_t idx, QemuUIInfo *info)
}
static void
-virtio_gpu_gl_block(void *opaque, bool block)
+virtio_gpu_gl_flushed(void *opaque)
{
VirtIOGPUBase *g = opaque;
VirtIOGPUBaseClass *vgc = VIRTIO_GPU_BASE_GET_CLASS(g);
+ if (vgc->gl_flushed) {
+ vgc->gl_flushed(g);
+ }
+}
+
+static void
+virtio_gpu_gl_block(void *opaque, bool block)
+{
+ VirtIOGPUBase *g = opaque;
+
if (block) {
g->renderer_blocked++;
} else {
g->renderer_blocked--;
}
assert(g->renderer_blocked >= 0);
-
- if (g->renderer_blocked == 0) {
- vgc->gl_unblock(g);
- }
}
static int
@@ -138,6 +144,7 @@ static const GraphicHwOps virtio_gpu_ops = {
.text_update = virtio_gpu_text_update,
.ui_info = virtio_gpu_ui_info,
.gl_block = virtio_gpu_gl_block,
+ .gl_flushed = virtio_gpu_gl_flushed,
};
bool
diff --git a/hw/display/virtio-gpu.c b/hw/display/virtio-gpu.c
index 7eb4265a6d..2e4a9822b6 100644
--- a/hw/display/virtio-gpu.c
+++ b/hw/display/virtio-gpu.c
@@ -850,7 +850,7 @@ void virtio_gpu_process_cmdq(VirtIOGPU *g)
g->processing_cmdq = false;
}
-static void virtio_gpu_gl_unblock(VirtIOGPUBase *b)
+static void virtio_gpu_gl_flushed(VirtIOGPUBase *b)
{
VirtIOGPU *g = VIRTIO_GPU(b);
@@ -1257,7 +1257,7 @@ static void virtio_gpu_class_init(ObjectClass *klass, void *data)
VirtioDeviceClass *vdc = VIRTIO_DEVICE_CLASS(klass);
VirtIOGPUBaseClass *vgc = VIRTIO_GPU_BASE_CLASS(klass);
- vgc->gl_unblock = virtio_gpu_gl_unblock;
+ vgc->gl_flushed = virtio_gpu_gl_flushed;
vdc->realize = virtio_gpu_device_realize;
vdc->reset = virtio_gpu_reset;
vdc->get_config = virtio_gpu_get_config;
diff --git a/hw/display/virtio-vga.c b/hw/display/virtio-vga.c
index b071909b68..d3c6404061 100644
--- a/hw/display/virtio-vga.c
+++ b/hw/display/virtio-vga.c
@@ -68,6 +68,16 @@ static void virtio_vga_base_gl_block(void *opaque, bool block)
}
}
+static void virtio_vga_base_gl_flushed(void *opaque)
+{
+ VirtIOVGABase *vvga = opaque;
+ VirtIOGPUBase *g = vvga->vgpu;
+
+ if (g->hw_ops->gl_flushed) {
+ g->hw_ops->gl_flushed(g);
+ }
+}
+
static int virtio_vga_base_get_flags(void *opaque)
{
VirtIOVGABase *vvga = opaque;
@@ -83,6 +93,7 @@ static const GraphicHwOps virtio_vga_base_ops = {
.text_update = virtio_vga_base_text_update,
.ui_info = virtio_vga_base_ui_info,
.gl_block = virtio_vga_base_gl_block,
+ .gl_flushed = virtio_vga_base_gl_flushed,
};
static const VMStateDescription vmstate_virtio_vga_base = {