
想像一下使用以下命令建立的檔案:
truncate -s1T file
echo test >> file
truncate -s2T file
我現在有一個 2 tebibyte 檔案(在磁碟上佔用 4kiB),"test\n"
寫入在中間。
我如何"test"
有效地恢復它,即無需讀取整個文件。
tr -d '\0' < file
會給我結果,但這需要幾個小時。
我想要的是只輸出檔案的非稀疏部分(因此上面僅"test\n"
或更可能是在儲存該資料的磁碟上分配的 4kiB 區塊)。
有 API 可以找出文件的哪一部分已分配(FIBMAP、FIEMAP、SEEK_HOLE、SEEK_DATA...),但哪些工具會公開這些內容?
一個可移植的解決方案(至少對於支援這些 API 的作業系統)將受到讚賞。
答案1
到目前為止我能想到的最好的方法是(ksh93,filefrag
從e2fsprogs
1.42.9 開始使用(一些舊版本有不同的 API),在 Linux 上基於範圍的檔案系統):
#! /bin/ksh93 -
export LC_ALL=C
for file do
filefrag -vb1 -- "$file" |
while IFS=": ." read -A a; do
[[ $a = +([0-9]) ]] && [[ ${a[@]} != *unwritten* ]] &&
command /opt/ast/bin/head -s "${a[1]}" -c "${a[7]}" -- "$file"
done
done
filefrag
使用支援它的檔案系統的 FIEMAP ioctl 報告文件的範圍。
這*unwritten*
部分涵蓋了已fallocated
寫入但尚未寫入的文件(非稀疏,但仍然充滿了我不感興趣的零)。
bsdtar
或的最新版本star
可以使用其中一些 API 來產生一個tar
檔案來識別稀疏部分。這將使更多便攜的解決方案,但隨後必須解析生成的 tar 檔案才能取得非稀疏部分。