So they can be derived from the DRM format as well.
While updating the users, ensure we don't announce support for
DRM formats in zwp_linux_dmabuf_v1 if the MetaMultiTextureFormat is
INVALID. This will be used for YUV subformats in following commits.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2191>
1. Move into the new 'common' folder and build for Wayland as well
so we will be able to share the code in follow-up commits.
2. Rename to cogl-drm-formats to make it more obvious that the format
map is more than an utility these days.
3. Drop the unused CoglTextureComponents part (see also previous
commit).
4. Move the map to the header, simplifying some future use-cases.
5. Sync formats with MetaWaylandBuffer and MetaWaylandDmaBufBuffer and
also use newly introduced opaque formats where appropriate.
This avoids duplicated code, ensures that new drm-formats added to
the dmabuf protocol have an adequate representation in Cogl from which
information like alpha support can be easily derived and finally
ensures we don't crash if the mappings got out of sync.
6. Remove some likely untested formats. In case some of these are
actually needed on certain hardware, we can test whether we got
the correct mapping by also adding support for the corresponding
wl_shm_format in MetaWaylandBuffer by extending the gradient test in
https://gitlab.freedesktop.org/jadahl/wayland-test-clients
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3065>
This makes it possible to post KMS updates that will always defer until
just before the scanout deadline. This is useful to allow queuing cursor
updates where we don't want to post them to KMS immediately, but rather
wait until as late as possible to get lower latency.
We cannot delay primary plane compositions however, and this is due to
how the kernel may prioritize GPU work - not until a pipeline gets
attached to a atomic commit will it in some drivers get bumped to high
priority. This means we still need to post any update that depends on
OpenGL pipelines as soon as possible.
To avoid working on compositing, then getting stomped on the feet by the
deadline scheduler, the deadline timer is disarmed whenever there is a
frame currently being painted. This will still allow new cursor updates
to arrive during composition, but will delay the actual KMS commit until
the primary plane update has been posted.
Still, even for cursor-only we still need higher than default timing
capabilities, thus the deadline scheduler depends on the KMS thread
getting real-time scheduling priority. When the thread isn't realtime
scheduled, the KMS thread instead asks the main thread to "flush" the
commit as part of the regular frame update. A flushing update means one
that isn't set to always defer and has a latching CRTC.
The verbose KMS debug logging makes the processing take too long, making
us more likely to miss the deadline. Avoid this by increasing the
evasion length when debug logging is enabled. Not the best, but better
than changing the behavior completely.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2777>
While the default when passing NULL will be the main context of the main
thread, make it possible to specify another main context, so that
result handlers can be invoked on the right thread.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2777>
The previous logic didn't work correctly at least when priority-based
preeption wasn't supported by the DRM driver, such as in the case
of amdgpu. The call to glGetQueryObjecti64v would block on client
work which is already in progress (most likely for the next frame)
and delay notifying the ClutterFrameClock about presentation.
Conveniently, the Wayland transactions mechanism guarantees that all
fences of a dma-buf buffer are signalled before the buffer is
included in a frame, which means that dma-buf buffers are ready for
presentation when being directly scanned-out.
Direct scanout is only supported for dma-buf buffers too, which means
that all buffers going through direct scanout are effectively ready
and require no GPU rendering before presentation.
Assuming zero rendering time for dma-buf buffers going through direct
scanout simplifies the code and removes the need for
glGetQueryObjecti64v, thus avoiding the aforementioned issue where it
could block for longer than expected.
Closes: https://gitlab.gnome.org/GNOME/mutter/-/issues/2766
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/3080>
The existence of the KMS property just means that we can send an
InfoFrame but we also have to make sure the sink actually supports the
metadata type 1 and the selected transfer function.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2879>
We relied on them being valid longer to keep track of used GPUs. If we
don't have the CRTC (or output) we don't have a way to fetch the pointer
to the MetaGpu that drives the associated monitor.
This avoids a crash when trying to fetch said pointer from what would be
the NULL MetaCrtc pointer.
Fixes: 08593ea872 ("onscreen/native: Hold ref to the output and CRTC until detached")
Closes: https://gitlab.gnome.org/GNOME/mutter/-/issues/2667
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2887>
When an onscreen is "attached" it means it has an active CRTC and output
it interacts with, e.g. listens to configuration changes to update gamma
and privacy screen state.
MetaOutput and MetaCrtc are rather short lived objects meaning they are
disposed of and regenerated each time the compositor reloads monitor
resources, and while MetaOutput are indirectly kept alive due to the
MetaMonitor holding on to them during reloading, the same does not apply
to MetaCrtc, so to avoid trying to disconnect our signals from
disappeared outputs and CRTCs when we dispatch, hold our own references
to these objects.
Closes: https://gitlab.gnome.org/GNOME/mutter/-/issues/2665
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2885>
On exit, explicitly detach the onscreens during disposal. This means no
functional changes, but allows for doing more cleanup on detach that
doesn't need to be repeated on disposal.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2885>
In order to make things more and more asynchronus and to each time we
paint be an isolated event, that can be potentially be applied
individually or together with other updates, make it so that each time
we draw, we use the transient MetaFrameNative (ClutterFrame) instance to
carry a KMS update for us.
For this to work, we also need to restructure how we apply mode sets.
Previously we'd amend the same KMS update each frame during mode set,
then after the last CRTC was composited, we'd apply the update that
contained updates for all CRTC.
Now each CRTC has its own KMS update, and instead we put them in a per
device table, and whenever we finished painting, we'll merge the new
update into any existing one, and then finally once all CRTCs have been
composited, we'll apply an update that contains all the mode sets for all
relevant CRTCs on a device.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2855>
Instead of using the "discarded" page flip callback when the
"discarding" happened during actual immediate processing, communicate
the same via the KMS update feedback.
The "discarded" page flip callback is instead used only for when a
posted page flip is discarded. In the atomic backend, this only happens
on shutdown, while in the simple backend, this also happens when a
asynchronous retry sequence eventually is abandoned.
This allows further improvements making KMS handling fully async.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2854>
We test direct client buffer scanout using a TEST_ONLY commit on atomic,
and with various conditions in non-atomic, but if we end up failing to
actually commit despite this, handle the fallout asynchronously. What
this means is that we'll reschedule a new frame immediately.
For this to work, the same scanout buffer needs to be avoided for the
same CRTC. This is done by using the newly added signal on the
CoglScanout object to let the MetaWaylandBuffer object mark the current
buffer as non-working for the onsrceen that it failed on. This allows to
re-try buffers on the same onscreen when new ones are attached.
This queues a full damage, since we consumed the qeued redraw rect. The
redraw rect wasn't lost - it was accumulated to make sure the whole
primary plane was redrawed according to the damage region, whenever we
would end up no longer doing direct scanout, but this accumulation only
works when we're not intentionally stopping to scanout. For now, lets
just damage the whole view, it's just an graceful fallback in response
to an unexpected error anyway.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2854>
If we get a "ready" page flip feedback, it means the page flip was
symbolic, i.e. not real, e.g. as a result of an update that didn't
change the state of the primary plane. Warn if there is a "next fb"
meaning we expected to have a new buffer that we flipped to.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2854>
With detach meaning having the onscreen stop listening on configuration
changes on the corresponding backing mode setting objects. We need to do
this as there is a time between rebuilding the views, and that the new
mode sets are called, where the old onscreen is kept alive, but the
stage view is gone. At this point in time, if privacy screen or gamma
configuration changes, e.g. by the night light temperature changing, the
onscreen would attempt to schedule an update on the now gone stage view.
This commit also renames the "keep onscreen alive" to "detached
onscreens" to more clearly communicate that it's detached onscreens from
their corresponding mode setting objects.
Closes: https://gitlab.gnome.org/GNOME/mutter/-/issues/2621
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2863>
So we can remove the additional `next_fb` and `current_fb` pointers from
`MetaOnscreenNativeSecondaryGpuState`.
Some non-scanout buffers also need to be held in the case of GL blitting
which completes in the background. Those are referenced from the scanout
buffers themselves to ensure the source buffers live just as long.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2087>
As with GAMMA_LUT, track whether privacy screen state has been pushed to
KMS in the onscreen. This leaves MetaOutput and MetaCrtc to be about
configuration, and not application.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2814>
As with CRTC GAMMA_LUT, we're moving towards making the entity managing
KMS updates aware if there are any changes to be made, and whether KMS
updates are actually needed or not, and for privacy screen changes, this
means we need to communicate whether the privacy screen state is valid
or not. This allows the caller to create any needed MetaKmsUpdate.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2814>
We're moving towards making the entity managing KMS updates aware if
there are any changes to be made, and whether KMS updates are actually
needed or not, and for GAMMA_LUT changes, this means we need to
communicate whether the GAMMA_LUT state is valid or not. This allows the
caller to create any needed MetaKmsUpdate.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2814>
We rather confusingly still call a secondary display card that is
GPU-less (DisplayLink or other basic KMS device) a "secondary GPU",
so just because secondary_gpu_state is non-NULL doesn't mean we
can use it for rendering. The clearest indication of this is when
there is no EGL surface.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2341>
At first glance the `goto` looks like a loop, or potentially an infinite
loop. It's not a loop because the mode has changed at that point to
`META_SHARED_FRAMEBUFFER_COPY_MODE_PRIMARY`. But we can make it more
obvious and avoid the need for a goto.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2240>
There was a sanity check that complained if there was still a "next
framebuffer" when disposing an onscreen. This is correct to complain
about under normal operation, as we always wait until receiving the page
flip callback before cleaning up the onscreen and their state.
However, when there are many hotplugs occurring, we might end up with
race conditions when the above sanity check is not valid: when we have
more than one monitor active, paint 1 one of them, but receive a hotplug
event before we paint the other(s), we will discard the already painted
onscreen before really issuing a page flip.
In this situation, we will have the "next framebuffer", but having that
is not a bug, it's a race condition, thus to not leak in this situation,
make sure to clean up the next framebuffer here too.
Closes: https://gitlab.gnome.org/GNOME/mutter/-/issues/2081
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2225>
This significantly increases the chance of a fullscreen surface buffer
being scanned out instead of being painted via composition. This is
assuming the client supports the DMA buffer feedback Wayland protocol.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2146>
An incorrect assumption that after mode set there would be no pending
page flips was made. This meant that if there was a mode set, followed
by a page flip, if that page flip was for a CRTC on a now unused GPU,
we'd crash due to the renderer GPU data having already been freed. This
commit avoids that by keeping it alive as long as the page flips are
still in the air. It fixes crashes with backtraces such as
0) meta_render_device_get_egl_display (render_device=0x0)
at ../src/backends/native/meta-render-device.c:320
1) secondary_gpu_state_free (secondary_gpu_state=0x1c8cc30)
at ../src/backends/native/meta-onscreen-native.c:560
2) meta_onscreen_native_dispose (object=0x1cb65e0)
at ../src/backends/native/meta-onscreen-native.c:2168
3) g_object_unref (_object=<optimized out>)
at ../gobject/gobject.c:3540
4) g_object_unref (_object=0x1cb65e0)
at ../gobject/gobject.c:3470
5) clutter_stage_view_finalize (object=0x1cbb450)
at ../clutter/clutter/clutter-stage-view.c:1412
6) g_object_unref (_object=<optimized out>)
at ../gobject/gobject.c:3578
7) g_object_unref (_object=0x1cbb450)
at ../gobject/gobject.c:3470
8) meta_kms_page_flip_closure_free (closure=0x1d47e60)
at ../src/backends/native/meta-kms-page-flip.c:76
9) g_list_foreach (list=<optimized out>, func=0x7fb3ada67111 <meta_kms_page_flip_closure_free>, user_data=0x0)
at ../glib/glist.c:1090
10) g_list_free_full (list=0x1cb4d20 = {...}, free_func=<optimized out>)
at ../glib/glist.c:244
11) meta_kms_page_flip_data_unref (page_flip_data=0x1c65510)
at ../src/backends/native/meta-kms-page-flip.c:109
12) meta_kms_callback_data_free (callback_data=0x227ebf0)
at ../src/backends/native/meta-kms.c:372
13) flush_callbacks (kms=0x18e2630)
at ../src/backends/native/meta-kms.c:391
14) callback_idle (user_data=0x18e2630)
at ../src/backends/native/meta-kms.c
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2147>
It was dropping to zero after the first frame because it hadn't been
incremented high enough. So the second frame would crash with:
```
#0 g_type_check_instance_cast
#1 META_DRM_BUFFER
#2 copy_shared_framebuffer_cpu
```
That's the CPU-copy path (fallback-fallback) that probably no one is using
but it does work after this fix. Exactly the same issue as was fixed
in `copy_shared_framebuffer_primary_gpu` by 36352f44f9547ea1.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2104>
Systems with AMD GPUs do not take advantage of Mutter's zero-copy path
when driving DisplayLink screens. This is due to a very slow CPU access
to the zero-copy texture. Instead they fall back on primary GPU doing a
copy of the texture for fast CPU access. This commit accelerates texture
copy by working through damage regions only.
Tests on a 4K screen with windowed applications show significant
reduction of GPU utilisation.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/2033>
This replaces functionality that MetaRenderDevice and friends has
learned, e.g. buffer allocation, EGLDisplay creation, with the usage of
those helper objects. The main objective is to shrink
meta-renderer-native.c and by extension meta-onscreen-native.c, moving
its functionality into more isolated objects.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1854>