Linuxでのファイル編集は直接ディスクに保存されますか?


57

以前は、ファイルの変更はディスクに直接保存されると考えていました。つまり、ファイルを閉じて、保存をクリックするか選択するかを決めるとすぐに。しかし、最近の会話で、私の友人は私には、通常は真実ではないと言った。OS(具体的にはLinuxシステムについて話していました)はメモリ内の変更を保持し、メモリからディスクにコンテンツを実際に書き込むデーモンを持っています。

彼は、外部フラッシュドライブの例を挙げました。これらはシステムにマウントされ(メモリにコピーされ)、デーモンがまだコンテンツをフラッシュメモリに保存していないためにデータが失われることがあります。それがフラッシュドライブをアンマウントする理由です。

私はオペレーティングシステムが機能することについての知識を持っていないので、これが真実であるかどうか、そしてどのような状況であるかは全くわかりません。私の主な質問は次のとおりです。これはLinux / Unixシステム(および他のOS)で説明されているように起こりますか?たとえば、これは、ファイルを編集して保存した直後にコンピューターの電源を切ると、変更が失われる可能性が高いことを意味しますか?おそらく、ディスクの種類に依存します-従来のハードドライブとソリッドステートディスクのどちらですか?

質問は、明確化や比較が受け入れられたとしても、情報を保存するディスクを備えたファイルシステムに特に言及しています。


8
FAO:投票キューレビューアーを閉じます。これは学習教材のリクエストではありません。参照してくださいunix.meta.stackexchange.com/q/3892/22812
アンソニー・Gを-正義をモニカのために

2
キャッシュはユーザーにとって不透明であり、最良の場合sync、アプリケーションはflushキャッシュが書き戻されることを保証する必要がありますが、成功syncした場合でもカーネルキャッシュがディスクにフラッシュされるだけで物理ディスクへの書き戻しは保証されないため、遅延が発生する可能性がありますドライバーまたはディスクハードウェア(たとえば、失われたドライブ上のキャッシュ)
-crasic

1
教材を求めることには同意しませんが、その質問は現在の形では少し広いと思います。スコープをLinuxディストリビューション(または特定のOS)に制限し、場合によっては特定のストレージテクノロジーとファイルシステムに制限します。
ジェフシャラー

3
@AnthonyGeogheganが指摘したように、私はこの質問を学習教材のリクエストとは考えていません。かなり具体的だと思います。Linuxファイルシステムに関する長くて深い説明やマニュアルは求めませんでした。明確にしたかった簡単なアイデアについてのみ。
JuanRocamonde

3
@JeffSchallerのように、少し広いかもしれません。少し編集してみます。しかし、正直なところ、このサイトがLinuxの機能に直接対処するこの種の質問用ではない場合、それは何のためですか?
JuanRocamonde

回答:


70

ファイルを編集して保存した直後にコンピューターの電源をオフにすると、変更内容が失われる可能性がありますか?

彼らかもしれない。「最も可能性が高い」とは言いませんが、可能性は多くのことに依存します。


ファイル書き込みのパフォーマンスを向上させる簡単な方法は、OSがデータをキャッシュするだけで、書き込みが行われたアプリケーションに伝え(嘘をついて)、実際に後で書き込みを行うことです。これは、他のディスクアクティビティが同時に進行している場合に特に便利です。OSは読み取りを優先し、後で書き込みを行うことができます。また、一時ファイルがその後すぐに削除される場合など、実際の書き込みの必要性を完全に削除することもできます。

ストレージが遅い場合、キャッシュの問題はより顕著になります。高速のSSDから低速のUSBスティックにファイルをコピーするには、USBスティックが追いつかないため、書き込みキャッシュが大量に必要になります。ただし、cpコマンドの戻り速度が速いため、作業を続行できます。コピーしたファイルを編集することもできます。


もちろん、そのようなキャッシングにはマイナス面があり、実際に保存される前に一部のデータが失われる可能性があります。編集者が書き込みは成功したがファイルが実際にディスク上にないことを伝えた場合、ユーザーは不満を抱きます。これが、ファイルが実際にディスクにヒットした後にのみ返されることになっているfsync()システムコールがある理由です。編集者はそれを使用して、書き込みが成功したことをユーザーに報告する前にデータが正常であることを確認できます。

