1. 需求描述
Linux主机中原本有一块数据盘 /dev/sdb,挂载到了 /data 目录,存储了大量数据。
现在新增了一块数据盘 /dev/sdc,想要把sdb的数据完全拷贝到sdc,然后用sdb替换sdc,这个需求该怎样处理?
2. 实现思路
1、把sdb的数据拷贝到sdc
2、检查sdc数据
3、修改挂载配置,sdc替换sdb,重启主机
3. 拷贝硬盘全部数据
3.1. 拷贝硬盘全部数据概述
拷贝硬盘全部数据,有三种方法:
- 使用cp命令。不推荐,因为cp不能断点续传,所以拷贝大量文件时如果出错会浪费时间重传。
- 使用rsync命令。备选,支持断点续传,但是如果存在大量小文件时拷贝速度会很慢。
- 使用dd命令。首选,拷贝整个磁盘的数据,速度非常快且数据完整。
因此,这里选择使用dd命令来拷贝磁盘数据。
3.2. dd命令拷贝数据
1 | dd if=/dev/sdb of=/dev/sdc bs=64K conv=noerror,sync |
参数说明:
- if:input file,输入文件,这里就是要复制的源盘/dev/sdb。
- of:output file,输出文件,这里就是要复制的目标盘/dev/sdc。
- bs:block size,块大小,这里我们设置为64K。
- conv:convert,转换选项,这里我们设置为noerror(读写出错不停止)和sync(输入输出不足块大小时,会用空字符补足)。
dd命令默认的块大小是512字节,这意味着默认情况下,dd命令每次读取和写入的数据大小是512字节。如果我们的磁盘支持更大的块大小,那么增加块大小可以帮助提高数据复制的速度。在这个例子中,我们设定块大小为64K,这意味着dd命令每次读取和写入的数据大小是64K字节。
注意:在执行这个命令之前,确保/dev/sdc 没有被挂载并且没有其他程序正在使用。此外,这个操作可能会需要一些时间,需要耐心等待。
3.3. 查看dd进度
dd命令在复制数据完成后会自动结束。有时候,dd命令可能会运行非常长的时间,此时可以通过向dd命令发送SIGUSR1信号来查看它当前的进度。
1 | kill -USR1 $(pgrep ^dd) |
这条命令会找到dd命令的进程ID并向其发送SIGUSR1信号,这将导致dd命令打印出其当前的复制进度。
输出内容类似于:
1 | 6525616+0 records in |
这个输出中,6525616 指的是已经复制的块数量,块大小为64K(默认512),6525616*64*1024 = 427662770176
3.4. dd断点续传
dd命令本身并不支持断点续传。如果执行 dd 命令过程中出现了中断,那么重新执行dd命令会从头开始复制,比较浪费时间。
但是,我们可以使用一些参数来模拟断点续传的功能。
skip 参数可以让 dd 在复制数据前跳过源文件/设备的一定数量的块,seek 参数可以让 dd 在开始写入数据前跳过目标文件/设备的一定数量的块。
假设我们确认已知的dd进度为:
1 | 6525616+0 records in |
那么,断点续传可以使用如下命令:
1 | dd if=/dev/sdb of=/dev/sdc bs=64K skip=6525616 seek=6525616 conv=noerror,sync |
3.5. 修改UUID
使用dd拷贝一个设备到另一个设备,那么设备的UUID也被同时复制过去。这将导致两个设备拥有相同的UUID,这样在一些情况下可能会引发问题,比如在/boot/grub/grub.cfg文件或者/etc/fstab里面用UUID来标识设备。
要修改一个文件系统的UUID,需要使用对应文件系统的工具。
查看UUID命令:
1 | blkid /dev/sdc |
对于ext2,ext3,ext4文件系统,可以使用tune2fs命令,例如:
1 | tune2fs -U random /dev/sdc |
对于xfs文件系统,可以使用xfs_admin命令,例如:
1 | xfs_admin -U generate /dev/sdc |
对于btrfs文件系统,可以使用btrfstune命令,例如:
1 | btrfstune -f -u /dev/sdc |
注意:上述所有命令在执行之前,需要先确保该设备已经被卸载。
3.6. 修改UUID报错问题
1、执行修改UUID的命令:
1 | xfs_admin -U generate /dev/sdc |
报错:
1 | ERROR: The filesystem has valuable metadata changes in a log which needs to |
2、根据报错提示挂载磁盘,然后卸载磁盘。
1 | mkdir /sdc |
报错:
1 | mount: wrong fs type, bad option, bad superblock on /dev/sdc, |
3、尝试修复磁盘问题
1 | xfs_repair -L /dev/sdc |
输出:
1 | Phase 1 - find and verify superblock... |
4、再次尝试修改UUID
1 | xfs_admin -U generate /dev/sdc |
输出:
1 | Clearing log and setting UUID |
5、尝试挂载和卸载
1 | mount /dev/sdc /sdc |
4. 检查sdc数据(可选)
1、挂载 sdc
1 | mkdir /sdc |
2、比较数据
1 | rsync -P -avz /data/ /sdc |
5. 修改挂载配置
1、查看 sdc UUID
1 | blkid /dev/sdc |
2、修改 /etc/fstab 配置
1 | UUID=xxx /data xfs defaults 0 0 |
其中 xxx 修改为 sdc 的 UUID
3、重启主机
1 | reboot |