Eigene Dienste mit Upstart zünden

Aus LinuxUser 08/2011

Eigene Dienste mit Upstart zünden

© Mrozsz, sxc.hu

Durchstarten

Unter Ubuntu wacht der SysV-Init-Ersatz Upstart über die komplexen Vorgänge beim Systemstart. Mit dem richtigen Know-how fügen Sie bei Bedarf hier ein eigenes Startskript ein.

Nachdem der Kernel die Hardware initialisiert hat, reicht er unter Ubuntu die Kontrolle über das System direkt an das Programm Upstart weiter. Diesem wiederum fällt die Aufgabe zu, die Hardware einzurichten und alle für den Betrieb notwendigen Dienste zu starten. Auf einem modernen Linux-System sind das mittlerweile eine ganze Menge – angefangen beim Druckdienst Cups über das X-Window-System bis zum Gnome Display Manager GDM, um nur drei der bekannteren Gesellen zu nennen.

Versteckspiel

Auf der Festplatte suchen Sie ein Programm namens Upstart vergebens. Das Werkzeug nutzt aus gutem Grund ein Pseudonym: Sobald der Linux-Kernel gestartet ist und den Computer in Beschlag genommen hat, ruft er stur das Programm /sbin/init auf. Um direkt nach dem Systemstart als erster Prozess mit der Nummer (PID) 1 die Arbeit aufzunehmen, versteckt sich Upstart folglich genau hinter diesem Namen. Deshalb finden Sie Upstart in der Liste mit allen Prozessen (ps -A) stets unter dem Pseudonym init; seine Manpage rufen Sie analog dazu über man init auf.

Schlangestehen

Um das gesamte System möglichst schnell hochzufahren, böte es sich an, alle Dienste gleichzeitig zu starten. Dummerweise hängen einige von anderen ab: So nimmt beispielsweise der Druckdienst Cups seine Arbeit erst auf, wenn das Netzwerk steht. Um solche Abhängigkeiten zu berücksichtigen, verwendet Upstart ein ereignisgesteuertes System: Sobald ein bestimmtes Ereignis eintritt, wie etwa “Netzwerk aktiviert” oder “TV-Stick angeschlossen”, arbeitet Upstart alle zu diesem Ereignis passenden Jobs ab.

Hinter diesen Jobs verbergen sich einfache Textdateien, die die Befehle zum Starten der eigentlichen Dienste oder zum Einrichten der Hardware enthalten. Tritt zum Beispiel das Ereignis “Netzwerk aktiviert” auf, geht Upstart alle zugehörigen Dateien durch, von denen wiederum eine das Drucksystem hochfährt. Jobs voneinander unabhängiger Ereignisse bearbeitet Upstart parallel. So ist es etwa dem gerade eingestöpselten Fernsehempfänger in der Regel egal, ob das Netzwerk bereits läuft.

Arbeitgeber

Wollen Sie einen eigenen Dienst beim Systemstart automatisch hochfahren, erstellen Sie eine passende Job-Datei, die den Namen des Jobs als Dateinamen sowie das Suffix .conf trägt. Der Inhalt setzt sich recht einfach zusammen: Listing 1 zeigt ein Beispiel, das beim Systemstart die Software zum Messen von Lärm startet. In jeder Zeile steht eine Anweisung beziehungsweise Information an Upstart; Kommentare beginnen ähnlich wie in Shell-Skripten mit einer Raute.

Hinter den Schlüsselwörtern description und author steht in Anführungszeichen eine Beschreibung und der Name des Autors. Bei beiden handelt es sich um freiwillige Angaben. Über die Zeile start on legen Sie fest, bei welchen Ereignissen Upstart diesen Job auf die Reise schickt. Die Software benötigt mindestens ein Dateisystem (filesystem), um die gemessenen Daten abzulegen. In aktuellen Upstart-Versionen darf start on nur einmal auftauchen.

Listing 1

description "Beispiel für einen Job"
author "Tim Schürmann"
start on filesystem
exec /usr/bin/messdaemon --log=/var/log/laerm/messung.log
pre-start script
# Erstelle notwendiges Verzeichnis:
mkdir -p /var/log/laerm
end script
post-stop script
# Aufräumen:
rm -rf /var/log/laerm
end script
respawn
respawn limit 5 60
stop on filesystem

Gelegentliche Zwischenfälle

Bleibt noch die Frage, welche Ereignisse es gibt, wie sie heißen und wo sie herkommen. Das allererste Ereignis mit dem Namen startup erzeugt Upstart direkt nach seinem Start selbst. Darüber hinaus gilt der Start und das Beenden eines Jobs ebenfalls als Ereignis. Mit der Anweisung

start on starting cups

