From: Zbigniew Jędrzejewski-Szmek Date: Tue, 2 Jun 2026 16:05:34 +0000 (+0200) Subject: Add DLOPEN macros that stamp the caller's ELF and use it to ensure executables list... X-Git-Tag: v261-rc3~17 X-Git-Url: http://git.ipfire.org/gitweb/index.cgi?a=commitdiff_plain;h=112b56575644c57112c3c6c425c1c2e5493e2b23;p=thirdparty%2Fsystemd.git Add DLOPEN macros that stamp the caller's ELF and use it to ensure executables list their dlopen dependencies (#42398) Currently almost all the dlopens happen in libbasic or libshared code, so the ELF dlopen notes all end up in libsystemd-shared. Many distributions split this library and various binaries in separate packages, and the library ends up with soft-dependencies, even though many binaries are either completely useless or do not work at all with the dlopen dependency. This also makes it impossible to know which executable uses which dlopen dependency without inspecting the source code. If someone only wants to add the soft dependencies from libshared they can just avoid parsing the executable binaries. By design the code in libbasic/libshared still does the stamping too, at lower priorities, so that libsystemd-shared will always list all the optional dependencies, and if one wants to build a minimal system by default, they can just parse libsystemd-shared dlopen notes, and ignore the individual executables. But for many distribution the current setup is insufficient and requires adding a ton of manual library dependencies, as many executables become effectively broken or useless without the dlopen dependencies installed (eg: resolved fails to start without libssl, repart can do basically nothing without blkid, etc). Add a new set of DLOPEN_ macros that wrap the dlopen_lib and also pull in the ELF note voodoo, so that the callers get their ELF binaries stamped too. Convert a bunch of callers to use the macro, and use `required` dependencies for the callers that do not work without the dlopen library being available. The one caveat is that, in order to avoid duplicating the exact same note in a binary due to multiple call sites, some `asm` voodoo is done instead of the previous bare-C section-creating macro. The drawback of this approach is that if `--gc-sections` is used to link the binary (as we do), then binutils >= 2.36 is required for the `SHF_GNU_RETAIN` flag. This effectively cuts off CentOS 9, so what I did here is adding an override in meson to detect missing support, and drop `SHF_GNU_RETAIN`. The build works, but on CentOS 9 there's no dlopen ELF notes anymore. Given it's just that version, and it goes EOL next year, that seems ok to me. The alternative is to drop the usage of `--gc-sections` on CentOS 9, or to accept duplicated notes everywhere, and both seem worse. End result: ``` $ readelf --notes build/systemd-executor Displaying notes found in: .note.gnu.property Owner Data size Description GNU 0x00000010 NT_GNU_PROPERTY_TYPE_0 Properties: x86 ISA needed: x86-64-baseline Displaying notes found in: .note.gnu.build-id Owner Data size Description GNU 0x00000014 NT_GNU_BUILD_ID (unique build ID bitstring) Build ID: 8a0c3db54adb79ae54e1432255011aa4ab583742 Displaying notes found in: .note.ABI-tag Owner Data size Description GNU 0x00000010 NT_GNU_ABI_TAG (ABI version tag) OS: Linux, ABI: 3.2.0 Displaying notes found in: .note.dlopen Owner Data size Description FDO 0x0000006b FDO_DLOPEN_METADATA Dlopen Metadata: [{"feature":"pam","description":"Support for LinuxPAM","priority":"recommended","soname":["libpam.so.0"]}] FDO 0x0000007c FDO_DLOPEN_METADATA Dlopen Metadata: [{"feature":"seccomp","description":"Support for Seccomp Sandboxes","priority":"recommended","soname":["libseccomp.so.2"]}] FDO 0x00000090 FDO_DLOPEN_METADATA Dlopen Metadata: [{"feature":"bpf","description":"Support firewalling and sandboxing with BPF","priority":"recommended","soname":["libbpf.so.1","libbpf.so.0"]}] FDO 0x000000a0 FDO_DLOPEN_METADATA Dlopen Metadata: [{"feature":"cryptsetup","description":"Support for disk encryption, integrity, and authentication","priority":"recommended","soname":["libcryptsetup.so.12"]}] FDO 0x00000078 FDO_DLOPEN_METADATA Dlopen Metadata: [{"feature":"mount","description":"Support for mount enumeration","priority":"recommended","soname":["libmount.so.1"]}] $ readelf --notes build/systemd Displaying notes found in: .note.gnu.property Owner Data size Description GNU 0x00000010 NT_GNU_PROPERTY_TYPE_0 Properties: x86 ISA needed: x86-64-baseline Displaying notes found in: .note.gnu.build-id Owner Data size Description GNU 0x00000014 NT_GNU_BUILD_ID (unique build ID bitstring) Build ID: dcd4568842e32da3e71be27db3def51c6b459994 Displaying notes found in: .note.ABI-tag Owner Data size Description GNU 0x00000010 NT_GNU_ABI_TAG (ABI version tag) OS: Linux, ABI: 3.2.0 Displaying notes found in: .note.dlopen Owner Data size Description FDO 0x00000075 FDO_DLOPEN_METADATA Dlopen Metadata: [{"feature":"mount","description":"Support for mount enumeration","priority":"required","soname":["libmount.so.1"]}] FDO 0x00000072 FDO_DLOPEN_METADATA Dlopen Metadata: [{"feature":"selinux","description":"Support for SELinux","priority":"recommended","soname":["libselinux.so.1"]}] ``` --- 112b56575644c57112c3c6c425c1c2e5493e2b23