Skip to content
Menu
TechDudes.de
  • Allgemein
  • Server
  • Linux
  • Impressum
TechDudes.de

VGA-Passtrough mit KVM

Posted on 29. Mai 201331. Mai 2013 by Dennis

Dieses mal habe ich mich mit dem Durchreichen einer Grafikkarte an eine virtuelle Windowsinstallation unter KVM beschäftigt. Als Dom0 nutze ich hier ArchLinux, u.a. auch weil das Thema noch sehr in Bewegung ist und man wegen dem rolling Release immer einen neuen Kernel erhält. Der Vorteil von VGA-Passthrough ist, dass das Gast-System im Idealfall nahezu die volle Geschwindigkeit der Grafikkarte umsetzen kann. So könnte man z.B. an einem Fernseh-Server eine DomU für einen VDR haben kann, eine weitere DomU mit einem Windows für die WG-Mitbewohner die Windowsspiele auf dem Fernseher zocken möchten oder über XBMC dann das Fernsehprogramm sehen. Eine weitere DomU könnte als Proxy/Firewall/Mailserver und und und…

Mein Hintergedanke ist noch immer, dass dieses Projekt meinen aktuellen WG-Server, der mit YaVDR arbeitet ablösen kann. Der Linux Kernel 3.10 soll ja VDPAU für die Radeon Karten ermöglichen – das würde bedeuten, dass ich einen großen Server mit einer DomU als Fernsehreceiver mit BluRayplayer und eine DomU als Konsolenersatz nutzen könnte.

Info: Der Artikel ist derzeit noch „work-in-progress“, da meine Dokumentation noch nicht gut genug ist und ich nur als root unterwegs bin. Zum anderen bin ich mit der Geschwindigkeit auch noch nicht zufrieden. Ich bin jedoch froh, dass das Konzept quasi schon arbeitet. Dennoch werde ich weiter herumprobieren und an Parametern schrauben, bis ich ein zufriedenstellendes Ergebnis habe – der Artikel wird daher sicherlich noch mehrmals geupdated werden. Wichtig ist mir erstmal, dass man hier erstmal einen Ausgangspunkt für seine eigenen Recherchen hat und in späteren Versionen des Artikels dann quasi mit Copy & Paste ans Ziel kommt.

Die Hardware (IOMMU / VT-D tauglich):

Wichtig ist, dass man ein System mit IOMMU (bei AMD) bzw. VT-D (bei Intel) hat. Bei AMD ist das bei den neueren 900er Sets der Fall – vorher sollte man sich aber versichern, dass dieses Feature auch vom Mainboardhersteller ins BIOS gebracht wurde. Ich habe mir dazu extra ein AMD-Board mit 990er Chipsatz gegönnt. Recht praktisch sind auch Kombidesktops wie der von Logitech. Man hat nur einen USB-Receiver, der dann exklusiv an eine DomU durchgereicht wird.

Mainboard: Asus M99X-Evo
Cpu: Athlon II 640
RAM: 4 GB RAM (ECC)
Festplatte: eine kleine 160er Sata 2,5
Tastatur: Logitech MK520 Wireless Desktop

Grafikkarte Dom0: Matrox Millenium
Grafikkarte DomU: ATI Radeon 4850, jetzt 6850

Pakete installieren:

Die folgenden Pakete müssen installiert werden:
libvirt qemu dnsmasq

Grub Parameter setzen:

Ein Auszug aus meiner menu.cfg. Die Parameter iommu=pt iommu=1 sind wichtig.

linux   /vmlinuz-linux root=UUID=328873c3-cc85-4c75-8b77-ac9a7763d532 ro iommu=pt iommu=1 quiet
echo    'Initiale Ramdisk wird geladen …'
initrd  /initramfs-linux.img

Modprobe Parameter setzen:

Damit die Dom0 nicht die Karte nutzt, habe ich die Kernelmodule geblacklistet, sodass die Karte nicht angesprochen wird.

[root@Virtking modprobe.d]# cat blacklist.conf

install nouveau /bin/false
install radeon /bin/false

