This article explains how to move a KVM virtual disk image file from a plain file to a raw hard disk partition. It then explains how to grow the virtual disk to use the full partition size.
Why using a disk partition for the virtual machine image
Using a plain file for a virtual machine disk image is the easiest configuration when you setup some virtual machine environment. It allows to start quickly for the setup and you can copy easily the virtual machine for a backup.
However, using a raw disk partition for the virtual machine provides better performance in general. The overhead of the guest file system is avoided as we have a direct access to the partition.
Copy the virtual machine image on the partition
To copy the virtual machine image on our partition, the easiest way is to use the dd
command. This step assumes that the virtual machine is stopped. In the example, the partition is /dev/sdb10
, this partition is bigger than the image file (if this is not the case, the image will be truncated).
$ sudo dd if=windows-xp.img of=/dev/sdb10 bs=1048576
5120+1 records in
5120+1 records out
5368709121 bytes (5.4 GB) copied, 331.51 s, 16.2 MB/s
Resize the virtual disk to the full partition size
The virtual disk partition should be changed to use the full disk space provided by our /dev/sdb10
partition. For this, we can use the fdisk
command:
$ sudo fdisk /dev/sdb10
Command (m for help): p
Disk /dev/sdb10: 22.0 GB, 22019042304 bytes
...
Device Boot Start End Blocks Id System
/dev/sdb10p1 * 1 651 5229126 7 HPFS/NTFS
You can easily change the partition to use the full disk by deleting the partition and creating it again so that you get something such as:
/dev/sdb10p1 1 2676 21494938+ 7 HPFS/NTFS
Now, we have to resize the file system on the virtual disk partition /dev/sdb10p1
. For this, we will use kpartx
to get access to the disk partitions provided by our /dev/sdb10
partition:
$ sudo kpartx -v -a /dev/sdb10
add map sdb10p1 (251:1): 0 42989877 linear /dev/sdb10 63
After the partitions are mapped, we can look at the filesystem before resizing it with the ntfsresize
command. We use this command to know the good size for resizing the file system.
$ sudo ntfsresize --info /dev/mapper/sdb10p1
ntfsresize v2.0.0 (libntfs 10:0:0)
Device name : /dev/mapper/sdb10p1
NTFS volume version: 3.1
Cluster size : 4096 bytes
Current volume size: 5354623488 bytes (5355 MB)
Current device size: <b>22010817024</b> bytes (22011 MB)
Checking filesystem consistency ...
100.00 percent completed
Accounting clusters ...
Space in use : 4786 MB (89.4%)
Collecting resizing constraints ...
You might resize at 4785565696 bytes or 4786 MB (freeing 569 MB).
Please make a test run using both the -n and -s options before real resizing!
And we can do the resize by using the Current device size
as the new file system size.
$ sudo ntfsresize -s 22010817024 /dev/mapper/sdb10p1
ntfsresize v2.0.0 (libntfs 10:0:0)
Device name : /dev/mapper/sdb10p1
NTFS volume version: 3.1
Cluster size : 4096 bytes
Current volume size: 5354623488 bytes (5355 MB)
Current device size: 22010817024 bytes (22011 MB)
New volume size : 22010810880 bytes (22011 MB)
Checking filesystem consistency ...
100.00 percent completed
Accounting clusters ...
Space in use : 4786 MB (89.4%)
Collecting resizing constraints ...
WARNING: Every sanity check passed and only the dangerous operations left.
Make sure that important data has been backed up! Power outage or computer
crash may result major data loss!
Are you sure you want to proceed (y/[n])? y
Schedule chkdsk for NTFS consistency check at Windows boot time ...
Resetting $LogFile ... (this might take a while)
Updating $BadClust file ...
Updating $Bitmap file ...
Updating Boot record ...
Syncing device ...
Successfully resized NTFS on device '/dev/mapper/sdb10p1'.
At this stage, our virtual machine disk image was moved from a plain file to a raw disk partition that it uses entirely.
Change the virtual machine definition
The virtual machine definition must now be changed to use our partition. You can do this by copying the XML definition to another file, thus creating a new virtual machine. This is the best thing to do so that you can still use the old configuration. If you do such copy, you have to change the uuid
as well as the network mac
address.
The disk type
parameter must be changed to block
and the dev
parameter must now point to the device partition.
<domain type='kvm'>
...
<disk type='block' device='disk'>
<source dev='/dev/sdb10'/>
<target dev='hda' bus='ide'/>
</disk>
...
</domain>
After this, start the virtual machine!
The next step is to setup virtio to boost performance by using paravirtualization.