@ -1,247 +1,110 @@
## Automated Setup
#### WORKING ON IT!!!
## Manual Setup
< b > Note< / b > : Replace win10 with your virtual machine's name on libvirt hooks and virsh commands.
< details >
< summary > < b > Enable IOMMU< / b > < / summary >
```sh
sudo nano /etc/default/grub
```
Append < b > iommu=pt< / b > , and < b > intel_iommu=on< / b > or < b > amd_iommu=on< / b > kernel options to < b > GRUB_CMDLINE_LINUX_DEFAULT< / b > for your CPU.
Then, update grub configuration.
### **Enable IOMMU**
#### ** *Set the kernel paramater depending on your CPU.***
#### For GRUB user, edit grub configuration.
| /etc/default/grub |
| ----- |
| `GRUB_CMDLINE_LINUX_DEFAULT="intel_iommu=on iommu=pt ..."` |
| OR |
| `GRUB_CMDLINE_LINUX_DEFAULT="amd_iommu=on iommu=pt ..."` |
#### ** *Generate grub.cfg***
```sh
sudo grub-mkconfig -o /boot/grub/grub.cfg
grub-mkconfig -o /boot/grub/grub.cfg
```
< details >
< summary > < b > Verify IOMMU< / b > < / summary >
#### Reboot your system for the changes to take effect.
After setting kernel parameter on grub config, reboot your system and verify IOMMU is enabled.
< br / >
### **Verify IOMMU**
#### ** *If you don't see any output when running following command, IOMMU is not functioning.***
```sh
dmesg | grep 'IOMMU enabled'
```
< / details >
< / details >
### **Install required tools**
< details >
< summary > < b > Install required tools < / b > < / summary >
< summary > < b > Gentoo Linux < / b > < / summary >
```sh
sudo pacman -S qemu libvirt edk2-ovmf virt-manager dnsmasq ebtables
emerge -av qemu virt-manager libvirt ebtables dnsmasq
```
< / details >
< details >
< summary > < b > Enable services< / b > < / summary >
Enable libvirtd service and start default network.
< summary > < b > Arch Linux< / b > < / summary >
```sh
sudo systemctl enable --now libvirtd
sudo virsh net-start default
sudo virsh net-autostart default
pacman -S qemu libvirt edk2-ovmf virt-manager dnsmasq ebtables
```
< / details >
< details >
< summary > < b > Setup Guest OS< / b > < / summary >
Download [virtio ](https://fedorapeople.org/groups/virt/virtio-win/direct-downloads/stable-virtio/virtio-win.iso ) driver.
Launch < b > virt-manager< / b > and create new virtual machine. Check < b > Customize before install< / b > on final step.
< b > Overview< / b > > Chipset: Q35, Firmware: UEFI< br / >
< b > CPUs< / b > > CPU model: host-passthrough, CPU topology: Best for your machine :)< br / >
< b > SATA Disk< / b > > Disk bus: virtio< br / >
< b > NIC< / b > > Device model: virtio< br / >
< b > Add Hardware< / b > > CDROM: virtio-win.iso
< b > Begin Installation< / b > and install Windows.. Windows can't detect virtio devices, so you need to < b > Load Driver< / b > from < b > virtio-disk/amd64/win10< / b > when prompted.
After successful installation, install virtio-drivers from virtio CDROM.
< / details >
< details >
< summary > < b > Attach PCI Devices< / b > < / summary >
Remove < b > Tablet, Spice Channel, Video XQL< / b > and other applicable devices.
< b > Add Hardware< / b > > PCI Devices: GPU and HDMI audio
< / details >
< details >
< summary > < b > NVIDIA GPU< / b > < / summary >
Nvidia GPU vBIOS requires patching to work. Though, some NVIDIA GPU works without patching.
< details >
< summary > < b > Dump GPU vBIOS< / b > < / summary >
< b > Windows</ b > > Use [GPU-Z ](https://www.techpowerup.com/gpuz/ )< br />
< b > Linux< / b > > Try following but doesn't seem to work:
< summary > < b > Fedora< / b > < / summary >
```sh
su
echo 1 > /sys/bus/pci/devices/0000:01:00.0/rom
cat /sys/bus/pci/devices/0000:01:00.0/rom > vbios.rom
echo 0 > /sys/bus/pci/devices/0000:01:00.0/rom
dnf install @virtualization
```
Or, you can download vBIOS from [TechPowerUp ](https://www.techpowerup.com/vgabios/ ), which might (not) be already patched.
< / details >
< details >
< summary > < b > Patching vBIOS< / b > < / summary >
Use Hex Editor and search for string VIDEO, and remove everything before char < b > U< / b > , i.e. HEX value 55.
< / details >
< br / >
### **Enable required services**
< details >
< summary > < b > Using Patched vBIOS < / b > < / summary >
< summary > < b > SystemD< / b > < / summary >
```sh
sudo virsh edit win10
systemctl enable --now libvirtd
```
Search for < b > hostdev< / b > . Add
```xml
< rom file = "path/to/your/patched_vbios.rom" / >
```
before
```xml
< address >
```
< / details >
< / details >
< details >
< summary > < b > Libvirt Hooks< / b > < / summary >
< b > Libvirt hooks automate the process of running specific tasks during VM state change.< / b >
More info at: [PassthroughPost ](https://passthroughpo.st/simple-per-vm-libvirt-hooks-with-the-vfio-tools-hook-helper/ )
< details >
< summary > < b > Create Libvirt hook< / b > < / summary >
```sh
sudo mkdir /etc/libvirt/hooks
sudo touch /etc/libvirt/hooks/qemu
sudo chmod +x /etc/libvirt/hooks/qemu
```
/etc/libvirt/hooks/qemu |
---------- |
```sh
#!/bin/bash
GUEST_NAME="$1"
HOOK_NAME="$2"
STATE_NAME="$3"
MISC="${@:4}"
< summary > < b > OpenRC< / b > < / summary >
BASEDIR="$(dirname $0)"
HOOKPATH="$BASEDIR/qemu.d/$GUEST_NAME/$HOOK_NAME/$STATE_NAME"
set -e # If a script exits with an error, we should as well.
if [ -f "$HOOKPATH" ]; then
eval \""$HOOKPATH"\" "$@"
elif [ -d "$HOOKPATH" ]; then
while read file; do
eval \""$file"\" "$@"
done < < < "$(find -L "$HOOKPATH" -maxdepth 1 -type f -executable -print;)"
fi
```
< b > Restart libvirtd< / b >
```sh
sudo systemctl restart libvirtd
rc-update add libvirtd default
rc-service libvirtd start
```
< / details >
< details >
< summary > < b > Start Script< / b > < / summary >
### Sometimes, you might need to start default network manually.
```sh
sudo mkdir -p /etc/libvirt/hooks/qemu.d/win10/prepare/begin
sudo touch /etc/libvirt/hooks/qemu.d/win10/prepare/begin/start.sh
sudo chmod +x /etc/libvirt/hooks/qemu.d/win10/prepare/begin/start.sh
```
/etc/libvirt/hooks/qemu.d/win10/prepare/begin/start.sh |
-------------- |
```sh
#!/bin/bash
set -x
# Stop display manager
systemctl stop display-manager
# Unbind EFI Framebuffer
echo efi-framebuffer.0 > /sys/bus/platform/drivers/efi-framebuffer/unbind
# Unload NVIDIA kernel modules
modprobe -r nvidia_drm nvidia_modeset nvidia_uvm nvidia
# Unload AMD kernel module
# modprobe -r amdgpu
# Detach GPU devices from host
# Use your GPU and HDMI Audio PCI host device
virsh nodedev-detach pci_0000_01_00_0
virsh nodedev-detach pci_0000_01_00_1
# Load vfio module
modprobe vfio-pci
```
< / details >
< details >
< summary > < b > Stop Script< / b > < / summary >
virsh net-start default
virsh net-autostart default
```
### **Setup Guest OS**
### ** *NOTE: You should replace win10 with your VM's name where applicable***
#### ** *Download [virtio ](https://fedorapeople.org/groups/virt/virtio-win/direct-downloads/stable-virtio/virtio-win.iso ) driver.***
### Launch ** *virt-manager*** and create a new virtual machine. Select ** *Customize before install*** on Final Step.
### In ** *Overview*** section, set ** *Chipset*** to ** *Q35***, and ** *Firmware*** to ** *UEFI***
### In ** *CPUs*** section, set ** *CPU model*** to ** *host-passthrough***, and ** *CPU Topology*** to whatever fits your system.
### For ** *SATA*** disk of VM, set ** *Disk Bus*** to ** *virtio***.
### In ** *NIC*** section, set ** *Device Model*** to ** *virtio***
### Add Hardware > CDROM: virtio-win.iso
### Now, ** *Begin Installation***. Windows can't detect the ** *virtio disk***, so you need to ** *Load Driver*** and select ** *virtio-iso/amd64/win10*** when prompted.
### After successful installation of Windows, install virtio drivers from virtio CDROM.
< br / >
### **Attaching PCI devices**
### Remove Channel Spice, Display Spice, Video XQL, Sound ich* and other unnecessary devices.
### Now, click on ** *Add Hardware***, select ** *PCI Devices*** and add the PCI Host devices for your GPU's VGA and HDMI Audio
### Some GPU vBIOS needs to be patched for UEFI Support.
----- TODO: vBIOS patching ------
### To use patched vBIOS, edit VM's configuration
```sh
sudo mkdir -p /etc/libvirt/hooks/qemu.d/win10/release/end
sudo touch /etc/libvirt/hooks/qemu.d/win10/release/end/stop.sh
sudo chmod +x /etc/libvirt/hooks/qemu.d/win10/release/end/stop.sh
virsh edit win10
```
/etc/libvirt/hooks/qemu.d/win10/release/end/stop.sh |
---------- |
```sh
#!/bin/bash
set -x
# Unload vfio module
modprobe -r vfio-pci
# Attach GPU devices to host
# Use your GPU and HDMI Audio PCI host device
virsh nodedev-reattach pci_0000_01_00_0
virsh nodedev-reattach pci_0000_01_00_1
# Rebind framebuffer to host
echo "efi-framebuffer.0" > /sys/bus/platform/drivers/efi-framebuffer/bind
# Load NVIDIA kernel modules
modprobe nvidia_drm
modprobe nvidia_modeset
modprobe nvidia_uvm
modprobe nvidia
# Load AMD kernel module
# modprobe amdgpu
# Restart Display Manager
systemctl start display-manager
```xml
...
< hostdev mode = 'subsystem' type = 'pci' managed = 'yes' >
< source >
...
< / source >
< rom file = '/home/me/patched.rom' / >
...
< / hostdev >
...
```
< / details >
< / details >
[Video card driver virtualisation detection ](https://wiki.archlinux.org/index.php/PCI_passthrough_via_OVMF#Video_card_driver_virtualisation_detection )< br />
[Keyboard/Mouse Passthrough ](https://wiki.archlinux.org/index.php/PCI_passthrough_via_OVMF#Passing_keyboard/mouse_via_Evdev )< br />
[Audio Passthrough ](https://wiki.archlinux.org/index.php/PCI_passthrough_via_OVMF#Passing_VM_audio_to_host_via_PulseAudio )< br />
[Troubleshooting ](https://wiki.archlinux.org/index.php/PCI_passthrough_via_OVMF#Troubleshooting )
< b > See Also< / b >
> [Single GPU Passthrough by joeknock90 ](https://github.com/joeknock90/Single-GPU-Passthrough )< br />