Linux

如果 dd 接收到與輸出文件相同的輸入文件會發生什麼

  • August 28, 2021

假設我不小心跑了sudo dd if=/dev/sda of=/dev/sda而不是sudo dd if=/dev/sda of=/dev/sdb

而且我不想等待 500gb 操作完成才知道我是否破壞了我的系統。

有誰知道結果會是什麼,所以我可以安靜地等待它完成,或者只是中斷它並開始全新安裝這麼久?

編輯:這是結果輸出

$ time sudo dd if=/dev/sda of=/dev/sda bs=64K conv=sync,noerror status=progress
512001769472 bytes (512 GB, 477 GiB) copied, 9084 s, 56.4 MB/s
dd: error writing '/dev/sda': No space left on device
7814181+1 records in
7814181+0 records out
512110190592 bytes (512 GB, 477 GiB) copied, 9088.72 s, 56.3 MB/s

real    151m28.774s
user    0m28.459s
sys 5m33.146s

孤立地,dd if=/dev/sdx of=/dev/sdx將寫入已經存在的相同數據。沒有傷害(*)。

但是,如果設備處於活動狀態,例如被文件系統使用,則可能存在競爭條件:

dd 讀取數據 (A),文件系統寫入數據 (B),dd 寫入數據 (A),導致 (B) 失去/損壞。

所以它仍然可能導致數據失去或系統崩潰。

如果是 SSD 儲存,其他可能的副作用是浪費寫入周期,並導致稀疏文件/精簡卷/快照佔用更多儲存空間。


另請注意,如果您對正常文件而不是塊設備執行相同的操作,則結果將是一個空文件並且所有數據都失去:

$ dd if=foobar of=foobar
0+0 records in
0+0 records out
0 bytes copied, 0.000179684 s, 0.0 kB/s

那是因為沒有conv=notrunc第一件事dd就是將輸出文件截斷為 0 字節,那時,它可以從 0 字節文件中讀取的也只有 0 字節。


(*) 除非您使用能夠更改偏移量的其他選項,例如seek, skip, noerror, sync, … 或者如果您最終使用不同但相同的設備if=/dev/sdx of=/dev/sdx1,例如通過分區引入此類偏移量。在這種情況下dd,最終會重複寫入相同的數據模式(通過讀取它之前在偏移處寫入的內容)。它會破壞一切。

還有一個更模糊的極端情況,即設備不正常地返回錯誤數據而沒有正確地將其報告為讀取錯誤。在這種情況下,您最終會將損壞的數據寫回設備。

引用自:https://unix.stackexchange.com/questions/666627