oracular (7) daemon.7.gz

Provided by: manpages-de_4.23.1-1_all bug

BEZEICHNUNG

       daemon - Schreiben und Paketieren von System-Daemons

BESCHREIBUNG

       Ein Daemon ist ein Diensteprozess, der im Hintergrund läuft und das System beaufsichtigt oder
       Funktionalitäten für andere Prozesse bereitstellt. Traditionell werden Daemons so implementiert, dass sie
       einem ursprünglich aus SysV-Unix stammenden Schema folgen. Moderne Daemons sollten einem einfacheren,
       aber dennoch leistungsfähigeren Schema folgen (hier »neuartige« Daemons genannt), wie es von systemd(1)
       implementiert wird. Diese Handbuchseite deckt beide Schemata ab und enthält insbesondere Empfehlungen für
       Daemons, die im Systemd-Init-System aufgenommen werden sollen.

   SysV-Daemons
       Wenn ein traditioneller SysV-Daemon startet, sollte er die folgenden Schritte als Teil seiner
       Initialisierung ausführen. Beachten Sie, dass diese Schritte von neuartigen Daemons (siehe unten) nicht
       benötigt werden. Sie sollten daher nur implementiert werden, wenn die Kompatibilität zu SysV essenziell
       ist.

        1. Alle offenen Dateideskriptoren außer der Standardeingabe, -ausgabe und -fehlerausgabe (d.h. den drei
           ersten Dateideskriptoren 0, 1, 2) werden geschlossen. Dies stellt sicher, dass kein versehentlich
           geöffneter Dateideskriptor im Daemon-Prozess verbleibt. Unter Linux wird dies am besten dadurch
           implementiert, dass durch /proc/self/fd iteriert wird, mit der Rückfalloption, von Dateideskriptor 3
           bis zu dem von getrlimit() für RLIMIT_NOFILE zurückgelieferten Wert durchzuiterieren.

        2. Alle Signal-Handler werden auf ihre Vorgaben zurückgesetzt. Dies erfolgt am besten durch Iteration
           durch alle verfügbaren Signale bis zur Grenze von _NSIG und dem Zurücksetzen dieser auf SIG_DFL.

        3. Zurücksetzen der Signal-Maske mittels sigprocmask().

        4. Bereinigen des Umgebungsblocks, Entfernen oder Zurücksetzen der Umgebungsvariablen, die einen
           negativen Einfluss auf die Laufzeit des Daemons haben könnten.

        5. Aufrufen von fork(), um einen Hintergrundprozess zu erzeugen.

        6. Aufruf von setsid() im Kind, um von jedem Terminal zu trennen und eine unabhängige Sitzung zu
           erzeugen.

        7. Erneuter Aufruf von fork() im Kind, um sicherzustellen, dass der Daemon niemals wieder ein Terminal
           erlangen kann. (Dies ist relevant, falls das Programm und alle seine Abhängigkeiten nicht sorgfältig
           genug sind, um bei jedem »open()«-Aufruf, der möglicherweise einen TTY-Geräteknoten erlangen könnte,
           stets »O_NOCTTY« festzulegen.)

        8. Aufruf von exit() im ersten Kind, so dass nur das zweite Kind (der eigentliche Daemon) verbleibt.
           Dies stellt sicher, dass der Daemon-Prozess PID 1 als neuen Elternprozess bekommt, wie das bei allen
           Daemons der Fall sein sollte.

        9. Verbinden von /dev/null im Daemon-Prozess mit der Standardeingabe, -ausgabe und -fehlerausgabe.

       10. Zurücksetzen der Umask auf 0 im Daemon-Prozess, so dass die an open(), mkdir() und ähnliche
           weitergegebenen Dateimodi direkt die Zugriffsmodi auf die erstellten Dateien und Verzeichnisse
           steuern.

       11. Ändern des aktuellen Verzeichnisses im Daemon-Prozess auf das Wurzelverzeichnis (/), um zu vermeiden,
           dass der Daemon unfreiwillig die Einhängepunkte vor dem Aushängen blockiert.

       12. Schreiben der Daemon-PID (wie von getpid() zurückgeliefert) im Daemon-Prozess in eine PID-Datei,
           beispielsweise /run/foobar.pid (für einen hypothetischen Daemon »foobar«), um sicherzustellen, dass
           der Daemon nicht mehr als einmal gestartet wird. Dies muss so implementiert werden, dass kein
           Ressourcenwettlauf möglich ist, so dass die PID-Datei nur aktualisiert wird, wenn gleichzeitig
           sichergestellt ist, dass die vorher in der PID-Datei gespeicherte PID nicht mehr existiert oder zu
           einem fremden Prozess gehört.

       13. Abgeben der Privilegien im Daemon-Prozess, falls möglich und zutreffend.

       14. Benachrichtigen des ursprünglich gestarteten Prozesses aus dem Daemon-Prozess, dass die
           Initialisierung abgeschlossen ist. Dies kann über eine unbenannte Pipe oder einen ähnlichen
           Kommunikationskanal, der vor dem ersten fork() erstellt wurde und daher in sowohl dem ursprünglichen
           als auch dem Daemon-Prozess verfügbar ist, erfolgen.

       15. Aufrufen von exit() im ursprünglichen Prozess. Der Prozess, der den Daemon gestartet hat, muss in der
           Lage sein, sich darauf zu verlassen, dass dieser exit() passiert, nachdem die Initialisierung
           abgeschlossen und die externen Kommunikationskanäle etabliert und zugreifbar sind.

       Die BSD-Funktion daemon() sollte nicht verwandt werden, da sie nur eine Teilmenge dieser Schritte
       implementiert.

       Ein Daemon, der Kompatibilität mit SysV-Systemen bereitstellen muss, sollte das oben dargestellte Schema
       implementieren. Es wird allerdings empfohlen, dieses Verhalten über eine Befehlszeilenoption optional und
       konfigurierbar zu gestalten, um die Fehlersuche zu erleichtern und um die Integration in Systeme, die
       Systemd verwenden, zu erleichtern.

   Neuartige Daemons
       Moderne Dienste für Linux sollten als neuartige Daemons implementiert werden. Dies erleichtert die
       Beaufsichtigung und Steuerung zur Laufzeit und vereinfacht ihre Implementierung.

       Zur Entwicklung eines neuartigen Daemons muss keiner der für SysV-Daemons empfohlenen
       Initialisierungsschritte implementiert werden. Bei neuartigen Init-Systemen wie Systemd sind diese alle
       redundant. Da einige dieser Schritte sogar die Prozessüberwachung, Dateideskriptorweitergabe und andere
       Funktionalitäten des Diensteverwalters stören, wird empfohlen, sie nicht auszuführen, wenn sie als
       neuartiger Dienst ausgeführt laufen.

       Beachten Sie, dass neuartige Init-Systeme die Ausführung eines Daemon-Prozesses in einem sauberen
       Prozesskontext garantieren: Es wird garantiert, dass der Umgebungsblock bereinigt ist, dass
       Signal-Handler und -Masken zurückgesetzt sind und dass kein übrig gebliebener Dateideskriptor
       weitergegeben wird. Daemons werden in ihrer eigenen Sitzung ausgeführt, wobei die Standardeingabe mit
       /dev/null und die Standardausgabe/Standardfehlerausgabe mit dem Protokollierungsdienst
       systemd-journald.service(8) verbunden ist, außer dies ist anders konfiguriert. Die Umask ist
       zurückgesetzt.

       Es wird empfohlen, dass neuartige Daemons folgendes implementieren:

        1. Falls zutreffend sollte der Daemon über den Abschluss des Startens oder Statusaktualisierungen den
           Diensteverwalter mittels der Schnittstelle sd_notify(3), insbesondere READY=1 und STATUS=…,
           informieren.

        2. Falls SIGTERM empfangen wird, soll der Daemon sich herunterfahren und sauber beenden. Es sollte
           mittels sd_notify(3) eine Stopp-Benachrichtigung gesandt werden.

        3. Falls SIGHUP empfangen wird, sollen die Konfigurationsdateien, falls zutreffend, neu geladen werden.
           Dies sollte mit Benachrichtigungen mittels sd_notify(3) kombiniert werden: RELOADING=1 und READY=1.

        4. Es soll ein korrekter Exit-Code vom Haupt-Daemon-Prozess bereitgestellt werden, da dieser vom
           Diensteverwalter benutzt wird, um Dienstefehler und Probleme zu erkennen. Es wird empfohlen, dem in
           LSB-Empfehlungen für SysV-Init-Skripte[1] definierten Exit-Code-System zu folgen.

        5. Falls möglich und zutreffend sollte die Steuerschnittstelle mittels des D-Bus-IPC-Systems zugänglich
           gemacht und ein Bus-Name als letzten Schritt in der Initialisierung erlangt werden.

        6. Stellen Sie eine .service-Unit-Datei zur Integration mit Systemd bereit, die Informationen zum
           Starten, Beenden und anderseitigen Verwalten des Daemons enthält. Siehe systemd.service(5) für
           Details.

        7. Verlassen Sie sich soweit möglich auf die Funktionalitäten des Diensteverwalters, den Zugriff des
           Daemons auf Dateien, Dienste und andere Ressourcen zu begrenzen, d.h. im Falle von Systemd, verlassen
           Sie sich auf Systemds Ressourenbegrenzungssteuerung statt Ihre eigene zu implementieren, verlassen
           Sie sich auf den Privilegienabgabe-Code von Systemd, statt ihn in Ihrem Daemon zu implementieren und
           so weiter. Siehe systemd.exec(5) für die verfügbaren Steuerungen.

        8. Falls D-Bus verwandt wird, ermöglichen Sie die Bus-Aktivierung Ihres Daemons, indem Sie eine
           D-Bus-Dienste-Aktivierungsdatei bereitstellen. Dies hat eine Reihe von Vorteilen: Ihr Daemon kann
           erst bei Bedarf gestartet werden; er kann parallel zu anderen Daemons, die ihn benötigen, gestartet
           werden — wodurch die Parallelisierung und die Systemstartgeschwindigkeit maximiert wird; Ihr Daemon
           kann im Fehlerfall neu gestartet werden, ohne eine Bus-Anfrage zu verlieren, da die Bus-Warteschlagen
           aktivierbare Dienste erbitten. Siehe unten für Details.

        9. Falls Ihr Daemon Dienste für andere lokale Prozesse oder Clients in der Ferne über ein Socket
           anbietet, sollte es gemäß des nachfolgend dargestellten Schemas Socket-aktivierbar sein. Ähnlich der
           D-Bus-Aktivierung ermöglicht dies bedarfsgesteuertes Starten von Diensten sowie verbesserte
           Parallelisierung beim Starten der Dienste. Für zustandslose Protokolle (wie Syslog, DNS) kann ein
           Daemon, der Socket-basierte Aktivierung implementiert, auch ohne Verlust einer einzelnen Anfrage neu
           gestartet werden. Siehe unten für Details.

       10. Falls der Dienst Sockets oder andere Dateien selbst öffnet und diese Dateideskriptoren einen Neustart
           überleben sollen, sollte der Daemon sie im Diensteverwalter mittels sd_notify(3) mit FDSTORE=1
           speichern.

       11. Statt den Aufruf syslog() zum direkten Protokollieren in den Systemprotokolldienst zu verwenden, kann
           ein neuartiger Daemon einfach auf die Standardfehlerausgabe mittels fprintf() protokollieren, was
           dann an Syslog weitergeleitet wird. Falls Protokollierungsstufen notwendig sind, können diese durch
           Voranstellen von Zeichenketten wie »<4>« (für Protokollierungsstufe 4 »WARNING« im
           Syslog-Prioritätsschema) vor individuellen Protokollierzeilen kodiert werden. Dies folgt einem
           ähnlichen Stil wie das printk()-Stufensystem des Linux-Kernels. Für Details siehe sd-daemon(3) und
           systemd.exec(5).

       12. Da neuartige Daemons ohne ein steuerndes TTY (aber sie selbst als ihren eigenen Sitzungsleiter)
           aufgerufen werden, sollte sichergestellt werden, dass bei open(2)-Aufrufen, die möglicherweise einen
           TTY-Geräteknoten referenzieren, stets O_NOCTTY festgelegt wird, so dass nicht versehentlich ein
           steuerndes TTY erlangt wird.

       Diese Empfehlungen sind ähnlich zu, aber nicht identisch mit den Apple-MacOS-X-Daemon-Anforderungen[2].