setzt Upstart den eigenen Job zeitgleich mit Cups in Bewegung. Alternativ zu starting gibt es noch started. Damit läuft der eigene Job zu einem unbestimmten Zeitpunkt nach dem Start von Cups an. Soll der eigene Job dagegen erst dann anlaufen, wenn der Druckdienst stoppt, führt folgende Anweisung zum Ziel:

start on stopped cups

Einige Systemdienste produzieren eigene Ereignisse, wie etwa der Hardware-Manager Udev beim Einstöpseln eines Peripheriegeräts. Das Ereignis trägt dabei einen Namen nach dem Schema Subsystem-device-Aktion, wobei Subsystem für das Udev-Subsystem und Aktion für die entsprechende Aktion steht. Ein neu angeschlossener Datenträger löst also das Event block-device-added aus.

Eine Liste mit typischen Ereignissen sowie weitere Hilfestellungen liefert ab Ubuntu 11.04 beziehungsweise Upstart 0.9.4 die Manpage man upstart-events (Abbildung 1).

Abbildung 1: Ab Ubuntu 11.04 liefert die Manpage <code srcset=

upstart-events wichtige Ereignisse auf.” width=”300″ height=”294″ /> Abbildung 1: Ab Ubuntu 11.04 liefert die Manpage upstart-events wichtige Ereignisse auf.

Setzt ein Job mehrere Ereignisse voraus, verknüpfen Sie diese in den Anweisungen über das Schlüsselwort and:

start on local-filesystem and started dbus

In diesem Beispiel müssen das Messaging-Framework Dbus gestartet und die lokalen Dateisysteme eingehängt sein, damit Upstart den Job ausführt. Analog verlangt das Verknüpfen mit or, dass eines der Ereignisse bereits eingetreten ist. Zusammen mit runden Klammern erstellen Sie beliebig komplexe Bedingungen, wie sie beispielsweise der Job für den Druckdienst Cups verwendet (siehe Listing 2). Mehr zum Ereignis runlevel erfahren Sie im Kasten “Altlasten”.

Listing 2

start on (filesystem and (started dbus or runlevel [2345]) and stopped udevtrigger)

Altlasten

Nach wie vor setzen viele Distributionen auf den Ansatz SysV-Init, bei dem eine Reihe von Skripten nacheinander startet [2]. Zudem unterscheidet SysV-Init zwischen verschiedenen Gesamtkonfigurationen des Systems, den sogenannten Runleveln. Diese erhalten jeweils eine Nummer und umfassen jeweils unterschiedliche Dienste. Im Runlevel 2 steht beispielsweise noch kein Netzwerk bereit.

Vielen Diensten von Drittanbietern liegen immer noch passende Skripte für SysV-Init bei. Um diese nicht auf einen Schlag nutzlos zu machen, bindet Upstart sie über einen kleinen Kniff ein: Nach allen Ereignissen führt es den Job rc aus, der wiederum das Skript /etc/init.d/rc anwirft. Dieses arbeitet alle verbliebenen SysV-Init-Skripte im Verzeichnis /etc/init.d wie gewohnt, also eines nach dem anderen ab.

Möchten Sie erreichen, dass ein eigener Job erst danach beziehungsweise mit diesen alten SysV-Init-Skripten startet, verwenden Sie hinter start on das Ereignis runlevel:

start on runlevel [2345]

In diesem Fall würde der Job in den Runleveln 2, 3, 4 und 5 starten. Das Stoppen erfolgt analog:

stop on runlevel [!2345]

Das Ausrufezeichen verkehrt das Argument ins Gegenteil. Dieser Behelf war eigentlich nur als Übergangshilfe gedacht, bis die Maintainer alle alten SysV-Init-Skripte in Upstart-Jobs umgeschrieben haben. Doch selbst in Ubuntu 11.04 tummeln sich noch immer diverse SysV-Init-Skripte im Verzeichnis /etc/init.d.

Dienstverhältnis

Nachdem geklärt ist, wann der Job anläuft, fehlt nur noch das zu startende Programm, welches Sie über exec festlegen (Listing 1, Zeile 5). Dabei geben Sie das vollständige Kommando einschließlich etwaiger Parameter an. Die beiden Zeilen start on und exec ergeben bereits einen vollständigen, minimalen Job. Upstart startet den hinter exec angegebenen Prozess übrigens grundsätzlich im Vordergrund: Auf diese Weise fällt es der Software leichter, zu überprüfen, ob ein Prozess noch läuft.

Anstelle von exec dürfen Sie ein komplettes Shell-Skript angeben, das Upstart dann mittels /bin/sh ausführt. Die Befehle des Skripts müssen dabei zwischen den Schlüsselwörtern script und end script stehen. Ergänzend dürfen Sie ein Skript angeben, das Upstart noch vor dem eigentlichen Programm (im Beispiel der messdaemon) ausführt. Das pre-start-Skript eignet sich dazu, um eine Arbeitsumgebung für das eigentliche Programm einzurichten (Listing 1, Zeilen 7 bis 10). Analog gibt es die Anweisung post-stop, die immer dann zum Einsatz kommt, wenn sich der Hauptprozess beendet (Listing 1, Zeilen 12 bis 15).

