Wie kann ich alle gestoppten Jobs beenden?

91

Wenn ich versuche, meinen Linux-Server zu verlassen, erhalte ich folgende Meldung:

Es gibt gestoppte Jobs.

: Gibt es einen einzigen Befehl, um diese zu töten?

Zubair
quelle
Zusätzliche Beispiele in den Fragen und Antworten zu U & L: unix.stackexchange.com/questions/124428/…
slm
Ich hatte jetzt das gegenteilige Problem, es würde nicht vor gestoppten Jobs warnen, wenn ich die Shell beende! Musste shopt -s checkjobsin meinem .bashrc
Sam Watkins
1
drücke nochmal strg + d, es wird dich jetzt verlassen und diese Jobs erledigen
Jens Timmerman

Antworten:

73

Geben Sie Folgendes ein, um alle angehaltenen Jobs unter der Bash schnell zu beenden:

kill -9 `jobs -ps`

jobs -pslistet die Prozess-IDs ( -p) der angehaltenen ( -s) Jobs auf.
kill -9 `jobs -ps`Sendet SIGKILL-Signale an alle.

ooshro
quelle
22
-1 für "kill Jobs"
1
hat nicht funktioniert, als der Job "sudo su" war. Das heißt, es hat sudo kill `jobs -p`nicht funktioniert, aber die explizite Eingabe von PID hat funktioniert.
user13107
14
Warum wird das so hoch geschätzt? Es ist falsch. Wenn die Prozesse gestoppt werden, kann ein killsolcher Vorgang nichts bewirken, da die Prozesse gestoppt werden und das standardmäßig an sie gesendete SIGTERM (-15) nicht verarbeiten.
Slm
6
kill -9 erledigt den Trick.
Zeitplan für den
84

Versuchen Sie Folgendes einzugeben:

kill -9 $(jobs -p)
dukevin
quelle
9
Das sollte reichen, aber ich denke, er sollte zuerst ein SIGTERM (-15) senden, bevor er ein SIGKILL (-9) sendet. Vielleicht wäre es besser, etwas wie "kill $ (jobs -p); sleep 3s; kill -9 $ (jobs -p)" vorzuschlagen. Wenn Sie zuerst SIGTERM senden, können die Jobs möglicherweise einen sauberen Exit ausführen (Freigabe der zugewiesenen Ressourcen usw.).
Rems
3
Kevin Duke, Ihre Antwort hat für mich funktioniert. Ich konnte nicht wählen, weil ich keinen Ruf von 15 habe. kill -9 $ (jobs -p)
2
@rems Außer, wie slm betont hat, bekommen sie das SIGTERM nicht, weil sie gestoppt sind.
Paul Gear
1
Funktioniert nicht auf zsh. Da zsh nicht POS IX-kompatibel ist .
Max Coplan
Wie soll man dann mit zsh umgehen?
fx-kirin
16

Die akzeptierte Antwort würde alle Jobs töten (was in diesem Fall ausreichend ist) und nicht nur die gestoppten. Wenn Sie nur die Gestoppten töten möchten, führen Sie Folgendes aus:

kill $(jobs -l | grep Stopped | cut -d' ' -f3)
Kit Sunde
quelle
grep / cut kann in einem awk Befehl kombiniert werden: awk '/Stopped/{print $3}')
laebshade 20.10.15
2
Das -sArgument auf der akzeptierten Antwort filtert nur die gestoppten
79E09796
12

Der einfachste Weg besteht darin, den Ausgang einfach sofort erneut zu versuchen. bashbedeutet "alle gestoppten Jobs beenden und beenden".

Geekosaurier
quelle
4
Das wird ein HUP senden, das nicht unbedingt alle Jobs stoppt.
Stephen Niedzielski
7
for x in `jobs -p` ; do kill -9 $x ; done
monu
quelle
2
Sie können Code-Formatierungen für diese Zeile hinzufügen, um die Lesbarkeit zu verbessern.
Drcelus
Können Sie sich Ihre Formatierung noch einmal ansehen? Verwenden Sie vier Leerzeichen am Zeilenanfang, um einen Block als Code zu markieren (anstatt Backtick zu verwenden). Derzeit ist nicht klar, ob Sie Backticks in Ihrem Code verwenden oder versuchen, Code mithilfe von Backticks anzuzeigen.
Dunxd
Die Formatierung ist in Ordnung. Wir müssen die Jobs -p mit Backticks übergeben, da dies sonst kein Befehl ist und einen Fehler auslöst.
Montag,
5

Nur für den Fall, dass dies jemand anderem hilft - die meisten Leute sind hier, weil sie einige gestoppte Prozesse haben, die sie gestartet haben, möglicherweise über die Shell im Hintergrund. Ich musste Prozesse als root finden, die von anderen Benutzern gestoppt wurden, für die Varianten des jobsBefehls nicht ausreichen.

Ein bisschen herumgraben brachte man psmich dazu:

ps -a -o pid,user,cmd,state | grep 'T$'

Erläuterung: Das -aFlag zeigt alle Prozesse an und -osteuert dann die Ausgabe, welche Informationen zu jedem Prozess angezeigt werden. Ich wähle pid, user, cmd(die Befehlszeile), und state, was das ist Prozesszustand .

Von man ps:

