『なるほどUnixプロセス』を再読

『なるほどUnixプロセス』の2回目を読み終えた。Unix の基本的なプログラミングから、Resqueや Unicornのプロセス管理まで書かれている。普段の仕事でちゃんと意識できていないレイヤーなので面白かった。(直接的もしくは明示的に触れているレイヤーより低いレイヤーまで理解することは、すぐには仕事に役立たないかもしれないが、後々効いてくるのではないかと考えている。)

個人的に興味深かったところをいくつか抜粋する。

fork(2)

if fork
puts 'enterd the if block'
else
puts 'enterd the else block'
end

上のコードを実行すると、下のようにif句とelse句の両方が実行される。

enterd the if block
enterd the else block

少し奇妙な感じがするが、単に親プロセス側のforkは生成した子プロセスのpidを返すのでif句を実行し、子プロセス側のforkはnilを返すのでelse句を実行しているだけである。

デーモンプロセス

  1. fork(2)して子プロセスを生成し、親プロセスを終了させる(端末の制御はユーザーに戻っている)
  2. 生成した子プロセスをプロセスグループとセッショングループのリーダーにする
  3. もう一度fork(2)して、子プロセス(プロセスグループのリーダーでもセッショングループのリーダーでもない)を生成し、親プロセスを終了させる

上の手順で生成した最後のプロセスはセッションリーダーではないので、制御端末を持たないことが保証される。Rackのコードは下のようになっている。

def daemonize_app
if RUBY_VERSION < "1.9"
exit if fork
Process.setsid
exit if fork
Dir.chdir "/"
STDIN.reopen "dev/null"
STDOUT.reopen "dev/null", "a"
STDERR.reopen "dev/null", "a"
else
Process.daemon
end
end

ここではデーモンの起動中に作業ディレクトリが削除される可能性、プログラムが標準ストリームを利用する可能性を考慮している。また、Rubyの1.9以上だと`Process.daemon`だけで、現在のプロセスをデーモン化できる。

今後

Software engineer