AKTIVIERUNG

       Neuartige Init-Systeme stellen eine Reihe von zusätzlichen Mechanismen bereit, um Dienste zu aktivieren.
       Details dazu weiter unten. Es ist typisch, dass Dienste konfiguriert wurden, über mehr als einen
       Mechanismus gleichzeitig aktiviert zu werden. Beispielsweise könnte in einem Systemd-System
       bluetoothd.service aktiviert werden, wenn eine Bluetooth-Hardware eingesteckt wird oder wenn eine
       Anwendung mittels D-Bus auf seine Programmierschnittstelle zugreift. Oder ein Drucker-Server-Daemon
       könnte aktiviert werden, wenn Daten auf einem IPP-Port ankommen oder wenn ein Drucker eingesteckt wird
       oder wenn eine Datei im Drucker-Spool-Verzeichnis in die Warteschlange kommt. Selbst für Dienste, die
       dazu gedacht sind, beim Systemstart bedingungslos zu starten, ist es eine gute Idee, einige der unten
       dargestellten verschiedenen Aktivierungsschemata zu implementieren, um die Parallelisierung zu
       maximieren. Falls ein Daemon einen D-Bus-Dienst implementiert oder an einem Socket auf Anfragen wartet,
       erlaubt die Implementierung des kompletten Bus- und Socket-Aktivierungsschematas das Starten des Daemons
       mit seinen Clients parallel durchzuführen (womit der Systemstart beschleunigt wird), da bereits alle
       Kommunikationskanäle etabliert sind und keine Anfrage verloren geht, da Client-Anfragen vom Bus-System in
       Warteschlangen gestellt werden (im Falle von D-Bus) oder durch den Kernel (im Falle von Sockets), bis die
       Aktivierung abgeschlossen ist.

   Aktivierung beim Systemstart
       Daemons der alten Art werden typischerweise exklusiv beim Systemstart (oder manuell durch den
       Systemadministrator) mittels SysV-Init-Skripten aktiviert, wie dies in der LSB Linux Standard Base
       Kern-Spezifikation[1] dargestellt ist. Diese Methode wird universell auf Linux-Init-Systemen unterstützt,
       sowohl bei denen der alten Art als auch bei neuartigen. Unter anderen Problemen haben die
       SysV-Init-Skripte den Nachteil, Shell-Skripte im Systemstartprozess zu involvieren. Neuartige
       Init-Systeme verwenden im Allgemeinen aktualisierte Versionen der Aktivierung, sowohl während des
       Systemstarts als auch während der Laufzeit und verwenden minimalere Dienstebeschreibungsdateien.

       Falls der Entwickler oder Administrator in Systemd sicherstellen möchte, dass ein Dienst oder eine andere
       Unit automatisch beim Systemstart aktiviert ist, wird empfohlen, einen Symlink auf die Unit-Datei im
       Verzeichnis .wants/ von entweder multi-user.target oder graphical.target, die normalerweise als
       Systemstartziele beim Systemstart verwandt werden, zu legen. Siehe systemd.unit(5) für Details über die
       Verzeichnisse .wants/ und systemd.special(7) für Details über die zwei Systemstartziele.

   Socket-basierte Aktivierung
       Um die Parallelisierung und Robustheit zu maximieren und die Konfiguration und Entwicklung zu
       vereinfachen, wird für alle neuartigen Daemons empfohlen, die über Warten an Sockets kommunizieren, eine
       Socket-basierte Aktivierung zu verwenden. In einem Socket-basierten Aktivierungsschema wird die
       Erstellung und das Binden des Sockets, an dem gewartet werden soll, als primären Kommunikationskanal von
       Daemons mit lokalen (und manchmal fernen) Clients aus dem Daemon-Code in den Diensteverwalter verschoben.
       Basierend auf einer Daemon-basierten Konfiguration installiert der Diensteverwalter die Sockets und gibt
       sie an die erstellten Prozesse, sobald der respektive Daemon gestartet wird. Optional kann die
       Aktivierung des Dienstes verzögert werden, bis der erste eingehende Verkehr auf dem Socket eintrifft, um
       eine bedarfsgesteuerte Aktivierung von Daemons zu realisieren. Allerdings ist der Hauptvorteil dieses
       Schemas, dass alle Anbieter und Konsumenten des Sockets parallel gestartet werden können, sobald alle
       Sockets etabliert sind. Zusätzlich können Daemons neugestartet werden und dabei nur eine minimale Anzahl
       an Client-Transaktionen verlieren oder sogar überhaupt keine Client-Anfrage (Letzteres stimmt
       insbesondere für zustandslose Protokolle wie DNS oder Syslog), da das Socket während des Neustarts
       angebunden und zugreifbar verbleibt und alle Anfragen in einer Warteschlange verbleiben, während der
       Daemon sie nicht verarbeiten kann.

       Neuartige Daemons, die Socket-Aktivierung unterstützen, müssen in der Lage sein, Sockets vom
       Diensteverwalter zu erhalten, statt sie selbst zu erstellen und sich daran zu binden. Für Details über
       die Programmierschnittstellen für dieses von Systemd bereitgestellte Schema, siehe sd_listen_fds(3) und
       sd-daemon(3). Für Details über die Portierung bestehender Daemons zu Socket-basierter Aktivierung, siehe
       unten. Mit minimalem Einsatz ist es möglich, Socket-basierte Aktivierung zusätzlich zu traditioneller
       interner Socket-Erstellung in der gleichen Codebasis zu erstellen, um sowohl neuartige als auch
       Init-Systeme der alten Art im gleichen Daemon-Programm zu unterstützen.

       Systemd implementiert Socket-basierte Aktivierung mittels .socket-Units, die in systemd.socket(5)
       beschrieben sind. Wenn Socket-Units für Socket-basierte Aktivierung konfiguriert werden, ist es
       wesentlich, dass alle Sockets, bei denen auf Anfragen gewartet wird, durch eine spezielle Ziel-Unit
       sockets.target hereingezogen werden. Es wird empfohlen, eine Anweisung WantedBy=sockets.target in den
       Abschnitt »[Install]« zu setzen, um eine solche Abhängigkeit automatisch bei der Installation einer
       Socket-Unit hinzuzufügen. Die notwendigen Ordnungs-Abhängigkeiten werden für alle Socket-Units implizit
       erstellt, falls DefaultDependencies=no nicht gesetzt ist. Für weitere Informationen über sockets.target,
       siehe systemd.special(7). Es ist nicht notwendig oder empfohlen, zusätzliche Abhängigkeiten auf
       Socket-Units abzulegen (zum Beispiel von multi-user.target oder ähnlichem), wenn eine in sockets.target
       installiert ist.

   Bus-basierte Aktivierung
       Wenn das D-Bus-IPC-System für die Kommunikation mit Clients verwandt wird, sollten neuartige Daemons
       Bus-Aktivierung verwenden, so dass sie automatisch aktiviert werden, wenn eine Client-Anwendung auf ihre
       IPC-Schnittstelle zugreift. Dies wird in D-Bus-Dienste-Dateien (die nicht mit Systemds
       Dienste-Unit-Dateien durcheinandergebracht werden dürfen) konfiguriert. Um sicherzustellen, dass D-Bus
       Systemd verwendet, um den Daemon zu starten und zu verwalten, verwenden Sie die Anweisung SystemdService=
       in diesen Dienste-Dateien, um den passenden Systemd-Dienst für einen D-Bus-Dienst zu konfigurieren.
       Stellen Sie beispielsweise für einen D-Bus-Dienst, dessen D-Bus-Aktivierungsdatei
       org.freedesktop.RealtimeKit.service heißt, sicher, dass SystemdService=rtkit-daemon.service in dieser
       Datei gesetzt ist, um ihn an den Systemd-Dienst rtkit-daemon.service zu binden. Dies wird benötigt, um
       sicherzustellen, dass der Daemon ohne Ressourcenwettläufe gestartet wird, wenn er über mehrere
       Mechanismen simultan aktiviert wird.

   Geräte-basierte Aktivierung
       Oft sollen Daemons, die einen besonderen Hardwaretyp verwalten, nur aktiviert werden, wenn die Hardware
       der entsprechenden Art eingesteckt oder andernfalls verfügbar gemacht wird. In einem neuartigen
       Init-System ist es möglich, die Aktivierung an Hardware-Einsteck-/Aussteck-Ereignisse zu binden. In
       Systemd können Kernel-Geräte, die in dem Gerätebaum sysfs/udev auftauchen, als Units offengelegt werden,
       falls sie mit der Zeichenkette »systemd« markiert sind. Wie andere Arten von Units können sie dann andere
       Units bei der Aktivierung (z.B. beim Einstecken) hereinziehen, und daher Geräte-basierte Aktivierung
       implementieren. Systemd-Abhängigkeiten können in der Udev-Datenbank mittels der Eigenschaft
       SYSTEMD_WANTS= kodiert werden. Siehe systemd.device(5) für Details. Oft ist es schöner, einen Dienst von
       Geräten nur indirekt über dedizierte Ziele hereinzuziehen. Beispiel: Statt bluetoothd.service von alle
       den verschiedenen Bluetooth-Dongles und anderen verfügbaren Hardwaren hereinzuziehen, ziehen Sie von
       ihnen bluetooth.target herein und dann bluetoothd.service von diesem Ziel. Dies stellt eine nettere
       Abstraktion bereit und ermöglicht Administratoren die Option, bluetoothd.service über einen Symlink
       bluetooth.target.wants/ uniform mit einem Befehl der Art enable von systemctl(1) zu steuern, statt den
       Udev-Regelsatz zu bearbeiten.

   Pfadbasierte Aktivierung
       Oft können Laufzeit-Daemons, die Spool-Dateien oder -Verzeichnisse (wie bei einem Drucksystem)
       verarbeiten, verzögert werden, bis diese Dateisystemobjekte den Zustand ändern oder nicht mehr leer sind.
       Neuartige Init-Systeme stellen einen Weg bereit, die Diensteaktivierung an Dateisystemänderungen zu
       binden. Systemd implementiert dieses Schema mittels in .path-Units konfigurierter pfadbasierter
       Aktivierung, wie in systemd.path(5) skizziert.

   Timer-basierte Aktivierung
       Einige Daemons, die Aufräumaufgaben erledigen, die regelmäßig ausgeführt werden sollen, ziehen aus
       Timer-basierter Aktivierung einen Nutzen. In Systemd ist dies mittels .timer-Units implementiert, wie in
       systemd.timer(5) beschrieben.

   Andere Formen der Aktivierung
       Es wurden andere Formen der Aktivierung vorgeschlagen und in einigen Systemen implementiert. Allerdings
       gibt es oft einfachere und bessere Alternativen oder sie können als Kombination der obigen Schemata
       zusammengestellt werden. Beispiel: Manchmal erscheint es nützlich, Daemons oder .socket-Units zu starten,
       wenn eine bestimmte IP-Adresse an einer Netzwerkschnittstelle konfiguriert ist, da Netzwerk-Sockets an
       diese Adresse gebunden werden sollen. Eine Alternative zur Implementierung hiervon ist die Verwendung der
       Socket-Option IP_FREEBIND/IPV6_FREEBIND von Linux, die mittels FreeBind=yes in Systemd-Socket-Dateien
       erreichbar ist (siehe systemd.socket(5) für Details). Diese Option erlaubt Sockets, wenn sie aktiviert
       ist, an nichtlokale, nichtkonfigurierte IP-Adressen gebunden zu werden und erlaubt damit Anbindungen an
       bestimmte IP-Adressen, bevor diese tatsächlich verfügbar werden; dies macht eine solche explizite
       Abhängigkeit auf die konfigurierte Adresse redundant. Ein anderer oft vorgeschlagener Auslöser für
       Dienste-Aktivierung ist niedrige Systemlast. Auch hier könnte allerdings ein überzeugender Ansatz sein,
       die Funktionalitäten des Betriebssystems korrekt zu benutzen, insbesondere des CPU- oder E/A-Schedulers
       von Linux. Anstatt Aufträge vom Anwenderbereich, basierend auf der Überwachung des
       Betriebssystem-Schedulers, einzuplanen, ist es empfehlenswert, die Einplanung von Prozessen dem
       Betriebssystem-Scheduler selbst zu überlassen. Systemd stellt einen feingranularen Zugriff auf die CPU-
       und E/A-Scheduler bereit. Falls ein vom Diensteverwalter ausgeführter Prozess den Umfang der für andere
       Prozesse verfügbaren CPU- oder E/A-Bandbreite nicht negativ beeinflussen soll, sollte er mit
       CPUSchedulingPolicy=idle und/oder IOSchedulingClass=idle konfiguriert werden. Optional kann dies mit
       Timer-basierter Aktivierung kombiniert werden, um Hintergrund-Aufträge während der Laufzeit und mit
       minimalen Auswirkungen auf das System einzuplanen und ihn aus der Systemstartphase selbst zu entfernen.

