Skip to content

Instantly share code, notes, and snippets.

@4ge32
Created April 22, 2019 10:57
Show Gist options
  • Save 4ge32/7139dfd3041d4d4723cd9faff18e9279 to your computer and use it in GitHub Desktop.
Save 4ge32/7139dfd3041d4d4723cd9faff18e9279 to your computer and use it in GitHub Desktop.

A fork() in the road を読んで

HotOS 2019 で Microsoft Research からの論文である.Unixの代表的なシステムコールであるfork()についての問題点を挙げている.

概要

fork()は最も基本的なシステムコールといっても良く,新しいプロセスを作るときに使われる.今回の論文の主張はfork()は1970年代のマシンではハックと呼べるものだったが,現代では過去の負債となっているというものでおり,カーネルから完全に取り除くべきであるというものである.ただし,ここでいうカーネルとはLinuxカーネルのことを直接指しているのではなく,著者の先行研究でのOSの実装のことを指している.

面白いのは,fork()は研究者にとっては研究を阻害するといったことや,教育者は歴史としては教えるべきだが最初に教わるべきプロセス作成の仕組みとしてはふさわしくないといった中々過激なことを言っているところである.

問題点

現代的なコンピュータシステムにおける問題点として次のようなことが挙げられている.

  • かつてはシンプルであったが,最早そうではない
    • 25もの特別なケースが親プロセスの状態を子プロセスにコピーするときに存在する.例えば,ファイルロック,タイマー,非同期IOやトレーシングなど.また,コピー後のメモリマッピングに関して,madvice()に与えるフラグも非常に多いものとなっている.
  • fork() はユーザ空間においてOSの抽象化をうまく扱えていない
    • 例えばバッファIOについてユーザは明示的にfork()の前にバッファをフラッシュする必要がある.
  • スレッドセーフでない
    • fork()によって作成されたプロセスはシングルスレッドのみとなる.親プロセスが関連するスレッドをシリアライズしない限り,子プロセスのメモリ空間は一貫性が保たれないものになってしまう可能性がある.一つのケースとして,一スレッドがメモリ割当を行うためにヒープをロックする一方でもう一つのプロセスがfork()を発行するといった状況が挙げられる.子プロセス内でメモリ割当を試みようとするとデットロックに陥る(本当か?).いくつかのUnixプログラミングガイドにおいてはマルチスレッドでのfork()を使用しないか,使用後にすぐにexec()を呼ぶことを推奨している.
  • セキュアでない
    • fork()は子プロセスが親からすべてを引き継ぐためセキュリティの観点から望ましくない.プログラマはファイルやメモリ,名前空間などにおける責任を明確に持たなければならない.
  • 遅い   * vfork()やcopy-on-writeによって高速化がなされてきた.しかし,最近ではcopy-on-writeのマッピングの時間でさえも問題となっている.Chromeでは最大100msもの遅れが生じ,Node.jsでは秒単位の遅れがfork()とexec()の間で起こりうる.そのため,標準ライブラリではposix_spawn()をfork()の代わりに用いるようにしているが,アプリケーションが直接fork()を読んでいるケースまで対応することは勿論できない.
  • スケールしない
    • fork()に先立つcopy-on-write()のマッピングがボトルネックになることは上記に述べた.しかし,fork()の仕様そのものがスケーラビリティに悪影響を及ぼすと主張されている.スケーラビリティの向上には不必要な資源共有を避けることが重要であるが,fork()は親プロセスとすべてを共有する.
  • メモリを使いすぎる *

スレッドとfork()について

以下の標準ライブラリ関数が内部でグローバルデータについて排他制御を行っており,fork()と併せて使用すべきではないものの例である(2009年時点).

  • malloc()
  • stdio (printf()など)
  • syslog()

マルチスレッド環境下において役に立つfork()の代替 pthread_atfork()

研究用OSでのfork()の考察

良い参考文献

UNIX上でのC++ソフトウェア設計の定石 (3)

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment