forked from pool/xorg-x11-server
Accepting request 899464 from home:patrikjakobsson:branches:X11:XOrg
Modesetting: Fix dirty updates for sw rotation OBS-URL: https://build.opensuse.org/request/show/899464 OBS-URL: https://build.opensuse.org/package/show/X11:XOrg/xorg-x11-server?expand=0&rev=793
This commit is contained in:
parent
90b3657e6e
commit
0dab94f9df
167
u_modesetting-Fix-dirty-updates-for-sw-rotation.patch
Normal file
167
u_modesetting-Fix-dirty-updates-for-sw-rotation.patch
Normal file
@ -0,0 +1,167 @@
|
|||||||
|
From 7d2802f13eecb38babeeb54ceae978a409b5c5d4 Mon Sep 17 00:00:00 2001
|
||||||
|
From: Patrik Jakobsson <patrik.r.jakobsson@gmail.com>
|
||||||
|
Date: Wed, 9 Jun 2021 20:58:59 +0200
|
||||||
|
Subject: [PATCH] modesetting: Fix dirty updates for sw rotation
|
||||||
|
Patch-Mainline: To be upstreamed
|
||||||
|
References: bsc#1182955
|
||||||
|
|
||||||
|
Rotation is broken for all drm drivers not providing hardware rotation
|
||||||
|
support. Drivers that give direct access to vram and not needing dirty
|
||||||
|
updates still work but only by accident. The problem is caused by
|
||||||
|
modesetting not sending the correct fb_id to drmModeDirtyFB() and
|
||||||
|
passing the damage rects in the rotated state and not as the crtc
|
||||||
|
expects them. This patch takes care of both problems.
|
||||||
|
|
||||||
|
Signed-off-by: Patrik Jakobsson <pjakobsson@suse.de>
|
||||||
|
---
|
||||||
|
hw/xfree86/drivers/modesetting/driver.c | 81 ++++++++++++++-----
|
||||||
|
.../drivers/modesetting/drmmode_display.c | 2 +-
|
||||||
|
.../drivers/modesetting/drmmode_display.h | 2 +
|
||||||
|
3 files changed, 63 insertions(+), 22 deletions(-)
|
||||||
|
|
||||||
|
diff --git a/hw/xfree86/drivers/modesetting/driver.c b/hw/xfree86/drivers/modesetting/driver.c
|
||||||
|
index ef4a314..deca1ed 100644
|
||||||
|
--- a/hw/xfree86/drivers/modesetting/driver.c
|
||||||
|
+++ b/hw/xfree86/drivers/modesetting/driver.c
|
||||||
|
@@ -503,9 +503,41 @@ GetRec(ScrnInfoPtr pScrn)
|
||||||
|
return TRUE;
|
||||||
|
}
|
||||||
|
|
||||||
|
+static void
|
||||||
|
+rotate_clip(PixmapPtr pixmap, BoxPtr rect, drmModeClip *clip, Rotation rotation)
|
||||||
|
+{
|
||||||
|
+ int w = pixmap->drawable.width;
|
||||||
|
+ int h = pixmap->drawable.height;
|
||||||
|
+
|
||||||
|
+ if (rotation == RR_Rotate_90) {
|
||||||
|
+ /* Rotate 90 degrees counter clockwise */
|
||||||
|
+ clip->x1 = rect->y1;
|
||||||
|
+ clip->x2 = rect->y2;
|
||||||
|
+ clip->y1 = w - rect->x2;
|
||||||
|
+ clip->y2 = w - rect->x1;
|
||||||
|
+ } else if (rotation == RR_Rotate_180) {
|
||||||
|
+ /* Rotate 180 degrees */
|
||||||
|
+ clip->x1 = w - rect->x2;
|
||||||
|
+ clip->x2 = w - rect->x1;
|
||||||
|
+ clip->y1 = h - rect->y2;
|
||||||
|
+ clip->y2 = h - rect->y1;
|
||||||
|
+ } else if (rotation == RR_Rotate_270) {
|
||||||
|
+ /* Rotate 90 degrees clockwise */
|
||||||
|
+ clip->x1 = h - rect->y2;
|
||||||
|
+ clip->x2 = h - rect->y1;
|
||||||
|
+ clip->y1 = rect->x1;
|
||||||
|
+ clip->y2 = rect->x2;
|
||||||
|
+ } else {
|
||||||
|
+ clip->x1 = rect->x1;
|
||||||
|
+ clip->x2 = rect->x2;
|
||||||
|
+ clip->y1 = rect->y1;
|
||||||
|
+ clip->y2 = rect->y2;
|
||||||
|
+ }
|
||||||
|
+}
|
||||||
|
+
|
||||||
|
static int
|
||||||
|
-dispatch_dirty_region(ScrnInfoPtr scrn,
|
||||||
|
- PixmapPtr pixmap, DamagePtr damage, int fb_id)
|
||||||
|
+dispatch_dirty_region(ScrnInfoPtr scrn, xf86CrtcPtr crtc,
|
||||||
|
+ PixmapPtr pixmap, DamagePtr damage, int fb_id)
|
||||||
|
{
|
||||||
|
modesettingPtr ms = modesettingPTR(scrn);
|
||||||
|
RegionPtr dirty = DamageRegion(damage);
|
||||||
|
@@ -520,13 +552,9 @@ dispatch_dirty_region(ScrnInfoPtr scrn,
|
||||||
|
if (!clip)
|
||||||
|
return -ENOMEM;
|
||||||
|
|
||||||
|
- /* XXX no need for copy? */
|
||||||
|
- for (i = 0; i < num_cliprects; i++, rect++) {
|
||||||
|
- clip[i].x1 = rect->x1;
|
||||||
|
- clip[i].y1 = rect->y1;
|
||||||
|
- clip[i].x2 = rect->x2;
|
||||||
|
- clip[i].y2 = rect->y2;
|
||||||
|
- }
|
||||||
|
+ /* Rotate and copy rects into clips */
|
||||||
|
+ for (i = 0; i < num_cliprects; i++, rect++)
|
||||||
|
+ rotate_clip(pixmap, rect, &clip[i], crtc->rotation);
|
||||||
|
|
||||||
|
/* TODO query connector property to see if this is needed */
|
||||||
|
ret = drmModeDirtyFB(ms->fd, fb_id, clip, num_cliprects);
|
||||||
|
@@ -549,20 +577,31 @@ static void
|
||||||
|
dispatch_dirty(ScreenPtr pScreen)
|
||||||
|
{
|
||||||
|
ScrnInfoPtr scrn = xf86ScreenToScrn(pScreen);
|
||||||
|
+ xf86CrtcConfigPtr xf86_config = XF86_CRTC_CONFIG_PTR(scrn);
|
||||||
|
modesettingPtr ms = modesettingPTR(scrn);
|
||||||
|
PixmapPtr pixmap = pScreen->GetScreenPixmap(pScreen);
|
||||||
|
- int fb_id = ms->drmmode.fb_id;
|
||||||
|
- int ret;
|
||||||
|
+ uint32_t fb_id;
|
||||||
|
+ int ret, c, x, y ;
|
||||||
|
|
||||||
|
- ret = dispatch_dirty_region(scrn, pixmap, ms->damage, fb_id);
|
||||||
|
- if (ret == -EINVAL || ret == -ENOSYS) {
|
||||||
|
- ms->dirty_enabled = FALSE;
|
||||||
|
- DamageUnregister(ms->damage);
|
||||||
|
- DamageDestroy(ms->damage);
|
||||||
|
- ms->damage = NULL;
|
||||||
|
- xf86DrvMsg(scrn->scrnIndex, X_INFO,
|
||||||
|
- "Disabling kernel dirty updates, not required.\n");
|
||||||
|
- return;
|
||||||
|
+ for (c = 0; c < xf86_config->num_crtc; c++) {
|
||||||
|
+ xf86CrtcPtr crtc = xf86_config->crtc[c];
|
||||||
|
+ drmmode_crtc_private_ptr drmmode_crtc = crtc->driver_private;
|
||||||
|
+
|
||||||
|
+ if (!drmmode_crtc)
|
||||||
|
+ continue;
|
||||||
|
+
|
||||||
|
+ drmmode_crtc_get_fb_id(crtc, &fb_id, &x, &y);
|
||||||
|
+
|
||||||
|
+ ret = dispatch_dirty_region(scrn, crtc, pixmap, ms->damage, fb_id);
|
||||||
|
+ if (ret == -EINVAL || ret == -ENOSYS) {
|
||||||
|
+ ms->dirty_enabled = FALSE;
|
||||||
|
+ DamageUnregister(ms->damage);
|
||||||
|
+ DamageDestroy(ms->damage);
|
||||||
|
+ ms->damage = NULL;
|
||||||
|
+ xf86DrvMsg(scrn->scrnIndex, X_INFO,
|
||||||
|
+ "Disabling kernel dirty updates, not required.\n");
|
||||||
|
+ return;
|
||||||
|
+ }
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@@ -574,7 +613,7 @@ dispatch_dirty_pixmap(ScrnInfoPtr scrn, xf86CrtcPtr crtc, PixmapPtr ppix)
|
||||||
|
DamagePtr damage = ppriv->slave_damage;
|
||||||
|
int fb_id = ppriv->fb_id;
|
||||||
|
|
||||||
|
- dispatch_dirty_region(scrn, ppix, damage, fb_id);
|
||||||
|
+ dispatch_dirty_region(scrn, crtc, ppix, damage, fb_id);
|
||||||
|
}
|
||||||
|
|
||||||
|
static void
|
||||||
|
diff --git a/hw/xfree86/drivers/modesetting/drmmode_display.c b/hw/xfree86/drivers/modesetting/drmmode_display.c
|
||||||
|
index 88992f5..b29db12 100644
|
||||||
|
--- a/hw/xfree86/drivers/modesetting/drmmode_display.c
|
||||||
|
+++ b/hw/xfree86/drivers/modesetting/drmmode_display.c
|
||||||
|
@@ -598,7 +598,7 @@ drmmode_crtc_can_test_mode(xf86CrtcPtr crtc)
|
||||||
|
return ms->atomic_modeset;
|
||||||
|
}
|
||||||
|
|
||||||
|
-static Bool
|
||||||
|
+Bool
|
||||||
|
drmmode_crtc_get_fb_id(xf86CrtcPtr crtc, uint32_t *fb_id, int *x, int *y)
|
||||||
|
{
|
||||||
|
drmmode_crtc_private_ptr drmmode_crtc = crtc->driver_private;
|
||||||
|
diff --git a/hw/xfree86/drivers/modesetting/drmmode_display.h b/hw/xfree86/drivers/modesetting/drmmode_display.h
|
||||||
|
index 59d79e9..0ed96ab 100644
|
||||||
|
--- a/hw/xfree86/drivers/modesetting/drmmode_display.h
|
||||||
|
+++ b/hw/xfree86/drivers/modesetting/drmmode_display.h
|
||||||
|
@@ -297,6 +297,8 @@ void drmmode_copy_fb(ScrnInfoPtr pScrn, drmmode_ptr drmmode);
|
||||||
|
|
||||||
|
int drmmode_crtc_flip(xf86CrtcPtr crtc, uint32_t fb_id, uint32_t flags, void *data);
|
||||||
|
|
||||||
|
+Bool drmmode_crtc_get_fb_id(xf86CrtcPtr crtc, uint32_t *fb_id, int *x, int *y);
|
||||||
|
+
|
||||||
|
void drmmode_set_dpms(ScrnInfoPtr scrn, int PowerManagementMode, int flags);
|
||||||
|
|
||||||
|
#endif
|
||||||
|
--
|
||||||
|
2.31.1
|
||||||
|
|
@ -1,3 +1,10 @@
|
|||||||
|
-------------------------------------------------------------------
|
||||||
|
Fri Jun 11 11:03:18 UTC 2021 - Patrik Jakobsson <patrik.jakobsson@suse.com>
|
||||||
|
|
||||||
|
- u_modesetting-Fix-dirty-updates-for-sw-rotation.patch
|
||||||
|
* Fixes broken rotation support for DRM drivers without hardware
|
||||||
|
rotation support or direct vram access (bsc#1182955)
|
||||||
|
|
||||||
-------------------------------------------------------------------
|
-------------------------------------------------------------------
|
||||||
Mon Apr 19 11:29:31 UTC 2021 - Stefan Dirsch <sndirsch@suse.com>
|
Mon Apr 19 11:29:31 UTC 2021 - Stefan Dirsch <sndirsch@suse.com>
|
||||||
|
|
||||||
|
@ -157,7 +157,7 @@ Requires: libpixman-1-0 >= 0.24
|
|||||||
Requires: Mesa
|
Requires: Mesa
|
||||||
%if 0%{?suse_version} >= 1315
|
%if 0%{?suse_version} >= 1315
|
||||||
Requires(post): update-alternatives
|
Requires(post): update-alternatives
|
||||||
Requires(postun): update-alternatives
|
Requires(postun):update-alternatives
|
||||||
%endif
|
%endif
|
||||||
Provides: xorg-x11-server-glx
|
Provides: xorg-x11-server-glx
|
||||||
Obsoletes: xorg-x11-server-glx
|
Obsoletes: xorg-x11-server-glx
|
||||||
@ -253,6 +253,8 @@ Patch1801: U_Fix-segfault-on-probing-a-non-PCI-platform-device-on.patch
|
|||||||
|
|
||||||
Patch1900: u_no-lto-for-tests.patch
|
Patch1900: u_no-lto-for-tests.patch
|
||||||
|
|
||||||
|
Patch1910: u_modesetting-Fix-dirty-updates-for-sw-rotation.patch
|
||||||
|
|
||||||
%description
|
%description
|
||||||
This package contains the X.Org Server.
|
This package contains the X.Org Server.
|
||||||
|
|
||||||
@ -405,6 +407,7 @@ sh %{SOURCE92} --verify . %{SOURCE91}
|
|||||||
%patch1600 -p1
|
%patch1600 -p1
|
||||||
%patch1801 -p1
|
%patch1801 -p1
|
||||||
%patch1900 -p1
|
%patch1900 -p1
|
||||||
|
%patch1910 -p1
|
||||||
|
|
||||||
%build
|
%build
|
||||||
%global _lto_cflags %{?_lto_cflags} -ffat-lto-objects
|
%global _lto_cflags %{?_lto_cflags} -ffat-lto-objects
|
||||||
|
Loading…
Reference in New Issue
Block a user