[root@Virtking modprobe.d]# cat kvm_iommu_map_guest.conf

options kvm allow_unsafe_assigned_interrupts=1

Und NPT (Nested Page Tables) deaktivieren. Das brachte mir ca. 300% mehr Speed in Grafikbenchmarks.
[root@Virtking modprobe.d]# cat kvm-amd.conf

options kvm-amd npt=0

Danach noch das neue initrd bauen:
mkinitcpio -p linux

und neustarten

Qemu Parameter setzen:

-> qemu.conf parameter
vi /etc/libvirt/qemu.conf

# ohne iommu: user="dennis" group="kvm"

# später

# Some examples of valid values are:
#
#       user = "qemu"   # A user named "qemu"
#       user = "+0"     # Super user (uid=0)
#       user = "100"    # A user named "100" or a user with uid=100
#
user = "root"

allow_unsafe_assigned_interrupts=1

# The group for QEMU processes run by the system instance. It can be
# specified in a similar way to user.
group = "root"

Virtuelle Maschine anlegen:

Hier kann man sich es erstmal bequem machen. Entweder man legt das ganze von Hand an, oder baut erstmal ein Gerüst, indem man sich mit VirtManager von einem anderen Computer auf die Dom0 verbindet und eine Maschine anlegt. Positiver Nebeneffekt ist, dass man relativ schnell die CPU und den USB-Receiver der Tastatur umgestellt hat.
Achtung: Wenn die Tastatur beim Start der DomU an diesee gebunden wird, kann man auf der Dom0 nichts mehr eintippen. Ein funktionierende SSH-Verbindung ist daher wichtig, es sei denn man hat 2 Tastaturen am Server.
Für die Virtio-Treiber sind die ISOs des Fedora Projektes sehr nützlich: http://alt.fedoraproject.org/pub/alt/virtio-win/latest/images/bin/

Hier als Beispiel meine vorläufige Konfiguration der Maschine:

[root@Virtking qemu]# cat /etc/libvirt/qemu/testmaschine001.xml

