OSがプロセスをフォークするときにCopy on Write最適化を実行するのを見てきました。理由は、ほとんどの場合forkがexecによって処理されるため、ページ割り当てのコストが発生したり、呼び出し元のアドレス空間から不必要にデータがコピーされたりしたくないからです。
これは、ext4またはxfs(ジャーナリング)ファイルシステムを搭載したLinuxでCPを実行するときにも発生します。起こらない場合は、なぜですか?
検索するキーワードはreflink
です。最近XFSに実装されました。
編集:XFS実装は、最初は実験的とマークされていました。この警告は、上記を書いてから数か月後のカーネルリリース4.16で削除されました:-)。
Linuxには、ユーザースペースプロセスがカーネルにファイルの書き込みコピーをコピーするように指示することを可能にするシステムコールがあります。 ioctlのオプションとして使用されるFICLONERANGEとFICLONEは、ファイルの書き込み時のコピーとファイル内の範囲のコピーを作成できるようにします。
これは、ファイルシステムがこれをサポートするコピーを作成するためにcp --reflinkによって使用されます。
cp
のsyscallを導入しない限り(または少なくともブロックをコピーする場合)、OSはcp
プログラムが書き込むデータが1つだけ別のブロックから読み取ります。その上、「複数のファイルが同じブロックを共有する」シナリオを管理するための追加のオーバーヘッドがあります。少数のブロックのみが異なる大きな類似ファイルはめったに発生しません。したがって、これらのブロックをコピーしてから、この管理オーバーヘッドをallファイルに追加する方が全体としては安上がりです。
ここで、たとえばBTRFSにファイルシステムの別のクローン/スナップショットを追加してファイル(それらの多く)を「コピー」する場合、状況は異なります。「コピー」したallファイルファイルシステム、およびそれらへの変更はすべてコピーオンライトになります。これは存在しますが、ext4にはありません。
「ジャーナリング」はそれとは完全に独立した概念であり、重要なのはファイルの管理構造です。