Einzelnes Gerät für PCI-Passthrough in separater IOMMU-Gruppe isolieren?

Einzelnes Gerät für PCI-Passthrough in separater IOMMU-Gruppe isolieren?

Ich habe unten IOMMU-Gruppen und -Geräte.

$ for a in /sys/kernel/iommu_groups/*; do find $a -type l; done | sort --version-sort
/sys/kernel/iommu_groups/0/devices/0000:00:00.0
/sys/kernel/iommu_groups/1/devices/0000:00:02.0
/sys/kernel/iommu_groups/2/devices/0000:00:04.0
/sys/kernel/iommu_groups/3/devices/0000:00:14.0
/sys/kernel/iommu_groups/3/devices/0000:00:14.2
/sys/kernel/iommu_groups/4/devices/0000:00:15.0
/sys/kernel/iommu_groups/4/devices/0000:00:15.1
/sys/kernel/iommu_groups/5/devices/0000:00:16.0
/sys/kernel/iommu_groups/6/devices/0000:00:17.0
/sys/kernel/iommu_groups/7/devices/0000:00:1c.0
/sys/kernel/iommu_groups/7/devices/0000:00:1c.7
/sys/kernel/iommu_groups/7/devices/0000:01:00.0
/sys/kernel/iommu_groups/7/devices/0000:02:00.0
/sys/kernel/iommu_groups/8/devices/0000:00:1f.0
/sys/kernel/iommu_groups/8/devices/0000:00:1f.2
/sys/kernel/iommu_groups/8/devices/0000:00:1f.3
/sys/kernel/iommu_groups/8/devices/0000:00:1f.4

Ich möchte dieses bestimmte Gerät /sys/kernel/iommu_groups/7/devices/0000:01:00.0in einer eigenen Gruppe isolieren, ohne dass sich andere Geräte in derselben Gruppe befinden.

Wie können wir ein einzelnes Gerät in einer separaten IOMMU-Gruppe für PCI-Passthrough für eine KVM-virtuelle Maschine isolieren?

Antwort1

Ich weiß, dass dies eine alte Frage ist, aber ich musste kürzlich versuchen, das herauszufinden.

Die Faustregel bei IOMMU ist, dass der Kernel die Zuordnungen für Sie herausfindet. Wenn der Kernel bootet, sucht er nach Geräten, die einer virtuellen I/O-Zuordnung (IOVA) zugeordnet werden können. Wenn die Geräte dieselbe IOVA haben, landen sie in derselben Gruppe. Dies wird getan, um sicherzustellen, dass jede Gruppe Geräte hat, die tatsächlich separat angesprochen und angesprochen werden können.

Es gibt mehrere Lösungen. Die erste ist, dass Sie versuchen könnten, die Karte an eine andere Stelle auf der Hauptplatine zu verschieben. Wenn es sich um eine PCI- und nicht um eine PCIe-Karte handelt, haben Sie wahrscheinlich Pech, da alle PCI-Ports wahrscheinlich derselben PCIe-Brücke zugeordnet sind und daher dieselbe IOVA verwenden.

Wenn Sie dies wirklich noch tun müssen, können Sie alle Geräte, die sich in derselben Gruppe befinden, nehmen und sie alle vfio-pci zuweisen. Anschließend können Sie die Zuweisungen dort vornehmen, wo die Geräte hin müssen.

Auf meinem Rechner hat beispielsweise Gruppe 13 eine Reihe von Geräten, darunter eine zusätzliche Grafikkarte (18:00). Hier ist meine Ausgabe aus diesem Verzeichnis:

root@rwl01:/sys/kernel/iommu_groups/13/devices# ll
total 0
drwxr-xr-x 2 root root 0 Feb 15 15:43 .
drwxr-xr-x 3 root root 0 Feb 15 15:43 ..
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:03:00.0 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.0
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:03:00.1 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.1
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:03:00.2 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.2
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:16:00.0 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.2/0000:16:00.0
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:16:01.0 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.2/0000:16:01.0
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:16:02.0 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.2/0000:16:02.0
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:16:03.0 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.2/0000:16:03.0
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:16:04.0 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.2/0000:16:04.0
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:16:08.0 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.2/0000:16:08.0
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:17:00.0 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.2/0000:16:00.0/0000:17:00.0
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:18:00.0 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.2/0000:16:01.0/0000:18:00.0
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:18:00.1 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.2/0000:16:01.0/0000:18:00.1
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:19:00.0 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.2/0000:16:02.0/0000:19:00.0
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:1a:00.0 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.2/0000:16:03.0/0000:1a:00.0
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:1b:00.0 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.2/0000:16:04.0/0000:1b:00.0
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:1b:00.1 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.2/0000:16:04.0/0000:1b:00.1
lrwxrwxrwx 1 root root 0 Feb 15 15:43 0000:1c:00.0 -> ../../../../devices/pci0000:00/0000:00:01.3/0000:03:00.2/0000:16:08.0/0000:1c:00.0

Wie Sie sehen, besteht das Verzeichnis aus einer Reihe von Links. Hier ist die Kette, wie die Dinge miteinander verbunden sind:

root@rwl01:/sys/kernel/iommu_groups/13/devices# lspci | grep -E '00:01.3|03:00.2|16:01.0'
00:01.3 PCI bridge: Advanced Micro Devices, Inc. [AMD] Device 1453
03:00.2 PCI bridge: Advanced Micro Devices, Inc. [AMD] Device 43b0 (rev 02)
16:01.0 PCI bridge: Advanced Micro Devices, Inc. [AMD] Device 43b4 (rev 02)

Bei mir befinden sich alle diese Geräte auf derselben Bridge, meine zusätzliche Grafikkarte, der RAID-Controller usw. Man kann diese nicht einfach trennen.

Doch kannst du

Sie müssen diehttps://queuecumber.gitlab.io/linux-acs-override/(ACS Override Kernel Patch) Damit können Sie Befehlszeilenparameter verwenden, um Teile von Gruppen als eigene Gruppen freizugeben. Nachdem Sie den Patch installiert haben, können Sie konfigurieren, welche Kernel-Befehlszeilenparameter Sie verwenden möchten:

pcie_acs_override =
        [PCIE] Override missing PCIe ACS support for:
    downstream
        All downstream ports - full ACS capabilties
    multifunction
        All multifunction devices - multifunction ACS subset
    id:nnnn:nnnn
        Specfic device - full ACS capabilities
        Specified as vid:did (vendor/device ID) in hex

Von hier aus sollten Sie das Gerät in eine eigene Gruppe einordnen können und schon kann es losgehen. Bei dieser Methode gibt es Probleme:

Hier sind ein paar gute Links:

Antwort2

Ich weiß, dass die ursprüngliche Frage aus dem Jahr 2019 stammt, aber so wie es sich anhört, könnte es mit aktuelleren Kerneln viel einfacher sein.

Für alle, die Probleme haben: Ich wollte eine Netzwerkkarte über eine Broadcom BCM5709 4-Port NetXtreme II Gigabit Ethernet-Karte durchleiten, die an einen HP Z600 angeschlossen war. Ich hatte bereits alle Virtualisierungen, VT-d und dergleichen im BIOS aktiviert.

Mein Problem bestand darin, dass, wenn ich eine Netzwerkkarte am 4-Port durchließ, nichts in Gruppe 12 für den Host zugänglich war, einschließlich der internen Netzwerkkarte, die ich für die Verbindung verwendete.


Dies ist ein nützlicher Abschnitt, der einige Grundlagen zum Bearbeiten der Kernel-Befehlszeile vermittelt https://pve.proxmox.com/pve-docs/chapter-sysadmin.html#sysboot_edit_kernel_cmdline

Roden

GRUB_CMDLINE_LINUX_DEFAULTDie Kernel-Befehlszeile muss in die Variable in der Datei eingefügt werden /etc/default/grub. Beim Ausführen update-grubwird der Inhalt an alle Linux-Einträge in /boot/grub/grub.cfg angehängt.

Systemd-Boot

Die Kernel-Befehlszeile muss als eine Zeile in eingefügt werden /etc/kernel/cmdline. Um Ihre Änderungen anzuwenden, führen Sie proxmox-boot-tool refresh[nicht sicher, was ohne Proxmox verwendet würde] aus, wodurch es als Optionszeile für alle Konfigurationsdateien in loader/entries/proxmox-*.conf festgelegt wird.


Anschließend finden Sie auf dieser Seite einige Details zu PCI Passthrough, die sich hauptsächlich auf Proxmox beziehen, das Prinzip sollte jedoch dasselbe sein: https://pve.proxmox.com/wiki/PCI_Passthrough


DIESES VIDEO HAT MIR AM MEISTEN GEHOLFEN!und war wirklich hilfreich und gründlich, als er Sie durch den Prozess führte. Es ist für eine bestimmte Implementierung, aber alles, was gezeigt wird, kann mit den oben und unten aufgeführten Informationen erreicht werden

https://www.youtube.com/watch?v=qQiMMeVNw-o&ab_channel=SpaceinvaderOne


Ich kann mich nicht erinnern, wo ich es her habe, aber dies ist ein wirklich nützlicher Befehl, um alle IOMMU-Gruppen für alle Geräte zu identifizieren (als Root ausführen):

for d in $(find /sys/kernel/iommu_groups/ -type l | sort -n -k5 -t/); do n=${d#*/iommu_groups/*}; n=${n%%/*}; printf 'IOMMU Group %s ' "$n"; lspci -nns "${d##*/}"; done;

