起源
~からhttps://btrfs.wiki.kernel.org/index.php/FAQ#What_are_the_crash_guarantees_of_overwrite-by-rename.3F
名前変更を使用して既存のファイルを上書きするのは原子性です。これは、ファイルの古いコンテンツまたは新しいコンテンツが存在することを意味します。次の順序:
echo "oldcontent" > file # make sure oldcontent is on disk sync echo "newcontent" > file.tmp mv -f file.tmp file # *crash*
減らす
ファイルに「newcontent」が含まれています。 file.tmpが存在しません
。 「oldcontent」を含むファイルに「newcontent」が含まれているか、長さが0であるか、まったく存在しない可能性があります。
このアプローチはfile
一貫性(「新しいコンテンツ」または「古いコンテンツ」を含む)を保証しますが、競合後に新しいデータが回復されたり、回復されなかったりする可能性があります。 (mv file.tmp file
与えられたより興味深い結果)
質問
「以前のコンテンツ」や「新しいコンテンツ」が失われないように、クラッシュ時に操作を再開する方法を実装したいと思います。どうすればいいですか?
これは次のことを保証します。
file
「古いコンテンツ」があるか、「file.tmp
新しいコンテンツ」があります。- または
file
「newcontent」がありますが、file.tmp
存在しません。
echo "oldcontent" > file
echo "newcontent" > file.tmp
# make sure files are on disk
sync
# a crash may happen at any time starting from this point.
ln file.tmp file.tmp2
mv -f file.tmp2 file
rm file.tmp
ベストアンサー1
両方のファイルの内容がディスクにあることを確認してsync
移動します。echo "newcontent" > file.tmp
これにより、「files.tmp
長さがゼロになる可能性がある」バリアントが削除されます。
後で競合が発生した場合、残りの不確実性はsync
ディレクトリエントリにのみ関連します。つまりどのファイルがどこを指しているか。移動後にsync
残る可能性は、あなたがリストしたものです。
file
「前のコンテンツ」が存在し、「前のコンテンツ」が含まれ、file.tmp
「新しいコンテンツ」が存在して含まれます。file
存在し、「newcontent」を含みますが、file.tmp
存在しません。
他の場所に接続してfile.tmp
安全装置を追加する必要はありません。
移動するとsync
他の結果が発生します。特に、データ損失に時間がかかります。今後これsync
。