INTEGRATION MIT SYSTEMD

   Schreiben von Systemd-Unit-Dateien
       Beim Schreiben von Systemd-Unit-Dateien wird empfohlen, die folgenden Vorschläge zu berücksichtigen:

        1. Falls möglich, nutzen Sie die Einstellung Type=forking in Dienstedateien nicht. Falls Sie es aber
           machen, stellen Sie sicher, den PID-Dateipfad mit PIDFile= zu setzen. Siehe systemd.service(5) für
           Details.

        2. Falls Ihr Daemon einen D-Bus-Namen auf dem Bus registriert, stellen Sie sicher, falls möglich
           Type=dbus in der Dienstedatei zu verwenden.

        3. Setzen Sie eine gut lesbare Beschreibung in Description=.

        4. Deaktivieren Sie DefaultDependencies= nicht, außer Sie wissen genau, was Sie tun und Ihre Unit ist in
           der frühen Systemstartphase oder im späten Herunterfahren beteiligt.

        5. Normalerweise werden wenige, falls überhaupt, Abhängigkeiten explizit definiert werden müssen. Falls
           Sie allerdings explizite Abhängigkeiten definieren, beziehen Sie sich nur auf Units, die in
           systemd.special(7) aufgeführt sind oder auf Namen, die von Ihrem eigenen Paket bekanntgegeben sind,
           um Ihre Unit-Datei Betriebssystem-unabhängig zu halten.

        6. Nehmen Sie einen Abschnitt »[Install]« auf, der die Installationsinformation für die Unit-Datei
           enthält. Siehe systemd.unit(5) für Details. Um Ihren Dienst beim Systemstart zu aktivieren, fügen Sie
           eine Anweisung WantedBy=multi-user.target oder WantedBy=graphical.target hinzu. Um Ihr Socket beim
           Systemstart zu aktivieren, fügen Sie WantedBy=sockets.target hinzu. Normalerweise wollen Sie auch
           sicherstellen, dass bei der Installation Ihres Dienstes auch Ihr Socket installiert wird, daher fügen
           Sie Also=foo.socket in Ihrer Dienstedatei foo.service für ein hypothetisches Programm foo hinzu.

   Systemd-Dienstedateien installieren
       Zum Bauinstallationszeitpunkt (d.h. make install während des Paketbaus) wird empfohlen, dass Pakete ihre
       Systemd-Unit-Dateien im Verzeichnis, das von pkg-config systemd --variable=systemdsystemunitdir (für
       Systemdienste) oder pkg-config systemd --variable=systemduserunitdir (für Benutzerdienste)
       zurückgeliefert wird, zu installieren. Damit wird der Dienst im System für explizite Anfragen verfügbar
       gemacht, aber nicht beim Systemstart automatisch aktiviert. Optional sollten während der
       Paketinstallation (z.B. rpm -i durch den Administrator) Symlinks in den
       Systemd-Konfigurationsverzeichnissen mit dem Befehl enable des Werkzeuges systemctl(1) erstellt werden,
       um sie beim Systemstart automatisch zu aktivieren.

       Für Pakete, die autoconf(1) verwenden, wird empfohlen, einen Configure-Skript-Auszug wie den
       nachfolgenden zu verwenden, um den Unit-Installationspfad während der Quellkonfiguration zu ermitteln:

           PKG_PROG_PKG_CONFIG()
           AC_ARG_WITH([systemdsystemunitdir],
                [AS_HELP_STRING([--with-systemdsystemunitdir=DIR], [Directory for systemd service files])],,
                [with_systemdsystemunitdir=auto])
           AS_IF([test "x$with_systemdsystemunitdir" = "xyes" -o "x$with_systemdsystemunitdir" = "xauto"], [
                def_systemdsystemunitdir=$($PKG_CONFIG --variable=systemdsystemunitdir systemd)

                AS_IF([test "x$def_systemdsystemunitdir" = "x"],
              [AS_IF([test "x$with_systemdsystemunitdir" = "xyes"],
               [AC_MSG_ERROR([systemd support requested but pkg-config unable to query systemd package])])
               with_systemdsystemunitdir=no],
              [with_systemdsystemunitdir="$def_systemdsystemunitdir"])])
           AS_IF([test "x$with_systemdsystemunitdir" != "xno"],
                 [AC_SUBST([systemdsystemunitdir], [$with_systemdsystemunitdir])])
           AM_CONDITIONAL([HAVE_SYSTEMD], [test "x$with_systemdsystemunitdir" != "xno"])

       Dieser Schnipsel ermöglicht die automatische Installation der Unit-Dateien auf Systemd-Maschinen und
       erlaubt optional ihre Installation selbst auf Maschinen, denen Systemd fehlt. (Die Anpassung des
       Schnipsels auf das Benutzer-Unit-Verzeichnis bleibt als Aufgabe für den Leser.)

       Damit make distcheck weiterhin funktioniert, wird auf automake(1) basierenden Projekten zusätzlich
       empfohlen, folgendes zur Datei Makefile.am auf oberster Ebene hinzuzufügen:

           AM_DISTCHECK_CONFIGURE_FLAGS = \
             --with-systemdsystemunitdir=$$dc_install_base/$(systemdsystemunitdir)

       Schließlich sollten Unit-Dateien im System mit einem Automake-Ausschnitt der folgenden Art installiert
       werden:

           if HAVE_SYSTEMD
           systemdsystemunit_DATA = \
             foobar.socket \
             foobar.service
           endif

       In der .spec-Datei von rpm(8) verwenden Sie Schnipsel der folgenden Art, um Dienste während der
       Installation/Deinstallation zu aktivieren/zu deaktivieren. Dies verwendet RPM-Makros, die zusammen mit
       Systemd ausgeliefert werden. Ziehen Sie die Paketierungsrichtlinien Ihrer Distribution für Details und
       die Äquivalente anderer Paketverwalter hinzu.

       Am Anfang der Datei:

           BuildRequires: systemd
           %{?systemd_requires}

       Und als Skriptteile, weiter unten:

           %post
           %systemd_post foobar.service foobar.socket

           %preun
           %systemd_preun foobar.service foobar.socket

           %postun
           %systemd_postun

       Falls der Dienst während der Aktualisierung neu gestartet werden soll, ersetzen Sie den Skriptteil
       »%postun« mit nachfolgendem:

           %postun
           %systemd_postun_with_restart foobar.service

       Beachten Sie, dass »%systemd_post« und »%systemd_preun« die Namen sämtlicher zu
       installierender/entfernender Units als durch Leerzeichen getrennte Argumente erwarten. »%systemd_postun«
       erwartet keine Argumente. »%systemd_postun_with_restart« erwartet die neu zu startenden Units als
       Argumente.

       Um Aktualisierungen von einer Paketversion, die nur SysV-Init-Skripte auslieferte, zu einer Paketversion,
       die sowohl SysV-Init-Skripte als auch eine native Systemd-Dienstedatei ausliefert, zu unterstützen,
       verwenden Sie Fragmente der folgenden Art:

           %triggerun -- foobar < 0.47.11-1
           if /sbin/chkconfig --level 5 foobar ; then
             /bin/systemctl --no-reload enable foobar.service foobar.socket >/dev/null 2>&1 || :
           fi

       Wobei 0.47.11-1 die erste Paketversion ist, die die native Unit-Datei enthält. Dieses Fragment bewirkt,
       dass bei der erstmaligen Installation der Unit-Datei diese nur aktiviert wird, falls das SysV-Init-Skript
       aktiviert ist und stellt damit sicher, dass der Aktivierungsstatus sich nicht ändert. Beachten Sie, dass
       der Befehl chkconfig, der zum Überprüfen des Aktivitätsstandes eines SysV-Init-Skriptes verwandt werden
       kann, Fedora-spezifisch ist. Hier werden andere Betriebssysteme andere Befehle verwenden müssen.

