Publish that linux windowing draft
This commit is contained in:
parent
d9f36ac2f1
commit
7ef7860c5e
2 changed files with 16 additions and 99 deletions
|
@ -1,7 +1,7 @@
|
||||||
---
|
---
|
||||||
title: "Graphics Dump: The Linux desktop"
|
title: "Graphics Dump: Surfaces and Wayland"
|
||||||
date: 2022-11-15
|
date: 2022-11-15
|
||||||
draft: true
|
draft: false
|
||||||
tags:
|
tags:
|
||||||
- Vulkan
|
- Vulkan
|
||||||
- Linux
|
- Linux
|
||||||
|
@ -9,84 +9,52 @@ series:
|
||||||
- Graphics Dump
|
- Graphics Dump
|
||||||
---
|
---
|
||||||
|
|
||||||
|
**Note (2025-01-01):** This has been sitting in my drafts since 2022, and I don't have any immediate plans to finish it. So I thought I might as well post it for my own reference.
|
||||||
|
|
||||||
This is a huge topic just by itself, but it's incredibly interesting as everything we said before is assuming that you're
|
This is a huge topic just by itself, but it's incredibly interesting as everything we said before is assuming that you're
|
||||||
either running your Vulkan program without any graphics output (_specifically_ presentation, as you can totally run the graphics
|
either running your Vulkan program without any graphics output (_specifically_ presentation, as you can totally run the graphics
|
||||||
part of Vulkan headless).
|
part of Vulkan headless.) For _brevity’s_ sake, and because there's already a lot of X11 information out there - I want to cover what specifically
|
||||||
|
happens on Wayland.
|
||||||
|
|
||||||
For _brevity’s_ sake, and because there's already a lot of X11 information out there - I want to cover what specifically
|
# On the Vulkan Side
|
||||||
happens on **Wayland**. This is especially troubling because there is a lot of misinformation on the web, especially around Wayland.
|
|
||||||
|
|
||||||
### On the Vulkan Side
|
|
||||||
|
|
||||||
Let's momentarily mention what exactly you need to do on Vulkan to get presentation working. We'll keep this short, but
|
Let's momentarily mention what exactly you need to do on Vulkan to get presentation working. We'll keep this short, but
|
||||||
it's important to get our bearings straight.
|
it's important to get our bearings straight. This may be a surprise to some, but Vulkan has nothing to do with presentation. This is pretty on par with Khronos APIs
|
||||||
|
|
||||||
This may be a surprise to some, but Vulkan has nothing to do with presentation. This is pretty on par with Khronos APIs
|
|
||||||
actually, as OpenGL also did not concern itself with presentation (GLX, EGL, and other similar stuff is _not_ related).
|
actually, as OpenGL also did not concern itself with presentation (GLX, EGL, and other similar stuff is _not_ related).
|
||||||
|
|
||||||
In Vulkan, to get presentation you must enable a device extension, specifically `VK_KHR_swapchain`. This is not the only
|
In Vulkan, to get presentation you must enable a device extension, specifically `VK_KHR_swapchain`. This is not the only
|
||||||
piece of the puzzle, as you also need a surface to render to. There is a lot of options, but we are only concerning ourselves with two:
|
piece of the puzzle, as you also need a surface to render to. There is a lot of options, but we are only concerning ourselves with two:
|
||||||
|
|
||||||
* `VK_KHR_surface` - this is the base surface extension
|
* `VK_KHR_surface`: this is the base surface extension
|
||||||
* `VK_KHR_wayland_surface` - needed to interface with the Wayland client
|
* `VK_KHR_wayland_surface`: needed to interface with the Wayland client
|
||||||
* `VK_KHR_directfb_surface` - we will get into this later, as it provides a way to display vulkan directly to the framebuffer.
|
* `VK_KHR_directfb_surface`: we will get into this later, as it provides a way to display vulkan directly to the framebuffer.
|
||||||
|
|
||||||
### Wayland
|
# How swap chains work (quickly)
|
||||||
|
|
||||||
We'll be exclusively talking about how Vulkan applications under Wayland function, specifically under two scenarios.
|
|
||||||
One will be through a typical desktop environment - in this case - KDE Plasma as well as a more barebones example, bare KMS.
|
|
||||||
For both cases I will be using SDL2 instead of interacting with the Wayland layer itself,
|
|
||||||
which will be the case for many games. This does not change much though, because unlike OpenGL - SDL2 does not really interact
|
|
||||||
or intercept Vulkan functionality, apart from creating a Vulkan surface.
|
|
||||||
|
|
||||||
I chose these two situations because one is your more typical desktop environment, where the compositor has to juggle many
|
|
||||||
windows vying for presentation. The bare KMS example is more relevant to something like a game system, and we can see if
|
|
||||||
anything is different here in terms how the swapchain and presentation is handled.
|
|
||||||
|
|
||||||
### How swap chains work (quickly)
|
|
||||||
|
|
||||||
So how do swap chains work (quickly?) For simplicity, we're talking about a typical MAILBOX swap chain.
|
So how do swap chains work (quickly?) For simplicity, we're talking about a typical MAILBOX swap chain.
|
||||||
|
|
||||||
Next image is requested by the application.
|
Next image is requested by the application.
|
||||||
If the image is still valid, its handle is returned to the application. This is also known as the _backbuffer_.
|
If the image is still valid, its handle is returned to the application. This is also known as the _backbuffer_.
|
||||||
While the application can hold onto this image, they can draw anything they wish into it.
|
While the application can hold onto this image, they can draw anything they wish into it.
|
||||||
Once the application has finished rendering, it "presents" (note: the application is usually not directly presenting it to the screen)
|
Once the application has finished rendering, it "presents" - although the application isn't in charge of actually presenting it to the screen.
|
||||||
|
|
||||||
### How do swap chains work (in real life)
|
# How do swap chains work (in real life)
|
||||||
|
|
||||||
Okay this sounds all well and good, but how does this work in _real life_? On a typical desktop environment, we have
|
Okay this sounds all well and good, but how does this work in _real life_? On a typical desktop environment, we have
|
||||||
many different windows, some of which misbehave or malfunction and don't return and present images in time with our
|
many different windows, some of which misbehave or malfunction and don't return and present images in time with our
|
||||||
display. Some of them even present _faster_ than the display, so who is managing this?
|
display. Some of them even present _faster_ than the display, so who is managing this?
|
||||||
|
|
||||||
Now in this case, I'll be covering how Wayland compositors handle this, specifically KWin. While the same might apply to X11 environments,
|
First we have to remember that KWin is a graphics application, and it also follows the same rules as any other. Right now, KWin
|
||||||
Wayland is the future and it's way, way simpler to explain.
|
|
||||||
|
|
||||||
First we have to remember that KWin itself, _is_ a graphics application and it also follows the same rules as any other. Right now, KWin
|
|
||||||
is built on OpenGL technologies but uses GBM to present stuff to the screen. Now KWin in this example, is the Wayland _server_ and other
|
is built on OpenGL technologies but uses GBM to present stuff to the screen. Now KWin in this example, is the Wayland _server_ and other
|
||||||
applications are Wayland _clients_. This includes XWayland, which is simply wrapping the Xorg server as a Wayland client.
|
applications are Wayland _clients_. This includes XWayland, which is simply wrapping the Xorg server as a Wayland client.
|
||||||
|
|
||||||
1. Your Vulkan application wants a Wayland surface, and is running on KWin Wayland.
|
# What is GBM?
|
||||||
2. It uses
|
|
||||||
|
|
||||||
### What is GBM??
|
|
||||||
|
|
||||||
GBM stands for _"generic buffer management"_ and is also part of the Mesa project. It's mostly used to initialize EGL on DRM KMS. This is
|
GBM stands for _"generic buffer management"_ and is also part of the Mesa project. It's mostly used to initialize EGL on DRM KMS. This is
|
||||||
Also meaningless to most people, including me. When researching _what_ GBM is, it's infuriating that there's really no simple explanation
|
Also meaningless to most people, including me. When researching _what_ GBM is, it's infuriating that there's really no simple explanation
|
||||||
to what it enables.
|
to what it enables.
|
||||||
|
|
||||||
Okay, let's go with an example. You want to implement a desktop compositor, where do you begin?
|
|
||||||
|
|
||||||
Here's some simple requirements:
|
|
||||||
1. You want to make sure you're booted into DRM KMS.
|
|
||||||
|
|
||||||
So let's display something to the screen, such as
|
|
||||||
|
|
||||||
You may have heard how Nvidia fought against Mesa with it's GBM, with EGLStreams before eventually conceding and
|
You may have heard how Nvidia fought against Mesa with it's GBM, with EGLStreams before eventually conceding and
|
||||||
implementing GBM - this is why. Since Wayland compositors need to initialize graphics through DRM KMS, it eventually needs to allocate
|
implementing GBM - this is why. Since Wayland compositors need to initialize graphics through DRM KMS, it eventually needs to allocate
|
||||||
memory. It does this via calling the Mesa GBM, which then in turn calls the GPU specific stuff.
|
memory. It does this via calling the Mesa GBM, which then in turn calls the GPU specific stuff.
|
||||||
|
|
||||||
## Conclusion
|
|
||||||
|
|
||||||
I hope this article clears up any misconceptions about the Linux graphics stack, and I definitely learned a lot while researching
|
|
||||||
This. While this was a nice overview of the entire stack, it would be really helpful if we could apply in this in a practical fashion,
|
|
||||||
so that's what I'm going to cover in the next article!
|
|
||||||
|
|
|
@ -1,51 +0,0 @@
|
||||||
---
|
|
||||||
title: "Steam Offline Achievements and Why They Sometimes Don't work"
|
|
||||||
date: 2022-10-05
|
|
||||||
draft: true
|
|
||||||
tags:
|
|
||||||
- Steam
|
|
||||||
- Gaming
|
|
||||||
---
|
|
||||||
|
|
||||||
If you've been paying attention these last couple of months, the Steam Deck is now in people's hands
|
|
||||||
and people are starting to discover how bad Steam Offline mode is.
|
|
||||||
<!--more-->
|
|
||||||
Thankfully Valve is improving the situation
|
|
||||||
in every update but there is one thing they cant fix: Why do some games require you to be online for achievements
|
|
||||||
and some don't?
|
|
||||||
|
|
||||||
## What works
|
|
||||||
|
|
||||||
In the best case, the game in question is actually using the Steam API properly, as Steamworks
|
|
||||||
already keeps a local cache of achievements and stats that will eventually get uploaded back to Steam
|
|
||||||
once you enter Online Mode again. This is fine, and it's been working this way for years.
|
|
||||||
|
|
||||||
## What doesn't work
|
|
||||||
|
|
||||||
However, in some cases, it doesn't always end up this way. Let's take for example, Nier Automata
|
|
||||||
as this is what tipped me off to this issue. I sometimes take my Steam Deck willingly offline because
|
|
||||||
I share my library with my girlfriend, but remember that this will happen sooner or later on a handheld. I haven't
|
|
||||||
gotten too far on the PC version of Automata, so I'm still in the beginning part of the game. I enter the Amusement Park and
|
|
||||||
beat the boss there, and much to my surprise.... nothing? Now I normally don't get too worked up about achievements, but it's
|
|
||||||
kind of insane that I earned one, and now I have no easy way to get it back without cheating or restarting the game again. Eugh. Let's figure out what's going on.
|
|
||||||
|
|
||||||
## Theory
|
|
||||||
|
|
||||||
I have a sneaking suspicion what's going on here, but until I take apart the Nier binary I have no idea yet.
|
|
||||||
|
|
||||||
I suspect that before the game records the achievement with Steamworks, it checks whether it's online,
|
|
||||||
whether through it's through its own game servers (since automata has online services) or through Steamworks. Right now
|
|
||||||
I'm going to assume it's checking the Steamworks API, so we'll be looking for those API calls. Once it detects
|
|
||||||
you're not online, it decides to not even record Steam achievements. I have no idea why developers might do this,
|
|
||||||
since _Steamworks_ already maintains a local cache. This is also made clear in the Steamworks documentation:
|
|
||||||
|
|
||||||
INSERT IMAGE
|
|
||||||
|
|
||||||
## Reverse Engineering
|
|
||||||
|
|
||||||
First, we need to break the Steam DRM. The DRM is quite simple, and it's been broken before. Much more knowledgeable people
|
|
||||||
have written up about this format, but in short the actual executable is wrapped within a Steam stub that checks whether it's launched through Steam and then decrypts the binary.
|
|
||||||
|
|
||||||
I tried Steamless to decrypt the game, but that didn't work, so I opted to dump the binary when the game was running. Then,
|
|
||||||
I threw the executable into Ghidra:
|
|
||||||
|
|
Loading…
Add table
Reference in a new issue