In der Community der Systemverwaltungsentwickler von systemd wird über die Reduzierung der Abhängigkeiten der Bibliothek libsystemd diskutiert, die nicht nur mit Komponenten von systemd verbunden ist, sondern auch mit vielen externen Anwendungen. Zum Beispiel verwenden in Fedora mehr als 150 Pakete libsystemd als Abhängigkeit. Der Initiator der Diskussion ist der Ansicht, dass die Einbeziehung zusätzlicher externer Bibliotheken, die nicht von den Entwicklern von systemd kontrolliert werden, die Angriffsfläche im Falle eines Kompromisses dieser externen Bibliotheken erheblich vergrößert, ähnlich wie es bei der Bibliothek liblzma der Fall war.
Neben liblzma und glibc werden in libsystemd auch die Bibliotheken libzstd, liblz4 und libgcrypt geladen, wobei die Aufrechterhaltung der Sicherheit zu einer kritisch wichtigen Aufgabe wird. libsystemd bietet Zugriff auf 12 grundlegende APIs (sd-bus, sd-daemon, sd-device, sd-event, sd-hwdb, sd-id128, sd-journal, sd-login, sd-netlink, sd-network, sd-path und sd-resolve). Es kann Situationen geben, in denen eine Anwendung, die libsystemd beispielsweise nur für den Aufruf der Funktion sd_notify verwendet, um systemd über Statusänderungen zu informieren, oder sd_journal, um Daten zu protokollieren, mit allen anderen Bibliotheken und API-Handlern verbunden wird. Als Lösung wird vorgeschlagen, libsystemd in mehrere separate Bibliotheken zu unterteilen, die für einzelne APIs verantwortlich sind, wodurch externe Abhängigkeiten nur dort geladen werden, wo sie erforderlich sind.
Die Entwickler von systemd halten eine Trennung für unangemessen, da die in libsystemd vorhandenen Handler miteinander verknüpft sind. Eine Trennung würde einen enormen Aufwand erfordern und entweder zu einem Effizienzverlust oder zu Code-Duplikation führen. Um den Speicherverbrauch in libsystemd zu reduzieren, wurde kürzlich eine Änderung beschlossen, die die dynamische Ladeimplementierung der Bibliotheken liblzma, libzstd und liblz4 mittels des Aufrufs dlopen() ermöglicht, wenn deren Funktionen tatsächlich benötigt werden. Eine ähnliche Änderung wird ab der nächsten Version auch für libgcrypt umgesetzt.
Eine solche Entscheidung wurde kritisiert, da anstelle einer klaren und direkten Verknüpfung die Lade von Drittanbieterbibliotheken nun nicht mehr explizit erfolgt, was die Diagnose erschwert, da die Verbindung der API-Aufrufe von libsystemd mit den Aufrufen von Funktionen aus externen Bibliotheken nicht offensichtlich ist. Der Übergang zur Lade über dlopen() verändert an sich nicht die Architektur, sondern verbirgt lediglich externe Komponenten vor den Entwicklern und Nutzern.
Lenart Pottering hat entschieden dagegen, die libsystemd in mehrere Bibliotheken zu teilen, da dieser Schritt die gemeinsame Nutzung des Codes in systemd erheblich komplizieren würde und es notwendig wäre, alle internen Handler als öffentlich zu kennzeichnen oder sie in jede Bibliothek statisch einzubinden. Im ersten Fall würde dies Probleme mit der Stabilität der API und den Namensräumen mit sich bringen, im zweiten Fall zu einer Vergrößerung aufgrund von Code-Duplikaten führen.
Für die nächste Version umgesetzte, bedarfsgerechte Ladefunktion für externe Bibliotheken wird von Lenart als optimale Strategie angesehen. Das Problem, Daten über dynamisch geladene Bibliotheken zu erhalten, soll durch das Hinzufügen zusätzlicher Felder mit Informationen über solche dynamischen Abhängigkeiten in ELF-Dateien gelöst werden, die von Debuggern verarbeitet und in der Ausgabe des Tools readelf angezeigt werden können.
Was die Bindung von libsystemd an eine große Anzahl von Anwendungen betrifft, riet Lennart den Anwendungsentwicklern, libsystemd nicht für eine einzelne Funktion zu laden, sondern einen Protokollhandler auf Anwendungsebene zu implementieren. Zum Beispiel ist die Implementierung der Funktionalität von sd_notify() relativ trivial und kann in wenigen Codezeilen unter Verwendung von UNIX-Sockets (AF_UNIX) erfolgen. Eine solche isolierte Implementierung von sd_notify ist seit 2017 für OpenSSH verfügbar und wurde kürzlich in den tragbaren Branch von OpenSSH 9.8 aufgenommen, dessen Veröffentlichung für die Mitte des Sommers geplant ist.
Quelle: opennet.ru
