KVM On The ODROID-XU4

Virtualization Keystone

This is a step-by-step guide for enabling KVM on an ODROID-XU4. This guide is only available in u-boot odroidxu4-v2017.05 and Linux kernel 4.9.x versions. The first step is to rebuild the kernel. KVM needs the arch timer instead of MCT (Multi-Core Timer), which is the default timer of ODROID-XU4 (by exynos5422-odroidxu4-kvm.dtb). And there are the virtualization related configurations in odroidxu4_kvm_defconfig file.

$ sudo apt update
$ sudo apt install git
$ git clone --depth 1 https://github.com/hardkernel/linux -b odroidxu4-4.9.y
$ cd linux
$ make odroidxu4_kvm_defconfig
$ make -j8
$ sudo make modules_install
$ sudo cp arch/arm/boot/zImage /media/boot/zImage_kvm
$ sudo cp arch/arm/boot/dts/exynos5422-odroidxu4-kvm.dtb /media/boot/

Modify the boot.ini file by changing “zImage” to “zImage_kvm”, and “exynos5422-odrooidxu4.dtb” to “exynos5422-odrooidxu4-kvm.dtb”

/media/boot/boot.ini

(……)
# Load kernel, initrd and dtb in that sequence
fatload mmc 0:1 0x40008000 zImage_kvm
(……)
if test “${board_name}” = “xu4”; then fatload mmc 0:1 0x44000000 exynos5422-odrooidxu4-kvm.dtb; setenv fdtloaded “true”; fi
(……)

Reboot the ODROID-XU4, then check whether KVM is enabled after the booting process is finished:

$ dmesg | grep HYP
[ 0.096589] CPU: All CPU(s) started in HYP mode.
[ 0.777814] kvm [1]: HYP VA range: c0000000:ffffffff
$ dmesg | grep kvm
[ 0.777771] kvm [1]: 8-bit VMID
[ 0.777793] kvm [1]: IDMAP page: 40201000
[ 0.777814] kvm [1]: HYP VA range: c0000000:ffffffff
[ 0.778642] kvm [1]: Hyp mode initialized successfully
[ 0.778713] kvm [1]: vgic-v2@10484000
[ 0.779091] kvm [1]: vgic interrupt IRQ16
[ 0.779127] kvm [1]: virtual timer IRQ60
$ cat /proc/interrupts | grep arch_timer
58: 0 0 0 0 0 0 0 0 GIC-0 29 Level arch_timer
59: 0 1857 1412 1345 16986 6933 5162 3145 GIC-0 30 Level arch_timer
Figure 1 Virtual Machine architecture
Figure 2 – Virtual Machine architecture

Ubuntu Minimal 16.04.3 Running using QEMU and KVM/ARM
To follow this section, make sure that KVM is already enabled, with 4GB or more storage space available. In this section, we will run the Ubuntu Minimal 16.04.3 image on the virtual machine using QEMU and KVM/ARM.

To begin, Install qemu-system-arm which is to virtualize the arm machine and required packages:

$ sudo apt update
$ sudo apt install qemu-system-arm kpartx

Next, prepare the guest OS kernel and dtb images. It is needed to set clock frequency for timer in dts file by adding a “clock-frequency = <100000000>;” line in the timer node).

$ wget https://www.kernel.org/pub/linux/kernel/v4.x/linux-4.13.tar.xz
$ tar Jxvf linux-4.13.tar.xz
$ cd linux
$ nano arch/arm/boot/dts/vexpress-v2p-ca15-tc1.dts

arch/arm/boot/dts/vexpress-v2p-ca15-tc1.dts
timer {
compatible = “arm,armv7-timer”;
interrupts = <1 13 0xf08>,
<1 14 0xf08>,
<1 11 0xf08>,
<1 10 0xf08>;
clock-frequency = <100000000>;
};

Build and copy zImage and dtb images to the working directory:

$ make vexpress_defconfig
$ make menuconfig

Enable the block layer —>
[*] Support for large (2TB+) block devices and files

$ make zImage dtbs -j8
$ cp arch/arm/boot/zImage ../
$ cp arch/arm/boot/dts/vexpress-v2p-ca15-tc1.dtb ../
$ cd ..

Prepare Ubuntu minimal root filesystem image by downloading the Ubuntu minimal 16.04.3 image and generate the root filesystem image from the image.

$ wget https://odroid.in/ubuntu_16.04lts/ubuntu-16.04.3-4.9-minimal-odroid-xu4-20170824.img.xz
$ unxz ubuntu-16.04.3-4.9-minimal-odroid-xu4-20170824.img.xz
$ sudo kpartx -a ubuntu-16.04.3-4.9-minimal-odroid-xu4-20170824.img
$ sudo dd if=/dev/mapper/loop0p2 of=ubuntu-minimal-16.04.3.img
$ sudo kpartx -d ubuntu-16.04.3-4.9-minimal-odroid-xu4-20170824.img

Modify the root filesystem for the guest environment by removing the ODROID-specific file and configuration:

$ mkdir rootfs
$ sudo mount ubuntu-minimal-16.04.3.img rootfs
$ cd rootfs
$ sudo rm ./first_boot
$ sudo rm ./etc/fstab
$ sudo touch ./etc/fstab
$ cd ..
$ sudo umount rootfs

Run qemu, where the host is Ubuntu Mate 16.04.3 / 4.9.50 kernel, and the guest is Ubuntu Minimal 16.04.3 / 4.13 kernel

$ qemu-system-arm -M vexpress-a15 -smp 2 -cpu host \
-enable-kvm -m 512 -kernel zImage -dtb vexpress-v2p-ca15-tc1.dtb \
-device virtio-blk-device,drive=virtio-blk \
-drive file=ubuntu-minimal-16.04.3.img,id=virtio-blk,if=none \
-netdev user,id=user -device virtio-net-device,netdev=user \
-append "console=tty1 root=/dev/vda rw rootwait fsck.repair=yes"
Figure 3 – The Host operating system runs the LTS Kernel 4.9.50 while the guest operating system runs the upstream Kernel 4.13

Be the first to comment

Leave a Reply