EXISTIERENDE DAEMONS PORTIEREN

       Da neuartige Init-Systeme wie Systemd zu traditionellen SysV-Init-Systemen kompatibel sind, ist es
       strenggenommen nicht notwendig, Daemons auf die neue Art zu portieren. Erfolgt dies, ermöglicht es aber,
       zusätzliche Funktionalitäten zum Daemon hinzuzufügen, sowie die Integration in das neuartige Init-System
       zu vereinfachen.

       Um einen bestehenden, SysV-kompatiblen Daemon zu portieren, werden die folgenden Schritte empfohlen:

        1. Falls noch nicht implementiert, fügen Sie einen zusätzlichen Befehlszeilenschalter zu dem Daemon
           hinzu, um die Daemonisierung zu deaktivieren. Dies ist nicht nur für den Einsatz in neuartigen
           Init-Systemen, sondern auch zur Erleichterung der Fehlersuche nützlich.

        2. Falls der Daemon zu anderer, auf dem lokalen System laufenden Software Schnittstellen mittels lokaler
           AF_UNIX-Sockets anbietet, sollte eine Socket-basierte Aktivierung (siehe oben) überlegt werden.
           Normalerweise reicht ein minimaler Patch, um dies zu implementieren: Erweitern Sie die
           Socket-Erstellung im Daemon-Code, so dass zuerst sd_listen_fds(3) auf bereits übergebene Sockets
           geprüft wird. Falls Sockets übergeben wurden (d.h. wenn sd_listen_fds() einen positiven Wert
           liefert), überspringen Sie den Socket-Erstellungsschritt und verwenden Sie die übergebenen Sockets.
           Zweitens sollten die System-Socket-Knoten für lokale, in der Socket-basierten Aktivierung verwandten
           AF_UNIX-Sockets nicht entfernt werden, wenn der Daemon heruntergefahren wird, falls Sockets übergeben
           wurden. Falls der Daemon normalerweise alle verbliebenen offenen Dateideskriptoren als Teil seiner
           Initialisierung schließt, müssen drittens die vom Diensteverwalter übergebenen Sockets verschont
           werden. Da neuartige Init-Systeme garantieren, dass keine verbliebenen Dateideskriptoren an
           ausgeführte Prozesse übergeben werden, könnte es eine gute Idee sein, einfach das Schließen aller
           verbliebenen offenen Dateideskriptoren zu überspringen, falls Sockets übergeben wurden.

        3. Schreiben und installieren Sie eine Systemd-Unit-Datei für den Dienst (und die Sockets, falls
           Socket-basierte Aktivierung verwandt wird, sowie eine Pfad-Unit-Datei, falls der Daemon ein
           Spool-Verzeichnis verarbeitet), siehe oben für Details.

        4. Falls der Daemon Schnittstellen mittels D-Bus offenlegt, schreiben Sie eine D-Bus-Aktivierungsdatei
           für den Dienst, siehe oben für Details.

ABLAGE VON DAEMON-DATEN

       Es wird empfohlen, den allgemeinen Richtlinien, beschrieben in file-hierarchy(7), für die Ablage von
       Paketdateien zu folgen.

SIEHE AUCH

       systemd(1), sd-daemon(3), sd_listen_fds(3), sd_notify(3), daemon(3), systemd.service(5),
       file-hierarchy(7)

ANMERKUNGEN

        1. LSB-Empfehlungen für SysV-Init-Skripte
           http://refspecs.linuxbase.org/LSB_3.1.1/LSB-Core-generic/LSB-Core-generic/iniscrptact.html

        2. Apple-MacOS-X-Daemon-Anforderungen
           https://developer.apple.com/library/mac/documentation/MacOSX/Conceptual/BPSystemStartup/Chapters/CreatingLaunchdJobs.html

ÜBERSETZUNG

       Die deutsche Übersetzung dieser Handbuchseite wurde von Helge Kreutzmann <debian@helgefjell.de> erstellt.

       Diese Übersetzung ist Freie Dokumentation; lesen Sie die GNU General Public License Version 3
       ⟨https://www.gnu.org/licenses/gpl-3.0.html⟩ oder neuer bezüglich der Copyright-Bedingungen. Es wird KEINE
       HAFTUNG übernommen.

       Wenn Sie Fehler in der Übersetzung dieser Handbuchseite finden, schicken Sie bitte eine E-Mail an die
       Mailingliste der Übersetzer ⟨debian-l10n-german@lists.debian.org⟩.