dd 将数据从输入流复制到输出流,同时应用所请求的块大小和转换。它不了解文件系统、分区边界,也不知道输出目标是否包含宝贵数据。因此,它既适用于映像和原始设备,也会在目标选错时立即造成破坏。
设备 · 第 7 课
dd
学习 `dd` 如何复制块数据流,以及如何避免输入、输出和大小错误造成破坏。
输入、输出与块大小
命令的一般形式如下:
$ dd if=input.img of=output.img bs=4M status=progress
if=选择输入;省略时,dd从标准输入读取。of=选择输出;省略时,dd写入标准输出。bs=设置普通复制时的输入和输出块大小。status=progress要求 GNUdd定期报告传输进度。
dd 复制的是块,并非固有地一次只复制一个字节。较大的 bs 可以减少系统调用开销,但最佳值取决于设备、对齐、缓存和工作负载。它不会改变所复制的逻辑数据。
哪个操作数选择 dd 写入的目标?
限制复制量
count= 限制处理的输入块数量。对于普通输入文件:
$ dd if=source.img of=prefix.img bs=1M count=2 status=progress
该命令请求两个输入块,每块最大 1 MiB,因此最多复制 2 MiB。对于管道等数据流,短读可能使简单乘法不再成立;需要完整输入块时,GNU dd 提供 iflag=fullblock。应根据本地实现区分二进制单位和后缀语法。
对于普通文件,bs=1M count=2 请求的最大数据量是多少?
将映像写入块设备
原始还原命令可能如下:
$ sudo dd if=backup.img of=/dev/sdX bs=4M status=progress conv=fsync
/dev/sdX 是特意使用的占位符,不是可以原样复制执行的命令。替换它之前:
- 为所有宝贵数据保留经过测试的备份。
- 使用
lsblk、udevadm或等效工具,根据型号、序列号、大小、传输方式和持久链接识别目标。 - 确认目标分区均未挂载、未用作交换空间、未加入 RAID 或 LVM,也未被其他服务打开。
- 每次拔插、重启或拓扑变化后,重新检查设备。
- 确保映像能够容纳,并确认确实打算写入整个设备。
输出设备会从开头起被覆盖。颠倒 if 和 of、选中系统磁盘,或在本应选择分区时选择整盘,都可能在没有确认提示的情况下摧毁数据。
原始设备写入前,验证型号、序列号、大小和活动使用情况的最重要原因是什么?
创建一致的映像
在文件系统不断变化时读取实时块设备,可能产生内部不一致的映像。应优先使用未挂载的文件系统、应用程序一致性快照,或文档规定的冻结/快照流程。数据库和虚拟机可能需要各自的静默操作。
原始设备映像会复制所有块,包括文件系统元数据和未使用区域,因此它可能比文件级备份大得多,也可能复制一些标识符;将克隆与原件同时挂载前,必须更改这些标识符。
为什么对已挂载且不断变化的文件系统创建映像可能不可靠?
完成与验证
命令完成且未出现 I/O 错误,并不能证明选择了预期的来源和目标,也不能证明映像可用。应记录确切身份和大小,确保缓冲输出已经到达存储,比较范围适当的回读数据或加密哈希,并按照备份计划测试恢复。
不要宣称使用 dd 覆盖就能保证安全擦除 SSD、闪存转换层、精简配置存储、快照或重映射扇区。应使用设备和平台支持的清理功能,并遵循明确的数据销毁策略。
dd 返回零退出状态,本身不能证明什么?
接触原始硬件前,只能使用普通文件或可丢弃的虚拟磁盘练习。管理 Linux 分区和文件系统中的分区与文件系统概念提供了必要背景。
课程已完成
你已完成 dd
现在,你可以将 dd 理解为不了解操作者意图的原始块复制工具。
区分
if、of、bs和count。验证持久目标身份及每个活动使用者。
从一致的存储状态创建映像。
复制后刷新、验证并测试恢复。
将每次原始设备输出都视为可能具有破坏性的操作。