Wie greife ich einen Prozess, der nicht stirbt, wenn die Shell beendet wird?

40060
sligocki

Wenn ich Emacs von der Shell aus laufe:

$ emacs foo & 

und dann töten Sie die Schale, Emacs stirbt.

Wie kann ich einen Befehl ausführen, damit er nicht stirbt, wenn die Shell stirbt?

Ich habe Verweise auf nohup gefunden, aber das scheint nicht zu helfen:

$ nohup emacs foo & 

tötet immer noch Emacs, wenn er stirbt.

29

3 Antworten auf die Frage

37
grawity

Die zuverlässigste Methode scheint zu sein:

(setsid emacs &) 

Dies wird verwendet, ( &)um sich in den Hintergrund setsidzu verzweigen und sich von der Steuerung zu lösen.

Sie können dies in eine Shell-Funktion einfügen:

fork() { (setsid "$@" &); }  fork emacs 

Die Möglichkeiten sind:

  • Der disowneingebaute Befehl:

    emacs & disown $! 

    &fungiert als Kommando-Trennzeichen und verwendet disownstandardmäßig den letzten Auftrag. Dies kann daher folgendermaßen verkürzt werden:

    emacs & disown 
  • Doppel- fork():

    (emacs &) 

    Befehle in Klammern ( )werden in einem separaten Shell-Prozess ausgeführt.

  • setsidWie von Rich vorgeschlagen, ist dies möglicherweise die beste Wahl, da durch das Erstellen einer neuen Sitzung der steuernde TTY des Prozesses aufgehoben wird :

    setsid emacs 

    Es ist jedoch auch ein wenig unvorhersehbar - es wird nur fork()Hintergrund sein, wenn es der Anführer einer Prozessgruppe ist (was nicht der Fall setsidist, wenn es beispielsweise in einem shSkript verwendet wird; in solchen Fällen wird es lediglich resistent gegen Strg- C.)

Großartig! diese arbeiten alle für mich. Schön, dass ich noch mehr Werkzeuge in meinem Arsenal habe. sligocki vor 13 Jahren 0
Hm ... würde `(exec emacs)` funktionieren? Hello71 vor 13 Jahren 0
@Hello: Es würde sich nicht nur von `(emacs)` unterscheiden. Wenn der Subshell ein einzelner Befehl gegeben wird, wird das "exec" zumindest im Fall von "bash" impliziert. Gleiches gilt für 'bash -c' foo '' gegenüber 'bash -c' exec foo'`. (Beachten Sie jedoch, dass sich emacs * selbst * möglicherweise vom Terminal löst. Gvim führt dies beispielsweise aus. Besser ist es, ein Programm mit bekanntem Verhalten zu testen.) grawity vor 13 Jahren 0
Toll zu lernen von der Doppelgabeltechnik; Vielen Dank! Dave Abrahams vor 12 Jahren 0
Ich habe dies beim Trolling gefunden, um ein eigenes Problem zu beheben. Der (setsid emacs &) hat für mich gearbeitet. Danke für eine gut geschriebene Antwort. Paulb vor 11 Jahren 0
13
Rich Homolka

Sie erwähnen nicht, ob dies als X-App oder als Konsolen-App ausgeführt wird.

Wenn es sich um eine Konsolen-App handelt, muss sie natürlich geschlossen werden. Sie haben den Input / Output losgelassen, technisch gesehen das (Pseudo) -Tty, auf dem es sich befand. Es ist sehr unwahrscheinlich, dass Sie dies gemeint haben. Nehmen wir an, Sie sprechen von einer X-App.

nohupsollte funktionieren, nicht sicher, warum es nicht ist. Wenn die Shell geschlossen wird, sendet sie SIGHUPan alle Prozesse in ihrer Prozessgruppe. nohup weist den Befehl an, SIGHUP zu ignorieren.

Sie können auch setsid versuchen, wodurch der Prozess von der Prozessgruppe getrennt wird

alias emacs='setsid emacs' 

Oder disownnach hinzufügen&

Ah, große Setsid arbeitet. Entschuldigung, dass ich nicht klar bin. Ja, ich beziehe mich auf X-Apps, die nicht wirklich in der Shell laufen. Grundsätzlich möchte ich Emacs (oder einen anderen Prozess) von der Shell aus starten, aber ich möchte nicht, dass es an die Shell gebunden ist. Ich fange gerade aus Bequemlichkeit damit an. sligocki vor 13 Jahren 0
5
Josh K

Überprüfen Sie Ihre Shell-Einstellungen. Sie können statt des Bildschirms auch versuchen nohup.

Mit Screen können Sie später mit `screen -r 'wieder in den Prozess einsteigen, wenn Sie die Verbindung mit` Ctrl-A Ctrl-D` trennen, bevor Sie sich abmelden. Broam vor 12 Jahren 0
Das ist ein sehr guter Punkt. Ich brauchte das Gegenteil, dh eine Subshell fälschen und mit anderen Aufgaben fortfahren, ohne auf ihre Fertigstellung zu warten, aber `screen -d -m sh -c" exit "macht viel mehr Sinn. Nemo vor 7 Jahren 0