<!-- WARNING: THIS IS AN AUTO-GENERATED FILE. CHANGES TO IT ARE LIKELY TO BE OVERWRITTEN AND LOST.
Changes to this xml configuration should be made using: virsh edit testmaschine001 or other
application using the libvirt API. -->
<domain type='kvm'>
 <name>testmaschine001</name>
 <uuid>cef56731-d06e-d1f1-d063-f8105645826b</uuid>
 <memory unit='KiB'>2097152</memory>
 <currentMemory unit='KiB'>2097152</currentMemory>
 <vcpu placement='static' cpuset='2-3'>2</vcpu>
 <os>
 <type arch='x86_64' machine='pc-i440fx-1.4'>hvm</type>
 <boot dev='hd'/>
 </os>
 <features>
 <acpi/>
 <apic/>
 <pae/>
 </features>
 <cpu mode='custom' match='exact'>
 <model fallback='allow'>Opteron_G3</model>
 <vendor>AMD</vendor>
 <feature policy='require' name='skinit'/>
 <feature policy='require' name='vme'/>
 <feature policy='require' name='mmxext'/>
 <feature policy='require' name='fxsr_opt'/>
 <feature policy='require' name='cr8legacy'/>
 <feature policy='require' name='ht'/>
 <feature policy='require' name='3dnowprefetch'/>
 <feature policy='require' name='3dnowext'/>
 <feature policy='require' name='wdt'/>
 <feature policy='require' name='extapic'/>
 <feature policy='require' name='pdpe1gb'/>
 <feature policy='require' name='osvw'/>
 <feature policy='require' name='nodeid_msr'/>
 <feature policy='require' name='ibs'/>
 <feature policy='require' name='cmp_legacy'/>
 <feature policy='require' name='3dnow'/>
 </cpu>
 <clock offset='utc'/>
 <on_poweroff>destroy</on_poweroff>
 <on_reboot>restart</on_reboot>
 <on_crash>restart</on_crash>
 <devices>
 <emulator>/usr/bin/qemu-system-x86_64</emulator>
 <disk type='file' device='disk'>
 <driver name='qemu' type='raw'/>
 <source file='/var/lib/libvirt/images/testmaschine001.img'/>
 <target dev='vdb' bus='virtio'/>
 <address type='pci' domain='0x0000' bus='0x00' slot='0x09' function='0x0'/>
 </disk>
 <disk type='block' device='cdrom'>
 <driver name='qemu' type='raw'/>
 <target dev='hdc' bus='ide'/>
 <readonly/>
 <address type='drive' controller='0' bus='1' target='0' unit='0'/>
 </disk>
 <controller type='usb' index='0'>
 <address type='pci' domain='0x0000' bus='0x00' slot='0x01' function='0x2'/>
 </controller>
 <controller type='ide' index='0'>
 <address type='pci' domain='0x0000' bus='0x00' slot='0x01' function='0x1'/>
 </controller>
 <controller type='sata' index='0'>
 <address type='pci' domain='0x0000' bus='0x00' slot='0x07' function='0x0'/>
 </controller>
 <controller type='pci' index='0' model='pci-root'/>
 <interface type='network'>
 <mac address='52:54:00:0a:66:b0'/>
 <source network='default'/>
 <model type='virtio'/>
 <address type='pci' domain='0x0000' bus='0x00' slot='0x03' function='0x0'/>
 </interface>
 <serial type='pty'>
 <target port='0'/>
 </serial>
 <console type='pty'>
 <target type='serial' port='0'/>
 </console>
 <input type='tablet' bus='usb'/>
 <input type='mouse' bus='ps2'/>
 <graphics type='vnc' port='-1' autoport='yes' keymap='de'/>
 <video>
 <model type='vga' vram='9216' heads='1'/>
 <address type='pci' domain='0x0000' bus='0x00' slot='0x02' function='0x0'/>
 </video>
 <hostdev mode='subsystem' type='pci' managed='yes'>
 <source>
 <address domain='0x0000' bus='0x01' slot='0x00' function='0x0'/>
 </source>
 <address type='pci' domain='0x0000' bus='0x00' slot='0x05' function='0x0'/>
 </hostdev>
 <hostdev mode='subsystem' type='pci' managed='yes'>
 <source>
 <address domain='0x0000' bus='0x01' slot='0x00' function='0x1'/>
 </source>
 <address type='pci' domain='0x0000' bus='0x00' slot='0x06' function='0x0'/>
 </hostdev>
 <hostdev mode='subsystem' type='usb' managed='yes'>
 <source>
 <vendor id='0x046d'/>
 <product id='0xc52b'/>
 </source>
 </hostdev>
 <memballoon model='virtio'>
 <address type='pci' domain='0x0000' bus='0x00' slot='0x04' function='0x0'/>
 </memballoon>
 </devices>
 </domain>

 
 

Vor dem Start der Maschine noch den Governor auf Performance stellen. Das brachte mir nochmal ca. 50% Speed und einen insgesamt flüssiger wirkenden Ablauf im Unigine Heaven 4.0 Benchmark.

cpupower frequency-set -g performance

 Vielen Dank geht an:

  • Das Fedora Wiki: http://fedoraproject.org/wiki/How_to_debug_Virtualization_problems#PCI_device_assignment
  • natürlich auch das KVM-Projekt an sich: http://www.linux-kvm.org/page/HOWTO
  • und tavi-tech, wo ich angefangen habe mich durch die Sache durchzuarbeiten: http://tavi-tech.blogspot.de/p/vga-passthrough-kvm.html
  • ’nbhs‘ aus dem Arch Linux Forum: https://bbs.archlinux.org/viewtopic.php?id=162768

 

 

Todo:

dmesg:
port. Nested cgroups may change behavior in the future.
[ 15.497875] cgroup: „memory“ requires setting use_hierarchy to 1 on the root.
[ 15.497996] cgroup: libvirtd (326) created nested cgroup for controller „devices“ which has incomplete hierarchy support. Nested cgroups may change behavior in the future.
[ 15.498105] cgroup: libvirtd (326) created nested cgroup for controller „blkio“ which has incomplete hierarchy support. Nested cgroups may change behavior in the future.
[ 34.849069] pci 0000:01:00.0: enabling device (0000 -> 0003)
[ 36.030584] assign device 0:1:0.0
[ 68.684243] pci-stub 0000:01:00.0: claimed by stub

-> stub
echo „modprobe pci_stub“
echo „unbind pci-pci bridge“
#01:00.0 0300: 10de:1040 (rev a1)
echo „10de 1040“ > /sys/bus/pci/drivers/pci-stub/new_id
echo „unbind pci device“
echo „0000:01:00.0“ > /sys/bus/pci/devices/0000:01:00.0/driver/unbind
echo „0000:01:00.0“ > /sys/bus/pci/drivers/pci-stub/bind
#echo „0000:03:07.0“ > /sys/bus/pci/drivers/ivtv/unbind
#echo „4444 0803“ > /sys/bus/pci/drivers/pci-stub/new_id
#echo 0000:03:07.0 > /sys/bus/pci/devices/0000\:03\:07.0/driver/unbind
#echo 0000:03:07.0 > /sys/bus/pci/drivers/pci-stub/bind

-> iommu BIOS/UEFI Setting 64MB:

OFF:

[    0.000000] Checking aperture…
[    0.000000] No AGP bridge found
[    0.000000] Node 0: aperture @ b4000000 size 32 MB
[    0.000000] Aperture pointing to e820 RAM. Ignoring.
[    0.000000] Your BIOS doesn’t leave a aperture memory hole
[    0.000000] Please enable the IOMMU option in the BIOS setup
[    0.000000] This costs you 64 MB of RAM
[    0.000000] Mapping aperture over 65536 KB of RAM @ b4000000
[    0.000000] PM: Registered nosave memory: 00000000b4000000 – 00000000b8000000

ON:
[ 0.000000] Checking aperture…
[ 0.000000] No AGP bridge found
[ 0.000000] Node 0: aperture @ f8000000 size 64 MB
[ 0.000000] Memory: 4009724k/5242880k available (4983k kernel code, 1085948k absent, 147208k reserved, 3967k data, 1092k init)
[ 0.000000] SLUB: Genslabs=15, HWalign=64, Order=0-3, MinObjects=0, CPUs=8, Nodes=1
[ 0.000000] Preemptible hierarchical RCU implementation.

Schreibe einen Kommentar Antworten abbrechen

Deine E-Mail-Adresse wird nicht veröffentlicht. Erforderliche Felder sind mit * markiert

Neueste Beiträge

  • Smart 451 Schlüsselbatterie wechseln und Schlüssel wieder anlernen
  • VDR Server im LXC-Container unter Proxmox
  • Einen guten Start in 2021
  • Arch Linux in Proxmox LXC – first Steps
  • Pimp your Zbox

Kategorien

  • Allgemein
  • Android
  • Arch Linux
  • Browser
  • Chrome
  • Debian
  • Docker
  • Firefox
  • IBM (Allgemein)
  • IBM (Server)
  • KVM
  • Linux
  • LXC
  • NAS
  • Raspberry Pi
  • Redhat / CentOS
  • Server
  • Sonstiges
  • Sun
  • Thunderbird
  • Toolbox
  • Ubuntu
  • Virtualisierung
  • Windows
  • Xen

Schlagwörter

18.04 451 Acer Android Arch Linux Aspier Batterie wechseln bios bios-mod container denicid docker Dropbox DVB-C dvb-c2 DVB-S2 id4me Install Installation Kubuntu kvm lga Linux LXC mailcow microcode mSATA nextcloud pin-mod Proxmox proxmox-ve pve ReverseProxy Schlüssel Schlüssel anlernen Schlüsselbatterie Smart Smart451 SSD Thunderbird Ubuntu V3-771 V3-771G VDR vt-d
©2025 TechDudes.de | Theme: Wordly by SuperbThemes