ドライブ自体がOSに同じ嘘をつき、書き込みが完了したと言うかもしれませんが、ファイルは実際にはドライブ内の揮発性書き込みキャッシュにしか存在しないので、私は「そうなっている」と言いました。ドライブによっては、それを回避する方法がない場合があります。

に加えてfsync()、システム全体の書き込みまたは特定のファイルシステム上のすべての書き込みがディスクにヒットしたことを確認するようシステムに要求するsync()およびsyncfs()システムコールもあります。ユーティリティsyncを使用してこれらを呼び出すことができます。

次に、に対するO_DIRECTフラグopen()もあります。これは、「このファイルとの間のI / Oのキャッシュ効果を最小限に抑えようとする」ことになっています。キャッシュを削除するとパフォーマンスが低下するため、独自のキャッシュを実行し、それを制御したいアプリケーション(データベース)で主に使用されます。(O_DIRECT問題がないわけではありませんが、manページのコメントはやや面白いです。)


停電時に何が起こるかは、ファイルシステムにも依存します。心配する必要があるのはファイルデータだけではなく、ファイルシステムメタデータです。ファイルデータをディスクに保存しても、見つからない場合はあまり役に立ちません。ファイルをより大きなサイズに拡張するだけでは、新しいデータブロックを割り当てる必要があり、どこかにマークを付ける必要があります。

ファイルシステムがメタデータの変更を処理する方法と、メタデータとデータの書き込みの順序は大きく異なります。たとえば、を使用してext4、マウントフラグを設定するdata=journalと、すべての書き込み(データ書き込みを含む)がジャーナルを通過するため、かなり安全になります。また、2回書かれることになるため、パフォーマンスが低下します。デフォルトのオプションは、メタデータが更新される前にデータがディスク上にあるように書き込みを順序付けようとします。他のオプションまたは他のファイルシステムは、より良い場合も悪い場合もあります。私は包括的な研究さえ試みません。


実際には、負荷の軽いシステムでは、ファイルは数秒以内にディスクにヒットするはずです。リムーバブルストレージを扱う場合は、メディアを引き出す前にファイルシステムをアンマウントして、データが実際にドライブに送信され、それ以上のアクティビティがないことを確認してください。(または、GUI環境にそれを行わせてください。)


あなたのsome cases whereリンクはそのような場合について言っていないようです—それは代わりにアプリ使わなかったときに問題があったと言ってますfsync。または、あなたが指摘しているこれらのケースを見つけるためにコメントを調べる必要がありますか?
ルスラン

1
syncシステムシェルコマンドとして直接使用して、カーネルを突いてすべてのキャッシュをフラッシュすることもできます。
古典的な

3
実際には、負荷の軽いシステムでは、ファイルはすぐにディスクにヒットします。 エディターfsync()がファイルの書き込み後に使用する場合のみ。Linuxのデフォルト/proc/sys/vm/dirty_writeback_centisecsは500(5秒)であり、PowerTopでは1500(15秒)に設定することをお勧めします。(kernel.org/doc/Documentation/sysctl/vm.txt)。負荷の軽いシステムでは、カーネルはすぐwrite()にディスクにフラッシュする前にページキャッシュ内でダーティになり、すぐに削除または変更された場合に最適化されます。
ピーター

2
ドライブ自体がOSに同じ嘘をつく可能性があるため、 + 1 。私の理解では、この種のキャッシュを行うドライブには、壊滅的な電力損失が発生した場合でもキャッシュを保存できる十分な電力容量があります。これはOS固有ではありません。Windowsには、ユーザーがプラグを抜く前にキャッシュをフラッシュする「USBを安全に取り外す」メカニズムがあります。
スタド

1
@studog、私は、特に消費者向けのハードウェアではそうは思いません。しかし、それは単なる妄想かもしれません。ただし、テストするのは面白いでしょう。
-ilkkachu

