ファイル キャッシュ

Windows の既定では、ディスクから読み取られるファイル データとディスクに書き込まれるファイル データはキャッシュされます。 つまり、読み取り操作は、物理ディスクではなく、システム ファイル キャッシュと呼ばれるシステム メモリ内の領域からファイル データを読み取ります。 同様に、書き込み操作では、ディスクではなくシステム ファイル キャッシュにファイル データが書き込まれます。この種類のキャッシュはライトバック キャッシュと呼ばれます。 キャッシュはファイル オブジェクトごとに管理されます。

キャッシュは、Windows の実行中に継続的に動作する キャッシュ マネージャーの方向で行われます。 システム ファイル キャッシュ内のファイル データは、オペレーティング システムによって決定された間隔でディスクに書き込まれ、そのファイル データによって以前に使用されていたメモリが解放されます。これはキャッシュ のフラッシュ と呼ばれます。 ファイルへのデータの書き込みを遅延させ、キャッシュがフラッシュされるまでキャッシュに保持するポリシーは、遅延書き込みと呼ばれ、キャッシュ マネージャーによって決定された時間間隔でトリガーされます。 ファイル データのブロックがフラッシュされる時間は、部分的には、キャッシュに格納されていた時間と、データが読み取り操作で最後にアクセスされてからの時間に基づいて決まります。 これにより、頻繁に読み取られるファイル データが、システム ファイル キャッシュ内で可能な限り長くアクセス可能な状態が維持されます。

このファイル データ キャッシュ プロセスを次の図に示します。

ファイル データ キャッシュ プロセス

前の図の実線矢印に示すように、256 KB のデータ領域は、ファイル読み取り操作中にキャッシュ マネージャーによって最初に要求されたときに、システム アドレス空間の 256 KB キャッシュ "スロット" に読み取られます。 次に、ユーザーモード プロセスによって、このスロット内のデータがそのアドレス空間にコピーされます。 プロセスでデータ アクセスが完了すると、プロセスのアドレス空間とシステム キャッシュ間の点線の矢印で示されているように、変更されたデータはシステム キャッシュの同じスロットに書き戻されます。 キャッシュ マネージャーは、データが一定の時間不要になると判断すると、システム キャッシュとディスクの間の点線の矢印で示すように、変更されたデータをディスク上のファイルに書き戻します。

ファイル データ キャッシュによって提供される I/O パフォーマンスの向上量は、読み取りまたは書き込みされるファイル データ ブロックのサイズによって異なります。 ファイル データの大きなブロックが読み取りおよび書き込まれると、I/O 操作を完了するためにディスクの読み取りと書き込みが必要になる可能性が高くなります。 この種の I/O 操作が増えるにつれて、I/O パフォーマンスがますます低下します。

このような状況では、キャッシュをオフにすることができます。 これは、CreateFiledwFlagsAndAttributes パラメーターの値としてFILE_FLAG_NO_BUFFERINGを渡すことによって、ファイルを開いた時点で行われます。 キャッシュが無効になっている場合、すべての読み取り操作と書き込み操作が物理ディスクに直接アクセスします。 ただし、ファイル メタデータは引き続きキャッシュされる可能性があります。 メタデータをディスクにフラッシュするには、 FlushFileBuffers 関数を 使用します。

フラッシュが発生する頻度は、システム パフォーマンスとシステムの信頼性のバランスを取る重要な考慮事項です。 システムがキャッシュを頻繁にフラッシュしすぎると、大量の書き込み操作のフラッシュが発生すると、システムのパフォーマンスが大幅に低下します。 システムが十分な頻度でフラッシュされない場合は、システム メモリがキャッシュによって枯渇するか、フラッシュの前にシステムの突然の障害 (コンピューターの電源が失われるなど) が発生する可能性が高くなります。 後者の場合、キャッシュされたデータは失われます。

適切な量のフラッシュが確実に行われるように、キャッシュ マネージャーは遅延ライターと呼ばれるプロセスを 1 秒ごとに生成します。 レイジー ライター プロセスは、ディスクに書き込まれるよう最近フラッシュされていないページの 8 分の 1 をキューに入れます。 システムパフォーマンスを最適化するためにフラッシュされるデータの量を常に再評価し、より多くのデータを書き込む必要がある場合は、より多くのデータをキューに入れます。 レイジー ライターは、アプリケーションまたはシステムによって削除されることを前提としているため、一時ファイルをフラッシュしません。

ウイルスチェック ソフトウェアなどの一部のアプリケーションでは、書き込み操作を直ちにディスクにフラッシュする必要があります。Windows では、書き込みキャッシュを使用してこの機能を提供します。 プロセスでは、CreateFile の呼び出しに FILE_FLAG_WRITE_THROUGH フラグを渡すことによって、特定の I/O 操作の書き込みスルー キャッシュを有効にします。 書き込みスルー キャッシュが有効になっている場合でも、データはキャッシュに書き込まれますが、キャッシュ マネージャーは遅延ライターを使用して遅延を発生させるのではなく、データをディスクに直ちに書き込みます。 プロセスでは、 FlushFileBuffers 関数を呼び出すことによって、開いたファイルを強制的にフラッシュすることもできます。

ファイル システム メタデータは常にキャッシュされます。 そのため、ディスクへのメタデータの変更を格納するには、ファイルをフラッシュするか、 FILE_FLAG_WRITE_THROUGHで開く必要があります。