Für mich begann ich ursprünglich mitGRUB_CMDLINE_LINUX_DEFAULT="quiet"


Ich habe die grundlegende Aktivierung von IOMMU aktiviertGRUB_CMDLINE_LINUX_DEFAULT="quiet intel_iommu=on"

Das gab mir:

IOMMU Group 12 00:1c.0 PCI bridge [0604]: Intel Corporation 82801JI (ICH10 Family) PCI Express Root Port 1 [8086:3a40]
IOMMU Group 12 00:1c.5 PCI bridge [0604]: Intel Corporation 82801JI (ICH10 Family) PCI Express Root Port 6 [8086:3a4a]
IOMMU Group 12 01:00.0 Ethernet controller [0200]: Broadcom Inc. and subsidiaries NetXtreme BCM5764M Gigabit Ethernet PCIe [14e4:1684] (rev 10)
IOMMU Group 12 1c:00.0 PCI bridge [0604]: Microsemi / PMC / IDT PES12T3G2 PCI Express Gen2 Switch [111d:8061] (rev 01)
IOMMU Group 12 1d:02.0 PCI bridge [0604]: Microsemi / PMC / IDT PES12T3G2 PCI Express Gen2 Switch [111d:8061] (rev 01)
IOMMU Group 12 1d:04.0 PCI bridge [0604]: Microsemi / PMC / IDT PES12T3G2 PCI Express Gen2 Switch [111d:8061] (rev 01)
IOMMU Group 12 1e:00.0 Ethernet controller [0200]: Broadcom Inc. and subsidiaries NetXtreme II BCM5709 Gigabit Ethernet [14e4:1639] (rev 20)
IOMMU Group 12 1e:00.1 Ethernet controller [0200]: Broadcom Inc. and subsidiaries NetXtreme II BCM5709 Gigabit Ethernet [14e4:1639] (rev 20)
IOMMU Group 12 1f:00.0 Ethernet controller [0200]: Broadcom Inc. and subsidiaries NetXtreme II BCM5709 Gigabit Ethernet [14e4:1639] (rev 20)
IOMMU Group 12 1f:00.1 Ethernet controller [0200]: Broadcom Inc. and subsidiaries NetXtreme II BCM5709 Gigabit Ethernet [14e4:1639] (rev 20)