14

ファイルの編集が常に直接ディスクに保存されるということはありえないことを証明する非常に簡単な方法があります。つまり、そもそもディスクによってバックアップされていないファイルシステムがあるという事実です。ファイルシステムがいない場合は持っている最初の場所でディスクを、それはおそらくすることができない、ディスクへの変更を書き、これまで

以下に例を示します。

  • tmpfs、RAM(より正確には、バッファキャッシュ)にのみ存在するファイルシステム
  • ramfs、RAMにのみ存在するファイルシステム
  • 任意のネットワークファイルシステム(NFS、CIFS / SMB、AFS、AFP、…)
  • 任意の仮想ファイルシステム(sysfsprocfsdevfsshmfs、...)

しかし、ディスクでバックアップされたファイルシステムの場合でも、通常これは当てはまりません。「SQLiteデータベースの破損方法」ページには、「同期の失敗」という章があり、書き込み(この場合はSQLiteデータベースへのコミット)がディスクへの到着に失敗するさまざまな方法について説明しています。SQLiteには、Atomic Commit In SQLiteを保証するために飛び越えなければならない多くのフープを説明するホワイトペーパーもあります。(ことに注意してくださいアトミック書き込みが単なる問題よりもはるかに困難で書くが、もちろん、ディスクへの書き込みがアトミック書き込みのサブ問題であり、あなたはこの論文から、あまりにも、その問題について多くのことを学ぶことができます。)本論文では、持っています上のセクションが間違って行くことができます物事についてのサブセクションが含まれて不完全なディスクフラッシュは、書き込みがディスクに到達するのを妨げる可能性のある微妙な複雑さの例を示します(実際にディスクに書き込みが行われていないことをHDDコントローラーが報告するなど)。 ATAの仕様では合法である場合もあります。これは、この点であいまいに表現されているためです)。


10
この答えの最初の部分は、使用された正確な単語についてただ熱心に語っています。ユーザーを笑する以外の目的にどのように役立つのかわかりません。明らかに、ネットワークファイルシステムはローカルディスクに書き込みを行いませんが、問題はまだそこにあります。
パイプ

3
@pipeが指摘したように、データを保存するためにディスクを使用しないため、ディスクにデータを保存しないファイルシステムがあるという事実は、それを持っている人がそれを直接保存するかどうかを決定しません。しかし、答えは面白そうです
-JuanRocamonde

1
@pipe「ベッサーヴィッサーリング」という用語を使用することは、ベッサーヴィッサーリングであると確信しています。権威を持つドイツのベッサーウィッサーとしてそれを言っています。
フォルカーシーゲル

11

Unix、Linux、Windowsを含むほとんどのオペレーティングシステムが書き込みキャッシュを使用して操作を高速化するのは事実です。つまり、シャットダウンせずにコンピューターの電源を切ることは悪い考えであり、データ損失につながる可能性があります。USBストレージを取り外す準備ができる前に取り外した場合も同様です。

ほとんどのシステムには、書き込みを同期化するオプションもあります。つまり、アプリケーションが成功の確認を受け取る前に、データはディスク上にありますが、速度は遅くなります。

つまり、コンピューターを適切にシャットダウンし、USBストレージを適切に取り外し準備する必要があるのには理由があります。


お返事ありがとうございます!Linuxで特定のファイルのディスク書き込みを強制する方法はありますか?たぶん、チュートリアルやドキュメントページへのリンク、SEの質問でも問題ありません:)
JuanRocamonde

4
fsync()プログラムからのsyscallを使用して、ファイルの書き込みを強制できます。シェルから、単にsyncコマンドを使用します。
RalfFriedl

2
Linuxの一部のバージョンにはいくつかのファイルシステムがあります(少なくともありました)sync。さらにはファイルシステムのため、正しく実装しsync、いくつかのディスクファームウェアが実装問題まだあるFLUSH CACHEノーオペレーションとして、またはすぐにそれから戻ると、バックグラウンドでそれを行うには。
ヨルグWミッターグ

9

1.フラッシュベースのストレージ

