It might not be there when shutting down, so get it from a more managed
place. Note that this isn't strictly needed right now, but eventually,
the MetaWaylandCompositor pointer will be cleared using a g_clear*()
helper, which clears the pointer before freeing the instance, which
wouldn't work here.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1863>
This will allow us less awkward startup, where previously we had to
pre-initialize Wayland very early so Cogl could bind the Wayland display
when it initialized. Move things around so we bind the Wayland EGL
display when initializing the rest of Wayland infrastructure.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1863>
The callback on_displayfd_ready() would unconditionally set the return
value to TRUE, regardless of the condition.
Use the GIO condition to determine if there was data written and adjust
the return value accordingly.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1851>
We initialize, but might not start, e.g. when a test case just needs a
backend and doesn't start mutter. When cleaning up, we'll still try to
clean up Xwayland integration, and this commit handles cleaning up
without having made the mess.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1856>
We make objects inert when disabling the seat, but we requests may still
have effect. This is especially bad if disabling is followed by
destroying, but also means e.g. set_cursor() not doing an early out
after the pointer capability was disabled.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1822>
MetaDisplay does a lot of things, and is a central part to anything
window management. To let Wayland units have an easier time tearing
down, make it so that the Wayland infrastructure is terminated before
MetaDisplay.
This also makes sure that X11 support is turned off, so that we don't
stumble upon Xwayland terminating due to the Wayland socket connection
being broken. Will mitigate that in a better way in a later commit.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1822>
We might not be the only entity holding on to the X11 GdkDisplay,
meaning the X11 connection will stay alive indefinitely, e.g. if the gjs
context has some reference to it.
Avoid running into issues due to X11 connection errors by setting the
libX11 handlers to no-ops, so when we are terminating; that means the
GDK X11 connection can stay "alive" until its too late, and we'll just
silently ignore any connection errors that may happen due to the
lingering GDK display reference.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1822>
Compositor behaviour when calling `wl_data_device_manager_get_data_device`
for the same seat multiple times is not very clearly defined in
the spec and both Mutter and Weston currently don't handle
the DnD case properly.
While Weston handles DnD only for the last created data device,
Mutter, because of some internal reshuffling, ends up toggling
between two devices.
Properly handling this case requires some bigger changes. So
in order to behave predictable and in line with Weston,
only take the last created data device into account while
still keeping the previous created ones around.
The main affect client here is Firefox, which gets very
confused by the toggling behaviour and becomes more stable
with this patch.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1841>
If a subsurface first gets reordered and afterwards detached from
the parent before the parent surface got commited, we currently
would end up reattaching the subsurface to its previous parent.
While clients should avoid this behaviour, it's legit according
to the spec.
We already prevent similar cases where the subsurface is destroyed -
extend that check to detaching, which includes the destroy case.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1831>
Use the new API to make sure the shaped texture has a valid size
during the next layout phase.
This is needed here because, quoting the previous commit:
When the texture size is invalidated using `invalidate_size()`, the new
size will only get calculated the next time `update_size()` is
called. This happens e.g. in `meta_shaped_texture_get_preferred_size()`
via `ensure_size_valid()`.
`update_size()` can chain up to `clutter_content_invalidate_size()`
as well as emitting a `size-changed` signal. If this happens during
layout, the result is a 'change the layout conditions during layout'
issue, causing heavy breakage in e.g. the Shell overview.
To fix this, expose `ensure_size_valid()` as API so callers can make
sure the texture has a valid size without creating redundant size
invalidations calls.
Note that if a buffer with a new size is attached we already trigger
`update_size()` explicitely, avoiding such situations.
Closes https://gitlab.gnome.org/GNOME/mutter/-/issues/1718
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1799>
If a client is naive enough to assume that it can set the selection while
it has got no surfaces, mutter will simply ignore the request and leave
the selection unchanged.
This is good and the expected behavior, however the poor client that did
this will enter in an inconsistent state where it "claimed" the selection,
but nobody told it that the wl_data_source is not current.
So, when the client is focused the next time, it will receive wl_data_offers
as usual, but it will still think all the time that it is owning the
selection. In the case of GTK, that takes client-side shortcuts, so any
attempted paste will still bring back the client-side aborted selection.
To fix this, cancel the selection right away if it happened while unfocused,
the client will be able to undo its own failed selection, and not assume
that future offers are its own.
Fixes: https://gitlab.gnome.org/GNOME/mutter/-/issues/1469
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1772>
It seems to be the preferred format of the Mesa V3D driver on
Raspberry Pi 4. If the compositor doesn't advertise it then Mesa will
fallback from `zwp_linux_dmabuf_v1` to `wl_drm`, incorrectly. Meaning
it will keep using a buffer with modifiers on an interface that does
not have modifiers.
Add support for `DRM_FORMAT_ABGR2101010`. It works, and prevents Mesa
from taking its broken fallback path.
Fixes: https://gitlab.gnome.org/GNOME/mutter/-/issues/1520
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1798>
For Xwayland, mutter creates the sockets in the standard /tmp/.X11-unix
directory.
Yet, if that directory already exists, it may have been created by
another user with full control over the created socket.
To avoid that issue, if the directory /tmp/.X11-unix already exists,
check that the permissions are as we expect, i.e. the directory belongs
to either root or the user herself, is writable and has the sticky bit.
Thanks to fabian@ritter-vogt.de for reporting that issue.
https://gitlab.gnome.org/GNOME/mutter/-/issues/1708
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1787>
Unlike other subsurface state, placement operations need to get
applied in order. As per spec:
```
Requests are handled in order and applied immediately to a pending
state. The final pending state is copied to the active state the
next time the state of the parent surface is applied.
```
Having placement operations being part of the subsurface state
makes it difficult to support arbitrary orderings. Make them
part of the parents surface pending state instead.
Closes https://gitlab.gnome.org/GNOME/mutter/-/issues/1691
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1768>
When deciding if `configure` event should be sent,
`meta_window_wayland_move_resize_internal` compares requested window size
with `window->rect` size. However, `window->rect` is only updated when `commit`
is received. So the following sequence produces incorrect result:
1. a window initially has size `size1`
2. `move_resize_internal` is called with `size2`. `configure` is sent
3. `move_resize_internal` is called with `size1` to restore original size,
but `commit` for `size2` haven't arrived yet. So `window->rect` still has size
`size1`, and thus new `configure` is not sent
4. `commit` for `size2` arrives, window changes size to `size2`
Expected window size in the end: `size1`
Actual: `size2`
To fix the issue, take size from pending `configure` events into account.
Fixes https://gitlab.gnome.org/GNOME/mutter/-/issues/1627
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1755>
This commit assumes that cursor surfaces work in a "mailbox" fashion. If
they are painted multiple times before a successful flip, all commits
but the last get discarded, and the last commit gets presented after the
flip succeeds. This is more or less how it works in the atomic backend,
and also more or less how it works in other backends, with the exception
that the cursor painting might fail without any way of knowing. This
assumption is still better than unconditionally discarding all cursor
surface feedbacks as if the cursor painting always fails.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1484>
Regarding the sequence = 0 fallback: in some cases (moving a cursor
plane on atomic amdgpu) we get sequence = 0 in the page flip callback.
This seems like an amdgpu bug, so work around it by assuming a sequence
delta of 1 (it is equal to 1 because of the sequence != 0 check above).
Sequence can also legitimately be 0 if we're lucky during the 32-bit
overflow, in which case assuming a delta of 1 will give more or less
reasonable values on this and next presentation, after which it'll be
back to normal.
Sequence is also 0 on mode set fallback and when running nested, in
which case assuming a delta of 1 every frame is the best we can do.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1484>
The presentation-time protocol allows surfaces to get accurate
timestamps of when their contents were shown on screen.
This commit implements a stub version of the protocol which correctly
discards all presentation feedback objects (as if the surface contents
are never shown on screen). Subsequent commits will implement sending
the presented events to surfaces shown on screen.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1484>
If `meta_xwayland_start_xserver()` returned via an error path, some of
the socket FDs were leaked.
Fix that, and add `steal_fd()` calls to make it clearer that FDs passed
to `g_subprocess_launcher_take_fd()` are transferred to it. There were
no bugs with how `GSubprocessLauncher` was being used.
Spotted while working on
https://gitlab.gnome.org/GNOME/glib/-/issues/2332.
Signed-off-by: Philip Withnall <pwithnall@endlessos.org>
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1738>
X11 clients can use different models of input handling, of which some
may not result focus being set synchronously.
For such clients, meta_focus_window() will not change the focus itself
but rely on the client itself to set the input focus on the desired
window.
Add a new MetaWindow API to check when dealing with such a window.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1716>
In the case that DnD is performed and succeeds, we want to release
the grab early, and let the transfer IPC happen in the back. For
that to happen without a hitch, drag source and offer must be left
related to each other after undoing the grab, even though the default
ungrabbing code does that automatically (indirectly, by unsetting the
drag focus).
In these cases, we used to manually unset the current source, so
this decoupling was skipped. Notably, one missed case is X11 DnD,
so we might end up with the situation there that DnD did succeed,
transfer is ongoing, but the source and offer are already decoupled,
this confused the machinery and missed the finishing XdndFinished
to be emitted to the X11 drag source.
The prior commits prepared for this source/offer decoupling being
a manual operation, this commit avoids doing this automatically
when ungrabbing.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1720>
This object is just being detached, with no code unref'ing it. Do
this whenever the XDnD selection goes unowned, usually a good
indication that the drag source no longer is one.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1720>
When (un)maximizing, (un)fullscreening, the move/resize action is
flagged with 'ACTION_MOVE' and 'ACTION_RESIZE' , while e.g.
'appears-focus' does not.
When a client misbehaved and didn't immediately reply to a configure
request with a commit with the corresponding ack_configure, the
following commit would trigger a oddly timed move, making the window
appear to move back to a previous position.
Avoid this issue by only carrying over the target window position if the
configuration actually contained a new position.
We cannot only rely on the flags however, as e.g. a new position should
be respected during interactive resize, even though only 'ACTION_RESIZE'
is passed in such scenarios.
Do the same for the size, except if the window state dictates that the
size is fixed to a certain size, e.g. being fullscreen or maximized.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1445>
Previously the wl_resource and MetaWaylandGtkSurface corresponding to
any client gtk_surface have been kept around until the exit of the
client due to the client side destroy method not signaling the
destruction to the server. Ideally the protocol would have specified a
destroy request marked as destructor to handle this automatically,
however this is no longer possible due to the destroy method being
implicitly generated in the absence of an explicit request in the
protocol. Adding a destroy request marked as destructor now would
generate a new destroy method that unconditionally would send the
request to the server, which would break clients running on servers not
supporting that request.
So instead of modifying the destroy request add a new "release"
destructor, that indicates to the server that it can release the
resource. This can be optionally be used by clients depending on the
server protocol version.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1307>
The MetaWaylandSurface corresponding to a MetaWaylandGtkSurface can be
destroyed before the MetaWaylandGtkSurface is destroyed. In its destroy
function MetaWaylandSurface however was unsetting the destructor of the
correspnding resource along with the gtk_surface1 interface
implementation. This was done to prevent further gtk_surface1 requests
on a NULLed MetaWaylandSurface, if it has been destroyed before the
MetaWaylandGtkSurface.
It would be enough to just unset the resource implementation, while
keeping the destructor to fix this leak. However the following commit
will rely on the implementation being available after the
MetaWaylandSurface has been destroyed. So instead introduce NULL checks
for all functions that can be called on the gtk_surface1 interface and
do not unset the implementation.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1307>
One for the public channel, and one for the private maintainance
channel. Use the public one for test clients, otherwise tests become
flaky, and the private one for MetaX11Display.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1681>
This commit consolidates DRM buffer management to the MetaDrmBuffer
types, where the base type handles the common functionality (such as
managing the framebuffer id using drmModeAdd*/RMFb()), and the sub types
their corresponding type specific behavior.
This means that drmModeAdd*/RmFB() handling is moved from meta-gpu-kms.c
to meta-drm-buffer.c; dumb buffer allocation/management from
meta-renderer-native.c.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1488>
Current Xwayland has marked the command line option "-listen" as
deprecated in favor of "-listenfd".
Use the pkg-config variable "have_listenfd" (if available) from Xwayland
to determine if we should use that option, to avoid a deprecation
warning when spawning Xwayland.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1682>
Mutter listens to two display connections, one for regular X11 clients
and another one for the so called "managed services".
Once an available display number is found for the regular X11 clients,
mutter would then redo the work to find another available display number
for the managed services.
Yet, it does so starting from the same initial display, which is a waste
of time since it just tried all displays to find the first available
one, so all these, including the regular display it just took, are now
in use.
So instead of starting over from the beginning when looking for a
display available for the managed services, continue from the next
display immediately after the one we found precedently.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1680>
Some X11 servers may not always create a lock file, yet mutter uses the
lock file to find a possible display number and then tries to bind to
the socket corresponding to that display number.
If it fails to bind, it will simply bail out. As a result, if an X11
server is already listening on that display but hadn't created a lock
file, mutter won't be able to start Xwayland.
To avoid that possible issue, make mutter retry with another display
for a given number of tries when binding fails even though the display
was supposed to be available based on the lock file presence.
Closes: https://gitlab.gnome.org/GNOME/mutter/-/issues/1604
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1669>
The function choose_xdisplay() calls open_display_sockets() which calls
ensure_x11_unix_dir().
We don't need to do that from within the loop though, as the directory
/tmp/.X11-unix is the same regardless of the display number.
Move the call to ensure_x11_unix_dir() from open_display_sockets() to
choose_xdisplay() prior to enter the display loop.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1669>
In case of failure to open the display sockets, we would not propagatre
the error which can cause a crash when trying to show the error message.
Properly propagate the error to avoid the crash.
Part-of: <https://gitlab.gnome.org/GNOME/mutter/-/merge_requests/1669>