12

Bash シェルのバックグラウンド プロセスで異なる動作が見られる理由を知りたい

ケース 1: Putty(SSH) を使用して Unix サーバーにログインした場合

  • デフォルトでは csh シェルを使用します
  • bashシェルに変更しました
  • 型付きスリープ 2000 &
  • エンターを押す

それは私に仕事番号を与えました。パテ ウィンドウで [x] をクリックしてセッションを強制終了しました。別のセッションを開き、プロセスを検索しようとしましたが、プロセスが強制終了しました。

ケース 2: ケース 1: Putty(SSH) を使用して Unix サーバーにログイン デフォルトでは csh シェルを使用

  • bashシェルに変更しました
  • vi mysleep.sh
  • sleep 2000 & 保存された mysleep.sh
  • ./mysleep.sh

ここでの違いは..スリープコマンドを直接実行する代わりに、スリープコマンドをファイルに保存してファイルを実行しています。

パテ ウィンドウで [x] をクリックしてセッションを強制終了しました。別のセッションを開き、プロセスを検索しようとしました。プロセスはまだ存在します。

なぜこれが起こっているのか分かりません。ログアウトした後でもプロセスを実行するには、bashでdisownを行う必要があると思いました。

親プロセスIDに見られる1つの違い..2番目のケース..スリープ2000の親プロセスIDは1になります.mysleep.shのプロセスが終了するとすぐに、カーネルが親プロセスを1に割り当てたように見えます.

4

4 に答える 4

20

ここでの違いは、実際に介在するプロセスです。ターミナル ウィンドウを閉じると、HUP シグナル (前述の an0nymo0usc0ward の「nohup」に関連する) がそこで実行されているプロセスに送信されます。HUP を受信したときのデフォルトのアクションは死ぬことです - signal(3) マンページから、

 No    Name         Default Action       Description
 1     SIGHUP       terminate process    terminal line hangup

最初の例では、スリープ プロセスはこの HUP シグナルを直接受け取り、他に何もするように設定されていないため終了します。(一部のプロセスは HUP をキャッチし、それを使用して何らかのアクションを実行します。たとえば、一部の構成ファイルを再読み込みします)。

2 番目の例では、シェル スクリプトを実行しているシェル プロセスが既に停止しているため、スリープ プロセスがシグナルを受信することはありません。UNIX では、すべてのプロセスに親プロセスが必要です。これは、wait(2) ファミリーの呼び出しがどのように機能し、実際に一般的にプロセスがどのように機能するかの内部構造によるものです。したがって、親プロセスが終了すると、カーネルはそれを里子として init (pid 1) に渡します。 Orphan プロセス (ウィキペディア)には、それに関する詳細情報があります。追加の技術的な詳細については、Zombie プロセスも参照してください。

于 2009-09-23T04:15:35.957 に答える
8

すでにプロセスを実行していますか?

^ z
bg
disown%<jobid>

新しいプロセス/スクリプト(ローカルマシンのコンソール上)?

nohup script.sh&

新しいプロセス/スクリプト(リモートマシンのコンソール上)?

必要に応じて、
2つのオプションがあります[さらにあります;-)]

ssh remotehost'nohup /path/to/script.sh </dev/null> nohup.out 2>&1&'

また

「画面」を使用

于 2010-02-17T13:40:09.207 に答える
3

「nohup cmd args...」を試してください

于 2009-09-23T03:52:36.780 に答える
0

スティーブンの答えは正しいですが、ここで難しい部分を強調したいと思います。

=>スリープをバックグラウンドで実行するだけのbashスクリプトを使用する

これの効果は、「スクリプト」がほぼ即座に終了することです (すべてのコマンドが実行されるため)。ただし、存続期間中に子プロセス (スリープ) を作成しました。これの効果は次のとおりです。

  • 「スクリプト」はもはや親になることはできず、スリープは init に孤立しています (pstree でうまく表示されます)。
  • スクリプトを開始した bash シェルには、基盤となるジョブがありません

このようなことはすべて、スクリプトを実行したときに発生し、ssh ログアウト/パテの終了とは何の関係もないことに注意してください。

最後にパテ セッションを閉じると、bash は「SIGHUP」を受け取りますが、それを他のプロセスに転送しません (ジョブが残っていないため)。 SIGHUP を に送信し、終了させました (お気づきのように)

お役に立てれば

于 2013-11-25T21:43:58.197 に答える