1

I'm currently trying to clone my boot drive that is a part of a RAID 1 setup to a single SSD (sdc in the image) so that I can boot from the non-RAID SSD setup on another computer. Is this possible? I tried using Clonezilla's official guide for this.

Current machine setup

I originally tried to use Clonezilla to clone sda to sdc but that ended quickly when I reached a partclone error.

Next, I tried cloning md0 to sdc. While Clonezilla let me clone it, it eventually left me with sdc with no partitions.

Help very much appreciated.

1 Answer 1

1

Okay so as far as I understand from your setup you have an 899.4G ext4 filesystem on md0, which is composed of sda1 and sdb1 in RAID-1. You wish to extract that ext4 filesystem out of md0 and put it on sdc which you will then put in another machine and try to boot off of it.

The reason why you can't just take an image of /dev/sda1 or /dev/md0 is that both these devices have metadata in them that prevent them being recognised as bare ext4 filesystems.

To be honest for simplicity's sake I would probably just do a filesystem-level tar-to-tar from the contents of / while it's running, to a partition on sdc. Like this:

$ sudo fdisk /dev/sdc
$ sudo mkfs.ext4 /dev/sdc1
$ sudo mount /dev/sdc1 /mnt
$ sudo tar -C / --one-file-system --xattrs --xattrs-include='*' -Spcf - | \
  sudo tar -C /mnt --numeric-owner --xattrs --xattrs-include='*.*' -pxvf -

That handles sparse files, hardlinks and special POSIX attributes (the --xattrs-include='*' is required to get all of them). It doesn't handle SELinux labels; maybe there is a way to do that with tar but you are using Ubuntu so probably not using SELinux anyway. You then need to install a bootloader on sdc.

I've never had a problem copying a root filesystem like that, even if it's in use, as long as I wasn't expecting to also clone app data and such that was changing under me.

But, if you really want to extract an image of the filesystem, I will show you how to do this by using my own system as an example. I will focus only on my /boot filesystem, which is a 2G ext4 on md0, which is sda1 and sdb1. This is good enough for a small example.

First you will need to boot into some form of live CD, because you're going to be copying data off of md0 and you shouldn't do that while md0 is in use. So, boot into your live system of choice; no need to activate md0 because we won't be using it. It doesn't matter if the live system does activate it though.

At some point near the start of your sda1 (or sdb1) there will be the magic number 0x53ef that is an ext4 superblock. Here's how to find it:

$ sudo xxd -l $((4*1024*1024)) -a /dev/sda1 | grep 53ef
00100430: e9ac 0060 6a00 ffff 53ef 0100 0100 0000  ...`j...S.......

That searches the first 4MiB of the block device for the 0x53ef sequence of bytes. It's most likely the superblock of my ext4 filesystem.

Now, the magic number is 56 bytes (hex 0x38) in to the start of the ext4 on-disk format, and then before that there is 1024 bytes (hex 0x400) of padding. So, the magic above is at byte position 0x100438 (each group of four is 2 bytes, so 0x100430+8). To find the start of the possible filesystem:

$ echo $((0x100438-0x38-0x400))
1048576

That's a decimal answer in bytes for the possible offset of the ext4 filesystem in sda1.

I will the extract it to a file, because it's only going to be ~2G in size for me:

$ sudo dd if=/dev/sda1 iflag=skip_bytes skip=1048576 bs=32768 > /var/tmp/boot.img
60960+0 records in                                                      
60960+0 records out
1997537280 bytes (2.0 GB, 1.9 GiB) copied, 0.89818 s, 2.2 GB/s

The iflag=skip_bytes says that the skip=1048576 is in single bytes, which enables us to skip to where we need to be but still read it in 32KiB chunks for performance reasons (bs=32768).

Now, I did that to file just to prove the point, but you are wanting to do this to your sdc disk. I'd partition that disk though, either by MBR or GPT, because you want space at the start to install a bootloader. So I'll assume you've done that and sdc1 partition now exists. To dd into that:

$ sudo dd if=/dev/sda1 iflag=skip_bytes skip=1048576 bs=32768 status=progress of=/dev/sdc1

A progress bar added there since this is going to be a really long operation.

Just to show it worked for me:

$ file /var/tmp/boot.img
/var/tmp/boot.img: Linux rev 1.0 ext4 filesystem data, UUID=4279ede6-332e-4b24-96e4-e575d34fa7dc, volume name "boot" (needs journal recovery) (extents) (64bit) (large files) (huge files)
$ sudo mount -v -t ext4 /var/tmp/boot.img /mnt
mount: /dev/loop17 mounted on /mnt.
$ ls -la /mnt                                                                        
total 330756                                                       
drwxr-xr-x  4 root root     4096 Jan 21 05:23 .    
drwxr-xr-x 23 root root     4096 Jan 21 05:21 ..                   
-rw-r--r--  1 root root   217458 Jan 15 10:30 config-4.15.0-134-generic
drwxr-xr-x  5 root root     4096 Jan 21 05:23 grub                 
-rw-r--r--  1 root root 75199113 Jan 21 05:23 initrd.img-4.15.0-134-generic
…etc…

At this point you should be able to boot back into your normal OS and mount sdc1 and poke about in it to verify it's correct, but you have one thing left to do: install a bootloader on sdc. Otherwise it won't boot when you put the drive in the other machine.

$ sudo grub-install /dev/sdc

Should do it. Now try putting sdc drive in another machine and booting it.

All of these operations (even the tar-to-tar) are quite scary and an error could destroy all your data, so I hope you have backups before you attempt any of this.

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .