試験では、次のように述べた。
プロセスが正常に終了する2つの方法を提供します。違いを説明してください。
どういう意味ですか?正常終了?
答え1
この文脈で使用される「通常」という用語は、通常、実行プロセスがシグナルによって終了したり予期せず衝突することなく、すべてのコマンドが正常に完了したときに終了することを意味します。例:Ctrl+C
コマンドがfind
実行中でfind
プロセスがシグナルを受信するとSIGINT
ヒットします。この信号を処理することは実装に依存しますが、通常、プロセスを正常に終了することを意味します。プログラムが正常に終了すると、プログラムで最後に実行された文関数がC
正常に返されたときに発生します。main
これは、例えば、全てのコマンドを完了せずに非決定論的に終了するプロセスとは対照的である。これは、プログラムエラーまたはプログラムを終了する他のプロセス信号が原因で発生する可能性があります。異常終了は、通常、x
実行中の状態やイベントが「正常」でないことを示す一部の戻り値を使用して、子プロセスが親プロセスに中断/終了するなど、プログラムに実装されているロジック内で決定されます。たとえば、プロセスはSIGKILL
信号を受信します。信号を処理できず、プロセスが終了します。
ここで、プロセスの抽象化は、呼び出しプロセス(シェルなど)に値を返す機能を共有するという点で、プログラミング機能と似ています。これらの戻り値の意味は、「成功」または「失敗」呼び出しの条件を定義します。したがって、この場合、これらの意味を定義または使用することはプログラマーの責任です。
具体的な例を挙げると、実行されたコマンドはbash
終了時に最終的に呼び出し側に値を返します。ここで、これ以外の値は、0
コマンドが異常終了したことを示します。bash
変数を調べて、$?
最後に実行された文の戻り値を確認できます。この戻り値を使用すると、存在しないファイルの読み込みを防ぐなど、スクリプトの実行フローを制御するのに役立ちます。
メモリに割り当てられたアドレス空間と関連リソースを解放し、タスクのCPUスケジューリングなど、プロセスの終了について話すときに考慮すべきその他の点がありますが、これは別の章です。
答え2
今は学校で何を教えるのかよく分からないが、正常終了「状態0(ゼロ)で終了」を意味します。
(少なくともCプログラムでは)これを行う3つの方法を考えることができます。
return 0; /* 1 */
exit(0); /* 2 */
_exit(0); /* 3 */
私の考えでは、(1)と(2)はほぼ同じですが、(3)は出力バッファをフラッシュせずにプロセスを終了させます。フォーク/実行状況でこれを使用すると、子プロセスが終了する前にバッファリングされたバイト(カーネルまたはstdioを介して)の二重出力を防ぐことができます。
答え3
プロセスを終了するには、シグナルそれに転送されます。これらのシグナルのほとんどについて、プロセスはこれらのシグナルをキャプチャし、いくつかの操作(ネットワークリソースの解放、さよならの印刷)を実行し(ほとんどの場合)終了することがあります。
私が説明したのは、プロセスを正常に終了する方法です。プロセスが操作を完了した場合、またはGUIプログラムの「x」ボタンを使用してプロセスを終了することもできます。でもUnix関連サイトなのでそうではないようです。
両方の信号はプロセスによって捕捉できません。信号を殺すそして停止信号。 SIGKILLによる終了は異常終了とみなされます。
正常終了
killall -SIGHUP firefox
killall -SIGINT firefox
異常終了
killall -SIGKILL firefox