I've been playing this idea for the past few days and I've finally got it to work.
First you need to compile a binary that will mount VHD files. But it can also mount VMDK, VDI and raw disk images. You can get the source to compile this program from here.
https://github.com/SophosLabs-zz/vdfuse
But before you compile vdfuse you need to run this command.
sudo apt install libfuse-dev virtualbox pkg-config
libfuse-dev has the required header files for vdfuse to compile.
virtualbox has pre-compiled drivers needed for mounting disk images.
pkg-config is used by a script when compiling vdfuse.
Now with all the required files and binaries, let compile vdfuse.
So the commands you need to run to compile vdfuse are as follows:
./autogen.sh
./configure
make
sudo make install
Next we need to add some scripts to run before init from within the intird.img.
Create these files as follows:
/usr/share/initramfs-tools/hooks/vdfuse
#!/bin/sh -e
PREREQ=""
prereqs()
{
echo "$PREREQ"
}
case "$1" in
prereqs)
prereqs
exit 0
;;
esac
. /usr/share/initramfs-tools/hook-functions
copy_exec /usr/local/bin/vdfuse /sbin
/usr/share/initramfs-tools/scripts/init-top/vdfuse
#!/bin/sh -e
PREREQ="udev"
prereqs()
{
echo "$PREREQ"
}
case "$1" in
prereqs)
prereqs
exit 0
;;
esac
if [ ! -z $vdisk ]; then
mkdir /vdhost
mkdir /dev/vdhost
mount -t ntfs $host /vdhost/
vdfuse -t VHD -f /vdhost$vdisk /dev/vdhost
mount -t ext4 $ROOT /root
fi
/usr/share/initramfs-tools/scripts/init-bottom/vdhost
#!/bin/sh -e
PREREQ=""
prereqs()
{
echo "$PREREQ"
}
case "$1" in
prereqs)
prereqs
exit 0
;;
esac
if [ -d ${rootmnt}/vdhost ]; then
mount -n -o move /vdhost ${rootmnt}/vdhost
fi
Next you need to make these files executeable by running the following:
sudo chmod +x /usr/share/initramfs-tools/hooks/vdfuse
sudo chmod +x /usr/share/initramfs-tools/scripts/init-top/vdfuse
sudo chmod +x /usr/share/initramfs-tools/scripts/init-bottom/vdhost
Now we need to build a new kernel using this command: sudo update-initramfs -k all -c
That's everything you need to do inside Linux. The final thing is setting up grub to boot the virtual disk image.
Here is the commands that need to added to the grub.cfg file.
set vhd=/vhd/Ubuntu.vhd
set vdhost
search --no-floppy -s root -f $vhd
loopback lp0 $vhd tdisk=VHD
linux (lp0,1)/vmlinuz root=/dev/vdhost/Partition1 vdisk=$vhd host=/dev/sda1 quiet splash
initrd (lp0,1)/initrd.img
Change /dev/sda1 to whichever device the VHD resides on.
vmware
(and supported by VirtualBox). What are you using to boot your VMs? vmware? Are you trying to boot a Linux machine by generating a VHD file? That's definitely possible but I do not think that is what you are searching for. – grochmal Sep 14 '16 at 19:49