ディスクの種類(従来のハードドライブとソリッドステートディスク)または私が知らない他の変数に依存しますか?Linuxでのみ発生しますか(発生した場合)、他のOSでも発生しますか?

選択肢がある場合は、クリーンなシャットダウンを行わずにフラッシュベースのストレージが電力を失うことを許可しないでください。

SDカードのような低コストのストレージでは、消去ブロック全体(4KBよりも数倍大きい)が失われ、異なるファイルまたはファイルシステムの重要な構造に属する可能性のあるデータが失われることが予想されます。

一部の高価なSSDは、電源障害が発生した場合により良い保証を提供すると主張する場合があります。ただし、サードパーティのテストでは、多くの高価なSSDがこれに失敗することが示唆されています。「ウェアレベリング」のためにブロックを再マップするレイヤーは複雑で独自のものです。考えられる障害には、ドライブ上のすべてのデータの損失が含まれます。

テストフレームワークを適用して、合計3000回を超える障害注入サイクルを使用して、6つの異なるベンダーの17種類のコモディティSSDをテストします。私たちの実験結果は、テストした17台のSSDデバイスのうち14台が、ビット破損、切り込み書き込み、非シリアル化書き込み、メタデータ破損、デバイス全体の障害など、電源障害時に驚くべき障害動作を示すことを示しています。

2017:https : //dl.acm.org/citation.cfm?id=2992782&preflayout=flat

2013:https : //www.usenix.org/system/files/conference/fast13/fast13-final80.pdf?wptouch_preview_theme=enabled

2.回転するハードディスクドライブ

回転するHDDにはさまざまな特性があります。安全性とシンプルさのために、フラッシュベースのストレージと同じ実際的な不確実性があると仮定することをお勧めします。

特定の証拠がない限り、明らかにそうではありません。私は、HDDを回転させるための比較数値を持っていません。

HDDでは、不完全に書き込まれた1つのセクターに悪いチェックサムが残る可能性があります。これにより、後で読み取りエラーが発生します。大まかに言って、HDDのこの障害モードは完全に予期されています。ネイティブLinuxファイルシステムは、それを念頭に置いて設計されています。彼らはfsync()、このタイプの電力損失障害に直面して契約を維持することを目指しています。(SSDでこれが保証されることを本当に望んでいます)。

しかし、Linuxファイルシステムがすべての場合にこれを達成するかどうか、またはそれが可能かどうかはわかりません。

このタイプの障害の後の次の起動では、ファイルシステムの修復が必要になる場合があります。これはLinuxであるため、ファイルシステムの修復で不明な質問が表示される可能性があります。Yを押すだけで解決できることを期待できます。

2.1 fsync()コントラクトがわからない場合

fsync()コントラクトは、良いニュースと悪いニュースの両方のソースです。最初に良いたよりを理解しなければなりません。

良いニュース:fsync()ファイルデータを書き込む正しい方法として文書化されています(たとえば、「保存」を押したとき)。そして、例えば、テキストエディタは、を使用してアトミックに既存のファイルを置き換えなければならないことが広く理解されていますrename()。これは、常に古いファイルを保持するか、新しいファイル(fsync()名前を変更する前に編集された)を取得することを確認するためのものです。新しいファイルの半分書かれたバージョンを残したくありません。

悪いニュース:長年の間、最も人気のあるLinuxファイルシステムでfsync()を呼び出すと、システム全体が事実上数十秒間ハングする可能性がありました。アプリケーションはこれについて何もできないので、fsync()なしでrename()を楽観的に使用することは非常に一般的でした。これは、このファイルシステムで比較的信頼できるようです。

したがって、fsync()を正しく使用しないアプリケーションが存在します。

このファイルシステムの次のバージョンでは、fsync()のハングを回避しました-同時に、fsync()の正しい使用に依存するようになりました。

これはすべてかなり悪いです。この歴史を理解することは、多くの相反するカーネル開発者によって使用された退屈な口調と悪意によって助けられないでしょう。

