I think this article is a misunderstanding of the real core of the issue. It is related to the distribution of ELF binary-only files (executables or shared libs)... or video games (or the steam client).<p>I have been playing on native elf/linux for more than 10 years, and ABI issues has been a nightmare (the worst being game devs or game engine devs forgetting to add the -static-libgcc and -static-libstdc++ options, since libgcc and libstdc++ ABIs are just HORRIBLE and not reliable even on the medium run).<p>I'll explain the "Right Way" down below, but let's warn people now: it requires more work to craft "correct" ELF files for binary-only distribution than for windows. FACT, deal with it, eat the bullet, etc... and 99% of game devs and many game engine devs DO NOT KNOW THAT.<p>Indeed, glibc is heavy on the usage of GNU ELF symbol "versions" (called version names) for its ABI, and cherry picking of the "right" version name is FULLY MANUAL.<p>Open source "toolchains" default to building "open source", aka for a symbol, it will select by default the most recent version, which is exactly what you DON'T WANT while building binaries for games!!<p>While building for a game, you want to select "not too recent" version names for your binaries, that to be able to load on "not too recent" distros. Because, and you can check it, glibc devs are _REALLY_ heavy on the usage of version names, and that for external <i>AND INTERNAL</i> symbols. (I put aside the nasty issue of the brand new ELF relative relocation only supported in latest ELF loaders...).<p>The cheap way is to have a "target"/not too recent glibc installed somewhere then link your game binaries with it. Easy to say as toolchain reconfiguration can be a nightmare (game engine builders are supposed to deal with that). But this is the most "easy" way to be sure not too recent version names get selected for symbols. And I don't talk about building properly a glibc... (yeah, it is sadistical).<p>"Not Too Recent" glibc ABI:<p><a href="https://sourceware.org/glibc/wiki/Glibc%20Timeline" rel="nofollow">https://sourceware.org/glibc/wiki/Glibc%20Timeline</a><p>First AAA vulkan native elf/linux games are from 2017/2019, then based on the previous document, the version names of a glibc close to 2.30 should be appropriate for video game distributed ELF files.<p>Now, there is a way (the "Right Way")to manually select the version names you want, it is documented in the second part of the page there:<p><a href="https://sourceware.org/binutils/docs/ld/VERSION.html" rel="nofollow">https://sourceware.org/binutils/docs/ld/VERSION.html</a><p>It means that for all distributed ELF files, the game devs, via some specific build system support, _MUST_ select the version name for earch symbol (or some presets) they use, and this does include the glibc _INTERNAL_ symbols too: for instance the glibc internal "libc_start" symbol is versioned, namely if you link with a glibc >= 2.34, your ELF executables will refuse to load on distros with a glibc < 2.34... whaaaaaaat?!<p>In practice, game devs after generating the ELF files they will distribute, must audit their version names, for instance with the command "$readelf -a -W some_game_elf_file", at the end of the output you have the "required version names". Then they would have to cherry pick "less recent" version names for the symbols with "too recent" version names.<p>If I recall properly, in glibc source code you have somewhere some text files with the list of version names per symbols.<p>Additional note: Ofc, all system interface ELF shared libs must be libdl-ed (dlopen/dlsym/dlclose) with proper fallback code paths. This will work around any version names in those shared libs.
Video game core system interface shared libs: vulkan loader->legacy libglvnd loader (or directly libGL)->CPU rendering, libasound (alsa-lib), libxkbcommon(-11) for user key symbols (if needed), x11 xcb-libs (wayland code is static in game binaries), and that's it.<p>At some point in time, we thought libdl-ing the libc itself... but I was told (have to be checked) that some specific libc runtime setup must be performed at process startup for some critical services, which setup code won't be run upon libdl-ing the libc. In this case, you would not have a main() function but the crude ELF entry point... which is nearly a main() anyway. That would have solved for good the issues of version names since everything would happen through libdl with its 3 symbols (dlopen/dlsym/dlclose) which have extremely old version names then are (at this time) "safe".<p>To check dependencies of ELF files, like the version names, "$readelf -a -W some_game_binary" and do inspect the NEEDED entries which should have only glibc libs (and private ELF shared libs with location relative to the process current working directory as you should avoid the usage of $ORIGIN like hell, namely ELF executable must manually verify the process current working directory is "correct" for their private stuff).<p>An alternative would be pure "IPC" based _SIMPLE_ system interfaces: The _real_ wayland core set of interfaces seems ok... but pulseaudio[012] IPC interfaces are just too complex, and obviously do fail hard stability in time (currently nothing beat the stability in time of the alsa-lib imperfect ABI... yeah, you still need free() from the libc). There is no IPC interfaces for vulkan3D (and those would have to be seriously tested for performance and probably tied to wayland, but shared memory command ring buffers with shared memory atomic pointers/counters may do the trick). Neither there are some IPC interfaces for user key symbols, probably because of the ultra-complex data format, xkb, and because the location and configuration of those user files are not rigorously defined. Joypad support is "linux device files", then is naturally "IPC-ed".<p>Don't forget, games want a small set of as simple as possible binary interfaces, and that very stable-in-time.