Qemu and VirtualBox virtualize guest hardware for Windows and Linux hosts. Linux containers use the host kernel and virtualize the operating system.
Qemu
# Installation apt install qemu-system kvm syslinux extlinux ipxe grub-pc-bin dosfstools -y # Run qemu and built-in vnc server qemu-system-x86_64 -vnc :0 --enable-kvm -cpu host -smp 1 -m 1G -net nic,model=rtl8139 -net user -drive file=VirtualXPVHD -usbdevice tablet \ #-usb -device usb-host,hostbus=1,hostaddr=27 -device usb-host,hostbus=1,hostaddr=31 # Start with nographic and rdp qemu-system-x86_64 --enable-kvm -cpu host -smp 1 -m 2G -device rtl8139,netdev=host,mac=52:55:0a:00:02:02 -netdev user,id=host,net=192.168.76.0/24,hostfwd=tcp::3389-:3389 -drive file=VirtualXPVHD --soundhw ac97 -usb -device usb-tablet -nographic -vnc :0 -monitor stdio -serial none qemu-system-x86_64 --enable-kvm -cpu host -smp 1 -m 2G -device rtl8139,netdev=host,mac=52:55:0a:00:02:02 -netdev user,id=host,net=192.168.76.0/24,hostfwd=tcp::3389-:3389 -drive file=VirtualXPVHD --soundhw ac97 -usb -device usb-tablet -nographic -vnc :0 -monitor none -serial chardev:char0 -chardev stdio,mux=off,id=char0 qemu-system-x86_64 --enable-kvm -cpu host -smp 1 -m 2G -device rtl8139,netdev=host,mac=52:55:0a:00:02:02 -netdev user,id=host,net=192.168.76.0/24,hostfwd=tcp::3389-:3389,hostfwd=tcp::23-:23 -drive file=VirtualXPVHD --soundhw ac97 -usb -device usb-tablet -nographic -vnc :0 -chardev stdio,mux=on,id=char0 -mon chardev=char0,mode=readline -serial none qemu-system-x86_64 -vnc :0 --enable-kvm -cpu host -smp 1 -m 450 -drive file=disk.img --nographic -kernel linux -initrd initrd -monitor stdio -serial none qemu-system-x86_64 --enable-kvm -append 'console=ttyS0 root=/dev/sda1 rw' -initrd boot/initrd.img-4.9.0-6-amd64 -kernel boot/vmlinuz-4.9.0-6-amd64 -drive file=rootfs.img -m 1000 -netdev tap,id=tap1,ifname=tap1 -device rtl8139,netdev=tap1
bootcfg /ems on /port com1 /baud 9600 /id 1 sc config TlntSvr start= demand
<<-EOF \ stdbuf -oL sed s/.*/sleep\ 2\ \\\&\\\&\ printf\ %s\\\\\\\\\\\\r\ \&/e | \ telnet localhost Administrator Administrator dir exit EOF
bootcfg /ems on /port com1 /baud 9600 /id 1 sc config TlntSvr start= demand
<<-EOF \ stdbuf -oL sed s/.*/sleep\ 2\ \\\&\\\&\ printf\ %s\\\\\\\\\\\\r\ \&/e | \ telnet localhost Administrator Administrator dir exit EOF
# Download netboot files apt-get install debian-installer-9-netboot-i386 -y #wget -r --no-parent --no-host-directories --cut-dirs 7 http://ftp.debian.org/debian/dists/stable/main/installer-i386/current/images/netboot/ #curl -o- http://ftp.debian.org/debian/dists/stable/main/installer-i386/current/images/netboot/netboot.tar.gz | tar xzf - # Boot with debian mini.iso and dhcp bootfile preseed.cfg wget http://ftp.debian.org/debian/dists/stable/\ main/installer-i386/current/images/netboot/mini.iso # Boot with pxelinux.0 as dhcp bootfile qemu-system-i386 -net nic \ -net user,tftp=/usr/lib/debian-installer/images/9/i386/text,bootfile=/pxelinux.0 \ -m 512 -boot c -drive format=raw,file=disk.img --enable-kvm # Examples with preseed config as dhcp bootfile and mini.iso qemu-system-i386 -net nic \ -net user,tftp=$PWD,bootfile=tftp://10.0.2.2/d-i/stretch/./preseed.cfg \ -m 512 -cdrom mini.iso -boot d -drive format=raw,file=disk.img --enable-kvm # Load kernel from qemu qemu-system-i386 -net nic \ -net user,tftp=$PWD,bootfile=tftp://10.0.2.2/d-i/stretch/./preseed.cfg \ -kernel /usr/lib/debian-installer/images/9/i386/text/debian-installer/i386/linux \ -initrd /usr/lib/debian-installer/images/9/i386/text/debian-installer/i386/initrd.gz \ -append auto=true \ -m 512 -boot c -drive format=raw,file=disk.img --enable-kvm # Configuration files for ipxe over tftp cat >> tftpboot/pxelinux.cfg/default <<IPXE timeout 10 default pxe label pxe menu label ^pxe kernel ipxe.lkrn append initrd=pxe.cfg IPXE cat > tftpboot/pxe.cfg <<IPXE dhcp kernel debian-installer/i386/linux auto=true priority=critical vga=788 initrd=debian-installer/i386/initrd.gz netcfg/disable_dhcp=true url=tftp://10.0.2.2/preseed.cfg ip=10.0.2.100:::255.255.255.0:linux:eth0:on initrd debian-installer/i386/initrd.gz boot IPXE
Disk images
Mounting disk images
# Create and mount a raw image qemu-img convert VirtualXPVHD -O raw windows.raw cd $(mkdir -v $(basename $(losetup --find --partscan --show windows.raw))| cut -d\' -f2 ) cd - mount /dev/$(basename $OLDPWD)p1 $OLDPWD ls $OLDPWD umount $OLDPWD rmdir $OLDPWD losetup -D # Mount vhd disk image guestmount -a VirtualXPVHD -o nonempty .
Boot floppy with syslinux and ipxe
dd count=0 seek=2880 of=boot.dsk mkdosfs boot.dsk syslinux boot.dsk cd $(mkdir -v $(basename $(losetup -f)) | cut -d\' -f 2) mount $OLDPWD/boot.dsk . cat > syslinux.cfg <<-CFG default ipxe label ipxe kernel ipxe.lkrn append initrd=ipxe.cfg CFG cp /usr/lib/ipxe/ipxe.lkrn . cat > ipxe.cfg <<-IPXE #!ipxe dhcp kernel debian-installer/i386/linux auto=true priority=critical vga=788 initrd=debian-installer/i386/initrd.gz netcfg/disable_dhcp=true url=tftp://10.0.2.2/preseed.cfg initrd debian-installer/i386/initrd.gz boot IPXE umount . && cd - && rmdir $OLDPWD
Create a bootable hard disk image with grub, ipxe and extlinux
dd count=0 seek=1M of=disk.img sfdisk disk.img <<-SFDISK label: dos label-id: 0x5c81f5df device: disk.img unit: sectors disk.img1 : start=2048, size=1046528, type=83, bootable SFDISK cd $(mkdir -v $(basename $(losetup --find --partscan --show disk.img )) | cut -d\' -f 2) && cd - mkfs /dev/$(basename $OLDPWD)p1 mount /dev/$(basename $OLDPWD)p1 $OLDPWD && cd - mkdir boot/grub -p cat > boot/grub/grub.cfg <<-GRUB timeout=5 menuentry "Network boot (iPXE)" { linux16 /ipxe.lkrn initrd16 /ipxe.cfg } GRUB cp /usr/lib/ipxe/ipxe.lkrn . cat > ipxe.cfg <<-IPXE #!ipxe dhcp kernel debian-installer/i386/linux auto=true priority=critical vga=788 initrd=debian-installerx/i386/initrd.gz url=tftp://10.0.2.2/preseed.cfg initrd debian-installer/i386/initrd.gz boot IPXE grub-install --target=i386-pc --boot-directory=/tmp/loop0/boot $OLDPWD/disk.img umount . && cd - && rmdir $OLDPWD losetup -D cd $(mkdir -v $(basename $(losetup --find --show disk.img --offset $((512*2048)))) | cut -d\' -f 2) mount /dev/$(basename $PWD) . cd - && cd - cp /usr/lib/ipxe/ipxe.lkrn . > extlinux.conf cat <<-CFG default ipxe label ipxe kernel ipxe.lkrn append initrd=ipxe.cfg CFG losetup --detach /dev/$(basename $PWD) cd - && umount $OLDPWD && rmdir $OLDPWD
Network
Virtual distributed ethernet VDE
apt-get install vde2 cat >> /etc/network/interfaces.d/vde <<-VDE auto vde0 iface vde0 inet static address 10.0.2.1 netmask 255.255.255.0 vde2-switch -t vde0 vde2-slirp -dhcp
VDE with QEMU guests
# Commands for virtula network vde_pcapplug -s /run/vde.ctl eth0 vde_pcapplug -s /var/run/vde2/mytap.ctl eth0 slirpvde -s /var/run/vde2/vde0.ctl -m 660 dpipe vde_plug /var/run/vde2/vde0.ctl/ -m 660 -g vde2-net = vde_plug -m 660 -g vde2-net /var/run/vde2/mytap.ctl/ vde_pcapplug -m 660 -g vde2-net -s /var/run/vde2/mytap.ctl tap0 vde_plug2tap qemu-system-x86_64 -nographic -append console=ttyS0 -net user -net nic qemu-system-x86_64 -enable-kvm -cpu host -m 2G -hda VirtualXPVHD -nographic -monitor stdio -serial none -netdev vde,sock=/var/run/vde2/vde0.ctl,id=vde -device rtl8139,netdev=vde -vnc :0 qemu-system-x86_64 -vnc :0 --enable-kvm -cpu host -smp 1 -m 1G -net nic,model=rtl8139 -net user -drive file=disk.img --nographic qemu-system-x86_64 -vnc :0 --enable-kvm -cpu host -smp 1 -m 450 -drive file=disk.img --nographic -kernel linux -initrd initrd -monitor stdio
# Routing sysctl net.ipv4.ip_forward=1 iptables -n -t nat -L iptables -t nat -A POSTROUTING -s 192.168.33.254/24 ! -d 192.168.33.254/24 -j MASQUERADE
VirtualBox
Virtual machine configuration of VirtualBox VBoxManage - https://www.virtualbox.org
Install virtualbox and the vboxdrv kernel module. apt-get install virtualbox-qt virtualbox linux-kernel-headers virtualbox-guest-additions # Create a windows virtual guest VBoxManage setextradata global GUI/Input/HostKeyCombination 65507 VBoxManage createvm --name "$(basename $PWD)" --register --basefolder /tmp VBoxManage storagectl "$(basename $PWD)" --name IDE --add ide VBoxManage storageattach "$(basename $PWD)" --storagectl IDE --port 0 --device 0 --type dvddrive --medium /usr/share/virtualbox/VBoxGuestAdditions.iso VBoxManage modifyvm "$(basename $PWD)" --cpus 1 --memory 1042 --ioapic on --accelerate3d on --nic1 nat --cableconnected1 on --vrde off #--boot1 disk --boot2 floppy #VBoxManage storagectl "$(basename $PWD)" --name FLOPPY --add floppy #VBoxManage storageattach "$(basename $PWD)" --storagectl FLOPPY --port 0 --device 0 --type fdd --medium /opt/VirtualBox/floppy.img #VBoxManage createmedium disk --filename "$(basename $PWD)" --size 5000 VBoxManage storageattach "$(basename $PWD)" --storagectl IDE --port 0 --device 1 --type hdd --mtype immutable --medium "$(basename $PWD)" VBoxManage sharedfolder add "$(basename $PWD)" --name "$(basename $PWD)" --hostpath $PWD VBoxManage startvm "$(basename $PWD)" --type gui VBoxManage startvm "$(basename $PWD)" --type headless #VBoxManage extpack install [--replace] <tarball> VBoxManage internalcommands createrawvmdk -rawdisk /dev/sdb1 -filename sdb1.vmdk VBoxManage storageattach "$(basename $PWD)" --storagectl IDE --device 1 --port 1 --type hdd --medium sdb1.vmdk VBoxManage sharedfolder add "$(basename $PWD)" --name USB --hostpath "/mnt/usb/VirtualBox" VBoxManage controlvm "$(basename $PWD)" pause VBoxManage controlvm "$(basename $PWD)" savestate VBoxManage controlvm "$(basename $PWD)" resume VBoxManage controlvm "$(basename $PWD)" poweroff VBoxManage discardstate "$(basename $PWD)" VBoxManage unregistervm "$(basename $PWD)" --delete
Windows XP
In VirtualBox the Windows image works without changes. For qemu the Windows image requires different drivers.
Here are some links about this problem:
# Download Windows XP image cd $(mktemp -d) wget https://download.microsoft.com/download/7/2/C/72C7BAB7-2F32-4530-878A-292C20E1845A/WindowsXPMode_en-us.exe # Requirements for qemu drivers apt-get install p7zip-full qemu ntfs-3g dosfstools libguestfs-tools cabextract usermod -a $(getent passwd 1000 | cut -d: -f1) -G disk,kvm
Create virtual Windows XP machine VirtualXPVHD
Linux containers
Linux containers use the linux kernel to virtualize the operating system.
# Install LXC apt-get install gnome-boxes virsh lvm2 lxc cgroupfs-mount cgmanager iptables docker.io systemd-containers cat > /etc/lxc/default.conf <<-'LXC' lxc.aa_profile = unconfined lxc.network.type = veth lxc.network.link = lxcbr0 lxc.network.flags = up lxc.network.hwaddr = 00:16:3e:xx:xx:xx LXC cat > /etc/lxc/dnsmasq.conf <<-'LXC' interface=lxcbr0 bind-interfaces domain=local,10.0.3.0/24 dhcp-range=10.0.3.100,10.0.3.200,1h dhcp-option=40,local log-dhcp LXC cat > /etc/default/lxc-net <<-'LXC' USE_LXC_BRIDGE="true" LXC_BRIDGE="lxcbr0" LXC_ADDR="10.0.3.1" LXC_NETMASK="255.255.255.0" LXC_NETWORK="10.0.3.0/24" LXC_DHCP_RANGE="10.0.3.2,10.0.3.254" LXC_DHCP_MAX="253" LXC_DHCP_CONFILE="/etc/lxc/dnsmasq.conf" LXC_DOMAIN="" LXC # Create and start LXC containers service lxe-net restart mount -t tmpfs tmpfs /var/lib/lxc lxe-create -n busybox -t busybox lxe-destroy -n busybox -t busybox lxc-create --name=debian --template=debian lxc-start --name=debian lxc-attach --name=debian
KVM
Kernel based virtual machine with btrfs root disk. - https://www.linux-kvm.org/page/Using_VirtIO_NIC - http://btrfs.wiki.kernel.org
lkvm run -k vmlinuz-4.18.5-300.fc29.x86_64 -i initramfs-4.18.5-300.fc29.x86_64.img -d disk.img -n -m 2000 -p 'root=UUID=04277801-2387-4949-a82a-46b5d6f2dbd4'
sysctl net.ipv4.ip_forward=1 ifconfig tap0 0 brctl addif br0 tap0 eth0
bash <<-'EOF' dd count=0 seek=6M of=disk.img && \ losetup --find --show disk.img | while read; do echo $REPLY mkfs.btrfs $REPLY cd -P "$(mktemp -d)" && cd - || exit 1 mount $REPLY $OLDPWD && cd - btrfs subvolume create HEAD btrfs subvolume snapshot -r HEAD $(date -Ih) done #cleanup losetup -D EOF
QEMU s390 emulation
In virtualization with KVM the guest and host use the same cpu instructions. With QEMU a different processor architecture can be emulated. This can be used to test Debian GNU/Linux on IBM S/390
# Download and install software requirements apt install crossbuild-essential-s390x qemu-system-s390x wget -L -r -nd -np -nH -P generic \ http://cdn-aws.deb.debian.org/debian/dists/stretch/main/installer-s390x/current/images/generic/ # The boot image is availabe as source git clone https://git.qemu.org/git/qemu.git git submodule update --init roms/SLOF # Boot configuration can ignore errors patch -p1 <<-'EOF' diff --git a/configure b/configure index 58862d2ae8..316dcd20d3 100755 --- a/configure +++ b/configure @@ -52,7 +52,6 @@ print_error() { error_exit() { print_error "$@" - exit 1 } do_compiler() { EOF sh configure --cross-prefix=s390x-linux-gnu- make -C pc-bios/s390-ccw qemu-system-s390x \ -bios s390-ccw.img \ -kernel generic/kernel.debian \ -initrd generic/initrd.debian
qemu-system-x86_64 --enable-kvm --nographic -cpu host -m 1000 \ -net nic,model=rtl8139 -net user,tftp=$PWD,bootfile=tftp://10.0.2.2/preseed.cfg \ -cdrom /tmp/tmp.*/srv/mirror/debian-cd-test/debian-9.0-amd64-CD-1.iso \ -kernel /tmp/tmp.*/srv/mirror/tmp/sid/CD1/install.amd/vmlinuz \ -initrd /tmp/tmp.*/srv/mirror/tmp/sid/CD1/install.amd/initrd.gz \ -append 'console=ttyS0 auto=true priority=critical url=tftp://10.0.2.2/example-preseed.txt' \
lkvm run --9p /mnt,hostfs modprobe 9pnet_virtio mount -t 9p -o trans=virtio hostfs /mnt/ -oversion=9p2000.L
# Wine apt install wine winetricks # vcrun6 vb6run # winetricks wsh57 wscript.exe=native cscript.exe=native # https://bugs.debian.org/cgi-bin/bugreport.cgi?bug=701871 WINETRICKS_DOWNLOADER=curl winetricks wsh57 msxml6 mdac28 dotnet40 cat > .curlrc <←CURLRC insecure CURLRC apt install crossbuild-essential-i386