#!/usr/bin/env bash ## QEMU hooks. How to use. # chmod +x qemu # sudo ln -sf "$(pwd)/qemu" /etc/libvirt/hooks/qemu ## Virsh devices. VIRSH_GPU="pci_0000_06_00_0" VIRSH_GPU_AUDIO="pci_0000_06_00_1" ## Log file. Only tells if the GPU was un/binded correctly. LOG=/tmp/qemu_log.txt if [[ "$1" == "GPU"* ]]; then if [ "$2" == "prepare" ]; then ## Kill the Window Manager. Yours may vary. killall i3 > /dev/null 2>&1 sleep 5 ## Just in case ## Remove the framebuffer and console echo 0 > /sys/class/vtconsole/vtcon0/bind echo 0 > /sys/class/vtconsole/vtcon1/bind echo efi-framebuffer.0 > /sys/bus/platform/drivers/efi-framebuffer/unbind ## Detach the GPU and USB virsh nodedev-detach "$VIRSH_GPU" >> "$LOG" 2>&1 virsh nodedev-detach "$VIRSH_GPU_AUDIO" >> "$LOG" 2>&1 ## Load vfio. modprobe vfio-pci ## Start the network. if [[ $(virsh net-list --all | grep "virt1" | awk '{print $2}') != "active" ]]; then virsh net-start virt1 fi fi if [ "$2" == "release" ]; then ## Stop the network. if [ "$(virsh net-list --all | grep "virt1" | awk '{print $2}')" == "active" ]; then ## "destroy" actually stops it. virsh net-destroy virt1 fi ## Unload vfio module. modprobe -r vfio-pci modprobe -r vfio_iommu_type1 modprobe -r vfio ## Reattach the GPU and USB. virsh nodedev-reattach "$VIRSH_GPU_AUDIO" >> "$LOG" 2>&1 virsh nodedev-reattach "$VIRSH_GPU" >> "$LOG" 2>&1 ## Reload the framebuffer and console. echo 1 > /sys/class/vtconsole/vtcon0/bind nvidia-xconfig --query-gpu-info > /dev/null 2>&1 echo "efi-framebuffer.0" > /sys/bus/platform/drivers/efi-framebuffer/bind fi fi