Falls nötig, geben Sie dem Dienst noch ein post-start mit, das Upstart direkt nach dem Start des Dienstes ausführt. Doch Vorsicht: Da Upstart voraussetzt, dass der Dienst im Vordergrund läuft, bestehen wenig Möglichkeiten, um festzustellen, wann genau der Start abgeschlossen ist. Daher startet es das Skript immer parallel mit dem eigentlichen Dienst.

Die Skripte in post-stop und pre-start bestehen jeweils nur aus einer Anweisung, weshalb Sie sie in diesem Fall schlicht in eine Zeile schreiben dürfen. Wann Upstart die Befehle hinter welchen Schlüsselwörtern ausführt, verdeutlicht noch einmal Abbildung 2.

Abbildung 2: Die Ereignisse beim Ausführen einer Job-Datei in ihrer zeitlichen Reihenfolge.

Abbildung 2: Die Ereignisse beim Ausführen einer Job-Datei in ihrer zeitlichen Reihenfolge.

Urlaubssperre

Beendet sich das Messprogramm unerwartet, übernimmt Upstart bei Bedarf für Sie die Aufgabe, es umgehend neu zu starten. Dies erledigen Sie über das Schlüsselwort respawn. Liegt jedoch ein Programmfehler vor, führt ein endloser Neustart eventuell dazu, dass Sie damit das System überlasten. Mit respawn limit 5 60 versucht Upstart die Messsoftware höchstens fünf Mal in 60 Sekunden neu zu starten (Listing 1, Zeile 18). Diese Angabe setzt jedoch nur Zeitspanne und Iteration. Das macht es notwendig, ein zusätzliches respawn hinterher zu schieben.

Fährt das Netzwerk aus irgendeinem Grund herunter, kann das Messprogramm keine Daten mehr versenden und sollte daher ebenfalls terminieren. Das Ereignis, bei dem Upstart den Job anhält, legt stop on fest (Listing 1, Zeile 19). Dabei sendet Upstart zunächst das Signal SIGTERM, dass dem Prozess die Möglichkeit gibt, sich ordnungsgemäß zu beenden, und wartet ein paar Sekunden. Sollte der Prozess immer noch laufen, würgt Upstart ihn mit dem Kill-Signal (SIGKILL) ab (Abbildung 2).

Personalversammlung

Die fertige Job-Datei kopieren Sie nach /etc/init. Upstart berücksichtigt sie spätestens beim nächsten Boot-Vorgang. In diesem Ordner liegen einige Standard-Jobs, die sich etwa um das Einrichten des Netzwerks oder den Start des Drucksystems kümmern. Sie eignen sich in Kopie als Ausgangspunkt für eigene Experimente.

Möchten Sie nicht bis zum nächsten Systemstart warten, weisen Upstart entweder an, die geänderten Job-Dateien neu zu laden:

sudo initctl reload-configuration

oder starten den Job per Hand. Unter der Voraussetzung, dass die Job-Datei messstation.conf heißt, geschieht dies mit

sudo start messstation

Das Werkzeug start gehört zum Upstart-Paket und steht als Abkürzung für

sudo initctl start messstation

Analog existiert der Befehl stop, mit dem Sie den Job wieder anhalten. Eine Liste mit allen Jobs wirft das Kommando initctl list aus (Abbildung 3). Probleme protokolliert Upstart unter /var/log/boot.

Abbildung 3: Der Befehl <code srcset=

initctl list liefert eine Liste aller Jobs und des jeweiligen Status.” width=”240″ height=”300″ /> Abbildung 3: Der Befehl initctl list liefert eine Liste aller Jobs und des jeweiligen Status.

Ab Upstart 0.9.4, das erstmals in Ubuntu 11.04 zum Einsatz kommt, haben Sie die Möglichkeit, die Jobs per initctl check-config auf Fehler zu überprüfen. Der Befehl spürt insbesondere problematische Abhängigkeiten auf, etwa wenn sich zwei Dienste gegenseitig voraussetzen. Geht alles glatt, beendet sich Upstart einfach ohne jede Rückmeldung. Mit dem Kommando initctl show-config listen Sie alle Jobs und die zugehörigen Ereignisse auf (Abbildung 4).

Abbildung 4: Über <code srcset=

initctl show-config erhalten Sie eine Liste einen Überblick über die aktuellen Jobs.” width=”300″ height=”216″ /> Abbildung 4: Über initctl show-config erhalten Sie eine Liste einen Überblick über die aktuellen Jobs.

