Entfernen Sie einen Zombie-Prozess aus der Prozesstabelle

8

Ich habe einen nervigen Zombie-Prozess, der von init übernommen wird und der nicht verschwindet. Ich habe gelesen, dass es eine Möglichkeit gibt, einen Dummy-Prozess zu erstellen, den Zombie als untergeordnetes Element dieses neuen Prozesses anzuhängen , ihn dann zu beenden und ihn aus der Prozesstabelle zu entfernen.

Wie würde ich das genau machen?

Und ja, ich habe das meiste gelesen:

Ein Zombie-Prozess ist bereits tot und kann daher nicht getötet werden.

Oder

Sie sollten Ihr System einfach neu starten

Und

Zombie-Prozesse verbrauchen keine Ressourcen, Sie sollten sie einfach sein lassen

Leider überprüfen viele Programme die Prozesstabelle, um festzustellen, ob eine Instanz bereits ausgeführt wird, und lehnen es ab, eine neue zu starten, wenn ein Eintrag in der Prozesstabelle vorhanden ist.

Und ein Neustart jedes Mal, wenn meine SSHFS-Verbindung unterbrochen wird und Sublime mitgenommen wird, ist irgendwie albern.

Skerit
quelle
7
... mit einer Schrotflinte. ;)
Nathan C
+1, weil ich auf die Hauptleitung schaute und "Kill Zombie" sah
HopelessN00b

Antworten:

16

Die einzige Möglichkeit, einen Zombie loszuwerden, besteht darin, seinen Elternteil wait()dazu zu bringen, seinen Exit-Status zu melden. Sie können dies tun, indem Sie SIGCHLDan das übergeordnete Element senden , vorausgesetzt, das übergeordnete Element ist ordnungsgemäß geschrieben.

Wenn Sie Zombies haben, bedeutet dies normalerweise, dass der Elternteil NICHT richtig geschrieben ist (da das Kind bereits SIGCHLDan seinen Elternteil gesendet wurde , als es starb und ein Zombie wurde). Der nächste Schritt besteht also darin, den Elternteil zu töten.
Ein Tool wie pstree(mit der -pOption) kann Ihnen die Abstammungslinie Ihrer Zombies anzeigen, damit Sie wissen, welcher Prozess der übergeordnete ist.
Wenn der Elternteil stirbt, wird der Zombie von adoptiert init, was immer bedeutet, wait()dass Kinder sterben, und er wird glücklich alle Zombies töten, die er adoptiert.

Wenn der übergeordnete Prozess initbereits (PID 1) ist, befinden Sie sich in einer Situation, die niemals eintreten sollte. Sie können versuchen, an SIGCHLDzu senden init, aber das sollten Sie wirklich nicht tun müssen. Wenn dies nicht funktioniert, müssen Sie nur einen Neustart durchführen, da Ihr System initdefekt ist und seine Aufgabe nicht erfüllt .

(Dies sind die "Schrotflinten" -Optionen.)


Einige kreativere Leute als ich haben sich diese Option ebenfalls ausgedacht, wenn Sie vermeiden möchten, den übergeordneten Prozess zu beenden:

  1. Bestimmen Sie die PIDS der Zombie- und übergeordneten Prozesse
    (In diesem Beispiel ist der Zombie PID 3101 und der übergeordnete PID 3100).
  2. Feuer hoch gdbund attachzu den Eltern:
    attach 3100
  3. Ruf waitpidnach dem Zombie:
    call waitpid(3101,0,0)
  4. Trennen Sie sich vom übergeordneten Element ( detach) und beenden Sie den Debugger.

(Dies ist ein fein abgestimmtes Scharfschützengewehr.)

voretaq7
quelle
1
heh, tolle Antwort. "Mosin" Gewehr genau dort.
Danila Ladner
1
@DanilaLadner Ich wünschte, ich könnte Kredit aufnehmen, aber bis ich auf eine kleine Google-Jagd ging, um zu sehen, was Skerit bedeutet, "den Zombie als Kind eines Dummy-Prozesses anzuhängen", waitpid()kam mir der Gedanke, den Debugger zu verwenden, um ein nie erzwungenes zu erzwingen . Ich bin ein schrecklicher Ex-Programmierer ...
voretaq7
call waitpidkehrt nie für mich zurück
deFreitas
0

Warum machst du dir Sorgen um die Zombie-Prozesse? Die Ressourcen, die sie gebunden halten, sind minimal (Platz für eine Skelettstrukturaufgabe, eine PID und nicht viel mehr). Sicher, es ist unpassend, aber das ist es. Suchen Sie nach ihren Eltern und beheben Sie diese, ersetzen Sie sie durch besser geschriebene Alternativen (könnte andere vorteilhafte Nebenwirkungen haben), melden Sie dies als Fehler (was sie sicherlich sind).

vonbrand
quelle