假设我不小心跑了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
答案1
孤立地,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
最终会重复写入相同的数据模式(通过读取之前在偏移处写入的内容)。它会腐蚀一切。
还有一种更模糊的极端情况,即设备不稳定地返回错误数据,而没有正确地将其报告为读取错误。在这种情况下,您最终会将损坏的数据写回设备。
答案2
当数据被读取、缓冲、写入(按顺序)时,不会发生任何事情