Problem
Mounting a virtual disk image used by KVM or Xen (.xm file) outside of the guest OS. (e.g on the Host/Dom0 machine)
Background
These images can not be mounted directly as they are not just a formatted partition, but a complete disk image with a boot sector. So if you try to just mount the file it will fail.
Solution
losetup to the rescue! We just need to mount it with losetup, specifying an offset to get past the bootstrap. This way we can also get to different partitions within the disk image.
Steps outlined
- Make sure the disk is not in use by the virtual machine! If its a LVM partition then you can take a LVM snapshot of the disk and mount the snapshot.
- Mount the virtual image to an lo device using an offset. If your wanting to mount the first partition in the virtual disk, then in most cases the offset will be 32256. If that doesn't work OR its not the first partition then read the instructions for calculating the offset.and use that value instead.
- Mount the lo device
Bash commands to mount the image
sudo losetup -o32256 /dev/loop0 /path/to/diskimage.xm
sudo mount /dev/loop0 /mnt/tmp
Clean up when your finished
sudo umount /dev/loop0
sudo losetup -d /dev/loop0
Calculate the offset steps outlined
If the above did not work, then it maybe because the offset ive suggested (32256) is not correct for your setup. The following shows how to calculate the offset for your setup.
- Make sure loop0 is free
- Mount image to loop0 without an offset
- Use fdisk to list partitions
- Find the start number of the partition you want to mount. Multiply that it by the number of bytes per sector (normally 512)
Calculate the offset Bash commands
sudo losetup -d /dev/loop0
sudo losetup /dev/loop0 /path/to/diskimage.xm
sudo fdisk -u -l /dev/loop0
Look for the "Units = " value and Start value for the partition you wish to mount. In this example its "512 bytes" and "63". The output should show something like;
Disk /dev/loop0: 10.5 GB, 10485760000 bytes
255 heads, 63 sectors/track, 1274 cylinders, total 20480000 sectors
Units = sectors of 1 * 512 = 512 bytes
Disk identifier: 0x0007b39a
Device Boot Start End Blocks Id System
/dev/loop0p1 * 63 20466809 10233373+ 83 Linux
Now multiply those two values to get your offset. (e.g. In this example its 512x63=32256)
Now unmount your lo device
sudo losetup -d /dev/loop0
...and start this HOWTO again but using your calculated offset value instead of 32256.