- ベストアンサー
c言語でプロセスIDを調べたい
unixのコマンドで ps aux と打つと "ユーザー名" "プロセスID" 。 。 。 。 がでますけど、この2番目の"プロセスID"を調べる関数ってありますか? ※というのも、プロセスID(ジョブ番号)を引数にして、そのプロセスが終了したら何か処理をさせるというプログラムを作りたいからです。よろしくお願いします。
- みんなの回答 (2)
- 専門家の回答
質問者が選んだベストアンサー
最適な方法はOSの種類によって異なるのですが、最近の UNIX なら procfs が /proc にマウントされていることがあり(機能としてprocfsが用意されていても、デフォルトインストールだとマウントされていない場合もあります)、これを利用する方法が考えられます。 procfs は 仮想的なファイルシステムで、たとえばプロセスID 12345のプロセスが存在する場合は、/proc/12345 というディレクトリが(勝手に)出来、その中にプロセスに関する詳細情報を得ることができる仮想的なファイルが(やはり勝手に)配置されます。そして、プロセスが消えると、それらのディレクトリ・ファイルは消滅します。 (どのような詳細情報を得られるかはOSによって大きく異なるようです。) この "/proc/12345" などのパス(ディレクトリ)が存在するかどうかを stat(2)などでテストすれば、特定のPIDのプロセスが存在するかがわかります。 int pid = 12345; /* 調べたい PID */ char path[50]; struct stat sb; snprintf(path, 50, "/proc/%d", pid); if(stat(path, &sb) == 0) { /* プロセスが存在する */ } else { /* 存在しない */ } なお、この方法では、当然ながらプロセスが終了したかどうかを一定時間毎に stat(2)を呼んで調べる必要があるという問題があります。また、監視対象のプロセスが終了した後に、同じPIDでまったく別のプロセスが上がってくるケースも理論上は考えられ、statを呼び出す時間間隔によっては、そのようなケースでは監視対象プロセスの終了を検出できない、というおそれもあります(最近のUNIXでは、一度使用したPIDはなるべく再利用しないようになっている場合が多いので、その確率は非常に小さいですが)。 OSによっては、特定のプロセスが終了したことをカーネルが能動的に通知してくれる機能が提供されている場合がありますので(FreeBSD なら kqueue など)それを利用したほうが効率がよく、確実にプロセスの終了を検知できるプログラムを書けるでしょう。
その他の回答 (1)
- επιστημη(@episteme)
- ベストアンサー率46% (546/1184)
popen が一番楽ではないかと。 FILE* fp = popen("ps aux","r"); ...
お礼
ありがとうございます。 やってみたんですが、プロセスがいつ死んだかを常にスキャンし続けるため、popenを連発することになるのですが、そうするとそれらが全て別プロセスとして発生するので、popenのプロセスがかなり大量に発生し、スマートじゃありません。その結果かどうか分かりませんが、処理が長くなりすぎるとプログラムが途中で落ちてしまいました。
お礼
ありがとうございます。 /proc以下にファイルができるんですね。 おかげで良いプログラムができました。