[WIP] Implement a Wayland DisplayServer

Resolves godotengine/godot-proposals#990.
Depends on #68944.
(This post will be updated over time to reflect the current status of the project. I hope it won't feel weird whenever that happens.)
Wayland specific issues:

Tablet support only works with very basic setups, failing to properly handle multiple tools.

DRI_PRIME detection is not yet implemented (gotta find a way to test it)

There have been multiple reports of corrupted graphics with this backend and the Vulkan driver. The cause of this is yet unknown, but seems to happen only in iGPU + dGPU scenarios. This issue has been confirmed with other Wayland + Vulkan programs, hinting at a more generic issue, perhaps with mesa. Update: It looks like this issue might be fixed in a later mesa update. Currently waiting for further confirmation.

All processing stops once the window is hidden. Currently there's no way of preventing this state. See: https://gitlab.freedesktop.org/wayland/wayland-protocols/-/merge_requests/199 and https://gitlab.freedesktop.org/wayland/wayland-protocols/-/issues/38

On Sway, resizing the window through window_set_size acts weirdly, as if it were set only temporarily. This might be a compositor bug (could also be improper use of the API, don't remember if I tested).

On Sway, DnD doesn't update the cursor properly. This may be a compositor bug.

Miscellaneous notes:

Scrolling on a touchpad is a little bit too fast. This is a generic issue (see #49873), but gesture support, already implemented through the pointer gestures protocol, alleviates it.

The splash doesn't resize. This means that tiling WMs will have a wrongly sized window until the end of loading. There's no clean way of improving this and, while hacks are definitely possible, I'm not sure that it's currently worth it.

The aim of this PR is to eventually implement a fully working DisplayServer compatible with the Wayland protocol on Godot 4.x, which had architectural changes that led to the closing of #27463.
This backend is available only in single-window mode due to incompatibilities with Wayland's and Godot's windowing API.
It is currently beta quality. It's definitely usable, albeit with some features missing, such as HiDPI, which will be implemented in a separate PR. The main focus of this phase is testing, fixing bugs, matching the behaviour to the documentation or the X11 implementation and implementing the few stubs left.
Virtual keyboard support is possible and planned.
Animated cursors could be implemented (perhaps even easily) but they're extremely low priority.
Someone proposed xdg-desktop-portal, but that is out of scope regarding this implementation and should be implemented separately.
I've added some simple SCons builders that generate protocol wrappers through wayland-scanner.
Wayland and X11 are both enabled by default in the build system and the first that works will be selected at runtime, although expect errors in the log for now as they have to literally fail to fallback to either one.
The client library gets loaded through some dlopen wrappers and all Wayland stuff (except currently libdecor) is embedded into thirdparty/linux_headers/wayland, allowing dependency-free building (but not running).
Note that wayland-scanner is still required for now at build time. I guess we could do some build-and-run trickery, dunno.
Some methods aren't implemented yet (left as stubs). Namely:

window_set_mouse_passthrough (Wayland doesn't support polygonal regions, only rect regions.)
window_set_ime_active (requires implementing text-input-unstable-v3; it can and will be done)
window_set_ime_position (same as above)
screen_get_usable_rect (could be implemented through configure_bounds, but it'd come from the window's perspective, as there's no way to ask the free area for a particular screen.)

Thanks to:

@ddevault and @toger5, from which I initially took the key mapping code.
@dos1 for helping me with many, long, headache inducing things.
@smohantty for some very small build fixes.
@vmedea for a bunch of very useful fixes.

I'm always open to external contributions (especially as I've never worked on anything like this before) be it patches, testing, reviews, general technical help or even just moral support, they're all very appreciated!

@Riteo ,
I am working on adding a wayland backend to linuxbsd platform for platyform. Good that you already have a working prototype with vulkan . Would love to contribute to avoid duplication of effort.

@smohantty if you want to contribute for now I guess that you could wait for the new, asynchronous prototype (I'm working on it right now, I'm free pretty much only on late fridays and the weekend, sorry about that) and maybe review it then? Or I guess you could also share any findings you had or say what you think of the proposed new architecture in the PR.

OK, I moved everything into another thread, but it looks like call_deferred, used for window callbacks, can't be always used. For example when running a scene it prints ERROR: Do not use progress dialog (task) while flushing the message queue or using call_deferred()!. At least now it doesn't crash anymore when you move the pointer too much though.

Update on that: the issue is not only caused by window rect changes but also by inputs in general, as the input dispatching function uses call_deferred and it's called by the event thread too. I might have to add some sort of event queue in the main thread and dispatch it there if I don't find a better solution.

Following the recent issue with call_deferred and ProgressDialog, I've decided that I'll try implementing an actual event queue, maybe even just wrapping wayland events for handling in the main thread. I previously discarded this idea since I was sure that everything could've been done off-thread and didn't like the idea of adding yet another event queue when we already got Input and MessageQueue, but I've got to pick it back up due to these assumptions being wrong.

@smohantty if you want to contribute for now I guess that you could wait for the new, asynchronous prototype (I'm working on it right now, I'm free pretty much only on late fridays and the weekend, sorry about that) and maybe review it then? Or I guess you could also share any findings you had or say what you think of the proposed new architecture in the PR.

Currently, I am looking at kWayland(https://github.com/KDE/kwayland) and qtWayland(https://github.com/qt/qtwayland) for reference as they have implemented all the features ( multi-window , server and client-side decoration async event etc)  will be helpful in designing wayland integration in godot.

@smohantty are you sure we can reference them? They look to be mostly GPL code, a license incompatible with Godot's MIT license. Also, I'm not sure if QT's architecture might be comparable with Godot's. As you can see, there are quite a few shortcomings and limitation to take in considerations that are quite unique.

@smohantty are you sure we can reference them? They look to be mostly GPL code, a license incompatible with Godot's MIT license. Also, I'm not sure if QT's architecture might be comparable with Godot's. As you can see, there are quite a few shortcomings and limitation to take in considerations that are quite unique.

The reference is just to understand the full feature set we have to provide not to copy the implementation.
The most of the wayland integration i have went through provides a logical window concept as well as some kind of parent-child window relationship to support multiple windows. If we can code a wayland client in isolation which provides interface that play nicely with the DisplayServer interface then it will be good as it will not bloat the wayland Displayserver class. The Server will use the logical window concept and adds hook for the events .
one more wayland integration for reference (https://github.com/Enlightenment/efl/tree/master/src/lib/ecore_wl2)
So am just going through all different implementations to come up with all the building blocks required to provide all the features we need and at the same time easy to maintain as well as extend in the future.
My rough idea is to develop the Wayland support as a separate module/library which can be consumed by the DisplayServer.
Would love to hear your thoughts about it.

@smohantty mhh, what you're proposing is actually kind of done in other parts of the engine, look in the drivers folder of the source code for some examples. I thought of doing something similar but in the end doing what you're proposing would risk making all methods of DisplayServerWayland just one or two calls to this hypothetical class, which for something as specialized as a Wayland display server would just add needless complexity. X11DisplayServer, for example, does all X11 stuff inside of it, without a specialized driver.
At most, in my opinion, we could do just a WaylandEventQueue class, or something like that, that implements all wrapped events (which after some thinking seems like the safest thing to do at this point IMO) and gives a convenient interface for consuming Wayland events only, but that could be split at the end if considered too bulky.
For now, I'd make everything in the DisplayServerWayland, see if it works in the first place, because as you can see, things that could've sounded good enough weren't due to unexpected constraints in Godot's architecture, and then clean-up/optimize/split/whatever, because we might spend a lot of time polishing something, plugging it into WaylandDisplayServer and see it fail gloriously as it did with me twice.
Maybe it could be me that I'm always too afraid of over-engineering things, but I think that at this point this is the best route to take IMO.

Ok, new update: I've implemented a very basic message queue and it looks like it works. The commit message should contain some info on roughly what I did, still in the usual brain dump format used by this update too.
As usual, after some other thinking, I changed the way things will go, understanding that if I were to wrap all Wayland events I would've reimplemented wl_display_dispatch, which is not very useful. :p
That's why I'll be just implementing the basic messages that the editor needs to know about in the main thread, which is pretty much stuff with callbacks (window changes, input events, etc), so that on the Wayland layer we can do everything that has to be immediate as soon as possible (especially to avoid filling up the oh-so-precious and limited Wayland event buffer), leaving the main thread all the time it needs to do whatever it pleases, and to let all of the scene tree and whatever know that these things happened, while the List used for the queue keeps growing without any issue (just like X does, AFAIK).
Right now the only message implemented and working is the window rect change message, which makes the DisplayServer rescale the buffer on window resize.
I've still not tested this queue extensively, I've pretty much just rescaled the window a bunch of times and called it a day, as input dispatching is currently temporarily #if 0'ed out. I'll probably implement it tomorrow (read: later in the day, I'm well past 0:00 AM), "it shouldn't take long(tm)", but as usual it's very, very, late and I'm pretty tired.
Synchronization is still pretty sketchy, but we've still got time to polish it and make absolutely sure that there won't be race conditions or stalls, also looking where to use the right mutexes at the right place, instead of one monolithic WaylandState mutex, which, very superficially, I don't think would be the right solution.
Closing up, I feel like I've finally gone out of the loop of thinking a lot about how to do something "the right way", implementing it and seeing it fail gloriously, which was pretty frustrating and took a lot of time. Instead, I found that concentrating first on making it work and eventually polishing seems to work pretty nicely for now, especially for my mental health. So there's the possibility that I might make certain choices in the moment without thinking about it too much just to make something work, and only then then try to improve/clean/refactor it.

I've implemented scroll and modifier support. There's just this weird issue where non physical shortcuts get registered as lowercase. It may be something very stupid that I did, but for now I'll go to sleep.
Although the running game window is kinda broken (on sway its buffer is offset for some reason), we're slowly getting closer to actually getting something that can be tried by more people!

I've just added double click and keyboard support, so technically the editor should be just enough usable to do something. There's still a lot missing, but we're slowly getting there.

I'm adding window event support too, but if on sway the window gets tabbed out, its focus out event isn't handled until it is shown again. Probably process_events doesn't get called and the message queue isn't read.

For some reason context_vulkan->window_resize() breaks everything when the renderer is set in multithreaded mode. I can see that the X11 display server did nothing in particular regarding renderer synchronization, but I have to do RenderingServerDefault::get_singleton()->sync() before resizing the window to avoid a race condition.

After attempting to implement other things, I think that the prototype (read: "messy code") stage is currently over. Everything else that has to be implemented depends either on some external library or is complex enough to deserve some more well structured code.
So for now, while trying to add more complex features, I'll try to refactor/cleanup/fix some things and slowly refine the whole implementation. I might also take more into consideration the older codebases, since I've built an idea of how Wayland works and stuff like clipboard support and advanced pointer features should be the same.
The only big problem left is, IMO, multiple window support. The difference between popups and toplevels in XDG shell imposes some weird restrictions that will be interesting to fix.

Welp, I tried making the CI work with this PR for fun by adding the relevant dependencies, but it somehow messes up. I guess that the code generated on my machine uses functions not available on the older wayland-client library that Ubuntu provides.

@roberti42 I should've explained it before, sorry.
Wayland protocols are defined in an XML file. The actual API is generated using wayland-scanner, a program made just for that. It looks like it's pretty common to run it during the build process, and is a practice also done in the older implementations too. I always wondered why it was so common and I never looked into it, but I think this is the reason, as those C files are generated by it.

@Riteo ok now I see, thank you for the explanation. Then you need to ensure that generate-api.sh will use wayland-scanner version 1.19.0, I suppose.
This is how I've done it my system. Because I have version 1.19.0 in /usr/bin and 1.20.0 in /usr/local/bin, I put /usr/bin before everything else in PATH:
cd thirdparty/wayland-protocols/xdg-shell
export PATH=/usr/bin:${PATH}
generate-api.sh

And now it compiles and runs (both tools and editor), although the fonts are pixelated.

@roberti42 I don't get what you mean by pixelated. Is it a DPI thing?

@Riteo yes. I have a 4k monitor, but when I start Godot with --display-driver wayland it seems like it is running at 96 DPI.

@roberti42 makes sense, I haven't implemented HiDPI support yet as I don't have a HiDPI monitor. If you wish I can do it and let you test the implementation.

@Riteo count me in

Quick warning for anyone wanting to try this PR right now: currently the program crashes with more than one screen. The reason for the crash is an accidental preservation of the assumption that the screen list's elements have a constant address after I ported the code from using a List to a LocalVector for the screen list. I'll probably push a fix tomorrow. In the meanwhile, disconnect any extra screen if you really want to try it right now.
Also, on a different note, I'm sure I can improve a lot the window screen detection algorithm, which left me really unsatisfied. To not base myself on assumptions I'm working on a way of  working with a 2x2 grid of virtual displays. I know that the current implementation of the algorithm's kinda floppy, I'm sorry.

Update on output scale support: Wayland seems to implement it by basically dividing the logical screen size by the scale factor (eg. 1920x1080 screen, 960x540 logical size), thus making windows smaller, and allowing to attach bigger buffers achieving some sort of supersampling. I think that to implement this correctly it would be more elegant to implement it in the core, perhaps reading the new screen_get_scale, otherwise I might need to do some nasty conversions eg. for pointer positions, as a window's size currently depends on the buffer. Thus, I'm postponing output scaling support in order to work on other things, only later looking for a good way of handling it.

What are you planning to do concerning window decorations? will there be a native window header? Or are you going to rely on the xdg-decoration protocol?

@toger5 I haven't investigated that aspect at all tbh.

Regarding CSD and SSD - I recommend supporting the xdg-decoration spec, which allows compositors that support server side decorations to have them, while compositors that don't (notably Mutter/GNOME) get client side decorations. This seems to be the way to go, considering the community is almost split down the middle. The xdg-decoration spec mandates CSD anyway, as long as the compositor does not support SSD.
Thank you for all your work by the way, it is highly appreciated! I would love to help with this effort. I have two monitors, one 4K and one 1440p. Although I am a seasoned developer, I suspect I'm a bit too green on the technicalities of the engine to be of much help in that regard.

@Lampomaniac I'll probably do that then, thanks for the tip!
@smohantty just to be sure, will you ever make a PR for that cursor commit or are you gonna keep it for yourself? That can absolutely be the case, mind you, I just want avoid doing the same stuff that someone else is doing. Since it's been a while I'm gonna merge the latest changes and then work on something, if that messes up your work, please let me know.

Oh, sorry for the double post, I forgot to answer to the second part of your message @Lampomaniac: if you don't want to help with the implementation (which is totally understandable), even just testing is appreciated! Just one thing, by "seasoned developer", do you mean that you're experienced with the Wayland protocol? If yes (if you want), would you tell me if you know whether it's possible, at least with a separate protocol I missed, to detect which screen a window covers the most?

I added partial mouse mode support in the form of pointer confinement and capturing, although the latter is pretty useless without relative pointer support, which I'll add next. For some reason, floating pointer confinement is broken on sway, and I think that it might be related to the issue I linked in 90dd228d6361e65db96331b752c2375ab0fd9c87's description, although I'm not 100% sure. Do other window managers (especially floating ones) have this issue too?

would you tell me if you know whether it's possible, at least with a separate protocol I missed, to detect which screen a window covers the most?

There's no spec that does that for you, to my knowledge anyway. It is doable using some math of and the xdg-output spec, although I am unsure of how well supported this spec is. The reason (I believe) you have to use this spec instead of wl_output is that it gives you logical sizes and positions.

@Lampomaniac are you sure that logical sizes are enough for understanding which screen is covered the most by a particular window? The only events we've got at our disposal are output enter/leave events, so unless there's a window covering a grid of screens (thus, surely covering fully at least one screen), I don't think its possible to gain useful information from them alone.

@smohantty a while ago I've asked you whether you were going to add cursor support yourself, since I noticed that you committed something concerning such feature in your fork. You've not answered since then, and I've got to a point where the next logical step is implementing it. Sorry if I do something you were willing to do.

As anticipated, I've implemented cursor theme and hiding support. This is a really big step forward, making not only the editor but a lot of games more usable too! I actually wanted to push this commit this morning after a quick post-sleep review, but I'm feeling quite happy with how it has come, so I'm taking the risk!
Although I've tried to keep my implementation reasonably compatible with DisplayServerX11's (heavily adapting some code too), I'm sure that somebody will find issues with their theme. For me, for example, there are two cursors missing even though I use Adwaita and the code uses DisplayServerX11's names and fallbacks. As we're getting more and more feature complete, testing is more and more encouraged!
Also, although I'm trying to not get the usual vicious cycle of refactoring, I'm aware of there being some (relatively) major issues here and there in the general structure of the program, such as dumping everything in platforms/linuxbsd without making separate subfolders for both the two DisplayServers, having some very sketchy threading and having either very long variable names or very short ones. The latter issue is also exacerbated by the leftovers of the old design, where there are long chains of structures which were meant to be passed to each Wayland event listener in order to have them work on their own isolated state, approach which resulted too limiting. I'm still finding the time and the right moment to clean up everything.

Hi Riteo,
Thank you very much for the time already spent, I (and I'm sure others) am (are) following you work with great interest 👍.
As you say you'd be interested for some people to test your current implementation, could you sketch a bit what your are willing to see in action? I mean, what to test, what is the most important and what did you struggle to implement?
A kind of check-list would be optimal, and/or a list of steps on how to test the relevant parts. If you can't describe what you want, maybe you can record your screen "clicking & dragging windows" so that I and others can reproduce the exact same test bench? As we have different setups this could be the best way to make sure no corner case is left out and outline some known bug.
Reproducible testcases would, in my opinion, be the best way to measure progress.
Oh, and I almost forget, what kind of debug information would be of interest when observing a crash 😉.

Hi @dvergeylen, I've thought about it for a while and I think that for now I think that a more "random" testing might be better, since I'm not actually entirely sure on what to test, and a video wouldn't allow for random enough tests.
There are just a few things to take into consideration, namely the only known issue of some leaked references on exit and the list of unimplemented features I wrote into the OP: multiple windows, custom cursors, clipboard handling, HiDPI, keep screen on, DnD, touch input and client side decorations. If there's something I left out in this list, please let me know.
Tip: since multiple windows support is broken, and navigating to the editor settings is kinda difficult, one might want to enable it by adding this to their editor settings file (usually located at ~/.config/godot/editor_settings-4.tres) under [resource]:
interface/editor/single_window_mode = true

Oh right, @dvergeylen, btw, regarding what debug information to send in case of a crash, all I usually need are reproduction steps and a backtrace of a debug build, usually dumped when the engine crashes.

@Lampomaniac are you sure that logical sizes and positions are enough to understand which screen is covered the most by a particular window? The only events we've got at our disposal are output enter/leave events, so unless there's a window covering a grid of screens (thus, surely covering fully at least one screen), I don't think its possible to gain useful information from them alone.

You might be right. You should be able to get an educated guess on which screen has the most coverage though, but I suspect another solution is preferrable. Many applications lazy out and always fullscreen on the first index display, if that is what you are trying to accomplish!
I am tempted to give client side decorations a go, by basically finding an MIT-licensed implementation and "pasting" it in. Foot for example (the terminal emulator that is) is a good candidate. I'll come back if I make some progress, but don't hold your breath!

@Lampomaniac don't worry, even just an attempt is highly appreciated! Anyways, what would be the external implmementation for? Wouldn't it enough to "just" add some buttons from our side, or is there more going on? Perhaps, based on my limited understanding, it could be better to add our own client decorations, as it would allow to potentially integrate it better with the engine, even just graphically. I'm gonna really throw a random guess, but I was thinking about putting the main viewport under a container with the status bar and buttons as regular Controls, but, again, I'm not sure.

@Riteo I think that might not be a good idea. It's important (in my opinion) to keep the CSD simple and recognizable. The plan isn't to literally copy someone else's CSDs, but rather use a proven, efficient and standards compliant implementation that we can then style as we please. The more I've though about it, the more important it is to support the xdg-decoration spec as well. I'll see if I can't do both at the same time.
As I've said, I have practically no knowledge of the engine internals so I also might be shooting entirely in the dark. Guess we'll find out! 😁

After some thinking I'm pretty sure that I should properly handle multiple seats and that whatever worked before (if it even works anymore) worked by pure chance.
For the (understandably) unititiated, Wayland handles multiple input devices in one session through the concept of seats, comprising of an optional pointer, keyboard and touchscreen each. These seats are used by compositors like sway to effectively implement collaborative multi pointer support (you read that right).
I'm not sure on what behaviour to give it though, but I think that, in high level terms, it should revolve around the concept of a current seat: when the editor detects an interaction from a pointer, keyboard or (eventually) touch screen that is not the current one, it cleans up the current state (for example it unconstrains the pointer if applicable), looks for the seat from which this new pointer/keyboard came from, makes it the new current seat and sets its state like the previous one (like pointer constraint status etc), so that for whatever reason one might switch from one seat to the other cleanly and easily.
What do you think?

I should've implemented popups and popup menus fully, with the exception of proper window manager side closing (eg. forced closing on unfocus) which causes a segfault or other stalls due to a sudden invalidation of the popup surface and some issues with the rendering device, among some more obscure bugs. Once they'll become usable enough I'll mark them as implemented in the OP.

I would've liked to update you before about what's going on but I was pretty busy (and by that I mean that I had very little contiguous free time at hand). But here we go, describing what's happened before, what is happening now what's going to happen in the future:
It all started with the popups. Apparently when closed they liked to fail in two different epic ways on sway and on Weston by crashing the client on the latter and by segfaulting the whole compositor on the former.
Fastforward to now and the issue is seemingly gone. I literally opened my laptop to do some Godot/Wayland stuff for the first time in like a month and popups close flawlessly both on sway and on Weston. I updated a bunch of software but not Weston nor Sway and I'm not sure what was the cause, perhaps mesa or even the kernel? I'll try look into it further but now I can complete this port I guess.
Now that I can finally continue working on this I'll cleanup some of the mess I made debugging this weird issue, see what's left to implement and perhaps really finishing this project on which I'm working on since the start of this year pretty much.
Thank you all for your patience.

I ran the editor in single-window mode because I'm dumb. The issue is still there.
I'll build the required mesa test and fix this mess.
Sorry again.

Please don't apologize, we are all super thankful for you to donate your time to work on this. Thank you for contributing.

New update: popups work very well on Weston, even better than sway... Except when they don't and stall any drawing to their buffer in the case of progress indicators, which for some reason work on sway.
Since beta is coming, I'm thinking of putting popups aside and polishing the rest of the single-window implementation (expecially with synchronization) in order to at least push some sort of wayland support for 4.0 which from my light testing on sway worked very well and was more than usable.
In that case the priorities would become: GLES3, code cleanup and accomodating wayland properly in the build system.
I already asked a bit on the developer chat and some people seemed favourable.
Any thoughts?

In that case the priorities would become: GLES3, code cleanup and accomodating wayland properly in the build system.
I already asked a bit on the developer chat and some people seemed favourable.
Any thoughts?

That sounds really good. It would be great to just have it in the code base. Other contributors then also have an easier time helping out with the popups if the main wayland code is on main.
I am really excited to see the first wayland pr beeing merged!

I just compiled your (@Riteo) branch. I am getting the following issue when running:
[UserName@fedora godot]$ ./bin/godot.linuxbsd.tools.64
Godot Engine v4.0.alpha.custom_build.d7893a031 - https://godotengine.org
wl_registry@2: error 0: invalid version for global wl_output (4): have 2, wanted 3
MESA-INTEL: warning: Performance support disabled, consider sysctl dev.i915.perf_stream_paranoid=0
Vulkan API 1.2.0 - Using Vulkan Device #0: Intel - Intel(R) Iris(R) Graphics 6100 (BDW GT3)
ERROR: Condition "err" is true. Returning: ERR_CANT_CREATE
   at: _initialize_queues (drivers/vulkan/vulkan_context.cpp:1267)
ERROR: Condition "err != OK" is true. Returning: ERR_CANT_CREATE
   at: _window_create (drivers/vulkan/vulkan_context.cpp:1377)
ERROR: Can't show a Vulkan window.
   at: show_window (platform/linuxbsd/display_server_wayland.cpp:1667)
ERROR: Condition "format == DATA_FORMAT_MAX" is true. Returning: INVALID_ID
   at: screen_get_framebuffer_format (drivers/vulkan/rendering_device_vulkan.cpp:6801)
ERROR: Mismatch fragment shader output mask (1) and framebuffer color output mask (0) when binding both in render pipeline.
   at: render_pipeline_create (drivers/vulkan/rendering_device_vulkan.cpp:6265)
ERROR: Condition "format == DATA_FORMAT_MAX" is true. Returning: INVALID_ID
   at: screen_get_framebuffer_format (drivers/vulkan/rendering_device_vulkan.cpp:6801)
ERROR: Mismatch fragment shader output mask (1) and framebuffer color output mask (0) when binding both in render pipeline.
   at: render_pipeline_create (drivers/vulkan/rendering_device_vulkan.cpp:6265)
ERROR: Condition "format == DATA_FORMAT_MAX" is true. Returning: INVALID_ID
   at: screen_get_framebuffer_format (drivers/vulkan/rendering_device_vulkan.cpp:6801)
ERROR: Mismatch fragment shader output mask (1) and framebuffer color output mask (0) when binding both in render pipeline.
   at: render_pipeline_create (drivers/vulkan/rendering_device_vulkan.cpp:6265)
ERROR: Condition "format == DATA_FORMAT_MAX" is true. Returning: INVALID_ID
   at: screen_get_framebuffer_format (drivers/vulkan/rendering_device_vulkan.cpp:6801)
ERROR: Mismatch fragment shader output mask (1) and framebuffer color output mask (0) when binding both in render pipeline.
   at: render_pipeline_create (drivers/vulkan/rendering_device_vulkan.cpp:6265)

ERROR: Condition "!windows.has(p_window)" is true. Returning: false
   at: window_is_valid_swapchain (drivers/vulkan/vulkan_context.cpp:1421)
ERROR: Condition "!dl" is true.
   at: draw_list_bind_render_pipeline (drivers/vulkan/rendering_device_vulkan.cpp:7330)
ERROR: Condition "!dl" is true.
   at: draw_list_bind_index_array (drivers/vulkan/rendering_device_vulkan.cpp:7477)
ERROR: Condition "!dl" is true.
   at: draw_list_bind_uniform_set (drivers/vulkan/rendering_device_vulkan.cpp:7404)
ERROR: Condition "!dl" is true.
   at: draw_list_set_push_constant (drivers/vulkan/rendering_device_vulkan.cpp:7511)
ERROR: Condition "!dl" is true.
   at: draw_list_draw (drivers/vulkan/rendering_device_vulkan.cpp:7529)
ERROR: Immediate draw list is already inactive.
   at: draw_list_end (drivers/vulkan/rendering_device_vulkan.cpp:7838)

================================================================
handle_crash: Program crashed with signal 11
Engine version: Godot Engine v4.0.alpha.custom_build (d7893a031f9e40feb51a28fb83f9613308ee9e60)
Dumping the backtrace. Please include this when reporting the bug on: https://github.com/godotengine/godot/issues
[1] /lib64/libc.so.6(+0x3ea70) [0x7ff298ab2a70] (??:0)
[2] /usr/lib64/libvulkan_intel.so(+0x1e0513) [0x7ff289e61513] (??:0)
[3] /usr/lib64/libvulkan_intel.so(+0x1e1036) [0x7ff289e62036] (??:0)
[4] /usr/lib64/libvulkan_intel.so(+0x1e7369) [0x7ff289e68369] (??:0)
[5] VulkanContext::flush(bool, bool) (/home/UserName/Projects/godot/drivers/vulkan/vulkan_context.cpp:1897 (discriminator 4))
[6] RenderingDeviceVulkan::_flush(bool) (/home/UserName/Projects/godot/drivers/vulkan/rendering_device_vulkan.cpp:8967)
[7] RenderingDeviceVulkan::texture_get_data(RID, unsigned int) (/home/UserName/Projects/godot/drivers/vulkan/rendering_device_vulkan.cpp:2792)
[8] RendererRD::TextureStorage::texture_2d_get(RID) const (/home/UserName/Projects/godot/servers/rendering/renderer_rd/storage_rd/texture_storage.cpp:1084)
[9] RenderingServerDefault::texture_2d_get(RID) const (/home/UserName/Projects/godot/servers/rendering/rendering_server_default.h:195 (discriminator 2))
[10] ImageTexture::get_image() const (/home/UserName/Projects/godot/scene/resources/texture.cpp:214)
[11] ./bin/godot.linuxbsd.tools.64() [0x3871d1d] (/home/UserName/Projects/godot/editor/editor_themes.cpp:102)
[12] create_editor_theme(Ref<Theme>) (/home/UserName/Projects/godot/editor/editor_themes.cpp:1510 (discriminator 4))
[13] create_custom_theme(Ref<Theme>) (/home/UserName/Projects/godot/editor/editor_themes.cpp:1790 (discriminator 4))
[14] ProjectManager::ProjectManager() (/home/UserName/Projects/godot/editor/project_manager.cpp:2568 (discriminator 4))
[15] Main::start() (/home/UserName/Projects/godot/main/main.cpp:2689 (discriminator 1))
[16] ./bin/godot.linuxbsd.tools.64(main+0x133) [0x23b3e09] (/home/UserName/Projects/godot/platform/linuxbsd/godot_linuxbsd.cpp:71)
[17] /lib64/libc.so.6(+0x29550) [0x7ff298a9d550] (??:0)
[18] /lib64/libc.so.6(__libc_start_main+0x89) [0x7ff298a9d609] (??:0)
[19] ./bin/godot.linuxbsd.tools.64(_start+0x25) [0x23b3c15] (??:?)
-- END OF BACKTRACE --
================================================================
Aborted (core dumped)
[UserName@fedora godot]$

@toger5
Try with line 503 in display_server_wayland.cpp changed this way:
- 		sd->wl_output = (struct wl_output *)wl_registry_bind(wl_registry, name, &wl_output_interface, 3);
+ 		sd->wl_output = (struct wl_output *)wl_registry_bind(wl_registry, name, &wl_output_interface, 2);

Out of curiosity, which compositor are you using?

Gnome (mutter)

Mhhh, from my side surely there is a protocol version issue like @dos1 noted, the most I've tested are pretty recent sway and weston but I'll see how to handle older compositors and whether we need certain features of newer protocol versions.
From toger's log:
wl_registry@2: error 0: invalid version for global wl_output (4): have 2, wanted 3

I'm not sure though how a wrongly registered output might interfere with vulkan in such a way but we'll see:
ERROR: Condition "format == DATA_FORMAT_MAX" is true. Returning: INVALID_ID
   at: screen_get_framebuffer_format (drivers/vulkan/rendering_device_vulkan.cpp:6801)
ERROR: Mismatch fragment shader output mask (1) and framebuffer color output mask (0) when binding both in render pipeline.
   at: render_pipeline_create (drivers/vulkan/rendering_device_vulkan.cpp:6265)

@toger5 could you please tell me more about your configuration?

Using Nvidia 970, 415 drivers with Ubuntu 22.04 Gnome  GNOME Shell 42.2 I don't have a crash, but exactly same error message at start
Godot Engine v4.0.alpha.custom_build.d7893a031 - https://godotengine.org
wl_registry@2: error 0: invalid version for global wl_output (5): have 2, wanted 3
Vulkan API 1.2.0 - Using Vulkan Device #0: NVIDIA - NVIDIA GeForce GTX 970
ERROR: Condition "err" is true. Returning: ERR_CANT_CREATE
   at: _update_swap_chain (drivers/vulkan/vulkan_context.cpp:1663)
ERROR: Condition "err != OK" is true. Returning: ERR_CANT_CREATE
   at: _window_create (drivers/vulkan/vulkan_context.cpp:1386)
ERROR: Can't show a Vulkan window.
   at: show_window (platform/linuxbsd/display_server_wayland.cpp:1667)

ERROR: Condition "!windows.has(p_window)" is true. Returning: false
   at: window_is_valid_swapchain (drivers/vulkan/vulkan_context.cpp:1421)
ERROR: Condition "!dl" is true.
   at: draw_list_bind_render_pipeline (drivers/vulkan/rendering_device_vulkan.cpp:7330)
ERROR: Condition "!dl" is true.
   at: draw_list_bind_index_array (drivers/vulkan/rendering_device_vulkan.cpp:7477)
ERROR: Condition "!dl" is true.
   at: draw_list_bind_uniform_set (drivers/vulkan/rendering_device_vulkan.cpp:7404)
ERROR: Condition "!dl" is true.
   at: draw_list_set_push_constant (drivers/vulkan/rendering_device_vulkan.cpp:7511)
ERROR: Condition "!dl" is true.
   at: draw_list_draw (drivers/vulkan/rendering_device_vulkan.cpp:7529)
ERROR: Immediate draw list is already inactive.
   at: draw_list_end (drivers/vulkan/rendering_device_vulkan.cpp:7838)

and later error spam of
Wayland protocol error 0 on interface wl_registry@2

using patch from above, doesn't help, I just got a little different error:
wl_registry@2: error 0: invalid version for global wl_seat (18): have 5, wanted 7

and later still error spam about wayland protocol error

@qarmin well it looks like I took for granted way newer protocols than what are actually used in most compositors. That patch made Godot request an older wl_output (which I think would still require some extra steps to work properly) but it looks like that also wl_seats are too old compared to what Godot's expecting.
Could you run Godot with the environment variable WAYLAND_DEBUG=1 and send me the log?

1.txt - with used patch from above
2.txt - clear branch version

@qarmin thanks, later I'll downgrade the expected version where I can.
I think this shouldn't be that big of a problem since from what I read most version bumps are... Coordinated? That should mean that I can just cap at the latest useful version (which should coincide with yours) with minimal changes.

If you don't require features added in later versions for your code to actually work, you should pass something like MIN(3, version) or MAX(5, MIN(7, version)) to wl_registry_bind, where version is what you get from wl_registry.global handler. This way you always request a correct version as long as there's an overlap between what you expect and what the compositor supports, and you can still implement new features added in later versions.

@dos1 thanks, great tip! I should see how much it's worth though as I can see this getting messy very quickly.

You can simply use any wlroots-based compositor (Sway, phoc, Cage etc.) with X11 backend and this patch applied to wlroots. This will turn mouse events into (single) touch.

@dos1, sorry, I forgot to answer to this post. When I'll work on basic touch support I'll try with this, thanks!

@toger5 and @qarmin could you please try again on mutter to see if the latest patch I pushed is enough?

Hi @qarmin, From a very cursory look I can't see anything wrong, could you also add --verbose to the flags and send me the log? (e.g. bin/godot.linuxbsd.tools.64 --verbose)
Thanks for your testing.

With verbose flag - ABC2.txt

inxi -GSC -xx
System:
  Host: rafal-H87M-D3H Kernel: 5.15.0-41-generic x86_64 bits: 64
    compiler: gcc v: 11.2.0 Desktop: GNOME 42.2 tk: GTK 3.24.33 wm: gnome-shell
    dm: GDM3 Distro: Ubuntu 22.04 LTS (Jammy Jellyfish)
CPU:
  Info: quad core model: Intel Core i7-4770 bits: 64 type: MT MCP
    arch: Haswell rev: 3 cache: L1: 256 KiB L2: 1024 KiB L3: 8 MiB
  Speed (MHz): avg: 3834 high: 3886 min/max: 800/3900 cores: 1: 3842
    2: 3886 3: 3864 4: 3843 5: 3765 6: 3775 7: 3869 8: 3834 bogomips: 54278
  Flags: avx avx2 ht lm nx pae sse sse2 sse3 sse4_1 sse4_2 ssse3 vmx
Graphics:
  Device-1: NVIDIA GM204 [GeForce GTX 970] vendor: Gigabyte driver: nvidia
    v: 515.48.07 pcie: speed: 2.5 GT/s lanes: 16 ports: active: none
    off: DVI-D-1,DVI-I-1 empty: DP-1,HDMI-A-1 bus-ID: 01:00.0
    chip-ID: 10de:13c2
  Display: wayland server: X.org v: <IP_ADDRESS> with: Xwayland v: 22.1.1
    compositor: gnome-shell driver: X: loaded: nvidia
    unloaded: fbdev,modesetting,nouveau,vesa gpu: nvidia display-ID: 0
  OpenGL: renderer: NVIDIA GeForce GTX 970/PCIe/SSE2
    v: 4.6.0 NVIDIA 515.48.07 direct render: Yes

vkcube - works fine
Selected GPU 0: NVIDIA GeForce GTX 970, type: 2

echo $XDG_SESSION_TYPE
wayland

Thanks for giving me that much information! Just out of curiosity, what does happen if you run the editor with --gpu-index 1? It should use software rendering (the CPU). If it runs, please send me a log with --verbose and WAYLAND_DEBUG=1 too, so I avoid wasting your time too much.

When running editor(both this PR and master) with Lavapipe I have such crash
0x00007fffe9c39496 in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
(gdb) backtrace
#0  0x00007fffe9c39496 in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#1  0x00007fffe9c3f9c8 in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#2  0x00007fffe9c42b57 in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#3  0x00007fffe9c25e91 in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#4  0x00007fffe9c299cb in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#5  0x00007fffe9c29e08 in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#6  0x00007fffe9c31a89 in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#7  0x00007fffe9ba8623 in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#8  0x00007fffe9baa901 in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#9  0x00007fffe9b9bda8 in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#10 0x00007fffe9b808f0 in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#11 0x00007fffe99d1356 in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#12 0x00007fffe99d3303 in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#13 0x00007fffe99c3d3c in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#14 0x00007fffe99f24a9 in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#15 0x00007fffe99f201b in ?? () from /usr/lib/x86_64-linux-gnu/libvulkan_lvp.so
#16 0x00007ffff7aa5b43 in start_thread (arg=<optimized out>) at ./nptl/pthread_create.c:442
#17 0x00007ffff7b37a00 in clone3 () at ../sysdeps/unix/sysv/linux/x86_64/clone3.S:81

so I'm not able to test it

@qarmin now that's interesting. Regarding the crash, I "just" hope it's because Lavapipe isn't completely conformant (from the logs: WARNING: lavapipe is not a conformant vulkan implementation, testing use only.).
I wonder if it's somehow connected to that nvidia card of yours (and EGLStream compositor implementation from what I read)

@qarmin I've been thinking about your issue and would it be too messy to try another EGL compositor? (dunno, KDE?)
The issue looks very complicated and I can't think of many ways to debug it, if it's my fault (AFAICT, on AMD/GBM it works fine)

Works pretty well for me, no window decorations though on arch+kde

@nathanfranke that's probably due to the absence of client-side decorations. It's on my TODO list but it's one of those more complex things to do along with HiDPI support. Thanks for testing!

Well, preferring Wayland now obviously runs it in the CI, which uncovered stuff which I had no idea was there. I propose to add a step in the sanitized Linux job in order to run both DisplayServers one after the another.

I just tried again. It works but starts through xWayland. Is there any flag i need to set to make it start with wayland?

I just tried again. It works but starts through xWayland. Is there any flag i need to set to make it start with wayland?

If you compiled the latest commit, I think I messed something but I'm not sure where, I got issues setting up sanitizers on my musl machine.

I just tried again. It works but starts through xWayland. Is there any flag i need to set to make it start with wayland?

I just tried again an somehow it is working now!!!! Godot on wayland!!! super happy to see it in action :+1: :heart:
I am also really looking forward to hiDPI in the seperate pr you mentioned!

Drag and drop may be able to be, or may need to be, implemented using xdg desktop portals, although I'm not sure on that. Using the portals would allow the exported Godot application to function inside of Flatpak and other isolated environments, at least

@orowith2os you're sure? Shouldn't implementing the drag and drop part of the base protocol be enough?

@orowith2os you're sure? Shouldn't implementing the drag and drop part of the base protocol be enough?

Not using xdg portals for drag and drop would require that the app have access to the files in flatpak permissions, to be able to pull them in from outside. Again, I'm not sure, but it can be looked into. An example that may help is Electron, as it's MIT licensed and works as expected inside of Flatpak (aka with limited permissions)

@orowith2os mhhh. I thought that the file was transferred as a datastream, not as a path. What would the MIME type be in this case?

@orowith2os mhhh. I thought that the file was transferred as a datastream, not as a path. What would the MIME type be in this case?

From the Portals documentation, it seems they use application/vnd.portal.filetransfer?
https://flatpak.github.io/xdg-desktop-portal/#gdbus-org.freedesktop.portal.FileTransfer
I'm not sure how GTK implements it thooo..

Oh, and hiii! It seems I'm getting a crash when running the output executable on a Fedora 36 container (Toolbox) ^^
Here's my crash log: https://gist.github.com/lovelyyfiaaa/fcfe5ce327226572f97295990f78b84f

@lovelyyfiaaa hiii! I'm currently working on something else, but I think that this might be somehow related with seat handling and a null pointer somewhere in the process. Would you mind trying to wrap line 779 in an if block and see if it works around the problem?
That part of the code looks a bit weird, I'll put a review of that part in my TODO list.

@lovelyyfiaaa hiii! I'm currently working on something else, but I think that this might be somehow related with seat handling and a null pointer somewhere in the process. Would you mind trying to wrap line 779 in an if (ss->wl_pointer) block and see if it works around the problem?
That part of the code looks a bit weird, I'll put a review of that part in my TODO list.

It seems instead of the wl_pointer being null, it's actually the cursor_image instead that's null!

Okayy I have this now!!

@lovelyyfiaaa oh, right, I didn't check for the image presence, sorry.
What's going on in that photo?!

@lovelyyfiaaa oh, right, I didn't check for the image presence, sorry.
What's going on in that photo?!

Umm. The Projects window and the dialogs weren't displaying well.
They're just glitchy colors and that stuff ^^

@lovelyyfiaaa what's your system? Do you use anything particular other than that toolbox thing you talked about?

Nothing!! I have Fedora Sirverblue as the host, and running Godot on the host doesn't fix anything ^^

@lovelyyfiaaa that's weird :/
I'll try replicating it on my side. What's your GPU?

I wanted to throw out there: since the Steam Deck uses a custom Wayland display server, I can't get Godot to compile on SteamOS 3 since X11 isn't available. It would be amazing to get this in for Godot 4.
Let me know if I can do anything to help (with a little spare time here and there); full-time C++ dev, only a little Godot experience.

I wanted to throw out there: since the Steam Deck uses a custom Wayland display server, I can't get Godot to compile on SteamOS 3 since X11 isn't available. It would be amazing to get this in for Godot 4.
Let me know if I can do anything to help (with a little spare time here and there); full-time C++ dev, only a little Godot experience.

You can compile Godot on SteamOS 3 without problem, you just need to install the X11 development libraries (you'd need to install the Wayland development libraries to compile this PR too).
To do so you have to disable the read-only mode on the filesystem to be able to use pacman to install packages: https://www.reddit.com/r/SteamDeck/comments/t8al0i/install_arch_packages_on_your_steam_deck/
A better alternative (which is the one I used last I tried) is to use the Linux SDK we provide for Linux (not well documented yet but it works, some instructions in https://github.com/godotengine/buildroot/#using-the-sdks). That's what we use for official builds.

@leetNightshade yeah, akien's approach is better. Thanks for the offer for help! Don't worry, for now I'm fine! Just going slower because lately I've been allowing myself some more relax for the summer. You can try to break the hell out of this PR though, that's be very appreciated!

Hey, I was testing this in the editor and it seems to crash when moving the mouse on and off menus too quickly. To reproduce:

Open godot --editor and select a project
Select the menu at the top, e.g. Scene
Drag the mouse quickly on and off different menus

It seems to crash specifically on menus that have multiple levels like recent files having a second level.
Reproduced on swaywm. I built 2592247dad4b443aee269fe2da6c62b3977f430e.
(Please note that my build flags were a little weird because I did not like the slow build times: builtin_embree=no builtin_freetype=no builtin_libogg=no builtin_libpng=no builtin_libtheora=no builtin_libvorbis=no builtin_libvpx=no builtin_libwebp=no builtin_mbedtls=no builtin_miniupnpc=no builtin_opus=no builtin_pcre2=no builtin_wslay=no builtin_zlib=no linker=mold)
Coredump: https://m1.afileditch.ch/IlbWsReAVcPgAPFroDD.zst (warning: half a gigabyte uncompressed)
MESA-INTEL: warning: Haswell Vulkan support is incomplete
Vulkan API 1.2.0 - Using Vulkan Device #0: Intel - Intel(R) HD Graphics 4400 (HSW GT2)

Editing project: $HOME/godot/fun
Godot Engine v4.0.alpha.custom_build.2592247da - https://godotengine.org
MESA-INTEL: warning: Haswell Vulkan support is incomplete
Vulkan API 1.2.0 - Using Vulkan Device #0: Intel - Intel(R) HD Graphics 4400 (HSW GT2)
WARNING: FBX file import is enabled, but no FBX2glTF path is configured. FBX files will not be imported.
     at: _editor_init (modules/gltf/register_types.cpp:92)
Destroying popup menu 69 which is not the topmost in the stack.
Destroying popup menu 68 which is not the topmost in the stack.
xdg_wm_base@6: error 2: xdg_popup was destroyed while it was not the topmost popup
ERROR: Condition "err" is true. Returning: ERR_CANT_CREATE
   at: _update_swap_chain (drivers/vulkan/vulkan_context.cpp:1753)
ERROR: Condition "err != OK" is true. Returning: ERR_CANT_CREATE
   at: _window_create (drivers/vulkan/vulkan_context.cpp:1461)
ERROR: Can't show a Vulkan window.
   at: show_window (platform/linuxbsd/wayland/display_server_wayland.cpp:1704)
Error 71 while flushing the Wayland display.
ERROR: Condition "err" is true. Returning: ERR_CANT_CREATE
   at: _update_swap_chain (drivers/vulkan/vulkan_context.cpp:1753)

================================================================
handle_crash: Program crashed with signal 11
Engine version: Godot Engine v4.0.alpha.custom_build (2592247dad4b443aee269fe2da6c62b3977f430e)
Dumping the backtrace. Please include this when reporting the bug to the project developer.
[1] /usr/lib/libc.so.6(+0x38a40) [0x7f4cc02a0a40] (??:0)
[2] /usr/lib/libvulkan_intel.so(+0x1a60db) [0x7f4cba31b0db] (??:0)
[3] /usr/lib/libvulkan_intel.so(+0x9f309) [0x7f4cba214309] (??:0)
[4] /usr/lib/libvulkan_intel.so(+0x19c0c9) [0x7f4cba3110c9] (??:0)
[5] VulkanContext::prepare_buffers() (??:0)
[6] RenderingDeviceVulkan::prepare_screen_for_drawing() (??:0)
[7] RendererCompositorRD::prepare_for_blitting_render_targets() (??:0)
[8] RendererViewport::draw_viewports() (??:0)
[9] RenderingServerDefault::_draw(bool, double) (??:0)
[10] RenderingServerDefault::draw(bool, double) (??:0)
[11] Main::iteration() (??:0)
[12] OS_LinuxBSD::run() (??:0)
[13] $HOME/godot/bin/godot.linuxbsd.tools.64(main+0x187) [0x55e0d19c5900] (??:0)
[14] /usr/lib/libc.so.6(+0x232d0) [0x7f4cc028b2d0] (??:0)
================================================================25) [0x55e0d19c56a5] (??:0)

I hope this is not caused by Haswell Vulkan support is incomplete!

Hi @ndren, this is a known issue on which I researched an awful lot and which didn't happen at all on Weston, so I assume that it's a sway bug that I'll have to report properly some day to upstream. I also talked about this issue with other contributors and they said that it's fine for now if it works properly only in single window mode.
Still, thanks for testing and for your detailed bug report!

I wanted to link this pr: https://github.com/godotengine/godot/pull/64777
Is it a quick task to add that to the wayland version as well?

@toger5 I don't think that this might be doable with server-side decorations, but it can definitely be done with client-side decorations. This exact approach would mean that Godot should have some sort of CSD mode (basically placing some buttons and sending the signal), but this would probably require a separate PR, perhaps after this one is merged.

I think it would be best to allow the game devs to choose what their decorations should be, and implement a baseline one for use in the editor (and for default).
I'd say include it in this PR, since adding Wayland support would probably require CSDs due to some compositors not implementing SSDs.

@orowith2os This would definitely require some more invasive changes in godot, which shouldn't be made in one big PR at all. Also, I tried godot without CSDs on stuff like gnome and it's still kinda usable. I really think that it should be done soon after merge, this PR's getting already too invasive for my taste after the OpenGL implementation.

I havent fully read through the csd pr for mac os. But it looks like it is just an option to render the header bar with the close minimize and maximise buttons. So maybe it is as simple as turning on that option for the waylnad platform. I might be wrong though and if it is more effort it sound slike a seperate pr makes a lot of sense.

@toger5 at least through the XDG decoration protocol, there's no way of asking "overlapping" or any other special mode for server-side decorations. Just asking for client-side or server-side decorations: https://wayland.app/protocols/xdg-decoration-unstable-v1

Oh that is how it is done on mac os. They are overlappting the server side decoration?
It looked to me like it would just make godot render the decorations itself. Which is what is needdd for csd of course.

@toger5 that doesn't look like the case. The documentation of WINDOW_FLAG_EXTEND_TO_TITLE says:

Window content is expanded to the full size of the window. Unlike borderless window, the frame is left intact and can be used to resize the window, title bar is transparent, but have minimize/maximize/close buttons.`

Still, thanks for letting me know about this PR! I think I can take something useful from it, from a quick look perhaps we could extend the EditorTitleBar class, perhaps even transforming it to a generic WindowTitleBar.

Oh that is how it is done on mac os. They are overlappting the server side decoration?
It looked to me like it would just make godot render the decorations itself. Which is what is needdd for csd of course.

It is. There are window flags to extend client area to the full size of the window, and to make title bar transparent, window border and close/min/max buttons are rendered by OS. The only thing that is implemented by Godot is custom title bar (EditorTitleBar class) for moving window and handling double-clicks on title (this part is not macOS specific, it should work on any platform).

Godot should have some sort of CSD mode (basically placing some buttons and sending the signal)

It's not just a click signal, both macOS and Windows 11 display a tiling/full-screen popup when hovering the maximize button: see support snap layouts for Windows, on macOS it's probably can be done by creating a transparent standard zoom button.

@Riteo Not sure if it's already implemented, but maybe account for this: https://gitlab.freedesktop.org/wayland/wayland-protocols/-/merge_requests/65
Could be used as an option to disable vsync both in the game and in the compositor, rather than relying on the compositor settings to disable vsync.

@orowith2os I was already aware of this and it is in my private TODO list to add a comment at least documenting that this will be eventually available. Still, thanks for letting me know!

@orowith2os For the record, nothing really implements it so far (or at least nothing relevant to Godot's Wayland support) and it will still take some time until it will become relevant since compositors that use atomic KMS API can't even implement it right now at all with current kernels. This is going to change, but at this moment it isn't really something worth bothering with.
(I'm also not sure whether Godot will actually have to care about it at all as it looks to me as something for EGL/Vulkan WSI to deal with, but I may be wrong on this one)

It doesn't hurt to have it there, at least as a thing that's more in a "might work, might not" state. Although, it could be put off some more, especially if there's just the normal vsync toggle, and then rely on a tool like gamescope to disable the compositor's vsync.

Yeah looking closer at it, it really looks like it's not relevant to Godot at all, as it has no way to actually use it in any sensible manner. Godot just has to configure the swapchain correctly and that protocol is going to be used by WSI behind Godot's back.

I think I implemented the most essential features that should matter to the majority of people.
The "only" things left are either more "niche" use-cases or more complex things in general which would warrant another PR IMO
Perhaps the least important but most complex thing is support for animated cursors which might be trivial but looks like hell to implement properly and only affect, what, the loading cursor or some shiny animated minecraft sword cursor pack for wayland if it even exists.
HiDPI and CSD are definitely planned but as I said worthy of another PR.
Regarding touch support I now have a PinePhone with phosh which makes it technically a multitouch Linux device so I can implement it but since it would probably not affect many people I'd prefer to refine this one and work out a good implementation eventually.
Someone proposed xdg-desktop-portal support and I wouldn't mind to try implmementing it, but it looks like a pretty big job which if I understand correctly would also benefit other platforms, so it would really make sense to make it in another, DisplayServer agnostic, PR.
So if no one's against, I would start considering this PR "beta quality" so that I can actually start to concentrate on ironing things and making this work properly everywhere like in the case of @lovelyyfiaaa which resulted in a very garbled image.

Wouldn't embedded subwindows rather map to Wayland's subsurfaces rather than xdg-popups?

Also should rebase it on a git version of all the Wayland packages perhaps? Since this needs a lot of work by the time it's done the git changes would already be probably released in a stable ver.

@Riteo Have you looked at the new Wayland protocol ver?

While requesting globals I chose, for simplicity, just the latest common version with the features I need as globals that are too new gave compatibility problems on stable distros.

The only way for that to give compatibility problems is when you use the version number wrong. As the author of the implementation you know which minimal version your code NEEDS and which maximal version your code optionally SUPPORTS, and you also know which maximum version the running compositor PROVIDES. Therefore, what you need to request is exactly max(min(PROVIDES, SUPPORTS), NEEDS). If NEEDS equals SUPPORTS, then you can simply request a constant version.

1.27 which got released recently introduces content hints which I feel like would be potentially useful: https://www.phoronix.com/news/Wayland-Protocols-1.27

@Riteo It's for optimization/dynamic behavior based on the content currently displaying could be super helpful from the article, "The content type hint notification is used for enabling clients to provide hints to the Wayland compositor around the type of visual content provided by the app. In turn, the content type hint notifications can be used for the compositor to adapt its behavior. "

@Riteo for Mutter, KWin, yes. Recently updated to support the new Wayland protocol ver. For Sway, it's partially supported upstream they just added the ext-idle-notify-v1 on their most recent commit. Plus, you could add a fallback for these functions as well if the user is on an unsupported version.

@Riteo AFAIK, 1.26 (version b4 1.27) made compatibility between versions much easier to keep because they added 'wm_capabilities,' which the compositor uses to announce their capability to prevent breakage, e.g., preventing the compositor from using unsupported features and using fallbacks instead it does this through announcing its capabilities of XDG_Shell. Which would probably be a significant load off your back.
https://www.phoronix.com/news/Wayland-Protocols-1.26
https://lists.freedesktop.org/archives/wayland-devel/2022-July/042270.html

Oh, also single-pixel buffer support got added which can be used for a decent performance boost if I'm reading it correctly.

@Riteo https://gitlab.freedesktop.org/wlroots/wlroots/-/merge_requests/3543
Wlroots already merged v5 support a couple of months back.

@Riteo doesn't hurt to try it again single it was probably a bug that hopefully got fixed in 1.27 also probably a fact it was a newly added feature that caused the quirkiness. I could help to test as well if you want. Usually, I'm active on Discord which I can pass to you if you want me to help.

@Riteo w/e you prefer honestly.
Also about xdg-shell I'm pretty sure Mutter, KDE, and Sway supports up to v6.

@Riteo Sent the email.

@Riteo either or, just would be preferable if you add me now (So I don't forget lmao) and if you want to talk later tell me so I don't accidentally bother you :).

Yeah, that's for the best (sorry for all that opened your email and saw tons of notifications from GitHub)

The thing is though, shouldn't the compositor accept lower values than the ones it provides?

It does, but then you only get the behavior as specified by that particular version you're requesting. That's exactly what makes things backwards compatible - you get what you request.

made compatibility between versions much easier to keep because they added 'wm_capabilities,'

This has nothing to do with compatibility between versions. It's only about hiding stuff like minimize button on compositors where there's no such concept as minimization, and stuff like that.

@dos1 Ah, I see. Still pretty helpful in adapting the design to each WM & DE.

it would still be pretty useful

Then what you need to do is to either require a protocol version that includes wm_capabilities (which will severely impact compatibility across various distro versions, as you noted before), or write your code in a way that makes wm_capabilities support optional (so it doesn't unconditionally expect any messages introduced in later protocol versions to come and it checks for the bound protocol version before sending newly introduced requests). Pretty simple thing, Wayland is structured in a way that makes it easy, you just need to be aware of which protocol version you're working with and what is your baseline you intend to support in case of older compositors.

Leaving everything inside of the main window seems like the best path of action, judging from my conversations with the Inochi2D dev on why she didn't want the popups to go outside of the main window; they messed with HiDPI scaling.
Also, I'm wondering: why doesn't Godot use SDL rather than reimplementing how it connects to a display server? Is there some technical reason for that other than "it's too late to switch to it now"?

@Riteo good point, it might just be something with ImGUI and/or SDL screwing with it -- in any case, so long as you don't bang your head trying to get popups and the like working, it'll be fine.
Will give the PR you linked a read, thanks.

@Riteo Let me know if I get this right: is the crash in sway due to undefined behaviour then or is it unrelated to this?

Nice to know!
I'm not on the wlroots IRC, but I was one of the people who reported the bug (quite late, a month ago?) alongside with a crash dump.
Good luck merging!

Multi-threading is still an issue currently right?

I'm still unclear why we need X11 to switch to EGL? Is this also switching us from OpenGL to GLES? The other desktop platforms are using OpenGL (as opposed to real GLES), which is also what we did in Godot 3.

Mostly linking reasons AFAICT, we must be able to make a single binary for both X11 and Wayland and the direct link to libGL.so really messes up some things (although from what I understand GLAD supports dynamic loading of some sorts). There's also the advantage of code sharing (potentially even with android from what I understand) which IMO is a pretty nice advantage. Nonetheless this'll be split into a dedicated PR so it'll get thoroughly discussed.

Hm, ok! I look forward to discussing this separately, and especially hearing what other folks think, like @clayjohn and @BastiaanOlij, who are much, much better with rendering than me :-)
If we're still using GLAD with EGL, and we're still using OpenGL (as opposed to GLES), then this isn't that huge of a change.
However, I'm working on a OpenXR with OpenGL PR (#67775) and, unless I'm missing something, I think OpenXR with X11 only works with GLX (it needs some pointers from GLX in order to initialize - see XrGraphicsBindingOpenGLXlibKHR). It's possible to use OpenXR with EGL, but that appears to be specifically targeting GLES on Android (the structure used to initialize is called XrGraphicsBindingOpenGLESAndroidKHR). If switching to EGL blocks OpenXR iwith OpenGL, then it'd be best to stick with GLX, but come up with a way to dynamically load libGL.so.
Also, my recently merged OpenGL multiview PR (#65334) made the assumption that EGL was only used by Android for GLES, so if we made the switch, we'd also need to re-evaluate some of the code I added there.

unless I'm missing something, I think OpenXR with X11 only works with GLX

I don't want to overtake this PR with stuff about OpenXR, but I just found that there is a vendor extension from Monado (XR_MNDX_egl_enable) that appears to allow initializing via EGL. If we can make the assumption that anyone on Linux is using Monado, we could perhaps rely on this extension? But I don't know if that's a safe assumption, and I haven't dug deeper into this extension than just looking at the docs.

Will this make 4.0 release? It doesn't seem that likely now.

@Riteo Did you try updating xdg-shell?

Okayy I have this now!!

On this issue, I can reproduce the same display error on a Bevy codebase running on WGPU's Vulkan backend. The CSD built with sctk_adwaita works though since it uses tiny-skia (software-rendering) instead.
     Running `target/debug/native-launcher`
MESA-INTEL: warning: Performance support disabled, consider sysctl dev.i915.perf_stream_paranoid=0
2022-12-04T04:21:34.943853Z  INFO bevy_render::renderer: AdapterInfo { name: "AMD RADV ICELAND", vendor: 4098, device: 26880, device_type: DiscreteGpu, driver: "radv", driver_info: "Mesa 22.1.4", backend: Vulkan }
2022-12-04T04:21:35.206983Z  INFO native_launcher: Starting launcher: Native

But it works when I run it on integrated graphics on Vulkan.
    Finished dev [unoptimized + debuginfo] target(s) in 0.23s
     Running `target/debug/native-launcher`
MESA-INTEL: warning: Performance support disabled, consider sysctl dev.i915.perf_stream_paranoid=0
2022-12-04T04:21:34.943853Z  INFO bevy_render::renderer: AdapterInfo { name: "AMD RADV ICELAND", vendor: 4098, device: 26880, device_type: DiscreteGpu, driver: "radv", driver_info: "Mesa 22.1.4", backend: Vulkan }
2022-12-04T04:21:35.206983Z  INFO native_launcher: Starting launcher: Native

It could be that Godot would run just fine on OpenGL, but I haven't tested that out.

@Riteo (unrelated to this PR), to easily test things on other distros, I'd recommend giving https://github.com/89luca89/distrobox a shot. Its available in most distro's package managers now. :smiley:

@Riteo (unrelated to this PR), to easily test things on other distros, I'd recommend giving https://github.com/89luca89/distrobox a shot. Its available in most distro's package managers now. smiley

It's possible to modify the Flathub manifest to get it in flatpak format too, which might be easier. I'll toss together a manifest for it, so others here can try it.

The pr process mentioned, that when the pr is ready to be merged, it should be squashed.
https://docs.godotengine.org/en/stable/community/contributing/pr_workflow.html

Subscribing to follow the progress on this. Another Linux user here, Manjaro / KDE in my case... Wayland Plasma session may finally be stable enough to switch to from X11. The next release of Blender is said to support it, leaving Godot as one of the last 3D tools still waiting for the implementation. I take it in the meantime Godot will still run on Wayland but requires the slow compatibility layer provided by the Wayland-X11 process or what it was called.

I tested this with Sway on Ubuntu Jammy and it seems to work. I tested the editor and my 2D game (vulkan renderer) cursorily and had no issues. All seems smooth. My GPU is a fairly old AMD Radeon R9 380 series.
I did run into a build-time issue at first:
[ 14%] In file included from platform/linuxbsd/os_linuxbsd.cpp:38:
platform/linuxbsd/wayland/display_server_wayland.h:563:9: error: 'const wl_pointer_listener' has no non-static data member named 'axis_value120'
  563 |         };
      |         ^

I commented out that line and it built. Probably some wayland version conflict? libwayland-dev package version is at 1.20.0.

Mhh, that isn't supposed to be DisplayServer's concern. Do you have xdg-open available and fully working?

I mean the internal links supposed to open in Godot's own help browser, not the external/browser links. So it seemed like some kind of event issue. But if if it works as expected for other people I'll chalk it up to a local misconfiguration. Maybe I should try GNOME wayland :smile:

Not everyone needing it isn't an excuse from requiring it, imo, because again, even if more compositors implement SSDs than not, the Wayland spec says that apps need to be able to draw their own decorations, so I don't think having it work similar to PulseAudio applies here.
If libdecor isn't available in a distro, it seems like something to fix in that distro, especially if that distro has Wayland.

I agree with Oro, IMO. There is no reason to hold something up because of a small selection of users. Also, can the maintainers update the CI used to the newest Ubuntu version?

Uh I can replicate that, but I'm not sure what I might've missed. Double click detection seems to work, and I recall porting it almost directly from X11. Are we sure this isn't an upstream bug?

It's possible! I don't know where Godot's browser widget comes from.
Another help-related X11 difference I noticed after using the editor for a while is that tooltips don't appear.

TBF I'm not sure whether this is the most optimal approach, but it seems to work fine and I'm sure that this is harmless since these symbols will never be used in your case (specifically to your case, they're null pointers, so if they'd ever get called you'd notice it immediately as it'd segfault).

Just a case of messages looking more worrying than they are, then :smile:

How did you test fullscreening? Did you use the DisplayServer method or is there some compositor shortcut? It works from my testing on sway.

I tried the GNOME shortcut (meta+up) only.
On Sway everything works great. I noticed these problems only on GNOME.

I think that it's kinda... By design? Basically there's no proper HiDPI support yet (Wayland's approach is very funky and I think that it requires core changes) and your display is scaled by 2, so you get a window that's half the resolution that's upscaled to double the size, if that makes sense.

OK. It's just a noticeable difference from X11 on the same computer.
But I it likely has to do with the scaling factor, as you say.
I don't have any kind of scaling factor on the computer with Sway (it's a desktop with large monitor). The GNOME one is a laptop which, for some absurd reason, has a 4k screen, so some scaling is necessary. It just seemed somewhat on the excessive side.
BTW: I tried on yet another computer. Some laptop with two AMD GPUs, one built-in and one discrete (the only one which can do Vulkan). It uses DRI_PRIME. The display output was a mess, but vaguely recognizable, as if the horizontal width of the surface is wrong (a bit like in https://github.com/godotengine/godot/pull/57025#issuecomment-1213872256). I'm not able to debug this further right now, but it may be an edge case.

BTW: I tried on yet another computer. Some laptop with two AMD GPUs, one built-in and one discrete (the only one which can do Vulkan). It uses DRI_PRIME. The display output was a mess, but vaguely recognizable, as if the horizontal width of the surface is wrong (a bit like in https://github.com/godotengine/godot/pull/57025#issuecomment-1213872256). I'm not able to debug this further right now, but it may be an edge case.
Edit: This is only for the Vulkan renderer! For OpenGL it's fine. Note that Vulkan works with X11 emulation.

Great! Would you mind testing this in Wgpu's examples or Bevy's? They share the same bug so it would be great if you can also reproduce the bug there.
And yup! I have been using Wgpu's OpenGL renderer for my Bevy project, and there are no issues like in the Vulkan renderer!

I recall normal tooltips appearing, although I've never tried the help ones. Do the normal ones work for you?

No tooltips at all appear there! I've seen it work with the same code on another computer though, so not sure what causes it.

This issue really baffles me. Could you tell me some extra HW/SW info regarding the problematic computer? The fact that it's a Vulkan-only issue makes everything even more confusing.

Yes, the problem is Vulkan+Wayland only. Vulkan+X11 works fine,  GLES3+Wayland also.
It has two GPUs.

glxinfo without DRI_PRIME:
Extended renderer info (GLX_MESA_query_renderer):
    Vendor: AMD (0x1002)
    Device: KABINI (, LLVM 15.0.5, DRM 2.50, 6.0.0-5-amd64) (0x9851)
    Version: 22.2.4
    Accelerated: yes
    Video memory: 1024MB
    Unified memory: no
    Preferred profile: core (0x1)
    Max core profile version: 4.5
    Max compat profile version: 4.5
    Max GLES1 profile version: 1.1
    Max GLES[23] profile version: 3.2
Memory info (GL_ATI_meminfo):
    VBO free memory - total: 873 MB, largest block: 873 MB
    VBO free aux. memory - total: 1950 MB, largest block: 1950 MB
    Texture free memory - total: 873 MB, largest block: 873 MB
    Texture free aux. memory - total: 1950 MB, largest block: 1950 MB
    Renderbuffer free memory - total: 873 MB, largest block: 873 MB
    Renderbuffer free aux. memory - total: 1950 MB, largest block: 1950 MB
Memory info (GL_NVX_gpu_memory_info):
    Dedicated video memory: 1024 MB
    Total available memory: 3067 MB
    Currently available dedicated video memory: 873 MB
OpenGL vendor string: AMD
OpenGL renderer string: KABINI (, LLVM 15.0.5, DRM 2.50, 6.0.0-5-amd64)
OpenGL core profile version string: 4.5 (Core Profile) Mesa 22.2.4
OpenGL core profile shading language version string: 4.50
OpenGL core profile context flags: (none)
OpenGL core profile profile mask: core profile

glxinfo with DRI_PRIME=1
Extended renderer info (GLX_MESA_query_renderer):
    Vendor: AMD (0x1002)
    Device: AMD Radeon R7 M360 (iceland, LLVM 15.0.5, DRM 3.48, 6.0.0-5-amd64) (0x6900)
    Version: 22.2.4
    Accelerated: yes
    Video memory: 2048MB
    Unified memory: no
    Preferred profile: core (0x1)
    Max core profile version: 4.6
    Max compat profile version: 4.6
    Max GLES1 profile version: 1.1
    Max GLES[23] profile version: 3.2
Memory info (GL_ATI_meminfo):
    VBO free memory - total: 1717 MB, largest block: 1717 MB
    VBO free aux. memory - total: 5385 MB, largest block: 5385 MB
    Texture free memory - total: 1717 MB, largest block: 1717 MB
    Texture free aux. memory - total: 5385 MB, largest block: 5385 MB
    Renderbuffer free memory - total: 1717 MB, largest block: 1717 MB
    Renderbuffer free aux. memory - total: 5385 MB, largest block: 5385 MB
Memory info (GL_NVX_gpu_memory_info):
    Dedicated video memory: 2048 MB
    Total available memory: 7498 MB
    Currently available dedicated video memory: 1717 MB

The first one is used for rendering the display manager. But only the second one is capable of Vulkan. So any intensive rendering has to, somehow, transfer surface between the GPUs. I'm not surprised that this is an edge case.

Great! Would you mind testing this in Wgpu's examples or Bevy's? They share the same bug so it would be great if you can also reproduce the bug there.

Sure! I haven't built rust stuff in a while but I can check.

What are some specific steps to reproduce the Vulkan issues? I can try to reproduce it in a container on my end to see where, specifically, the issue lies.

Mh. This makes me wonder, can you replicate it with any other Wayland-native Vulkan (3d?) program, if you even have any other at all? From how you've put it, that could perhaps even be some compositor thing or who knows what.

Yup! I was saying that this bug also occurs in Bevy (probably the WGPU side).

What are some specific steps to reproduce the Vulkan issues? I can try to reproduce it in a container on my end to see where, specifically, the issue lies.

Just run a Vulkan app on Wayland.. but you have to do it on a laptop with this configuration:
Integrated graphics: can only use OpenGL (mine can also  use Vulkan, but weirdly only on X11?)
Discrete graphics: only can use Vulkan

Oh, I only have desktops over here.... But if it happens with any Vulkan app, then it doesn't seem like a Godot issue, might be something with the compositor?

@fianathedevgirl well that explains why I can't replicate it, at least... I've a laptop with only integrated AMD graphics and nothing else. I wonder if that might be simulated somehow though... Can there be multiple instances of llvmpipe?
@orowith2os

might be something with the compositor?

I'm having the same feeling, wondering if all compositors have this issue.

not suree.. should I try it with Smithay?

Sway, GNOME, KDE, and anything else you can get your hands would be ideal, but only the first three would be needed

Mh. This makes me wonder, can you replicate it with any other Wayland-native Vulkan (3d?) program, if you even have any other at all?

Yes. I've updated my previous post. I have exactly the same issue with the wgpu examples.

From how you've put it, that could perhaps even be some compositor thing or who knows what.

It could be a sway bug. That said, it's strange that XWayland does manage to get it right. From what I understand XWayland is simply a wayland application with no special API access. So how do Vulkan applications running on XWayland display correctly.

@vmedea I'm not sure, it still uses X11 graphics drivers (from mesa) from what I remember.

That's a good point. Ok, i have no idea in that case. May very well be a mesa bug too! Hadn't thought of that angle.
To be honest I hope this particular edge case doesn't hold up wayland support in godot. It's an old laptop, a "maybe she can still run linux on it" throwaway lol… It's easy to work around and I think the specific hardware software combination must be quite rare. I won't spam the PR about it anymore unless I have important new information.

To be honest I hope this particular edge case doesn't hold up wayland support in godot.

I fear that it may.

I think the specific hardware software combination must be quite rare.

iGPU + dGPU are pretty common IMO. We don't know if this might happen in less specific circumstances, but considering the little testing this PR got, it might as well be worse than we can see.

I won't spam the PR about it anymore unless I have important new information.

Don't worry about it, this PR is already pretty silent and this sounds like a pretty bad issue in my view.

I am following this PR long time ago, so I can help testing, I have a gnome wayland session that now I can't even use x11 because a bug in nobara linux, and I have an integerated amd + Nvidia DGPU.

I did find a new issue (I think):

Mainloop notification NOTIFICATION_APPLICATION_FOCUS_IN is never raised. This is used in the editor to rescan for new and changed files when having switched to another application and back, which doesn't trigger right now.

iGPU + dGPU are pretty common IMO.

It is, it definitely needs more testing that it happens in other such cases too, or only when one card uses the (recent) amdgpu driver and one uses (ancient) radeon.

WARNING: Can't obtain the XDG decoration manager. Decorations won't show up.
     at: DisplayServerWayland (platform/linuxbsd/wayland/display_server_wayland.cpp:3203)
OpenGL Renderer: RENOIR (renoir, LLVM 14.0.5, DRM 3.48, 6.0.14-201.fsync.fc36.x86_64)

WARNING: Icon not supported by this display server.
     at: set_icon (servers/display_server.cpp:507)
ERROR: The host fxr folder does not exist: /usr/share/dotnet/host/fxr
   at: try_get_path_from_dotnet_root (modules/mono/editor/hostfxr_resolver.cpp:323)
ERROR: .NET: One of the dependent libraries is missing. Typically when the `hostfxr`, `hostpolicy` or `coreclr` dynamic libraries are not present in the expected locations.
   at: find_hostfxr (modules/mono/mono_gd/gd_mono.cpp:126)
ERROR: .NET: Failed to load hostfxr
   at: initialize (modules/mono/mono_gd/gd_mono.cpp:397)
WARNING: Icon not supported by this display server.
     at: set_icon (servers/display_server.cpp:507)
ERROR: Error opening file '/home/ywmaa/Documents/AMSG/Advanced-Movement-System-Godot/icon.png'.
   at: load_image (core/io/image_loader.cpp:90)
ERROR: Error opening file '/home/ywmaa/Documents/MyGameDev/Room/icon.png'.
   at: load_image (core/io/image_loader.cpp:90)
Editing project: /home/ywmaa/Documents/Godot Projects/WaylandTest
Godot Engine v4.0.beta.mono.custom_build.a00b7cf84 - https://godotengine.org
WARNING: Can't obtain the XDG decoration manager. Decorations won't show up.
     at: DisplayServerWayland (platform/linuxbsd/wayland/display_server_wayland.cpp:3203)

[ywmaa@ywmaa linux-editor-mono]$ Vulkan API 1.3.235 - Using Vulkan Device #0: AMD - AMD Unknown (RADV RENOIR)

WARNING: Icon not supported by this display server.
     at: set_icon (servers/display_server.cpp:507)
ERROR: The host fxr folder does not exist: /usr/share/dotnet/host/fxr
   at: try_get_path_from_dotnet_root (modules/mono/editor/hostfxr_resolver.cpp:323)
ERROR: .NET: One of the dependent libraries is missing. Typically when the `hostfxr`, `hostpolicy` or `coreclr` dynamic libraries are not present in the expected locations.
   at: find_hostfxr (modules/mono/mono_gd/gd_mono.cpp:126)
ERROR: .NET: Failed to load hostfxr
   at: initialize (modules/mono/mono_gd/gd_mono.cpp:397)
WARNING: FBX file import is enabled in the project settings, but no FBX2glTF path is configured in the editor settings. FBX files will not be imported.
     at: _editor_init (modules/gltf/register_types.cpp:85)

================================================================
handle_crash: Program crashed with signal 11
Engine version: Godot Engine v4.0.beta.mono.custom_build (a00b7cf84c36a6a1da27ec76999f2f6e4a7350f1)
Dumping the backtrace. Please include this when reporting the bug to the project developer.
[1] /lib64/libc.so.6(+0x3fa70) [0x7fd75243fa70] (??:0)
-- END OF BACKTRACE --
================================================================

if I open the editor the project manager works, but when I launch a project it crashes, is it related to me not installing .NET ?

Try running the project manager with the command line flag --rendering-driver vulkan and see if it passes that.

with this same thing, project manager works, the editor crashes, also I didn't build godot I grabbed the artifacts of this pull request, should I build it ?

I didn't know that you could do that.

you can go to the Linux Builds (Details), go to summary, scroll down to the bottom, there you have the artifacts.
it only has mono stuff, not the GD script only editor.

Oh, I'd recommend building it then, especially if you've never used the mono flavour. If your distro has it packaged, also install libdecor-0, otherwise it won't show CSDs.

Fedora's dnf :
Package libdecor-0.1.1-1.fc36.x86_64 is already installed

so this time after installing .net 6 the editor didn't crash, but from the project manager to the editor there isn't a window title, so I can't resize nor move the window with only the mouse, this is intended ?
for me I can use keyboard shortcuts to do these stuff.

also what should I test in the editor ?

@vmedea after some pretty dumb mistakes with debugging (I thought that it was a generic issue due to a misreading)

Great! Yes, I can confirm that help links work now.
Tooltips also work in all cases I tried.
Also, the app notification works correctly, the editor imports new resources on re-focus now.
I did find a new bug: full screen is not set for new windows. The reason is that in _show_window, window_set_mode is called with wd.visible still false, so it'll be skipped. Moving up the wd.visible = true solved it for me.
BTW: Some updates regarding the amdgpu/radeon hybrid GPU issue: Even the official vkcube_wayland suffers from the issue. I have checked this in sway as well as weston. I'm now 100% convinced that this is not a specific problem with the code here but a deeper issue in either mesa or wlroots with negotiating buffer modifiers.

I figured I'd test things out a little as well. I'm just starting to get into development using Godot so I might not hit the in-depth edge cases, but maybe I'll fat-finger something or break things out of ignorance, hah
My Wayland environment:
Operating System: Fedora Linux 38
KDE Plasma Version: 5.26.4
KDE Frameworks Version: 5.101.0
Qt Version: 5.15.7
Kernel Version: 6.2.0-0.rc1.14.fc38.x86_64 (64-bit)
Graphics Platform: Wayland

I built your wayland branch from: https://github.com/Riteo/godot/tree/wayland
Only quirk I've found so far, and forgive me if this was covered in earlier conversation and I missed it, is that context menus sometimes appear out of place when right clicking on certain elements.
Right-clicking/opening the context menu on the script field for a Node opens in the correct position:

However, the context menu for the Scene's tab opens far away:

If I maximize the editor the location of the Scene's context menu makes more sense.

I'll let you know if anything else comes up while I'm learning and poking.

Do you have multiple monitors? I remember having a similar issue with QT apps, where when a monitor to the right of my primary monitor and above it would throw off the QT dropdowns.

Also, since weston doesn't work (I presume you used the DRM backend?) and I struggle to see how wlroots would cause this issue

Yes, I use the DRM backend only. But I don't really know where the DRM buffer negotiation happens. For a moment I thought weston used wlroots too. It doesn't, so it can't really be the culprit.
There is only one reported issue on freedesktop about a similar problem I could find (https://gitlab.freedesktop.org/mesa/mesa/-/issues/6660), but it concerns different hw. I might report one at some point….

Great! Although note that I haven't directly changed anything with tooltips, so I'm not sure what fixed them for you.

It was luck!!! The actual problem had to do with scroll wheel handling setting an invalid bit in the current button mask, fix is this:
diff --git a/platform/linuxbsd/wayland/display_server_wayland.cpp b/platform/linuxbsd/wayland/display_server_wayland.cpp
index bba85c7e8694609c4a4ddfbd83378f4923aaf166..bcdf4caeeb0366a440184c013b49474c78425361 100644
--- a/platform/linuxbsd/wayland/display_server_wayland.cpp
+++ b/platform/linuxbsd/wayland/display_server_wayland.cpp
@@ -948,8 +948,6 @@ void DisplayServerWayland::_wl_pointer_on_axis(void *data, struct wl_pointer *wl

        PointerData &pd = ss->pointer_data_buffer;

-       MouseButton button_pressed = MouseButton::NONE;
-
        switch (axis) {
                case WL_POINTER_AXIS_VERTICAL_SCROLL: {
                        pd.scroll_vector.y = wl_fixed_to_double(value);
@@ -960,10 +958,6 @@ void DisplayServerWayland::_wl_pointer_on_axis(void *data, struct wl_pointer *wl
                } break;
        }

-       // These buttons will get unpressed when the event is sent.
-       pd.pressed_button_mask |= mouse_button_to_mask(button_pressed);
-       pd.last_button_pressed = button_pressed;
-
        pd.button_time = time;
 }

Mh that doesn't sound completely right. Does scrolling still work after this patch?

Yes, it only removes (sort of) dead code, note that button_pressed is never assigned. So it ends up setting button bit -1 which is interpreted as bit 31 of the mask, and the tooltip code only triggers if the user isn't pressing any buttons.

This is a bit too generic, as I push to this branch pretty often. Could you include the commit next time? It should also be embedded in the Godot version number.

@Riteo, I'm sorry! You are correct, I was mistaken about my earlier report regarding the context menus! I cloned the repo and built straight from master. I should have known better. I'm a dolt and totally ignored the source branch of this PR.
I've checked out the wayland branch, built at commit [a4c1032870](https://github.com/Riteo/godot/commit/a4c103287094fa9e2a8181ce213ad5fba177dcd4) and now things are hunky-dory. There are no issues with context menus.
Please disregard my previous report. I'll be more careful next time to prevent and reduce unnecessary noise.
@orowith2os I do have two monitors!  Thankfully the dropdowns are right were they should be, even when split across each monitor's edge.

You know, that's a good question. I don't know if it's known behavior, so I'll look into it a little bit. I have a hankering it's an XWayland quirk as you've hinted at too. Thanks for being patient and thorough!

I wonder if mouse_button_to_mask should just return 0 in case MouseButton::NONE (which equals -1) gets passed to it.

I think that would make sense! Or some kind of assertion failure maybe. There have been some updates to this code in master, ButtonMask is a fully-fledged bitmask now, instead of reusing Button, but this particular behavior wasn't changed.
It does cause the compilation to fail with errors like this:
platform/linuxbsd/wayland/display_server_wayland.h:709:29: error: conflicting return type specified for 'virtual MouseButton DisplayServerWayland::mouse_get_button_state() const'
  709 |         virtual MouseButton mouse_get_button_state() const override;
      |                             ^~~~~~~~~~~~~~~~~~~~~~

Good news: the rendering issue with wayland/vulkan on dual-GPU laptop appears to have been fixed with upgrade of the mesa packages from 22.2.4-1 to 22.3.2-1. It now works as-is, in vkcube-vulkan, wgpu examples and this godot PR.

Edit: there, I should've fixed it.

Seems to work!

This is amazing news! Wonder what change fixed that, and if it was voluntary.

I'm not sure. There was this huge package update (for debian bookworm), after rebooting it just worked. I hope it was intentional and will stay that way :smile:
Being able to run the editor on this laptop helped me find a new issue: keypad cursor/pgup/pgdn/etc keys don't work. When numlock is on, it generates numbers, with numlock off, the numpad keys don't seem to do anything. This is with wayland only, with X they work.

Thanks for the bug report! I'll add it to my TODO list and update you when I find something.

I think I found the cause. I printed the keycode and physical_keycode for the left arrow key on the keypad:
       NumLock  keycode    physical_keycode
X11    Off      KEY_LEFT   KEY_KP_4
X11    On       KEY_KP_4   KEY_KP_4
WL     Off      KEY_KP_4   KEY_KP_4
WL     On       KEY_KP_4   KEY_KP_4

So for X11, the 'keycode' depends on the numlock status but for wayland it doesn't. Not sure why, as you do pass in the xkb_state for translation. Maybe a matter of a change in _xkb_keysym_to_keycode?

Looks like Key::* was changed in regard to SUPER / HYPER:

Key::HYPER_L and Key::HYPER_R have been replaced with Key::HYPER
Key::SUPER_L and Key::SUPER_R were removed from the documentation and binding (no replacement) but they're still in core/os/keyboard.h

I noticed that I could drop my local patch to comment out .axis_value120=…, I think this was solved by embedding the WL headers.

@Riteo I've checked: the /usr/share/wayland/wayland.xml in libwayland-dev package on Ubuntu 22.04 (which I assume wayland-scanner uses to generate header files) doesn't define the axis_value120 event slot. It defines wl_pointer version 7 instead of 8.

but oh well, at least it works now.

Yes, if it's really important I could try to build the old commit again but I'm not sure it's worth it.
BTW: something that might be useful is to set a application id using xdg_toplevel_set_app_id (something like org.godotengine.Godot to match the .desktop name). To make it possible for sway to identify the window and automatically move the window to a certain workspace, for example.

I have a feature request, I don't know if it's easy but would be nice if there was a way to set a different app_id between the editor and the running game

Is this like, a thing needed to be user-selectable at runtime?

Not necessarily, I'm happy just having a difference to set sway rules that apply only to the running game vs the editor

Is this like, a thing needed to be user-selectable at runtime?

That's a good question. Thinking of it I think ideally a project setting would make sense. I mean, Godot itself is org.godotengine.Godot, but a released game will have its own XDG project name—or not, in any case, it's not the editor, so the default could be something else.

Hello! I'm trying to make this work here. I'm running Hyprland. I can run the project manager but I cannot open created projects. I believe the project manager runs on OpenGL, that's probably why it's working.
vkcube runs smoothly.
Tks in advance.
poiati@poiati-dell bin]$ ./godot.linuxbsd.editor.x86_64 --single-window
Godot Engine v4.0.beta.custom_build.af68cce9f - https://godotengine.org
libspeechd.so.2: cannot open shared object file: No such file or directory
OpenGL Renderer: AMD Radeon Graphics (renoir, LLVM 15.0.7, DRM 3.49, 6.1.9-arch1-1)
ERROR: Condition "status < 0" is true. Returning: ERR_CANT_OPEN
   at: init_device (drivers/alsa/audio_driver_alsa.cpp:89)
WARNING: All audio drivers failed, falling back to the dummy driver.
     at: initialize (servers/audio_server.cpp:218)

WARNING: Icon not supported by this display server.
     at: set_icon (servers/display_server.cpp:543)
Editing project: /home/poiati/godot/projects/test
Godot Engine v4.0.beta.custom_build.af68cce9f - https://godotengine.org
libspeechd.so.2: cannot open shared object file: No such file or directory
[poiati@poiati-dell bin]$ Vulkan API 1.3.224 - Using Vulkan Device #0: NVIDIA - NVIDIA GeForce RTX 3060 Laptop GPU
ERROR: Condition "err" is true. Returning: ERR_CANT_CREATE
   at: _update_swap_chain (drivers/vulkan/vulkan_context.cpp:1957)
ERROR: Condition "err != OK" is true. Returning: ERR_CANT_CREATE
   at: _window_create (drivers/vulkan/vulkan_context.cpp:1686)
ERROR: Can't show a Vulkan window.
   at: _show_window (platform/linuxbsd/wayland/display_server_wayland.cpp:2621)
ERROR: Condition "status < 0" is true. Returning: ERR_CANT_OPEN
   at: init_device (drivers/alsa/audio_driver_alsa.cpp:89)
WARNING: All audio drivers failed, falling back to the dummy driver.
     at: initialize (servers/audio_server.cpp:218)

ERROR: Condition "!windows.has(p_window)" is true. Returning: false
   at: window_is_valid_swapchain (drivers/vulkan/vulkan_context.cpp:1721)
ERROR: Condition "!dl" is true.
   at: draw_list_bind_render_pipeline (drivers/vulkan/rendering_device_vulkan.cpp:7106)
ERROR: Condition "!dl" is true.
   at: draw_list_bind_index_array (drivers/vulkan/rendering_device_vulkan.cpp:7253)
ERROR: Condition "!dl" is true.
   at: draw_list_bind_uniform_set (drivers/vulkan/rendering_device_vulkan.cpp:7180)
ERROR: Condition "!dl" is true.
   at: draw_list_set_push_constant (drivers/vulkan/rendering_device_vulkan.cpp:7287)
ERROR: Condition "!dl" is true.
   at: draw_list_draw (drivers/vulkan/rendering_device_vulkan.cpp:7305)
ERROR: Immediate draw list is already inactive.
   at: draw_list_end (drivers/vulkan/rendering_device_vulkan.cpp:7608)
WARNING: Blend file import is enabled in the project settings, but no Blender path is configured in the editor settings. Blend files will not be imported.
     at: _editor_init (modules/gltf/register_types.cpp:70)
WARNING: Icon not supported by this display server.
     at: set_icon (servers/display_server.cpp:543)
ERROR: Condition "!windows.has(p_window)" is true. Returning: false
   at: window_is_valid_swapchain (drivers/vulkan/vulkan_context.cpp:1721)
ERROR: Condition "!windows.has(p_window)" is true. Returning: false
   at: window_is_valid_swapchain (drivers/vulkan/vulkan_context.cpp:1721)
ERROR: Condition "!windows.has(p_window)" is true. Returning: false
   at: window_is_valid_swapchain (drivers/vulkan/vulkan_context.cpp:1721)
ERROR: Condition "!windows.has(p_window)" is true. Returning: false
   at: window_is_valid_swapchain (drivers/vulkan/vulkan_context.cpp:1721)
ERROR: Condition "!windows.has(p_window)" is true. Returning: false
   at: window_is_valid_swapchain (drivers/vulkan/vulkan_context.cpp:1721)
ERROR: Condition "!windows.has(p_window)" is true. Returning: false
   at: window_is_valid_swapchain (drivers/vulkan/vulkan_context.cpp:1721)

@riteo I'm running the latest Arch.

System:
  Host: poiati-dell Kernel: 6.1.9-arch1-1 arch: x86_64 bits: 64 compiler: gcc
    v: 12.2.1 Desktop: Hyprland dm: N/A Distro: Arch Linux
CPU:
  Info: 8-core model: AMD Ryzen 7 5800H with Radeon Graphics bits: 64
    type: MT MCP arch: Zen 3 rev: 0 cache: L1: 512 KiB L2: 4 MiB L3: 16 MiB
  Speed (MHz): avg: 1327 high: 3200 min/max: 1200/4462 boost: enabled cores:
    1: 1200 2: 1200 3: 1200 4: 1200 5: 1200 6: 1200 7: 1197 8: 1200 9: 1250
    10: 1200 11: 1200 12: 1200 13: 1198 14: 1200 15: 3200 16: 1200
    bogomips: 102241
  Flags: avx avx2 ht lm nx pae sse sse2 sse3 sse4_1 sse4_2 sse4a ssse3 svm
Graphics:
  Device-1: NVIDIA GA106M [GeForce RTX 3060 Mobile / Max-Q] vendor: Dell
    driver: nvidia v: 525.85.05 arch: Ampere pcie: speed: 2.5 GT/s lanes: 8
    bus-ID: 01:00.0 chip-ID: 10de:2560
  Device-2: AMD Cezanne [Radeon Vega Series / Radeon Mobile Series]
    vendor: Dell driver: amdgpu v: kernel arch: GCN-5.1 pcie: speed: 8 GT/s
    lanes: 16 ports: active: eDP-1 empty: none bus-ID: 05:00.0
    chip-ID: 1002:1638 temp: 36.0 C
  Device-3: CN0V976R8LG00173A31PA01 Integrated_Webcam_HD type: USB
    driver: uvcvideo bus-ID: 1-4:3 chip-ID: 0c45:6720
  Display: wayland server: X.org v: <IP_ADDRESS> with: Xwayland v: 22.1.7
    compositor: Hyprland driver: gpu: amdgpu display-ID: 1
  Monitor-1: eDP-1 model: AU Optronics 0xae8b res: 1920x1080 dpi: 142
    diag: 394mm (15.5")
  Message: No known Wayland EGL/GBM data sources. API: EGL/GBM

I'm wondering why it says "amdgpu" under display. I'm using nvidia drm kernel modules.

I'm wondering why it says "amdgpu" under display. I'm using nvidia drm kernel modules.

You have two graphics devices, one Nvidia RTX 3060M, and one AMD Radeon Vega which is part of your CPU. OpenGL applications would typically use the AMD one (less resource usage) unless you specify DRI_PRIME=1 I believe. And Vulkan apps may choose one or the other depending on various factors (Godot should default to the more powerful Nvidia GPU normally, provided that it does report better metrics than the AMD one).

@Riteo what would you recommend as the best way to debug this? I can try myself. Thank you!

I have a Wacom Intuos Pro tablet so tested the tablet support a bit:

Position and pressure works as expected
Tilt works too, but gives values from ~-60..60 in X and Y.  However, the documentation mentions the range should be -1.0..1.0
pen_inverted always returns false, even with the eraser side. The eraser works in Krita (in XWayland, Krita doesn't have native Wayland support yet).

@Riteo I see.
It's weird that I'm able to run vkcube using that same wayland compositor (natively, not XWayland). Maybe it's some sort of Vulkan extension that Godot uses that the demo app doesn't, but I'm also newbie in the rendering side.

Maybe vkcube-vulkan picks the other Vulkan device? Might be worth trying to make it use either (not sure how, there's not something standardized like DRI_PRIME for Vulkan). The NVidia one might not be able to create on-screen windows (swap chains).

Also note that NVIDIA's pretty messed up when it comes to Wayland stuff by itself, so I wouldn't be surprised if this were somehow their fault.

Yeah… Getting the buffer transfer to work between two different generation AMD cards was already a challenge, between AMD mesa and NVIDIA proprietary sounds like a horror show.

Both (vkcube, godot) select the NVIDIA card by default. I can confirm that in the console.

Both (vkcube, godot) select the NVIDIA card by default. I can confirm that in the console.

It is the problem of Nvidia, not Godot , all vulkan program ran with Nvidia will crash,it doesn't support prime offload , if you have due card on your computer, only what we can do is to run it with another card what is not nvidia

Both (vkcube, godot) select the NVIDIA card by default. I can confirm that in the console.

It is the problem of Nvidia, not Godot , all vulkan program ran with Nvidia will crash,it doesn't support prime offload , if you have due cards on your computer, only what we can do is to run it with another card what is not nvidia

I don't understand how you come to that conclusion. I 100% can run vkcube using my NVIDIA Card (Wayland). I also have been running Godot 4 (Vulkan Renderer) in X11 for years in the same hardware and other NVIDIA Cards I have at my disposal. I can also run Godot 4 RC1 here, through XWayland. I'm just unable to run that branch here, unfortunately I'm lacking time to properly debug it, but I will when I find some.

Both (vkcube, godot) select the NVIDIA card by default. I can confirm that in the console.

It is the problem of Nvidia, not Godot , all vulkan program ran with Nvidia will crash,it doesn't support prime offload , if you have due cards on your computer, only what we can do is to run it with another card what is not nvidia

I don't understand how you come to that conclusion. I 100% can run vkcube using my NVIDIA Card (Wayland). I also have been running Godot 4 (Vulkan Renderer) in X11 for years in the same hardware and other NVIDIA Cards I have at my disposal. I can also run Godot 4 RC1 here, through XWayland. I'm just unable to run that branch here, unfortunately I'm lacking time to properly debug it, but I will when I find some.

https://github.com/NVIDIA/open-gpu-kernel-modules/issues/317 issue is here, it is the problem of nvidia

Hello, you are right @Decodetalkers, this is an issue when we have integrated + nvidia GPU. I tried this branch from my desktop, where I have no integrated graphs and it worked like a charm. Thank you @Riteo, this looks awesome!
I always had stutter issues when running with X11, all is gone with Wayland, it runs smoothly! Do we have any idea when we are merging this? Maybe for 4.1? Tks!

aaaaaaaa quick question, how is drag-n-drop and copy-paste handled? Ideally Godot would use the FileTransfer portal for files and the normal Wayland protocols otherwise. This would be nice to have in X11 builds as well, so maybe it's best to have this done in a separate PR....

It might be better to use reverse-dns names; they make it easier to differentiate between community builds of Godot and official ones, as well as having less of a chance of conflicts between different window IDs.
OBS seems to do this for its windows, and Flatpak does too for seeing what folders it should access and what dbus names it should own. I don't think promoting old names like godot-editor would be good.

This https://github.com/godotengine/godot/pull/76946#discussion_r1191008746

Just a heads up, hopefully saves you some headaches: while testing current master merged into this, i noticed that commit 0a9f72d5a80c8957ef5172f546c9076089862cef "Make more base nodes thread safe" causes fairly random crashes (but usually at startup) in combination with this. Reverting it solves the problem. I don't know why.

Do you have a backtrace?

Unfortunately, not at the moment. I tried to get one but it was really out in the woods, some thread without debug information. So I first thought it was a Mesa bug, however, it happens on two different computers.
I couldn't reproduce it in X11/XWayland, which is why I post this here not as a new bug report. I'll try some more later.

I have a backtrace on a call to get_image that may be related to another commit, #75142.
================================================================
handle_crash: Program crashed with signal 11
Engine version: Godot Engine v4.1.dev.custom_build (7aa363ed5beece6b16e8d66a12b05b969b6ff323)
Dumping the backtrace. Please include this when reporting the bug to the project developer.
[1] /lib/x86_64-linux-gnu/libc.so.6(+0x42520) [0x7f122985f520] (??:0)
[2] godot(+0x2a43d98) [0x5623f87add98] (/home/ubuntu/upstream/godot/editor/plugins/tiles/tiles_editor_plugin.cpp:127)
[3] godot(+0x4d6d495) [0x5623faad7495] (/home/ubuntu/upstream/godot/core/os/thread.cpp:61)
[4] godot(+0x569ab04) [0x5623fb404b04] (thread.o:?)
[5] /lib/x86_64-linux-gnu/libc.so.6(+0x94b43) [0x7f12298b1b43] (??:0)
[6] /lib/x86_64-linux-gnu/libc.so.6(+0x126a00) [0x7f1229943a00] (??:0)
-- END OF BACKTRACE --

I really hope I got the bisecting wrong and this is the only one :smile:

AHHH that is apparently a different issue, that also happens with X11 (#77391).
Sorry for the noise.

Not a blocker, not urgent. Do you know where the Linux hdr color work is being done?

Regarding multi-windowing instead I proposed to make the specific subclasses such as Popup signal the DisplayServer about some predefined classes through an enum of sorts. I've still not tested this approach so it might not be good enough still.

I'm guessing this is what is causing #77753 that I opened recently? If so, I can note it on that issue and close it.

For the record, this PR enforces single-window mode for the time being.

Ah, thank you very much. I was not even aware there was a single-window mode available. That works perfectly.

So at startup? We're still in single window mode.

Yes, either at startup of the editor or the game.

I recall that a debug log from sway -d should tell at least something on why it disconnected from the client. Perhaps you could send me one?

I'll try that. Mind that it's a rare intermittent issue, which is why i haven't reported it before, so it may take a while.

EDIT: BTW I use sway too and I can't recall seeing this issue in a long time. Do you use something other than an AMD card? Sorry, I can't remember.

This is with an AMD card.

I recently tested wayland on my computers and both of them are running nobora linux with KDE one with Nvidia and the other Intel. the first time i run Godot it works without any issue but then if i try to run again Godot crashes on after the splash screen
================================================================
handle_crash: Program crashed with signal 11
Engine version: Godot Engine v4.1.dev.custom_build
Dumping the backtrace. Please include this when reporting the bug to the project developer.
[1] /lib64/libc.so.6(+0x39b70) [0x7fbb5ee64b70] (??:0)
[2] /lib64/libwayland-client.so.0(wl_proxy_marshal_flags+0xc4) [0x7fbb4a7ed744] (??:0)
[3] /run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot-wayland-thread-refactor/bin/godot.linuxbsd.editor.x86_64() [0xe31be8] (??:0)
[4] /lib64/libffi.so.8(+0x7be6) [0x7fbb5e603be6] (??:0)
[5] /lib64/libffi.so.8(+0x44bf) [0x7fbb5e6004bf] (??:0)
[6] /lib64/libffi.so.8(ffi_call+0x12e) [0x7fbb5e60318e] (??:0)
[7] /lib64/libwayland-client.so.0(+0x7f0e) [0x7fbb4a7e9f0e] (??:0)
[8] /lib64/libwayland-client.so.0(+0x8793) [0x7fbb4a7ea793] (??:0)
[9] /lib64/libwayland-client.so.0(wl_display_dispatch_queue_pending+0x7c) [0x7fbb4a7eaa3c] (??:0)
[10] /run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot-wayland-thread-refactor/bin/godot.linuxbsd.editor.x86_64() [0xe7922b] (??:0)
[11] /run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot-wayland-thread-refactor/bin/godot.linuxbsd.editor.x86_64() [0x418a495] (??:0)
[12] /run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot-wayland-thread-refactor/bin/godot.linuxbsd.editor.x86_64() [0x4e844a3] (??:0)
[13] /lib64/libc.so.6(+0x888a7) [0x7fbb5eeb38a7] (??:0)
[14] /lib64/libc.so.6(__clone+0x44) [0x7fbb5ef396f4] (??:0)
-- END OF BACKTRACE --
================================================================

Weirdly if i compile both the wayland branch and the wayland-thread-refactor branch while both crash after starting for the second time sometimes it causes the binary from the other branch to work.

@Riteo Yeah so far both my computers intel and nvidia computer have the same issue I also tested with the Nvidia computers integrated Intel GPU too and still gets the same crash
================================================================
handle_crash: Program crashed with signal 11
Engine version: Godot Engine v4.1.beta.custom_build
Dumping the backtrace. Please include this when reporting the bug to the project developer.
[1] /lib64/libc.so.6(+0x39b70) [0x7f70e9b2eb70] (??:0)
[2] /lib64/libwayland-client.so.0(wl_proxy_marshal_flags+0x90) [0x7f70e92cc710] (??:0)
[3] /run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot-wayland/bin/godot.linuxbsd.editor.x86_64() [0xaf9fc8] (/run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot-wayland/platform/linuxbsd/wayland/wayland_thread.cpp:1815)
[4] /lib64/libffi.so.8(+0x7be6) [0x7f70e92bcbe6] (??:0)
[5] /lib64/libffi.so.8(+0x44bf) [0x7f70e92b94bf] (??:0)
[6] /lib64/libffi.so.8(ffi_call+0x12e) [0x7f70e92bc18e] (??:0)
[7] /lib64/libwayland-client.so.0(+0x7f0e) [0x7f70e92c8f0e] (??:0)
[8] /lib64/libwayland-client.so.0(+0x8793) [0x7f70e92c9793] (??:0)
[9] /lib64/libwayland-client.so.0(wl_display_dispatch_queue_pending+0x7c) [0x7f70e92c9a3c] (??:0)
[10] /run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot-wayland/bin/godot.linuxbsd.editor.x86_64() [0xafd459] (/usr/include/c++/13/x86_64-redhat-linux/bits/gthr-default.h:779)
[11] /run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot-wayland/bin/godot.linuxbsd.editor.x86_64() [0x45d942d] (/run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot-wayland/core/os/thread.cpp:61)
[12] /run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot-wayland/bin/godot.linuxbsd.editor.x86_64() [0x4e2fa03] (thread.o:?)
[13] /lib64/libc.so.6(+0x888a7) [0x7f70e9b7d8a7] (??:0)
[14] /lib64/libc.so.6(__clone+0x44) [0x7f70e9c036f4] (??:0)
-- END OF BACKTRACE --
================================================================

got this from a debug build

@Riteo the version I just compiled was based of the wayland branch which I cloned from yesterday. I managed to get the project manager to open for a bit and copied the version and clipboard gives me v4.1.beta.custom_build

@Riteo got this from the command 1765f180c3988753f70a45e36b569f8a007a10b3

@Riteo  i did a fresh reclone of the repo and recompiled and this time got a version with hash this time v4.1.beta.custom_build [1765f180c]
I also got a different error in the backtrace
WaylandThread::_wp_primary_selection_device_on_selection(void*, zwp_primary_selection_device_v1*, zwp_primary_selection_offer_v1*) (/run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot/platform/linuxbsd/wayland/protocol/primary_selection.gen.h:373 (discriminator 1))

@Riteo  here the primary_selection.gen.h file zipped
primary_selection.zip

@Riteo heres the full backtrace I got
================================================================
handle_crash: Program crashed with signal 11
Engine version: Godot Engine v4.1.beta.custom_build (1765f180c3988753f70a45e36b569f8a007a10b3)
Dumping the backtrace. Please include this when reporting the bug to the project developer.
[1] /lib64/libc.so.6(+0x39b70) [0x7fbb7b8b7b70] (??:0)
[2] /lib64/libwayland-client.so.0(wl_proxy_marshal_flags+0x90) [0x7fbb7b055710] (??:0)
[3] /run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot/bin/godot.linuxbsd.editor.dev.x86_64() [0x1f2a70b] (/run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot/platform/linuxbsd/wayland/protocol/primary_selection.gen.h:473)
[4] WaylandThread::_wp_primary_selection_device_on_selection(void*, zwp_primary_selection_device_v1*, zwp_primary_selection_offer_v1*) (/run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot/platform/linuxbsd/wayland/wayland_thread.cpp:1815)
[5] /lib64/libffi.so.8(+0x7be6) [0x7fbb7b045be6] (??:0)
[6] /lib64/libffi.so.8(+0x44bf) [0x7fbb7b0424bf] (??:0)
[7] /lib64/libffi.so.8(ffi_call+0x12e) [0x7fbb7b04518e] (??:0)
[8] /lib64/libwayland-client.so.0(+0x7f0e) [0x7fbb7b051f0e] (??:0)
[9] /lib64/libwayland-client.so.0(+0x8793) [0x7fbb7b052793] (??:0)
[10] /lib64/libwayland-client.so.0(wl_display_dispatch_queue_pending+0x7c) [0x7fbb7b052a3c] (??:0)
[11] WaylandThread::_poll_events_thread(void*) (/usr/include/c++/13/bits/unique_lock.h:105)
[12] Thread::callback(unsigned long, Thread::Settings const&, void (*)(void*), void*) (/run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot/core/os/thread.cpp:61)
[13] std::thread::_Invoker<std::tuple<void (*)(unsigned long, Thread::Settings const&, void (*)(void*), void*), unsigned long, Thread::Settings, void (*)(void*), void*> >::operator()() (/usr/include/c++/13/bits/std_thread.h:300)
[14] std::thread::_State_impl<std::thread::_Invoker<std::tuple<void (*)(unsigned long, Thread::Settings const&, void (*)(void*), void*), unsigned long, Thread::Settings, void (*)(void*), void*> > >::_M_run() (/usr/include/c++/13/bits/std_thread.h:244)
[15] /run/media/tuxtheastronaut/ccf26561-c89e-45bf-b284-6054d78c53be/Documents/Godot/godot/bin/godot.linuxbsd.editor.dev.x86_64() [0x51f0ed3] (thread.o:?)
[16] /lib64/libc.so.6(+0x888a7) [0x7fbb7b9068a7] (??:0)
[17] /lib64/libc.so.6(__clone+0x44) [0x7fbb7b98c6f4] (??:0)
-- END OF BACKTRACE --
================================================================

How is Wayland support thro COSMIC? Well how is COSMIC support.

@Nyabinary

How is Wayland support thro COSMIC? Well how is COSMIC support.

You will need to ask the COSMIC developers how it's going over there. This PR is just for generic Wayland support. If COSMIC is a conforming Wayland compositor that implements the required protocols, then this should work just fine.

@Riteo Tank you for working on this
also to answer the question on what is cosmic its another desktop environment made by pop OS. right now its just modified gnome but I think they are planning to make it its own separate thing

Its not a modified GNOME its it own separate thing. Technically there two COSMIC though, current COSMIC which is just GNOME, then COSMIC their own in house DE.

@Riteo just tested it and so far it hasn't crashed at all 👍 Thanks.

I have found a different error today tho maybe is the desktop environments problem but so far godot is the only one to do this behavior were I cant full screen or maximize the window if i maximize the window instead the window just takes up half the screen and then i cant interact with anything inside the window until i resize it this is on my both my computers with Intel GPU
The editor also crashes when i try to edit a project tho i think thats not related to wayland since if i force x11 and try to edit a project it still crashes when editing a project and weirdly both never print any errors in the terminal as to why its closing. tho this might be a 4.2 issue thats unrelated to wayland or x11

@Riteo  im on nobra 38 which is based of fedora 38 with KDE plasma 5.27.6

@Riteo did some more testing and it looks like it happens after i try to fullscreen it will maximize and resize fine and all until i full screen then window placement and size starts to act strange. so i guess going fullscreen messes up how the window behaves until i restart

@Riteo ye its very inconsistent for me too sometimes i have the issue then sometimes it just dose not happen even if i try to make it happen i did test other games like xonotic with wayland and it didnt seems to have same issues other than sometimes when leaving maximized the window would just move all the way off screen

Great work! I'm just starting to test this. Basic usage seems to be fine.
Some issues encountered so far:

Randomly seen, not sure how serious this is:

WARNING: Entering a window while a window is hovered should never happen in DisplayServer.
     at: _event_callback (scene/main/window.cpp:676)

Icon shown in Waybar is wrong when in project manager:

After selecting project, also name is wrong. I'm not sure why KiCad was shown instead. KiCad is not running either.
I have not seen this behaviour in other programs.

Sometimes, when selecting the project from the project list, the project manager disappears, but the project won't start loading until a very long time. (10-30 minutes maybe?). I'll try to debug this more.

I've had one crash when selecting project from the manager. I'm trying to replicate this under debug build

Message: Process 43923 (godot.linuxbsd.) of user 1000 dumped core.

                Stack trace of thread 43943:
                #0  0x00007f325328e83c n/a (libc.so.6 + 0x8e83c)
                #1  0x00007f325323e668 raise (libc.so.6 + 0x3e668)
                #2  0x00007f32532264b8 abort (libc.so.6 + 0x264b8)
                #3  0x000055a9f6d942be n/a (/.../godot/bin/godot.linuxbsd.editor.x86_64 + 0xd2a2be)
                #4  0x00007f325323e710 n/a (libc.so.6 + 0x3e710)
                #5  0x00007f325328fdb4 pthread_mutex_lock (libc.so.6 + 0x8fdb4)
                #6  0x00007f3252de30e8 wl_display_dispatch_queue_pending (libwayland-client.so.0 + 0x80e8)
                #7  0x000055a9f6dff2ed n/a (/.../godot/bin/godot.linuxbsd.editor.x86_64 + 0xd952ed)
                #8  0x000055a9fad8837d n/a (/.../godot/bin/godot.linuxbsd.editor.x86_64 + 0x4d1e37d)
                ELF object binary architecture: AMD x86-64

Sometimes, when selecting the project from the project list, the project manager disappears, but the project won't start loading until a very long time. (10-30 minutes maybe?).

This is probably the weirdest. Judging from the backtrace you gave it's just a roundtrip message, which means that we send a message and wait for a reply to make sure that every message we queued up got read by the compositor. It's just a synchronization method... That's very weird.
For the record I'm pretty sure that try_set_mode is pretty hacky (IIRC we can't really depend on some assumptions did there regarding window mode setting but I'm not sure) but not that much to break a simple roundtrip. I'm seriously confused.

Yeah, this one is weird. The first time it happened, I had several processes stuck in the same state and they actually all recovered simultaneously maybe 10-30 min after they had been started.
It happened again with two processes. I had them stuck in the background for several hours and both actually revived just as I was starting to write this reply. I'm not sure what triggers them to continue. This time it was interacting with firefox.

I've had one crash when selecting project from the manager.

That's a bit weird. First of all, the thread cleanup error is my fault, I forgot to clean stuff up on a late init error like that. I've put this in my TODO list.
I could actually replicate similar issues over time myself on sway. For some reason certain globals just... Disappear. I'm not sure if they "pop in" at different times or something like that.

I'll try with WAYLAND_DEBUG=1
It shouldn't take too long if the crashes keep happening with same rate.

Could you give me some info regarding your setup such as GPU, distro and the compositor/DE used? That would be useful.

Sure. Radeon RX 580, Arch x86_64, labwc+lxqt (https://github.com/stefonarch/lxqt-labwc-session)

Ok, had another crash with WAYLAND_DEBUG=1
the signature is bit different on this.
bt1.txt
debuglog.txt

@Riteo Would love to help test this implementation. Currently stuck in the "build/installation phase". Running sway @ archlinux. xorg-xwayland is currently not installed.
git clone git@github.com:Riteo/godot.git -b wayland
scons
bin/godot.linuxbsd.editor.x86_64

output
Godot Engine v4.2.dev.custom_build.221513acc - https://godotengine.org
libspeechd.so.2: cannot open shared object file: No such file or directory
ERROR: EGL version is too old!
   at: initialize (drivers/egl/egl_manager.cpp:292)
ERROR: Could not initialize GLES3.
   at: DisplayServerWayland (platform/linuxbsd/wayland/display_server_wayland.cpp:1149)
ERROR: Can't create the Wayland display server.
   at: create_func (platform/linuxbsd/wayland/display_server_wayland.cpp:1087)
ERROR: X11 Display is not available
   at: DisplayServerX11 (platform/linuxbsd/x11/display_server_x11.cpp:5548)
ERROR: Unable to create DisplayServer, all display drivers failed.
   at: setup2 (main/main.cpp:2235)
ERROR: BUG: Unreferenced static string to 0: TextServerDummy
   at: unref (core/string/string_name.cpp:131)
ERROR: BUG: Unreferenced static string to 0: IPUnix
   at: unref (core/string/string_name.cpp:131)
ERROR: BUG: Unreferenced static string to 0: ResourceFormatImporterSaver
   at: unref (core/string/string_name.cpp:131)
ERROR: BUG: Unreferenced static string to 0: MovieWriterMJPEG
   at: unref (core/string/string_name.cpp:131)
ERROR: BUG: Unreferenced static string to 0: interface_added
   at: unref (core/string/string_name.cpp:131)
ERROR: BUG: Unreferenced static string to 0: TextServerAdvanced
   at: unref (core/string/string_name.cpp:131)
ERROR: BUG: Unreferenced static string to 0: ImageFormatLoader
   at: unref (core/string/string_name.cpp:131)
ERROR: BUG: Unreferenced static string to 0: ResourceFormatSaver
   at: unref (core/string/string_name.cpp:131)
ERROR: BUG: Unreferenced static string to 0: GDScriptEditorTranslationParserPlugin
   at: unref (core/string/string_name.cpp:131)
ERROR: BUG: Unreferenced static string to 0: MovieWriterPNGWAV
   at: unref (core/string/string_name.cpp:131)
ERROR: BUG: Unreferenced static string to 0: ScriptLanguage
   at: unref (core/string/string_name.cpp:131)
ERROR: BUG: Unreferenced static string to 0: ResourceFormatLoader
   at: unref (core/string/string_name.cpp:131)
ERROR: Pages in use exist at exit in PagedAllocator: N7Variant5Pools11BucketLargeE
   at: ~PagedAllocator (./core/templates/paged_allocator.h:170)
ERROR: Pages in use exist at exit in PagedAllocator: N7Variant5Pools12BucketMediumE
   at: ~PagedAllocator (./core/templates/paged_allocator.h:170)
ERROR: Pages in use exist at exit in PagedAllocator: N7Variant5Pools11BucketSmallE
   at: ~PagedAllocator (./core/templates/paged_allocator.h:170)

Tried with xorg-xwayland installed which resulted in godot running under xwayland session.
Can you point me in the right direction to get me started? Thanks!

@Riteo Would love to help test this implementation. Currently stuck in the "build/installation phase". Running sway @ archlinux. xorg-xwayland is currently not installed.
git clone git@github.com:Riteo/godot.git -b wayland
scons
bin/godot.linuxbsd.editor.x86_64

output
Godot Engine v4.2.dev.custom_build.221513acc - https://godotengine.org
ERROR: EGL version is too old!
   at: initialize (drivers/egl/egl_manager.cpp:292)
ERROR: Could not initialize GLES3.
   at: DisplayServerWayland (platform/linuxbsd/wayland/display_server_wayland.cpp:1149)
ERROR: Can't create the Wayland display server.
   at: create_func (platform/linuxbsd/wayland/display_server_wayland.cpp:1087)
ERROR: X11 Display is not available
   at: DisplayServerX11 (platform/linuxbsd/x11/display_server_x11.cpp:5548)
ERROR: Unable to create DisplayServer, all display drivers failed.
   at: setup2 (main/main.cpp:2235)
ERROR: BUG: Unreferenced static string to 0: TextServerDummy
   at: unref (core/string/string_name.cpp:131)
ERROR: BUG: Unreferenced static string to 0: IPUnix
   at: unref (core/string/string_name.cpp:131)
ERROR: BUG: Unreferenced static string to 0: ResourceFormatImporterSaver
   at: unref (core/string/string_name.cpp:131)
ERROR: BUG: Unreferenced static string to 0: MovieWriterMJPEG
   at: unref (core/string/string_name.cpp:131)
ERROR: BUG: Unreferenced static string to 0: interface_added
   at: unref (core/string/string_name.cpp:131)