Damjan Marion | f0ccbb0 | 2016-10-06 16:53:32 +0200 | [diff] [blame] | 1 | #!/bin/bash |
| 2 | |
| 3 | uio_drivers="igb_uio uio_pci_generic vfio-pci" |
| 4 | tmpfile=$(mktemp) |
| 5 | |
| 6 | |
| 7 | function bind_drv() { |
| 8 | addr=$1 |
| 9 | modalias=$(cat $selection/modalias) |
| 10 | native_drv=$(modprobe -R $modalias) |
| 11 | array=() |
| 12 | |
| 13 | for drv in $native_drv $uio_drivers; do |
| 14 | if [ -e /sys/bus/pci/drivers/$drv ]; then |
| 15 | echo driver $drv |
| 16 | drv_desc=$(modinfo $drv | grep description: | sed -e 's/.*:[[:space:]]\+//' ) |
| 17 | array+=("${drv}") |
| 18 | array+=("${drv_desc}") |
| 19 | fi |
| 20 | done |
| 21 | dialog --backtitle "PCI NIC Bind Utility" \ |
| 22 | --clear \ |
| 23 | --menu "Select kernel driver" 18 100 12 \ |
| 24 | "${array[@]}" 2> $tmpfile |
| 25 | retval=$? |
| 26 | selection=$(cat $tmpfile) |
| 27 | rm $tmpfile |
| 28 | if [ $retval -ne 0 ]; then |
| 29 | return |
| 30 | fi |
| 31 | vd=$(cat /sys/bus/pci/devices/${addr}/vendor /sys/bus/pci/devices/${addr}/device) |
| 32 | echo $addr | tee /sys/bus/pci/devices/${addr}/driver/unbind > /dev/null 2> /dev/null |
| 33 | echo $vd | tee /sys/bus/pci/drivers/${selection}/new_id > /dev/null 2> /dev/null |
| 34 | echo $addr | tee /sys/bus/pci/drivers/${selection}/bind > /dev/null 2> /dev/null |
| 35 | } |
| 36 | |
| 37 | function find_pci_slot() { |
| 38 | addr=$1 |
| 39 | [ ! "$(ls -A /sys/bus/pci/slots )" ] && echo "No PCI slot data" && return |
| 40 | for slot in $(find /sys/bus/pci/slots/* -maxdepth 0 -exec basename {} \;); do |
| 41 | slot_addr=$(cat /sys/bus/pci/slots/$slot/address) |
| 42 | if [[ "${addr}" == *"${slot_addr}"* ]]; then |
| 43 | echo "PCI slot: ${slot}" |
| 44 | return |
| 45 | fi |
| 46 | done |
| 47 | echo "Unknown PCI slot" |
| 48 | } |
| 49 | |
| 50 | ! type -ap dialog > /dev/null && echo "Please install dialog (apt-get install dialog)" && exit |
| 51 | if [ $USER != "root" ] ; then |
| 52 | echo "Restarting script with sudo..." |
| 53 | sudo $0 ${*} |
| 54 | exit |
| 55 | fi |
| 56 | |
| 57 | cd /sys/bus/pci/devices |
| 58 | |
| 59 | while true; do |
| 60 | array=() |
| 61 | for addr in *; do |
| 62 | class=$(cat ${addr}/class) |
| 63 | if [ "$class" = "0x020000" ]; then |
| 64 | name=$(lspci -s $addr | sed -e 's/.*: //') |
| 65 | if [ -e "/sys/bus/pci/devices/$addr/driver" ]; then |
| 66 | drv=$(basename $(readlink -f /sys/bus/pci/devices/$addr/driver)) |
| 67 | else |
| 68 | drv=" " |
| 69 | fi |
| 70 | slot=$(find_pci_slot ${addr}) |
| 71 | array+=("${addr}") |
| 72 | array+=("${drv}|${name}") |
| 73 | array+=("${slot}") |
| 74 | fi |
| 75 | done |
| 76 | |
| 77 | dialog --backtitle "PCI NIC Bind Utility" \ |
| 78 | --item-help \ |
| 79 | --clear \ |
| 80 | --column-separator '|' \ |
| 81 | --menu "Select NIC" 18 100 12 \ |
| 82 | "${array[@]}" 2> $tmpfile |
| 83 | |
| 84 | retval=$? |
| 85 | selection=$(cat $tmpfile) |
| 86 | rm $tmpfile |
| 87 | if [ $retval -ne 0 ]; then |
| 88 | exit |
| 89 | fi |
| 90 | bind_drv $selection |
| 91 | done |
| 92 | |
| 93 | |
| 94 | |