PROCESS STATE CODES
   Here are the different values that the s, stat and state output specifiers (header "STAT" or "S") will display to describe the
   state of a process:
           D    uninterruptible sleep (usually IO)
           R    running or runnable (on run queue)
           S    interruptible sleep (waiting for an event to complete)
           T    stopped, either by a job control signal or because it is being traced
           W    paging (not valid since the 2.6.xx kernel)
           X    dead (should never be seen)
           Z    defunct ("zombie") process, terminated but not reaped by its parent

also zum schluss leite ich es an grep T$was sagt, zeige mir alle prozesse die t in der letzten spalte haben.

Und dann habe ich eine schöne Liste aller Prozesse von verschiedenen Benutzern, die im gestoppten Zustand sind.

$ ps -a -o pid,user,cmd,state | grep 'T$'
  865 joson74+ python                      T
  885 joson74+ sh -c less                  T
  886 joson74+ less                        T
 1014 minames+ python3.4 -i /home/minames  T
 5352 MooKo    nano stdio.h                T
 7851 harry    tmux attach                 T
12083 harry    tmux attach                 T
13495 gorylla+ python3.4 -i /home/gorylla1 T
18009 conr1d   vim                         T
19664 enythin+ python                      T
24906 wardlist python                      T
hwjp
quelle
Das Anhängen von angehaltenen Jobs an die aktuelle Shell jobs -psist einfacher als diese Antwort. Davon abgesehen zeigt diese Antwort nicht nur Jobs, die über Ctrl-Zeine Shell angehalten wurden , sondern alle angehaltenen Jobs: andere Shells, andere Benutzer , einschließlich Jobs, die debuggt werden (z. B. von gdb).
Stéphane Gourichon
Für mich die beste Antwort, funktioniert aber nicht genau. Ich musste verwenden ps -el | grep T, um die Prozesse im Zustand 'T' zu finden.
dr0i
4

Wenn Sie einige angehaltene Jobs entfernen möchten, aber nicht alle, versuchen Sie Folgendes:

Wenn Sie zuerst Jobs auflisten, erhalten Sie ungefähr Folgendes:

$ jobs -l

[2]   4813 Stopped                 ./parse < call.txt
[3]-  4819 Stopped                 ./parse < call.txt

Wenn Sie kill an einen gestoppten Job senden, wird nichts anderes als die Warteschlange ausgeführt, als den Job in den Vordergrund zu stellen. Der Job wird beendet

$ fg %2
./parse < call.txt
Terminated

$ jobs -l
[3]-  4819 Stopped                 ./parse < call.txt
sergei
quelle
4

Wenn Sie diese Nachricht erhalten, müssen Sie sich normalerweise zweimal abmelden. Wenn Ctrl+DSie zum Beispiel zum ersten Mal auf die Warnmeldung klicken, die Sie über angehaltene Jobs informiert, werden Sie beim zweiten Mal abgemeldet, wenn Sie die Jobs beenden. Dies gilt auch für logoutund exitBefehle.

Zu töten sie manuell, versuchen: kill $(jobs -p).


Wenn Sie Jobs nicht aus Ihrer aktuellen Shell entfernen möchten, können Sie sie mit dem disownBefehl aus der Tabelle der aktiven Jobs entfernen, ohne sie zu beenden. Z.B

$ sleep 1000 &
[1] 19404
$ jobs
[1]+  Running                 sleep 1000 &
$ disown

Gestoppt Jobs kann auch durch den Zustand des Prozesses (bestimmt werden TZeichen) , was bedeutet , das Verfahren wurde gestoppt durch das Signal , wie beispielsweise SIGSTOP, SIGTSTPoder eine andere (wie SIGTTINoder SIGTTOU).

Wenn jobsein Shell-Built-In-Befehl nicht verfügbar ist, können gestoppte Prozesse mit dem folgenden Befehl aufgelistet werden:

ps wuax | awk '$8 ~ "T"'

Um sie alle zu töten, können Sie im Grunde Folgendes eingeben:

kill -9 $(ps wuax | awk 'NR>1 && $8 ~ "T" {print $2}')

Hier ist ein einfacher Test:

$ sleep 1000 &
[1] 2014
$ sleep 1000 &
[2] 2015
$ sleep 1000 &
[3] 2016
$ sleep 1000 &
[4] 2017
$ killall -STOP sleep
[1]   Stopped                 sleep 1000
[2]   Stopped                 sleep 1000
[3]   Stopped                 sleep 1000
[4]   Stopped                 sleep 1000
$ ps wuax | awk '$8 ~ "T"'
USER       PID %CPU %MEM    VSZ   RSS TTY      STAT START   TIME COMMAND
vagrant   2014  0.0  0.0   7228   832 pts/0    T    20:38   0:00 sleep 1000
vagrant   2015  0.0  0.0   7228   708 pts/0    T    20:38   0:00 sleep 1000
vagrant   2016  0.0  0.0   7228   760 pts/0    T    20:38   0:00 sleep 1000
vagrant   2017  0.0  0.0   7228   828 pts/0    T    20:38   0:00 sleep 1000
$ kill -9 $(awk 'NR>1 && $8 ~ "T" {print $2}' <(ps wuax))
$ jobs
[1]   Killed                  sleep 1000
[2]   Killed                  sleep 1000
[3]   Killed                  sleep 1000
[4]   Killed                  sleep 1000
Kenorb
quelle