From b50175fe867ae067888049318264824524c0616a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Michel=20D=C3=A4nzer?= Date: Tue, 26 Nov 2019 17:14:46 +0100 Subject: [PATCH 1/4] modesetting: Call glamor_finish from drmmode_crtc_set_mode This makes sure any pending drawing to a new scanout buffer will be visible from the start. This makes the finish call in drmmode_copy_fb superfluous, so remove it. Reviewed-by: Adam Jackson (Cherry picked from commit c66c548eabf06835cb0cb906598fb87c7bb30cf4) Reviewed-by: Kenneth Graunke --- hw/xfree86/drivers/modesetting/drmmode_display.c | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/hw/xfree86/drivers/modesetting/drmmode_display.c b/hw/xfree86/drivers/modesetting/drmmode_display.c index 336f7686e..8786d13a3 100644 --- a/hw/xfree86/drivers/modesetting/drmmode_display.c +++ b/hw/xfree86/drivers/modesetting/drmmode_display.c @@ -754,6 +754,7 @@ drmmode_crtc_set_mode(xf86CrtcPtr crtc, Bool test_only) xf86CrtcConfigPtr xf86_config = XF86_CRTC_CONFIG_PTR(crtc->scrn); drmmode_crtc_private_ptr drmmode_crtc = crtc->driver_private; drmmode_ptr drmmode = drmmode_crtc->drmmode; + ScreenPtr screen = crtc->scrn->pScreen; drmModeModeInfo kmode; int output_count = 0; uint32_t *output_ids = NULL; @@ -764,6 +765,12 @@ drmmode_crtc_set_mode(xf86CrtcPtr crtc, Bool test_only) if (!drmmode_crtc_get_fb_id(crtc, &fb_id, &x, &y)) return 1; +#ifdef GLAMOR_HAS_GBM + /* Make sure any pending drawing will be visible in a new scanout buffer */ + if (drmmode->glamor) + glamor_finish(screen); +#endif + if (ms->atomic_modeset) { drmModeAtomicReq *req = drmModeAtomicAlloc(); Bool active; @@ -1452,8 +1459,6 @@ drmmode_copy_fb(ScrnInfoPtr pScrn, drmmode_ptr drmmode) FreeScratchGC(gc); - glamor_finish(pScreen); - pScreen->canDoBGNoneRoot = TRUE; if (drmmode->fbcon_pixmap) -- GitLab From 094f42cdfe5d4c0b8e329445c529ee1e59278999 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Michel=20D=C3=A4nzer?= Date: Tue, 26 Nov 2019 17:16:37 +0100 Subject: [PATCH 2/4] xfree86/modes: Call xf86RotateRedisplay from xf86CrtcRotate If a new rotate buffer was allocated. This makes sure the new buffer has valid transformed contents when it starts being displayed. Reviewed-by: Adam Jackson (Cherry picked from commit 327df450ffcf5bda5b4254db0208d355860d1010) Reviewed-by: Kenneth Graunke --- hw/xfree86/modes/xf86Rotate.c | 3 +++ 1 file changed, 3 insertions(+) diff --git a/hw/xfree86/modes/xf86Rotate.c b/hw/xfree86/modes/xf86Rotate.c index a8f1e615c..05944cfcb 100644 --- a/hw/xfree86/modes/xf86Rotate.c +++ b/hw/xfree86/modes/xf86Rotate.c @@ -485,6 +485,9 @@ xf86CrtcRotate(xf86CrtcPtr crtc) if (damage) xf86CrtcDamageShadow(crtc); + else if (crtc->rotatedData && !crtc->rotatedPixmap) + /* Make sure the new rotate buffer has valid transformed contents */ + xf86RotateRedisplay(pScreen); /* All done */ return TRUE; -- GitLab From 8aad09dd79f0504715edac56e21439809a5d529e Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Michel=20D=C3=A4nzer?= Date: Tue, 26 Nov 2019 17:17:12 +0100 Subject: [PATCH 3/4] modesetting: Clear new screen pixmap storage on RandR resize Fixes random garbage being visible intermittently. Reviewed-by: Adam Jackson (Cherry picked from commit 9ba13bac9dd076f166ff0d063fc144b904a40d12) Reviewed-by: Kenneth Graunke --- hw/xfree86/drivers/modesetting/drmmode_display.c | 15 +++++++++++++++ 1 file changed, 15 insertions(+) diff --git a/hw/xfree86/drivers/modesetting/drmmode_display.c b/hw/xfree86/drivers/modesetting/drmmode_display.c index 8786d13a3..eca058258 100644 --- a/hw/xfree86/drivers/modesetting/drmmode_display.c +++ b/hw/xfree86/drivers/modesetting/drmmode_display.c @@ -1795,6 +1795,19 @@ drmmode_set_scanout_pixmap(xf86CrtcPtr crtc, PixmapPtr ppix) &drmmode_crtc->prime_pixmap); } +static void +drmmode_clear_pixmap(PixmapPtr pixmap) +{ + ScreenPtr screen = pixmap->drawable.pScreen; + GCPtr gc; + + gc = GetScratchGC(pixmap->drawable.depth, screen); + if (gc) { + miClearDrawable(&pixmap->drawable, gc); + FreeScratchGC(gc); + } +} + static void * drmmode_shadow_allocate(xf86CrtcPtr crtc, int width, int height) { @@ -3179,6 +3192,8 @@ drmmode_xf86crtc_resize(ScrnInfoPtr scrn, int width, int height) if (!drmmode_glamor_handle_new_screen_pixmap(drmmode)) goto fail; + drmmode_clear_pixmap(ppix); + for (i = 0; i < xf86_config->num_crtc; i++) { xf86CrtcPtr crtc = xf86_config->crtc[i]; -- GitLab From 87ca1bdf6935c4b11b41ca071f1f4b8d8347fee9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Michel=20D=C3=A4nzer?= Date: Tue, 3 Dec 2019 18:39:40 +0100 Subject: [PATCH 4/4] xwayland: Do flush GPU work in xwl_present_flush The Present code sends the idle notification event to the client after xwl_present_flush returns. If we don't flush our GPU work here, the client may race to draw another frame to the same buffer, so we may end up copying (parts of) that new frame instead of the one we meant to. Fixes https://gitlab.freedesktop.org/xorg/xserver/issues/835 Reviewed-by: Olivier Fourdan (Cherry picked from commit 2a2234ad1a0fe88400c1511fea67741e4ad09f7f) Reviewed-by: Kenneth Graunke --- hw/xwayland/xwayland-present.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-) diff --git a/hw/xwayland/xwayland-present.c b/hw/xwayland/xwayland-present.c index 2937d9c97..31c276623 100644 --- a/hw/xwayland/xwayland-present.c +++ b/hw/xwayland/xwayland-present.c @@ -24,6 +24,7 @@ */ #include "xwayland.h" +#include "glamor.h" #include @@ -412,9 +413,7 @@ xwl_present_abort_vblank(WindowPtr present_window, static void xwl_present_flush(WindowPtr window) { - /* Only called when a Pixmap is copied instead of flipped, - * but in this case we wait on the next block_handler. - */ + glamor_block_handler(window->drawable.pScreen); } static Bool -- GitLab