Bug 350159 - kwin_wayland needs KWIN_COMPOSE=Q set on platforms that recommend xrender, like QEMU
Summary: kwin_wayland needs KWIN_COMPOSE=Q set on platforms that recommend xrender, li...
Status: RESOLVED FIXED
Alias: None
Product: kwin
Classification: Plasma
Component: wayland-generic (show other bugs)
Version: git master
Platform: Other Linux
: NOR normal
Target Milestone: ---
Assignee: KWin default assignee
URL: https://phabricator.kde.org/D8363
Keywords:
Depends on:
Blocks:
 
Reported: 2015-07-13 01:54 UTC by bluescreenavenger
Modified: 2017-10-19 16:27 UTC (History)
0 users

See Also:
Latest Commit:
Version Fixed In: 5.12.0
mgraesslin: Wayland+
mgraesslin: ReviewRequest+


Attachments
Patch I tried... Please ignore the if (m_scene->initFailed()) { part. that was another test that didn't work (5.48 KB, patch)
2015-07-13 01:56 UTC, bluescreenavenger
Details

Note You need to log in before you can comment on or make changes to this bug.
Description bluescreenavenger 2015-07-13 01:54:23 UTC
It seems that Kwin doesn't work properly

I even tried to make it use qpainter instead of xrender, and it seems that I get the same behaviour. It might be that QTimer::singleShot(0, Compositor::self(), SLOT(fallbackToXRenderCompositing())); doesn't seem to work... I tried to make a fallbackToQPainterCompositing(), and that didn't work...

Reproducible: Always




no screens available, assuming 24-bit color
QPainter::begin: Paint device returned engine == 0, type: 2
QPainter::setRenderHint: Painter must be active to set rendering hints
QPainter::setPen: Painter not active
QPainter::setBrush: Painter not active
QPainter::setBrush: Painter not active
QPainter::drawRects: Painter not active
QPainter::setBrush: Painter not active
QPainter::drawRects: Painter not active
QPainter::setBrush: Painter not active
QPainter::drawRects: Painter not active
QPainter::setCompositionMode: Painter not active
QPainter::setBrush: Painter not active
QPainter::end: Painter not active, aborted
QPainter::begin: Paint device returned engine == 0, type: 2
QPainter::setRenderHint: Painter must be active to set rendering hints
QPainter::setPen: Painter not active
QPainter::setBrush: Painter not active
QPainter::setBrush: Painter not active
QPainter::drawRects: Painter not active
QPainter::setBrush: Painter not active
QPainter::drawRects: Painter not active
QPainter::setBrush: Painter not active
QPainter::drawRects: Painter not active
QPainter::setCompositionMode: Painter not active
QPainter::setBrush: Painter not active
QPainter::end: Painter not active, aborted
QPainter::begin: Paint device returned engine == 0, type: 2
QPainter::setCompositionMode: Painter not active
QPainter::begin: Paint device returned engine == 0, type: 2
QPainter::begin: Paint device returned engine == 0, type: 2
QPainter::setRenderHint: Painter must be active to set rendering hints
QPainter::setPen: Painter not active
QPainter::setBrush: Painter not active
QPainter::setCompositionMode: Painter not active
QPainter::setBrush: Painter not active
QPainter::setRenderHint: Painter must be active to set rendering hints
QPainter::setRenderHint: Painter must be active to set rendering hints
kglobalaccel-runtime: Loaded plugin "/opt/lib/i386-linux-gnu/plugins/org.kde.kglobalaccel5.platforms/KF5GlobalAccelPrivateKWin.so" for platform "org.kde.kwin"
kwin_core: KGlobalAcceld inited
kwayland-client: Connected to Wayland server over file descriptor: 15
kwin_core: Session path: "/org/freedesktop/login1/session/c2"
kwayland-client: Connected to Wayland server at: "wlhost-2680"
kwayland-client: Wayland Interface:  wl_compositor / 1 / 3
kwayland-client: Wayland Interface:  wl_subcompositor / 2 / 1
kwayland-client: Unknown interface announced:  wl_scaler / 3 / 2
kwayland-client: Unknown interface announced:  presentation / 4 / 1
kwayland-client: Wayland Interface:  wl_data_device_manager / 5 / 2
kwayland-client: Wayland Interface:  wl_shm / 6 / 1
kwayland-client: Wayland Interface:  wl_seat / 7 / 4
kwayland-client: Wayland Interface:  wl_output / 8 / 2
kwayland-client: Wayland Interface:  _wl_fullscreen_shell / 9 / 1
kwayland-client: Wayland Interface:  wl_compositor / 1 / 3
kwayland-client: Wayland Interface:  wl_shell / 2 / 1
kwayland-client: Wayland Interface:  wl_shm / 3 / 1
kwayland-client: Wayland Interface:  wl_seat / 4 / 3
kwayland-client: Wayland Interface:  wl_data_device_manager / 5 / 1
kwayland-client: Wayland Interface:  org_kde_plasma_shell / 6 / 1
kwayland-client: Unknown interface announced:  qt_surface_extension / 7 / 1
kwayland-client: Wayland Interface:  org_kde_plasma_window_management / 8 / 1
kwin_core: Initializing OpenGL compositing
kwin_wayland_backend: Connected to Wayland display? yes
kwin_core: Egl Initialize succeeded
kwin_core: EGL version:  1 . 4
OpenGL vendor string:                   VMware, Inc.
OpenGL renderer string:                 Gallium 0.4 on llvmpipe (LLVM 3.4, 128 bits)
OpenGL version string:                  3.0 Mesa 10.7.0-devel (git-2b8c518)
OpenGL shading language version string: 1.30
Driver:                                 LLVMpipe
GPU class:                              Unknown
OpenGL version:                         3.0
GLSL version:                           1.30
Mesa version:                           10.7
Linux kernel version:                   3.19
Requires strict binding:                no
GLSL shaders:                           yes
Texture NPOT support:                   yes
Virtual Machine:                        no
kwin_wayland_backend: Using Wayland rendering backend
kwin_wayland_backend: This is a highly experimental backend, do not use for productive usage!
kwin_wayland_backend: Please do not report any issues you might encounter when using this backend!
kwin_core: Driver does not recommend OpenGL 2 compositing
kwin_core: OpenGL driver recommends compositing fallback. Falling back
kwin_core: To overwrite the detection use the environment variable KWIN_COMPOSE
kwin_core: For more information see http://community.kde.org/KWin/Environment_Variables#KWIN_COMPOSE
kwin_core: Failed to initialize compositing, compositing disabled
kwin_core: The used windowing system requires compositing
kwin_core: We are going to quit KWin now as it is broken
Comment 1 bluescreenavenger 2015-07-13 01:56:57 UTC
Created attachment 93578 [details]
Patch I tried... Please ignore the if (m_scene->initFailed()) { part. that was another test that didn't work
Comment 2 bluescreenavenger 2015-07-13 02:09:04 UTC
Comment on attachment 93578 [details]
Patch I tried... Please ignore the if (m_scene->initFailed()) { part. that was another test that didn't work

>diff --git a/composite.cpp b/composite.cpp
>index 8371390..7a84ec6 100644
>--- a/composite.cpp
>+++ b/composite.cpp
>@@ -238,6 +238,10 @@ void Compositor::slotCompositingOptionsInitialized()
>             m_scene = NULL;
>         }
> 
>+        if (kwinApp()->shouldUseWaylandForCompositing()) {
>+            if (m_scene->initFailed()) {
>+            m_scene = SceneQPainter::createScene(this);
>+        }
>         // Do not Fall back to XRender - it causes problems when selfcheck fails during startup, but works later on
>         break;
>     }
>@@ -469,6 +473,17 @@ void Compositor::fallbackToXRenderCompositing()
>     setup();
> }
> 
>+// OpenGL self-check failed, fallback to QPainter
>+void Compositor::fallbackToQPainterCompositing()
>+{
>+    finish();
>+    KConfigGroup config(KSharedConfig::openConfig(), "Compositing");
>+    config.writeEntry("Backend", "QPainter");
>+    config.sync();
>+    options->setCompositingMode(QPainterCompositing);
>+    setup();
>+}
>+
> void Compositor::slotConfigChanged()
> {
>     if (!m_suspended) {
>diff --git a/composite.h b/composite.h
>index fc0ddd5..a961dc0 100644
>--- a/composite.h
>+++ b/composite.h
>@@ -203,6 +203,7 @@ private Q_SLOTS:
>      **/
>     void restart();
>     void fallbackToXRenderCompositing();
>+    void fallbackToQPainterCompositing();
>     void performCompositing();
>     void delayedCheckUnredirect();
>     void slotConfigChanged();
>diff --git a/libkwineffects/kwinglplatform.cpp b/libkwineffects/kwinglplatform.cpp
>index 6dee53b..01131aa 100644
>--- a/libkwineffects/kwinglplatform.cpp
>+++ b/libkwineffects/kwinglplatform.cpp
>@@ -37,7 +37,15 @@ namespace KWin
> {
> 
> GLPlatform *GLPlatform::s_platform = 0;
>-
>+static CompositingType getFallbackCompositor()
>+{
>+    if (QX11Info::isPlatformX11())
>+    {
>+        return XRenderCompositing;
>+    } else {
>+        return QPainterCompositing;
>+    }
>+}
> static qint64 parseVersionString(const QByteArray &version)
> {
>     // Skip any leading non digit
>@@ -502,7 +510,7 @@ QString GLPlatform::chipClassToString(ChipClass chipClass)
> GLPlatform::GLPlatform()
>     : m_driver(Driver_Unknown),
>       m_chipClass(UnknownChipClass),
>-      m_recommendedCompositor(XRenderCompositing),
>+      m_recommendedCompositor(getFallbackCompositor()),
>       m_mesaVersion(0),
>       m_galliumVersion(0),
>       m_looseBinding(false),
>@@ -765,11 +773,11 @@ void GLPlatform::detect(OpenGLPlatformInterface platformInterface)
>         }
> 
>         if (m_chipClass < R300) {
>-            // fallback to XRender for R100 and R200
>-            m_recommendedCompositor = XRenderCompositing;
>+            // fallback for R100 and R200
>+            m_recommendedCompositor = getFallbackCompositor();
>         } else if (m_chipClass < R600) {
>-            // XRender due to NPOT limitations not supported by KWin's shaders
>-            m_recommendedCompositor = XRenderCompositing;
>+            // fallback due to NPOT limitations not supported by KWin's shaders
>+            m_recommendedCompositor = getFallbackCompositor();
>         } else {
>             m_recommendedCompositor = OpenGL2Compositing;
>         }
>@@ -790,7 +798,7 @@ void GLPlatform::detect(OpenGLPlatformInterface platformInterface)
>         }
> 
>         if (m_chipClass < NV40) {
>-            m_recommendedCompositor = XRenderCompositing;
>+            m_recommendedCompositor = getFallbackCompositor();
>         } else {
>             m_recommendedCompositor = OpenGL2Compositing;
>         }
>@@ -808,7 +816,7 @@ void GLPlatform::detect(OpenGLPlatformInterface platformInterface)
>         m_looseBinding = false;
> 
>         if (m_chipClass < I915) {
>-            m_recommendedCompositor = XRenderCompositing;
>+            m_recommendedCompositor = getFallbackCompositor();
>         } else {
>             m_recommendedCompositor = OpenGL2Compositing;
>         }
>@@ -822,8 +830,8 @@ void GLPlatform::detect(OpenGLPlatformInterface platformInterface)
>     }
> 
>     if (isSoftwareEmulation()) {
>-        // we recommend XRender
>-        m_recommendedCompositor = XRenderCompositing;
>+        // we recommend to fallback
>+        m_recommendedCompositor = getFallbackCompositor();
>         if (m_driver < Driver_Llvmpipe) {
>             // Software emulation does not provide GLSL
>             m_limitedGLSL = m_supportsGLSL = false;
>diff --git a/scene_opengl.cpp b/scene_opengl.cpp
>index a35dc59..f801ab3 100644
>--- a/scene_opengl.cpp
>+++ b/scene_opengl.cpp
>@@ -577,11 +577,15 @@ SceneOpenGL *SceneOpenGL::createScene(QObject *parent)
>         }
>     }
>     if (!scene) {
>-        if (GLPlatform::instance()->recommendedCompositor() == XRenderCompositing) {
>-            qCCritical(KWIN_CORE) << "OpenGL driver recommends XRender based compositing. Falling back to XRender.";
>+        if (GLPlatform::instance()->recommendedCompositor() == XRenderCompositing || GLPlatform::instance()->recommendedCompositor() == QPainterCompositing) {
>+            qCCritical(KWIN_CORE) << "OpenGL driver recommends compositing fallback. Falling back";
>             qCCritical(KWIN_CORE) << "To overwrite the detection use the environment variable KWIN_COMPOSE";
>             qCCritical(KWIN_CORE) << "For more information see http://community.kde.org/KWin/Environment_Variables#KWIN_COMPOSE";
>-            QTimer::singleShot(0, Compositor::self(), SLOT(fallbackToXRenderCompositing()));
>+	    if (QX11Info::isPlatformX11()) {
>+                QTimer::singleShot(0, Compositor::self(), SLOT(fallbackToXRenderCompositing()));
>+	    } else {
>+                QTimer::singleShot(0, Compositor::self(), SLOT(fallbackToQPainterCompositing()));
>+	    }
>         }
>         delete backend;
>     }
Comment 3 Thomas Lübking 2015-07-13 05:53:16 UTC
please clean up the patch and upload it at git.reviewboard.kde.org

2 things:
1. "getFooBar" is javastyle - just name it "failsafeCompositor()" or whatever.
2.  if (GLPlatform::instance()->recommendedCompositor() == XRenderCompositing || GLPlatform::instance()->recommendedCompositor() == QPainterCompositing) {
should probably be if (!(GLPlatform::instance()->recommendedCompositor() & OpenGLCompositing)) or similar.
Comment 4 Martin Flöser 2015-07-13 06:12:41 UTC
The problem with the fallback approach is that it moves the re-try with different compositor to the next event cycle. I assume that this is the main problem on why the patch doesn't work.

I had already looked into that problem in the past and decided to delay it for the time being. It needs a restructuring/rethinking of the whole situation and also on how KWin should behave in that case. Especially I'm not sure yet what is the correct strategy for e.g. drm/gl requested, but fails. Should we fallback to drm/qpainter or would it be better to fallback to fbdev/qpainter?

Also I'm not sure whether we want to support things like Qemu anyway or whether we should consider VMs unsupported till there are proper KMS interfaces exposed on them.
Comment 5 bluescreenavenger 2015-07-13 09:19:47 UTC
This is when I try to call kwin_wayland with --windowed on a fullscreen-shell Weston session.

I tried to comment out the qApp->quit(); as an experiment, and that allowed the fallback to actually work. It's probably not upstreamable, which is why I didn't submit a ReviewBoard...
Comment 6 Martin Flöser 2015-07-13 09:29:21 UTC
(In reply to bluescreen_avenger from comment #5)
> I tried to comment out the qApp->quit(); as an experiment, and that allowed
> the fallback to actually work.

That verifies my thought that it's related to the moving to next event cycle.
Comment 7 bluescreenavenger 2015-07-13 10:49:24 UTC
Could it be upstreamable possibly if I add a check that it only calls qApp->quit(); if the options->compositingMode() is NOT xrender or qpainter?
Comment 8 Martin Flöser 2015-07-13 11:20:11 UTC
hmm that also doesn't sound correct. What if a backend only supports OpenGL and it's the only available backend? Then we need to quit. I think it needs to be better combined with the outstanding patch which adds the supportedCompositors to the backend. It then needs to check whether there is another compositor it could try.
Comment 9 bluescreenavenger 2017-01-05 04:10:32 UTC
It appears that on QXL, this issue is still not resolved, unless I manually specify it to use qpainter with an environment variable...
Comment 10 Martin Flöser 2017-10-18 20:08:17 UTC
Automatic compositing type selection in: https://phabricator.kde.org/D8363
Comment 11 bluescreenavenger 2017-10-19 11:03:24 UTC
Hi

That patch works!

Thanks
Comment 12 Martin Flöser 2017-10-19 16:27:25 UTC
Git commit 729bfd04a0c61f306e7e2fbc99d277397049b0d3 by Martin Flöser.
Committed on 19/10/2017 at 16:26.
Pushed by graesslin into branch 'master'.

Try all supported Compositor Types of the current Platform

Summary:
The Compositor now tries to create a Scene not just once but every
type supported by the Platform till it finds one which works. The user's
configuration is only used as a preferred hint and tried first if the
platform supports it.

This brings as an advantage that on platforms such as framebuffer the
user does not need to specify which compositor to use: KWin uses QPainter
automatically.

Also we don't need to do the "translation" from XRender to QPainter any
more. XRender is not supported by any platform using QPainter, so the
user configuration is ignored anyway.
FIXED-IN: 5.12.0

Test Plan: Run on framebuffer, verified debug output.

Reviewers: #kwin, #plasma

Subscribers: plasma-devel, kwin

Tags: #kwin

Differential Revision: https://phabricator.kde.org/D8363

M  +34   -17   composite.cpp
M  +3    -6    options.cpp

https://commits.kde.org/kwin/729bfd04a0c61f306e7e2fbc99d277397049b0d3