現在の解像度は、現在最も人気のあるLinuxファイルシステムです デフォルトでは、fsync()を必要とせずにrename()パターンをサポートします以前のバージョンとの「バグとバグの互換性」を実装します。これはマウントオプションで無効にできますnoauto_da_alloc

これは完全な保護ではありません。基本的には、rename()時に保留中のIOをフラッシュしますが、名前の変更前にIOの完了を待機しません。これは、たとえば60秒の危険ウィンドウよりもはるかに優れています!既存のファイルをrename()で置き換えるときにクラッシュ安全のためどのファイルシステムがfsync()を必要とするのという答えも参照してください

人気のないファイルシステムの中には、保護を提供しないものがあります。XFS はそうすることを拒否します。そしてUBIFSもそれを実装していません。明らかに受け入れられましたが、それを可能にするには多くの作業が必要です。同じページでは、UBIFSには、電力損失など、データの整合性に関する他の「TODO」問題がいくつかあることが指摘されています。UBIFSは、フラッシュストレージで直接使用されるファイルシステムです。UBIFSが言及しているフラッシュストレージの問題のいくつかは、SSDのバグに関連していると思われます。


5

負荷の軽いシステムでは、カーネルは、新しく書き込まれたファイルデータを、write()ディスクにフラッシュする前に、おそらく30秒後にページキャッシュに配置し、すぐに削除または変更された場合に最適化します。

Linuxのdirty_expire_centisecsデフォルトは3000(30秒)で、新しく書き込まれたデータが「期限切れ」になるまでの時間を制御します。(https://lwn.net/Articles/322823/を参照)。

関連する調整パラメータについてはhttps://www.kernel.org/doc/Documentation/sysctl/vm.txtを、その他の調整パラメータについてはgoogle をご覧ください。(例:google on dirty_writeback_centisecs)。

Linuxのデフォルト/proc/sys/vm/dirty_writeback_centisecsは500(5秒)です。PowerTopでは、電力消費を削減するために1500(15秒)に設定することをお勧めします。


また、ライトバックの遅延は、ファイルをディスクに書き込む前に、カーネルがファイルの大きさを確認する時間を与えます。遅延割り当てのファイルシステム(XFSや、おそらく最近のようなもの)は、iノード自体のスペースの割り当てとは別に、必要に応じて、新しく書き込まれたファイルのデータをディスク上のどこに置くかさえ選択しません。これにより、たとえば、他のファイル間の1メガのギャップに大きなファイルの先頭を置くことを回避できるため、断片化が軽減されます。

大量のデータが書き込まれている場合、ディスクへのライトバックは、ページキャッシュにどれだけダーティな(まだディスクに同期されていない)データがあるかについてのしきい値によってトリガーできます。

ただし、他のことをあまり行わない場合は、小さなファイルを保存してから5秒(または15秒)ハードディスクドライブのアクティビティライトが点灯しません。


エディターfsync()がファイルの書き込み後に使用した場合、カーネルは遅滞なくディスクに書き込みます。(そしてfsync、データが実際にディスクに送信されるまで戻りません)。


ディスクの書き込みキャッシュも問題になりますが、ディスクは通常、Linuxのページキャッシュアルゴリズムとは異なり、できるだけ早く書き込みキャッシュを永続的なストレージにコミットしようとします。ディスク書き込みキャッシュは、書き込みの小さなバーストを吸収するためのストアバッファーになりますが、読み取りを優先して書き込みを遅らせ、ディスクファームウェアにシークパターンを最適化する余地を与えることもできます(たとえば、1つではなく2つの近くの書き込みまたは読み取りを行う、その後、遠くを探し、次に戻って探します。)

回転(磁気)ディスクでは、書き込みの前に保留中の読み取り/書き込みがあった場合、SATA書き込みコマンドからのデータが電源オフから実際に安全になる前に、それぞれ7から10ミリ秒のシーク遅延がいくつか発生する場合があります。(この質問に関する他のいくつかの回答は、ディスク書き込みキャッシュと、ジャーナリングされたFSが破損を回避するために使用できる書き込みバリアについてより詳細に説明します。)

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.