Zurück | Inhalt | Weiter
In der vorherigen Lektion haben wir einige der Auswirkungen von Linux als Mehrbenutzer-Betriebssystem betrachtet. In dieser Lektion werden wir die Multitasking-Natur von Linux untersuchen und wie sie mit der Befehlszeilenschnittstelle gesteuert wird.
Wie bei jedem Multitasking-Betriebssystem führt Linux mehrere, gleichzeitige Prozesse aus. Zumindest scheinen sie simultan zu sein. Eigentlich kann ein einzelner Prozessorkern nur einen Prozess gleichzeitig ausführen, aber der Linuxkernel schafft es, jedem Prozess seinen Platz am Prozessor zuzuweisen, so dass es scheint, als liefen sie alle gleichzeitig.
Es gibt mehrere Befehle, die zur Steuerung von Prozessen verwendet werden. Diese sind:
-
ps
– die auf dem System laufenden Prozesse auflisten -
kill
– ein Signal an einen oder mehrere Prozesse senden (normalerweise um einen Prozess zu „töten“) -
jobs
– eine alternative Möglichkeit, die eigenen Prozesse aufzulisten -
bg
– einen Prozess in den Hintergrund stellen -
fg
– einen Prozess in den Vordergrund stellen
Ein praktisches Beispiel
Auch wenn es scheint, dass dieses Thema ziemlich obskur ist, kann es für den durchschnittlichen Benutzer, der hauptsächlich mit der grafischen Benutzeroberfläche arbeitet, sehr praktisch sein. Auch wenn es nicht offensichtlich ist, können die meisten (wenn nicht alle) grafischen Programme über die Befehlszeile gestartet werden. Ein Beispiel: Mit dem X Window System wird ein kleines Programm namens xload mitgeliefert, das die Systemauslastung grafisch darstellt. Sie können dieses Programm ausführen, indem Sie Folgendes eingeben:
xload
Beachten Sie, dass das kleine Fenster xload
erscheint und beginnt, die Grafik der Systemauslastung anzuzeigen. Auf Systemen, auf denen xload
nicht verfügbar ist, versuchen Sie stattdessen gedit
. Beachten Sie auch, dass unsere Eingabeaufforderung nach dem Start des Programms nicht wieder erscheint. Die Shell wartet auf die Beendigung des Programms, bevor sie die Kontrolle wieder abgibt. Wenn wir das xload
Fenster schließen, wird das xload-Programm beendet und die Eingabeaufforderung kehrt zurück.
Programm in den Hintergrund stellen
Um uns das Leben ein wenig zu erleichtern, starten wir das xload-Programm erneut, aber diesmal stellen wir es in den Hintergrund, damit die Eingabeaufforderung zurückkehrt. Dazu führen wir xload wie folgt aus:
xload &
1223$In diesem Fall kehrt die Eingabeaufforderung zurück, weil der Prozess in den Hintergrund gestellt wurde.
Stellen Sie sich nun vor, dass wir vergessen haben, das Symbol „&“ zu verwenden, um das Programm in den Hintergrund zu stellen. Es gibt noch Hoffnung. Wir können Ctrl-z
eingeben und der Prozess wird angehalten. Wir können dies überprüfen, indem wir sehen, dass das Programmfenster eingefroren ist. Der Prozess existiert noch, ist aber im Leerlauf. Um den Prozess im Hintergrund wieder aufzunehmen, geben Sie den Befehl bg
(kurz fürbackground) ein. Hier ein Beispiel:
xload
+ Stopped xload$ bg
+ xload &Listing Running Processes
Nun, da wir einen Prozess im Hintergrund haben, wäre es hilfreich, eine Liste der Prozesse anzuzeigen, die wir gestartet haben. Dazu können wir entweder den Befehljobs
oder den mächtigeren Befehl ps verwenden.
jobs
+ Running xload&$ ps
PID TTY TIME CMD1211 pts/4 00:00:00 bash1246 pts/4 00:00:00 xload1247 pts/4 00:00:00 ps$Killing a Process
Angenommen, wir haben ein Programm, das nicht mehr reagiert; wie werden wir es los? Wir verwenden natürlich den Befehl kill
. Probieren wir das mal mit xload
aus. Zuerst müssen wir den Prozess identifizieren, den wir beenden wollen. Dazu können wir entweder jobs
oderps
verwenden. Wenn wir jobs verwenden, erhalten wir eine Jobnummer zurück. Mit ps
erhalten wir eine Prozess-ID (PID). Wir machen es so: bothways:
xload &
1292$ jobs
+ Running xload&$ kill %1
$ xload &
1293 Terminated xload$ ps
PID TTY TIME CMD1280 pts/5 00:00:00 bash1293 pts/5 00:00:00 xload1294 pts/5 00:00:00 ps$ kill 1293
+ Beendet xload$Ein wenig mehr über kill
Während der kill
-Befehl verwendet wird, um Prozesse zu „töten“, ist sein eigentlicher Zweck, Signale an Prozesse zu senden. Meistens ist das Signal dazu gedacht, dem Prozess mitzuteilen, dass er verschwinden soll, aber es gibt noch mehr als das. Programme (wenn sie richtig geschrieben sind) lauschen auf Signale des Betriebssystems und reagieren darauf, meist um eine elegante Methode der Beendigung zu ermöglichen. Ein Texteditor könnte zum Beispiel auf ein Signal warten, das anzeigt, dass der Benutzer sich abmeldet oder dass der Computer heruntergefahren wird. Wenn er dieses Signal empfängt, könnte er die laufende Arbeit speichern, bevor er beendet wird. Der Befehl kill
kann eine Vielzahl von Signalen an Prozesse senden. Durch Eingabe von:
kill -l
wird eine Liste der von ihm unterstützten Signale ausgegeben. Viele sind eher obskur, aber einige sind nützlich zu wissen:
Signal # | Name | Beschreibung |
1 | SIGHUP | Auflegen-Signal. Programme können auf dieses Signal hören und darauf reagieren. Dieses Signal wird an Prozesse, die in einem Terminal laufen, gesendet, wenn Sie das Terminal schließen. |
2 | SIGINT | Unterbrechungssignal. Dieses Signal wird an Prozesse gegeben, um sie zu unterbrechen. Programme können dieses Signal verarbeiten und darauf reagieren. Wir können dieses Signal auch direkt ausgeben, indem wir Ctrl-c in das Terminalfenster eingeben, in dem das Programm läuft. |
15 | SIGTERM | Beendigungssignal. Dieses Signal wird an Prozesse gegeben, um sie zu beenden. Auch hier können Programme dieses Signal verarbeiten und darauf reagieren. Dies ist das Standardsignal, das durch den Befehl kill gesendet wird, wenn kein Signal angegeben wird. |
9 | SIGKILL | Kill-Signal. Dieses Signal bewirkt die sofortige Beendigung des Prozesses durch den Linux-Kernel. Programme können nicht auf dieses Signal hören. |
Angenommen, wir haben ein Programm, das hoffnungslos hängt und das wir loswerden wollen. Hier ist, was wir tun:
- Verwenden Sie den Befehl
ps
, um die Prozess-ID (PID) des Prozesses zu erhalten, den wir beenden wollen. - Erteilen Sie einen
kill
-Befehl für diese PID. - Wenn der Prozess sich weigert, sich zu beenden (d.h., er ignoriert das Signal), senden Sie immer schärfere Signale, bis er sich beendet.
ps x | grep bad_program
PID TTY STAT TIME COMMAND2931 pts/5 SN 0:00 bad_program$ kill -SIGTERM 2931
$ kill -SIGKILL 2931
Im obigen Beispiel haben wir den Befehl ps
mit der Option x verwendet, um alle unsere Prozesse aufzulisten (auch die, die nicht vom aktuellen Terminal gestartet wurden). Außerdem haben wir die Ausgabe des ps-Befehls in grep
eingefügt, um nur das Programm aufzulisten, an dem wir interessiert sind. Als nächstes haben wir kill verwendet, um ein SIGTERM-Signal an das störende Programm zu senden.In der Praxis ist es üblicher, dies auf folgende Weise zu tun, da das von kill
gesendete Standardsignal SIGTERM ist und kill auch die Signalnummer anstelle des Signalnamens verwenden kann:
kill 2931
Wenn der Prozess dann nicht beendet wird, zwingen Sie ihn mit dem SIGKILL-Signal:
kill -9 2931
Das war’s!
Damit ist die Lektionsreihe „Learning the Shell“ abgeschlossen. In der nächsten Serie, „Schreiben von Shell-Skripten“, werden wir uns ansehen, wie man Aufgaben mit der Shell automatisieren kann.
Weitere Lektüre
- Für eine ausführlichere Behandlung des Themas, siehe Kapitel 10 in The Linux Command Line.
- 1963 Timesharing: A Solution to Computer Bottlenecks, ein faszinierendes YouTube-Video des Computer History Museum, in dem das erste Timesharing-Betriebssystem beschrieben wird und wie es funktioniert. Es ist im Grunde die gleiche Methode, die von allen modernen Computern verwendet wird.