Mit dem Parameter -e nimmt der Befehl zudem noch komplexe Bedingungen auseinander und zeigt an, welche Teile Jobs und welche Ereignisse sind. Bei Bedarf leiten Sie diese Ausgabe in eine Datei um, und wandeln diese mit dem Hilfsprogramm Initctl2dot in ein Eingabeformat für das Programm Graphviz. Mit Letzterem wiederum erstellen Sie daraus einen Abhängigkeitsgraph, wie den aus Abbildung 5. Die passenden Kommandos finden Sie in Listing 3.

Abbildung 5: Das Werkzeug Initclt2dot produziert einen Übersichtsgraph, in dem Pfeile die Abhängigkeiten zwischen den Jobs und Ereignissen repräsentieren.

Abbildung 5: Das Werkzeug Initclt2dot produziert einen Übersichtsgraph, in dem Pfeile die Abhängigkeiten zwischen den Jobs und Ereignissen repräsentieren.

Listing 3

initctl show-config -e > ausgabe.txt
initctl2dot -f ausgabe.txt -o ausgabe.dot
dot ausgabe.dot -Tps > diagramm.ps

Mit dem universellen Upstart-Werkzeug /sbin/initclt haben Sie die Möglichkeit, selbst Ereignisse zu erzeugen:

sudo initctl emit meinereignis

Dies würde das frei erfundene Ereignis meinereignis auslösen, auf das dann ein selbstgeschriebener Job bei Bedarf reagiert.

Umgekehrt hat ein Job mit initctl die Möglichkeit, selbst Ereignisse absetzen. Dazu gilt es, in einem seiner Skripte den passenden Befehl einzubauen. Für das genannte Beispiel sähen die Einträge wie folgt aus:

emits messung-start
emits messung-ende

Um Upstart die Startreihenfolge der Jobs zu erleichtern, gibt das Schlüsselwort emits hier darüber Auskunft, welche Ereignisse ein Job absetzt.

Ausblick

Obwohl schon 2006 mit Ubuntu 6.10 “Edgy Eft” eingeführt, geht die Arbeit an Upstart munter weiter. So hat sich der Aufbau einer Job-Datei im Laufe der Zeit (leicht) geändert und ist immer noch nicht endgültig zementiert. Zukünftig soll Upstart auf Änderungen an Dateien und Verzeichnissen sowie auf zeitgesteuerte Ereignisse reagieren. Damit würden dann die entsprechenden Dienste wie Cron, Anacron und Atd überflüssig.

Allerdings gelang es Canonical bislang nicht, die anderen Distributionen von Upstart zu überzeugen. Im Gegenteil – mittlerweile drohen jetzt die letzten Verbündeten zur Konkurrenz namens Systemd überzulaufen (siehe Kasten “Alleine im Weltall”). Da Canonical sein hauseigenes Upstart jedoch vermutlich nicht so schnell beerdigt, stehen Entwicklern und Administratoren zukünftig als Ergänzung zum guten alten SysV-Init mit Upstart und Systemd zwei konkurrierende Ansätze ins Haus. 

Alleine im Weltall

Ursprünglich sollte das von Scott James Remnant erfundene und von Canonical gesponserte Upstart auch in anderen Distributionen zum Einsatz kommen. Fedora übernahm es ab Version 9, einige Netbook-Distributionen, wie etwa Googles Chromium verwenden es ebenfalls. OpenSuse wollte Upstart bereits mit Version 11.3 einführen, verschob die Integration aber immer wieder. Wer mag, darf das Werkzeug immerhin in den Versionen 11.3 und 11.4 nachinstallieren – wenngleich der Betrieb damit nicht immer ganz gefahrlos klappt.

Die Zurückhaltung hat einen Grund: Derzeit warten die Entwickler der großen Distributionen gespannt auf den Upstart-Konkurrenten Systemd, der einen noch schnelleren Start des Systems verspricht. Fedora steigt bereits mit der nächsten Version auf ihn um, aber auch OpenSuse, Debian und Mandriva liebäugeln offen mit Systemd. Unter dem Strich hält somit nur noch Ubuntu als einzige große Distribution an Upstart fest.

Infos

[1] Upstart-Homepage: http://upstart.ubuntu.com

[2] SysV-Init und Runlevel: Tim Schürmann, “Der nächste, bitte!”, LU 12/2010, S. 88 https://www.linux-community.de/22208

LinuxUser 08/2011 KAUFEN
EINZELNE AUSGABE
ABONNEMENTS
TABLET & SMARTPHONE APPS
E-Mail Benachrichtigung
Benachrichtige mich zu:

Hinweis: Dieser Artikel ist älter als ein Jahr, enthaltene Informationen sind möglicherweise veraltet.

0 Kommentare
Älteste
Neuste Beste Bewertung
Inline Feedbacks
Alle Kommentare anzeigen
Nach oben