[an error occurred while processing this directive] [an error occurred while processing this directive]

C-c で片方を kill したら、相手も道連れに。(SIGPIPE)

サーバ・クライアントプログラムを C で書いて、通信の実験中、 クライアントを Ctrl-c (C-c) で止めると、なぜかサーバも道連れになってしまう。
落ちるところは普通の send()。返り値がいくつ、とかチェックする間もなく落ちてしまう。 でも、クライアントを C-z で一度止めて kill したときには落ちない。 パケットキャプチャしてみると、どちらのケースでも FIN ではなく RST (リセット)パケットが飛んでいる。
いろいろ調べてみると、間が悪くRST パケットが飛んでくると、 SIGPIPE が返される模様。それで、SIGPIPE のシグナルハンドラが動いて、サーバプロセスも 道連れになってしまうみたい。
この挙動を止めるには、以下のように書いて SIGPIPE のシグナルハンドラを無効にする。
#include 

...

int main(){

  signal( SIGPIPE , SIG_IGN );
でも、man を見ていたら、send のオプションで抑制することもできるらしい。
MSG_NOSIGNAL (Linux 2.2 以降) 
ストリーム指向のソケットで相手側が接続を切断した時に、エラーとして 
SIGPIPE を送信しないように要求する。この場合でも EPIPE は返される。
ちなみに、sigpipe は、元々パイプでつながったプロセスのために作られたもの。 例えば、
$ grep なんとか | head -10
としたときに、右側の head は 10行読んだら、左の grep の処理はもう不要になってしまう。
こういうとき、左のプロセスに対し、SIGPIPEが送られる。
[an error occurred while processing this directive]