Ich habe alles entfernt, außer der Gruppe, die mich interessiert, Gruppe 12. Sie können die 4 Ports der Netzwerkkarte sehen, aber auch eine andere Netzwerkkarte, die integrierte. Wenn ich eine Netzwerkkarte durchgehe, ist für den Host leider nichts in Gruppe 12 zugänglich.


Ich habe einen funktionierenden Mechanismus gefunden, der die Netzwerkkarte in zwei Teile aufteilt, indemGRUB_CMDLINE_LINUX_DEFAULT="quiet intel_iommu=on pcie_acs_override=downstream"

Das gab mir

IOMMU Group 12 00:1c.0 PCI bridge [0604]: Intel Corporation 82801JI (ICH10 Family) PCI Express Root Port 1 [8086:3a40]
IOMMU Group 13 00:1c.5 PCI bridge [0604]: Intel Corporation 82801JI (ICH10 Family) PCI Express Root Port 6 [8086:3a4a]
IOMMU Group 18 1c:00.0 PCI bridge [0604]: Microsemi / PMC / IDT PES12T3G2 PCI Express Gen2 Switch [111d:8061] (rev 01)
IOMMU Group 19 1d:02.0 PCI bridge [0604]: Microsemi / PMC / IDT PES12T3G2 PCI Express Gen2 Switch [111d:8061] (rev 01)
IOMMU Group 20 1d:04.0 PCI bridge [0604]: Microsemi / PMC / IDT PES12T3G2 PCI Express Gen2 Switch [111d:8061] (rev 01)
IOMMU Group 21 1e:00.0 Ethernet controller [0200]: Broadcom Inc. and subsidiaries NetXtreme II BCM5709 Gigabit Ethernet [14e4:1639] (rev 20)
IOMMU Group 21 1e:00.1 Ethernet controller [0200]: Broadcom Inc. and subsidiaries NetXtreme II BCM5709 Gigabit Ethernet [14e4:1639] (rev 20)
IOMMU Group 22 1f:00.0 Ethernet controller [0200]: Broadcom Inc. and subsidiaries NetXtreme II BCM5709 Gigabit Ethernet [14e4:1639] (rev 20)
IOMMU Group 22 1f:00.1 Ethernet controller [0200]: Broadcom Inc. and subsidiaries NetXtreme II BCM5709 Gigabit Ethernet [14e4:1639] (rev 20)
IOMMU Group 23 01:00.0 Ethernet controller [0200]: Broadcom Inc. and subsidiaries NetXtreme BCM5764M Gigabit Ethernet PCIe [14e4:1684] (rev 10)

Sie können sehen, dass die 4-Port-NIC in zwei Paare aufgeteilt ist und keines davon in einer Gruppe mit der integrierten NIC ist. Ich vermute, dass sich jedes Paar auf demselben Bus (entschuldigen Sie die Terminologie) auf der Karte befindet, also ist das wahrscheinlich die kleinste Aufteilung, die ich erreichen konnte (ich habe andere Mechanismen ausprobiert, z. B. das Isolieren einer oder mehrerer Brücken, wie im Video beschrieben, aber sie waren schlechter als die oben genannten).

Ich hoffe, dass dies für jeden hilfreich sein kann, der das gleiche Problem hat.

verwandte Informationen