[plasma/kwin] /: backends/drm: re-allocate for tearing with compositing, too
Xaver Hugl <[email protected]>
| Newsgroups | gmane.comp.kde.cvs |
|---|---|
| Message-ID | <[email protected]> |
Git commit 7e8c82c765024465e6f590568d26a8a9ae3fb136 by Xaver Hugl.
Committed on 18/08/2026 at 18:42.
Pushed by zamundaaa into branch 'master'.
backends/drm: re-allocate for tearing with compositing, too
The format+modifiers normally used may not be compatible with tearing
on the hardware.
CCBUG: 524346
M +1 -1 autotests/drm/mockDrmTest.cpp
M +4 -2 src/backends/drm/drm_egl_layer.cpp
M +1 -1 src/backends/drm/drm_egl_layer.h
M +1 -1 src/backends/drm/drm_virtual_egl_layer.cpp
M +1 -1 src/backends/drm/drm_virtual_egl_layer.h
M +1 -1 src/backends/virtual/virtual_egl_backend.cpp
M +1 -1 src/backends/virtual/virtual_egl_backend.h
M +2 -2 src/backends/wayland/wayland_egl_backend.cpp
M +2 -2 src/backends/wayland/wayland_egl_backend.h
M +2 -2 src/backends/x11/x11_windowed_egl_backend.cpp
M +2 -2 src/backends/x11/x11_windowed_egl_backend.h
M +1 -1 src/compositor.cpp
M +1 -1 src/core/outputlayer.h
M +1 -1 src/plugins/colorpicker/colorpicker.cpp
M +1 -1 src/plugins/colorpicker/colorpickerlayer.cpp
M +1 -1 src/plugins/colorpicker/colorpickerlayer.h
M +1 -1 src/plugins/screencast/outputscreencastsource.cpp
M +1 -1 src/plugins/screencast/regionscreencastsource.cpp
M +1 -1 src/plugins/screencast/screencastlayer.cpp
M +1 -1 src/plugins/screencast/screencastlayer.h
M +2 -2 src/plugins/screenshot/screenshot.cpp
M +1 -1 src/plugins/screenshot/screenshotlayer.cpp
M +1 -1 src/plugins/screenshot/screenshotlayer.h
https://invent.kde.org/plasma/kwin/-/commit/7e8c82c765024465e6f590568d26a8a9ae3fb136
diff --git a/autotests/drm/mockDrmTest.cpp b/autotests/drm/mockDrmTest.cpp
index e7709e20107..752665f548c 100644
--- a/autotests/drm/mockDrmTest.cpp
+++ b/autotests/drm/mockDrmTest.cpp
@@ -464,7 +464,7 @@ void DrmTest::testModeset()
QCOMPARE(gpu->drmOutputs().size(), 1);
const auto output = gpu->drmOutputs().front();
const auto layer = renderBackend->compatibleOutputLayers(output).front();
- layer->beginFrame();
+ layer->beginFrame(nullptr);
output->renderLoop()->prepareNewFrame();
const auto frame = std::make_shared<OutputFrame>(output->renderLoop(), std::chrono::nanoseconds(1'000'000'000'000 / output->refreshRate()));
layer->endFrame(Region::infinite(), Region::infinite(), frame.get());
diff --git a/src/backends/drm/drm_egl_layer.cpp b/src/backends/drm/drm_egl_layer.cpp
index 1cd5ac6d3bf..108911c8187 100644
--- a/src/backends/drm/drm_egl_layer.cpp
+++ b/src/backends/drm/drm_egl_layer.cpp
@@ -50,12 +50,14 @@ EglGbmLayer::EglGbmLayer(EglGbmBackend *eglBackend, DrmGpu *gpu, DrmPlane::TypeI
{
}
-std::optional<OutputLayerBeginFrameInfo> EglGbmLayer::beginFrame()
+std::optional<OutputLayerBeginFrameInfo> EglGbmLayer::beginFrame(OutputFrame *frame)
{
m_scanoutBuffer.reset();
+ const bool tearing = frame && (frame->presentationMode() == PresentationMode::Async || frame->presentationMode() == PresentationMode::AdaptiveAsync);
+ const auto formats = tearing && !supportedAsyncDrmFormats().isEmpty() ? supportedAsyncDrmFormats() : supportedDrmFormats();
return m_surface.startRendering(targetRect().size(),
drmOutput()->transform().combine(OutputTransform::FlipY),
- supportedDrmFormats(),
+ formats,
drmOutput()->blendingColor(),
drmOutput()->layerBlendingColor(),
drmOutput()->needsShadowBuffer() ? pipeline()->iccProfile() : nullptr,
diff --git a/src/backends/drm/drm_egl_layer.h b/src/backends/drm/drm_egl_layer.h
index 13bafb1ab52..78679e94cd9 100644
--- a/src/backends/drm/drm_egl_layer.h
+++ b/src/backends/drm/drm_egl_layer.h
@@ -28,7 +28,7 @@ public:
explicit EglGbmLayer(EglGbmBackend *eglBackend, DrmPlane *plane);
explicit EglGbmLayer(EglGbmBackend *eglBackend, DrmGpu *gpu, DrmPlane::TypeIndex type);
- std::optional<OutputLayerBeginFrameInfo> beginFrame() override;
+ std::optional<OutputLayerBeginFrameInfo> beginFrame(OutputFrame *frame) override;
bool endFrame(const Region &renderedDeviceRegion, const Region &damagedDeviceRegion, OutputFrame *frame) override;
bool preparePresentationTest() override;
std::shared_ptr<DrmFramebuffer> currentBuffer() const override;
diff --git a/src/backends/drm/drm_virtual_egl_layer.cpp b/src/backends/drm/drm_virtual_egl_layer.cpp
index 92653d1e7ab..3a8ddf8eee7 100644
--- a/src/backends/drm/drm_virtual_egl_layer.cpp
+++ b/src/backends/drm/drm_virtual_egl_layer.cpp
@@ -38,7 +38,7 @@ VirtualEglGbmLayer::~VirtualEglGbmLayer()
releaseBuffers();
}
-std::optional<OutputLayerBeginFrameInfo> VirtualEglGbmLayer::beginFrame()
+std::optional<OutputLayerBeginFrameInfo> VirtualEglGbmLayer::beginFrame(OutputFrame *frame)
{
m_scanoutBuffer.reset();
diff --git a/src/backends/drm/drm_virtual_egl_layer.h b/src/backends/drm/drm_virtual_egl_layer.h
index c698712a5a7..567d0daabe7 100644
--- a/src/backends/drm/drm_virtual_egl_layer.h
+++ b/src/backends/drm/drm_virtual_egl_layer.h
@@ -33,7 +33,7 @@ public:
VirtualEglGbmLayer(EglGbmBackend *eglBackend, DrmVirtualOutput *output);
~VirtualEglGbmLayer() override;
- std::optional<OutputLayerBeginFrameInfo> beginFrame() override;
+ std::optional<OutputLayerBeginFrameInfo> beginFrame(OutputFrame *frame) override;
bool endFrame(const Region &renderedDeviceRegion, const Region &damagedDeviceRegion, OutputFrame *frame) override;
void releaseBuffers() override;
FormatModifierMap supportedDrmFormats() const override;
diff --git a/src/backends/virtual/virtual_egl_backend.cpp b/src/backends/virtual/virtual_egl_backend.cpp
index e8fdb585e7d..b8c0a2cc790 100644
--- a/src/backends/virtual/virtual_egl_backend.cpp
+++ b/src/backends/virtual/virtual_egl_backend.cpp
@@ -36,7 +36,7 @@ VirtualEglLayer::~VirtualEglLayer()
(void)m_backend->openglContext()->makeCurrent();
}
-std::optional<OutputLayerBeginFrameInfo> VirtualEglLayer::beginFrame()
+std::optional<OutputLayerBeginFrameInfo> VirtualEglLayer::beginFrame(OutputFrame *frame)
{
if (!m_backend->openglContext()->makeCurrent()) {
return std::nullopt;
diff --git a/src/backends/virtual/virtual_egl_backend.h b/src/backends/virtual/virtual_egl_backend.h
index f966f4bd50a..2e69951cc56 100644
--- a/src/backends/virtual/virtual_egl_backend.h
+++ b/src/backends/virtual/virtual_egl_backend.h
@@ -33,7 +33,7 @@ public:
VirtualEglLayer(BackendOutput *output, VirtualEglBackend *backend);
~VirtualEglLayer() override;
- std::optional<OutputLayerBeginFrameInfo> beginFrame() override;
+ std::optional<OutputLayerBeginFrameInfo> beginFrame(OutputFrame *frame) override;
bool endFrame(const Region &renderedDeviceRegion, const Region &damagedDeviceRegion, OutputFrame *frame) override;
FormatModifierMap supportedDrmFormats() const override;
diff --git a/src/backends/wayland/wayland_egl_backend.cpp b/src/backends/wayland/wayland_egl_backend.cpp
index 2462beab7fe..60d926129ff 100644
--- a/src/backends/wayland/wayland_egl_backend.cpp
+++ b/src/backends/wayland/wayland_egl_backend.cpp
@@ -53,7 +53,7 @@ GLFramebuffer *WaylandEglLayer::fbo() const
return m_buffer->framebuffer();
}
-std::optional<OutputLayerBeginFrameInfo> WaylandEglLayer::beginFrame()
+std::optional<OutputLayerBeginFrameInfo> WaylandEglLayer::beginFrame(OutputFrame *frame)
{
if (!m_backend->openglContext()->makeCurrent()) {
qCCritical(KWIN_WAYLAND_BACKEND) << "Make Context Current failed";
@@ -156,7 +156,7 @@ WaylandEglCursorLayer::~WaylandEglCursorLayer()
(void)m_backend->openglContext()->makeCurrent();
}
-std::optional<OutputLayerBeginFrameInfo> WaylandEglCursorLayer::beginFrame()
+std::optional<OutputLayerBeginFrameInfo> WaylandEglCursorLayer::beginFrame(OutputFrame *frame)
{
if (!m_backend->openglContext()->makeCurrent()) {
qCCritical(KWIN_WAYLAND_BACKEND) << "Make Context Current failed";
diff --git a/src/backends/wayland/wayland_egl_backend.h b/src/backends/wayland/wayland_egl_backend.h
index ff99d144cd4..6b66c87a58b 100644
--- a/src/backends/wayland/wayland_egl_backend.h
+++ b/src/backends/wayland/wayland_egl_backend.h
@@ -41,7 +41,7 @@ public:
~WaylandEglLayer() override;
GLFramebuffer *fbo() const;
- std::optional<OutputLayerBeginFrameInfo> beginFrame() override;
+ std::optional<OutputLayerBeginFrameInfo> beginFrame(OutputFrame *frame) override;
bool endFrame(const Region &renderedDeviceRegion, const Region &damagedDeviceRegion, OutputFrame *frame) override;
bool earlyScanoutChecks() override;
bool importScanoutBuffer(GraphicsBuffer *buffer, const std::shared_ptr<OutputFrame> &frame) override;
@@ -66,7 +66,7 @@ public:
WaylandEglCursorLayer(WaylandOutput *output, WaylandEglBackend *backend);
~WaylandEglCursorLayer() override;
- std::optional<OutputLayerBeginFrameInfo> beginFrame() override;
+ std::optional<OutputLayerBeginFrameInfo> beginFrame(OutputFrame *frame) override;
bool endFrame(const Region &renderedDeviceRegion, const Region &damagedDeviceRegion, OutputFrame *frame) override;
FormatModifierMap supportedDrmFormats() const override;
void releaseBuffers() override;
diff --git a/src/backends/x11/x11_windowed_egl_backend.cpp b/src/backends/x11/x11_windowed_egl_backend.cpp
index 13d5bc39b82..4541779565d 100644
--- a/src/backends/x11/x11_windowed_egl_backend.cpp
+++ b/src/backends/x11/x11_windowed_egl_backend.cpp
@@ -32,7 +32,7 @@ X11WindowedEglPrimaryLayer::~X11WindowedEglPrimaryLayer()
{
}
-std::optional<OutputLayerBeginFrameInfo> X11WindowedEglPrimaryLayer::beginFrame()
+std::optional<OutputLayerBeginFrameInfo> X11WindowedEglPrimaryLayer::beginFrame(OutputFrame *frame)
{
if (!m_backend->openglContext()->makeCurrent()) {
return std::nullopt;
@@ -110,7 +110,7 @@ X11WindowedEglCursorLayer::~X11WindowedEglCursorLayer()
m_texture.reset();
}
-std::optional<OutputLayerBeginFrameInfo> X11WindowedEglCursorLayer::beginFrame()
+std::optional<OutputLayerBeginFrameInfo> X11WindowedEglCursorLayer::beginFrame(OutputFrame *frame)
{
if (!m_backend->openglContext()->makeCurrent()) {
return std::nullopt;
diff --git a/src/backends/x11/x11_windowed_egl_backend.h b/src/backends/x11/x11_windowed_egl_backend.h
index 6b9bf839218..ed9da1ec452 100644
--- a/src/backends/x11/x11_windowed_egl_backend.h
+++ b/src/backends/x11/x11_windowed_egl_backend.h
@@ -28,7 +28,7 @@ public:
X11WindowedEglPrimaryLayer(X11WindowedEglBackend *backend, X11WindowedOutput *output);
~X11WindowedEglPrimaryLayer() override;
- std::optional<OutputLayerBeginFrameInfo> beginFrame() override;
+ std::optional<OutputLayerBeginFrameInfo> beginFrame(OutputFrame *frame) override;
bool endFrame(const Region &renderedDeviceRegion, const Region &damagedDeviceRegion, OutputFrame *frame) override;
FormatModifierMap supportedDrmFormats() const override;
void releaseBuffers() override;
@@ -49,7 +49,7 @@ public:
X11WindowedEglCursorLayer(X11WindowedEglBackend *backend, X11WindowedOutput *output);
~X11WindowedEglCursorLayer() override;
- std::optional<OutputLayerBeginFrameInfo> beginFrame() override;
+ std::optional<OutputLayerBeginFrameInfo> beginFrame(OutputFrame *frame) override;
bool endFrame(const Region &renderedDeviceRegion, const Region &damagedDeviceRegion, OutputFrame *frame) override;
FormatModifierMap supportedDrmFormats() const override;
void releaseBuffers() override;
diff --git a/src/compositor.cpp b/src/compositor.cpp
index 54df6209e88..3e04496fbbd 100644
--- a/src/compositor.cpp
+++ b/src/compositor.cpp
@@ -523,7 +523,7 @@ static bool prepareRendering(RenderView *view, LogicalOutput *logicalOutput, Bac
static bool renderLayer(RenderView *view, LogicalOutput *logicalOutput, BackendOutput *backendOutput, const std::shared_ptr<OutputFrame> &frame, const Region &surfaceDamage)
{
- auto beginInfo = view->layer()->beginFrame();
+ auto beginInfo = view->layer()->beginFrame(frame.get());
if (!beginInfo) {
return false;
}
diff --git a/src/core/outputlayer.h b/src/core/outputlayer.h
index 018d75d8482..252707c570f 100644
--- a/src/core/outputlayer.h
+++ b/src/core/outputlayer.h
@@ -95,7 +95,7 @@ public:
*/
virtual bool preparePresentationTest();
- virtual std::optional<OutputLayerBeginFrameInfo> beginFrame() = 0;
+ virtual std::optional<OutputLayerBeginFrameInfo> beginFrame(OutputFrame *frame) = 0;
virtual bool endFrame(const Region &renderedDeviceRegion, const Region &damagedDeviceRegion, OutputFrame *frame) = 0;
/**
diff --git a/src/plugins/colorpicker/colorpicker.cpp b/src/plugins/colorpicker/colorpicker.cpp
index a833f861529..9d4e66d95b3 100644
--- a/src/plugins/colorpicker/colorpicker.cpp
+++ b/src/plugins/colorpicker/colorpicker.cpp
@@ -121,7 +121,7 @@ QColor ColorPickerEffect::pick()
if (!layer.preparePresentationTest()) {
return;
}
- const auto beginInfo = layer.beginFrame();
+ const auto beginInfo = layer.beginFrame(nullptr);
if (!beginInfo) {
return;
}
diff --git a/src/plugins/colorpicker/colorpickerlayer.cpp b/src/plugins/colorpicker/colorpickerlayer.cpp
index d05ec121528..3dc2181e3b8 100644
--- a/src/plugins/colorpicker/colorpickerlayer.cpp
+++ b/src/plugins/colorpicker/colorpickerlayer.cpp
@@ -19,7 +19,7 @@ FormatModifierMap ColorPickerLayer::supportedDrmFormats() const
return {};
}
-std::optional<OutputLayerBeginFrameInfo> ColorPickerLayer::beginFrame()
+std::optional<OutputLayerBeginFrameInfo> ColorPickerLayer::beginFrame(OutputFrame *frame)
{
return OutputLayerBeginFrameInfo{
.renderTarget = RenderTarget(m_buffer),
diff --git a/src/plugins/colorpicker/colorpickerlayer.h b/src/plugins/colorpicker/colorpickerlayer.h
index 9dd6add972c..a114069b483 100644
--- a/src/plugins/colorpicker/colorpickerlayer.h
+++ b/src/plugins/colorpicker/colorpickerlayer.h
@@ -19,7 +19,7 @@ public:
FormatModifierMap supportedDrmFormats() const override;
void releaseBuffers() override;
- std::optional<OutputLayerBeginFrameInfo> beginFrame() override;
+ std::optional<OutputLayerBeginFrameInfo> beginFrame(OutputFrame *frame) override;
bool endFrame(const Region &renderedRegion, const Region &damagedRegion, OutputFrame *frame) override;
private:
diff --git a/src/plugins/screencast/outputscreencastsource.cpp b/src/plugins/screencast/outputscreencastsource.cpp
index 28e56700d69..43ec1844280 100644
--- a/src/plugins/screencast/outputscreencastsource.cpp
+++ b/src/plugins/screencast/outputscreencastsource.cpp
@@ -82,7 +82,7 @@ Region OutputScreenCastSource::render(GLFramebuffer *target, const Region &buffe
if (!m_layer->preparePresentationTest()) {
return Region{};
}
- const auto beginInfo = m_layer->beginFrame();
+ const auto beginInfo = m_layer->beginFrame(nullptr);
if (!beginInfo) {
return Region{};
}
diff --git a/src/plugins/screencast/regionscreencastsource.cpp b/src/plugins/screencast/regionscreencastsource.cpp
index a8ee50518cf..f85d65d04f4 100644
--- a/src/plugins/screencast/regionscreencastsource.cpp
+++ b/src/plugins/screencast/regionscreencastsource.cpp
@@ -77,7 +77,7 @@ Region RegionScreenCastSource::render(GLFramebuffer *target, const Region &buffe
if (!m_layer->preparePresentationTest()) {
return Region{};
}
- const auto beginInfo = m_layer->beginFrame();
+ const auto beginInfo = m_layer->beginFrame(nullptr);
if (!beginInfo) {
return Region{};
}
diff --git a/src/plugins/screencast/screencastlayer.cpp b/src/plugins/screencast/screencastlayer.cpp
index fc2bfce0ed2..0a62933ce97 100644
--- a/src/plugins/screencast/screencastlayer.cpp
+++ b/src/plugins/screencast/screencastlayer.cpp
@@ -28,7 +28,7 @@ FormatModifierMap ScreencastLayer::supportedDrmFormats() const
return m_formats;
}
-std::optional<OutputLayerBeginFrameInfo> ScreencastLayer::beginFrame()
+std::optional<OutputLayerBeginFrameInfo> ScreencastLayer::beginFrame(OutputFrame *frame)
{
return OutputLayerBeginFrameInfo{
.renderTarget = RenderTarget(m_buffer),
diff --git a/src/plugins/screencast/screencastlayer.h b/src/plugins/screencast/screencastlayer.h
index 3d563bd8299..5300975a87b 100644
--- a/src/plugins/screencast/screencastlayer.h
+++ b/src/plugins/screencast/screencastlayer.h
@@ -19,7 +19,7 @@ public:
FormatModifierMap supportedDrmFormats() const override;
void releaseBuffers() override;
- std::optional<OutputLayerBeginFrameInfo> beginFrame() override;
+ std::optional<OutputLayerBeginFrameInfo> beginFrame(OutputFrame *frame) override;
bool endFrame(const Region &renderedRegion, const Region &damagedRegion, OutputFrame *frame) override;
private:
diff --git a/src/plugins/screenshot/screenshot.cpp b/src/plugins/screenshot/screenshot.cpp
index b34afdfa0f3..b1c975a49a5 100644
--- a/src/plugins/screenshot/screenshot.cpp
+++ b/src/plugins/screenshot/screenshot.cpp
@@ -83,7 +83,7 @@ std::optional<QImage> ScreenShotManager::takeScreenShot(LogicalOutput *screen, S
if (!layer.preparePresentationTest()) {
return std::nullopt;
}
- const auto beginInfo = layer.beginFrame();
+ const auto beginInfo = layer.beginFrame(nullptr);
if (!beginInfo) {
return std::nullopt;
}
@@ -151,7 +151,7 @@ std::optional<QImage> ScreenShotManager::takeScreenShot(const Rect &area, Screen
if (!layer.preparePresentationTest()) {
return std::nullopt;
}
- const auto beginInfo = layer.beginFrame();
+ const auto beginInfo = layer.beginFrame(nullptr);
if (!beginInfo) {
return std::nullopt;
}
diff --git a/src/plugins/screenshot/screenshotlayer.cpp b/src/plugins/screenshot/screenshotlayer.cpp
index c1f78e33ead..4b608ff0275 100644
--- a/src/plugins/screenshot/screenshotlayer.cpp
+++ b/src/plugins/screenshot/screenshotlayer.cpp
@@ -19,7 +19,7 @@ FormatModifierMap ScreenshotLayer::supportedDrmFormats() const
return {};
}
-std::optional<OutputLayerBeginFrameInfo> ScreenshotLayer::beginFrame()
+std::optional<OutputLayerBeginFrameInfo> ScreenshotLayer::beginFrame(OutputFrame *frame)
{
return OutputLayerBeginFrameInfo{
.renderTarget = RenderTarget(m_buffer),
diff --git a/src/plugins/screenshot/screenshotlayer.h b/src/plugins/screenshot/screenshotlayer.h
index 01f69734c06..87cf31115ce 100644
--- a/src/plugins/screenshot/screenshotlayer.h
+++ b/src/plugins/screenshot/screenshotlayer.h
@@ -19,7 +19,7 @@ public:
FormatModifierMap supportedDrmFormats() const override;
void releaseBuffers() override;
- std::optional<OutputLayerBeginFrameInfo> beginFrame() override;
+ std::optional<OutputLayerBeginFrameInfo> beginFrame(OutputFrame *frame) override;
bool endFrame(const Region &renderedRegion, const Region &damagedRegion, OutputFrame *frame) override;
private: