Tuesday, May 20, 2014

[メモ] Apache+mod_sslでSIGBUSが発生した件

@hirose31さんと、Apache HTTPDからHTTPSでファイルダウンロード中にサーバプロセスがSIGBUSで死ぬって件にぶちあたり、

「OpenSSLの中でmemcpyがSIGBUSしてます」「な、なんだってー!」

って調べたのですが、理由は以下のとおりだった。

  • HTTPSの場合、デフォルト設定だとファイル読込にmmap(2)が使われる
    • mmapされたファイルのサイズが変更されてもApacheはそれを検知しようがない
    • そして、ファイル末尾以降のデータを読もうとするとセグメンテーションエラー(SIGBUS)が発生し、Apacheのサーバプロセスは異常終了する
  • HTTPの場合は、ローカルファイルシステムの場合sendfile(2)が使われるので、ファイルサイズが変更になってもApacheは異常終了しない

この動作はApacheの「仕様」っぽいです。日本語版だとNFS特有の現象のように読めるけど、英語版は以下のように書かれています。
Deleting or truncating a file while httpd has it memory-mapped can cause httpd to crash with a segmentation fault.
EnableMMAP Directive - core - Apache HTTP Server
言われてみれば当然だけど、mmapやsendfile等を自動的に使い分けているサーバの場合、これが原因だとは気づきにくいですよね。

というわけで、ApacheでHTTPSサイトを構築する場合はEnableMMAP Offにしておきましょう、さもないとアラートが上がってきたりしてウザいですよという話でした。本当は配信ファイルを全てアトミックに更新できばいいのですが、運用的にできないこともありますからね。

Apache以外のサーバでも同様の問題があるかどうかは知りません。

No comments:

Post a Comment