QEMU, kurz für Quick Emulator ist wohl eine der verbreitesten Betriebssystemvirtualisierungslösungen für Linux. Es gibt verschiedenste Gründe, warum man eine virtuelle Maschine einsetzen möchte: Man ist Anbieter von vServern, der Kollege kommt mit einem Programm um die Ecke, das man sofort ausprobieren müsse, weil es ja so toll ist -- läuft aber nur unter Windows, oder die Wetter-App vom Pariser Flughafen läuft nur unter Windows 3.11.
Da es sich ja hierbei um ein recht populäres Paket handelt, sollte es jedem
gängigen Paketmanager bekannt sein. Meistens heisst es qemu
.
Das schöne an QEMU ist ja, dass man sich mit zwei Befehlen eine komplette Linux-Maschine erstellen kann. Wir nehmen hier im Beispiel mal ein x86_64 Alpine Linux, da das Install-ISO nur 40M groß ist, einen Shell-Installer hat und ziemlich schnell ist:
> wget http://dl-cdn.alpinelinux.org/alpine/v3.12/releases/x86_64/alpine-virt-3.12.0-x86_64.iso
2020-09-20 13:40:16 (9,81 MB/s) - ‘alpine-virt-3.12.0-x86_64.iso’ saved [41943040/41943040]
> qemu-img create -f qcow2 alpine-vm.img 4G
Formatting 'alpine-vm.img', fmt=qcow2 cluster_size=65536 compression_type=zlib size=4294967296 lazy_refcounts=off refcount_bits=16
qemu-system-x86_64 --enable-kvm -m 2G \
-cdrom alpine-virt-3.12.0-x86_64.iso -boot order=d \
-drive file=alpine-vm.img,format=qcow2
Und es sollte automatisch vom ISO-Image gebootet werden, so dass man die
Installation ganz normal über setup-alpine
oder bei anderen Distributionen
über den grafischen Installer durchführen kann.
Was haben die beiden obigen Befehle nun bewirkt?
qemu-img create
haben wir mitgeteilt, dass es ein Festplatten-Image der Größe
4GB mit dem Namen alpine-vm.img
anlegen soll. Dabei haben wir über den
Parameter -f
das Format qcow2
angegeben. Lässt man den Parameter weg, wird
raw
angenommen.
Der offensichtlichste Unterschied zwischen den Formaten ist, dass bei raw
die
4GB schon vorher reserviert werden und der Platz vom Host-System nicht mehr
benutzt werden kann. Das klingt erstmal nach Platzverschwendung, kann aber zur
besseren IO-Performance führen. Bei qcow2
(Copy on Write) wird der Platz beim
Host erst belegt, wenn er auch wirklich benötigt wird.
Ist man z.B. geneigt, seine VMs in der Azure-Cloud laufen zu lassen,
funktioniert dies nur mit dem Format raw
.
Der zweite Befehl startet nun die VM und bootet vom Install-ISO. Die Kommandozeilenparameter bewirken dabei Folgendes:
enable-kvm sorgt hier für Aktivierung der kernel-bassed Virtual
Machine-Module in Form von kvm
und z.B. bei Intel-Prozessoren kvm_intel
.
Bei allen gängigen Distributionen sollten diese Module mit dem
Linux-Kernel-Paket kompiliert worden sein und der Einsatz dieser Option sollte
out-of-the-box funktionieren.
m 2G Hauptspeicher für den Gast auf 2GB setzen. Verzichtet man auf diese Option, werden standardmäßig nur 128M zugeteilt. Das kann schonmal zu langen Gesichtern führen, wenn der Installer die initramdisk entpacken möchte und sich mit einer Kernel-Panic verabschiedet.
cdrom alpine-virt-3.12.0-x86_64.iso Ein CD-ROM-Device mit diesem ISO simulieren
boot order=d Von CD-ROM booten
drive file=alpine-vm.img,format=qcow2 Das oben angelegte Festplatten-Image einbinden
Nach der Installation des Gastsystems sollte man die Optionen boot order
und
cdrom
weglassen, damit es auch von dem Festplatten-Image bootet.
QEMU versucht, einige Dinge automatisch zu konfigurieren, damit man sofort
loslegen kann. So auch das Netzwerk. Es wird sofort eine Netzwerkkarte angelegt,
die vom internen DHCP-Server mit einer Adresse aus dem 10.0.2.0/24
-Netz
versorgt wird und zum aktiven Host-NIC via NAT verbunden wird -- man kommt also
aus dem Gast direkt ins gleiche Netzwerk wie der Host. Mehr zur
Netzwerkkonfiguration, z.B. mit VDE2
Jetzt ist das Ganze natürlich so schon lauffähig, nur bei einer Vielzahl von
virtuellen Maschinen ist das Handling und Management nur über
QEMU-Kommandozeilenparameter ziemlich umständlich. Dazu wollen wir uns in diesem
Teil den virt-manager
anschauen, einer grafischen Benutzeroberfläche, die auf
libvirt
aufbaut, etwa folgendermaßen:
libvirt
, von Redhat entwickelt, ist eine abstrahierende Bibliothek, um auf
verschiedene Virtualisierungsplattformen zuzugreifen, nicht nur KVM. Zudem
wartet sie mit jeder Menge Bindings für jede Menge verschiedener
Programmiersprachen auf.
Auch hier sollte es für die gängigen Distributionen kein Problem sein, die erforderlichen Pakete zu installieren:
libvirt
virt-manager
Danach ist der Daemon libvirtd
zu starten. Je nach Distribution oder
Supervision-Daemon kann das unterschiedlich ausfallen. Bei systemd
z.B.
# > systemctl start libvirtd
# > systemctl status libvirtd
● libvirtd.service - Virtualization daemon
Loaded: loaded (/usr/lib/systemd/system/libvirtd.service; disabled; vendor preset: disabled)
Active: active (running) since Sun 2020-09-20 21:31:42 CEST; 19s ago
TriggeredBy: ● libvirtd-ro.socket
● libvirtd.socket
● libvirtd-admin.socket
Docs: man:libvirtd(8)
https://libvirt.org
Main PID: 8940 (libvirtd)
Tasks: 17 (limit: 32768)
Memory: 10.6M
CGroup: /system.slice/libvirtd.service
└─8940 /usr/bin/libvirtd --timeout 120
Sep 20 21:31:42 archeus systemd[1]: Started Virtualization daemon.
# >
Jetzt sollte man den virt-manager
normal starten können und folgendes Fenster
zu sehen bekommen:
Da wir eine vorhandene Maschine hinzufügen wollen -- und zwar jene, die wir gerade im obigen Verlauf des Artikels erstellt haben -- müssen wir erst einen Storage Pool anlegen. Dazu Rechtsklick auf den Eintrag QEMU/KVM und dann auf Details.
Unten über das +-Symbol einen neuen Pool anlegen, Zielverzeichnis angeben und
schon sollte unser alpine-vm.img
in der Liste auftauchen.
Nun können wir mit dem ersten Icon der Toolbar im Hauptfenster eine neue VM hinzufügen. Ein Wizard sollte sich öffnen:
Option Import existing Disk Image wählen und auf Weiter.
Image aus dem Pool auswählen und unten ein System eintragen.
Speicher und Anzahl CPUs zuweisen.
Im nächsten Schritt vergeben wir nur noch einen aussagekräftigen Namen und bestätigen mit Finish.
Schon wird die VM automatisch gestartet: