ユーザランドのプロセスから見たwrite(2)は、ページキャッシュのおかげで(メモリが潤沢にある環境下では)ブロックされない(待たされない)というのは id:naoya さんの丁寧な解説のおかげでわかると思うのですが、一方、fsync(2)などの実際にディスクに書き込む処理、
あと id:hirose31 さんがコメントしてますが、アプリケーションが SYNC モードでファイルを開いてたり、明示的に fsync() してたりするとそこで wait が発生するのは言わずもがな、です。
Linux I/O のお話 write 編 - naoyaのはてなダイアリー
The fsync() function does not return until the system has completed that action or until an error is detected.
fsync
常に処理待ちとなっている I/O リクエストが存在する、ということなります。なので、ページキャッシュの容量の問題ではなく、ディスクの性能がボトルネックになっている、と言えそうです。
http://blog.mizzy.org/articles/2007/05/25/linux-disk-io-01
は「ディスク」自身が『書き込みが終わったよ』というまでブロックして戻りません。
さて、ハードディスクにはキャッシュメモリ (なういハードディスクは32MBものキャッシュメモリがディスクユニット自体に搭載されているようです) が搭載されています。
にあるように、キャッシュメモリは読み出しだけでなく書き込みの性能も上げてくれます。つまり、OSから「これ、ディスクにちゃんと書き込んでね」と依頼されたときに、ハードディスクは実際の円盤には書き込まずとも、ハードディスクユニット内のキャッシュメモリに書き込んだら「うん。ちゃんと書いたよ!」とお返事を返せるわけです。
こうやってキャッシュメモリ上に格納されたデータは、後でちゃんと円盤に書き込まれて永続化されるわけですが、それまでの間に不意の電源断 (停電、ブレーカ(NFB,MCB,MCCB)が落ちた、電源ケーブルがひっかかって抜けたった) が起ってしまった場合は、キャッシュメモリ上の「ちゃんと書いたよ」といったはずのデータは失われてしまいます。(多分…)
さてさて、一部の RAID カード (例えば3wareのもの) には、256MBものwrite cacheが搭載できる製品があります。こんなにキャッシュしたら万が一電源断したときに失われるデータが多くなるのでは?と心配になるかもしれませんが、大丈夫です。BBUがあれば。
BBU (Battery Backup Unit) とは、電源断になったときに、蓄えておいた電源をキャッシュユニットに供給して、キャッシュ上のデータを保存し続けるためのものです。数十時間は持つようなので、BBUが枯渇するまでに通電再開できればキャッシュ上のデータは保たれますし、後、ハードウエアの電源が投入されディスクが回り始めればキャッシュ上のデータはちゃんと円盤に書き込まれます。
ちなみに、3wareの9550SXとかをLinux 2.6で使ってるのですが、ちゃんと元気に働いてます。DBサーバやストレージサーバなんかで使ってます。
ちょっと定量的な数値はないのですが、体験的にはこのRAIDカードのwrite cacheはかなり効果があると感じています。もちろん用途にもよるのですが、「ディスク」性能で困っている方は、多少の出費は必要ですが、試してみるのもいいんじゃないかと思います。
まとめ
- ユーザランドのプロセス(アプリケーション)から見たwriteは、d:id:naoya:20070523:1179938637 が詳しい
- ついでに、その次の、ほんとに「ディスク」に書き込む処理も考えてみよう
- ハードディスクには、(数MB〜数十MBの)キャッシュメモリが搭載されている
- ハードディスクは、円盤に書かずともキャッシュメモリに書いた時点で「書き込み完了」とOSに返すことができる
- が、キャッシュメモリ上のデータは不意の電源断で失われる可能性がある
- キャッシュメモリのおかげで、『ほんとに「ディスク」に書き込む処理』はより短い時間で返すことができる(ことが期待できる)
ぜひ、おためしを!